diff --git a/Elsa.sln b/Elsa.sln
index 0f9d79d47..97074488c 100644
--- a/Elsa.sln
+++ b/Elsa.sln
@@ -283,6 +283,8 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "storage", "storage", "{B818
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Elsa.CSharp", "src\modules\Elsa.CSharp\Elsa.CSharp.csproj", "{24331E82-D7AF-45B1-ACF0-CA6C3B0B77DC}"
EndProject
+Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Elsa.Python", "src\modules\Elsa.Python\Elsa.Python.csproj", "{790E94F2-5393-47DF-AC52-D9247F5B243A}"
+EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@@ -709,6 +711,10 @@ Global
{24331E82-D7AF-45B1-ACF0-CA6C3B0B77DC}.Debug|Any CPU.Build.0 = Debug|Any CPU
{24331E82-D7AF-45B1-ACF0-CA6C3B0B77DC}.Release|Any CPU.ActiveCfg = Release|Any CPU
{24331E82-D7AF-45B1-ACF0-CA6C3B0B77DC}.Release|Any CPU.Build.0 = Release|Any CPU
+ {790E94F2-5393-47DF-AC52-D9247F5B243A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {790E94F2-5393-47DF-AC52-D9247F5B243A}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {790E94F2-5393-47DF-AC52-D9247F5B243A}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {790E94F2-5393-47DF-AC52-D9247F5B243A}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
@@ -839,6 +845,7 @@ Global
{B818988E-639C-4E6E-85C1-B231BCAD9DAB} = {5BA4A8FA-F7F4-45B3-AEC8-8886D35AAC79}
{732BF088-6AD7-4C4D-9A48-8074253596D4} = {B818988E-639C-4E6E-85C1-B231BCAD9DAB}
{24331E82-D7AF-45B1-ACF0-CA6C3B0B77DC} = {6EF07978-A6D2-40EB-891D-7D70C5F37E76}
+ {790E94F2-5393-47DF-AC52-D9247F5B243A} = {6EF07978-A6D2-40EB-891D-7D70C5F37E76}
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {D4B5CEAA-7D70-4FCB-A68E-B03FBE5E0E5E}
diff --git a/src/bundles/Elsa.WorkflowServer.Web/Elsa.WorkflowServer.Web.csproj b/src/bundles/Elsa.WorkflowServer.Web/Elsa.WorkflowServer.Web.csproj
index 1c119c42a..e60ce26af 100644
--- a/src/bundles/Elsa.WorkflowServer.Web/Elsa.WorkflowServer.Web.csproj
+++ b/src/bundles/Elsa.WorkflowServer.Web/Elsa.WorkflowServer.Web.csproj
@@ -15,6 +15,7 @@
+
diff --git a/src/bundles/Elsa.WorkflowServer.Web/Program.cs b/src/bundles/Elsa.WorkflowServer.Web/Program.cs
index 0b47f2415..22fe348bb 100644
--- a/src/bundles/Elsa.WorkflowServer.Web/Program.cs
+++ b/src/bundles/Elsa.WorkflowServer.Web/Program.cs
@@ -151,7 +151,20 @@ services
options.AppendScript("string Greet(string name) => $\"Hello {name}!\";");
options.AppendScript("string SayHelloWorld() => Greet(\"World\");");
})
- .UseJavaScript(options => options.AllowClrAccess = true)
+ .UseJavaScript(options =>
+ {
+ options.AllowClrAccess = true;
+ options.ConfigureEngine(engine =>
+ {
+ engine.Execute("function greet(name) { return `Hello ${name}!`; }");
+ engine.Execute("function sayHelloWorld() { return greet('World'); }");
+ });
+ })
+ .UsePython(options =>
+ {
+ options.AddScript("def greet(name): return f\"Hello {name}!\";");
+ options.AddScript("def say_hello_world(): return greet(\"World\");");
+ })
.UseLiquid(liquid => liquid.FluidOptions = options => options.Encoder = HtmlEncoder.Default)
.UseHttp(http =>
{
diff --git a/src/clients/Elsa.Api.Client/Converters/ExpressionJsonConverter.cs b/src/clients/Elsa.Api.Client/Converters/ExpressionJsonConverter.cs
index 80913a8e5..586e8b540 100644
--- a/src/clients/Elsa.Api.Client/Converters/ExpressionJsonConverter.cs
+++ b/src/clients/Elsa.Api.Client/Converters/ExpressionJsonConverter.cs
@@ -51,6 +51,7 @@ public class ExpressionJsonConverter : JsonConverter
"Literal" => typeof(LiteralExpression),
"CSharp" => typeof(CSharpExpression),
"JavaScript" => typeof(JavaScriptExpression),
+ "Python" => typeof(PythonExpression),
"Liquid" => typeof(LiquidExpression),
"Object" => typeof(ObjectExpression),
_ => throw new ArgumentOutOfRangeException(nameof(expressionTypeName), expressionTypeName, null)
@@ -62,6 +63,7 @@ public class ExpressionJsonConverter : JsonConverter
nameof(LiteralExpression) => "Literal",
nameof(CSharpExpression) => "CSharp",
nameof(JavaScriptExpression) => "JavaScript",
+ nameof(PythonExpression) => "Python",
nameof(LiquidExpression) => "Liquid",
nameof(ObjectExpression) => "Object",
_ => throw new ArgumentOutOfRangeException(nameof(expressionType), expressionType, null)
diff --git a/src/clients/Elsa.Api.Client/Expressions/CSharpExpression.cs b/src/clients/Elsa.Api.Client/Expressions/CSharpExpression.cs
index 9a0bac7e8..4ef724b49 100644
--- a/src/clients/Elsa.Api.Client/Expressions/CSharpExpression.cs
+++ b/src/clients/Elsa.Api.Client/Expressions/CSharpExpression.cs
@@ -4,7 +4,7 @@ using Elsa.Api.Client.Contracts;
namespace Elsa.Api.Client.Expressions;
///
-/// Represents a c# expression.
+/// Represents a C# expression.
///
public class CSharpExpression : IExpression
{
@@ -19,19 +19,19 @@ public class CSharpExpression : IExpression
///
/// Initializes a new instance of the class.
///
- /// The c# expression.
+ /// The C# expression.
public CSharpExpression(string value)
{
Value = value;
}
///
- /// Gets or sets the c# expression.
+ /// Gets or sets the C# expression.
///
public string? Value { get; set; }
///
- /// Returns the c# expression.
+ /// Returns the C# expression.
///
public override string ToString() => Value ?? "";
}
\ No newline at end of file
diff --git a/src/clients/Elsa.Api.Client/Expressions/PythonExpression.cs b/src/clients/Elsa.Api.Client/Expressions/PythonExpression.cs
new file mode 100644
index 000000000..d7e44d571
--- /dev/null
+++ b/src/clients/Elsa.Api.Client/Expressions/PythonExpression.cs
@@ -0,0 +1,37 @@
+using System.Text.Json.Serialization;
+using Elsa.Api.Client.Contracts;
+
+namespace Elsa.Api.Client.Expressions;
+
+///
+/// Represents a Python expression.
+///
+public class PythonExpression : IExpression
+{
+ ///
+ /// Initializes a new instance of the class.
+ ///
+ [JsonConstructor]
+ public PythonExpression()
+ {
+ }
+
+ ///
+ /// Initializes a new instance of the class.
+ ///
+ /// The Python expression.
+ public PythonExpression(string value)
+ {
+ Value = value;
+ }
+
+ ///
+ /// Gets or sets the Python expression.
+ ///
+ public string? Value { get; set; }
+
+ ///
+ /// Returns the Python expression.
+ ///
+ public override string ToString() => Value ?? "";
+}
\ No newline at end of file
diff --git a/src/modules/Elsa.CSharp/Activities/RunCSharp/RunCSharp.cs b/src/modules/Elsa.CSharp/Activities/RunCSharp/RunCSharp.cs
index c8a5c6e0f..57c1c7124 100644
--- a/src/modules/Elsa.CSharp/Activities/RunCSharp/RunCSharp.cs
+++ b/src/modules/Elsa.CSharp/Activities/RunCSharp/RunCSharp.cs
@@ -27,12 +27,6 @@ public class RunCSharp : CodeActivity