-
Notifications
You must be signed in to change notification settings - Fork 53
Enable external DF SDK #839
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
8ab426e
c90c070
f2e291c
419ae37
049c4f7
1297298
0d1cc12
88dcc98
1ac8d49
d7fe44f
6f2d654
65913c3
00bbf2e
1bff0cb
a793c75
635a341
d4b5084
3f3dea6
8dd5ebb
4668b8d
765b963
e1273d3
b24b6ec
7e98f7d
71070b5
42cdca6
73fcc5e
cb2a17c
9ab5b09
5511464
bf4b2f2
7c24933
dee9ad9
6f7fa8a
889f65f
a1e5993
8fe3d36
6b36ee1
6e1e97f
8e0e103
e85c19e
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,28 @@ | ||
// | ||
// Copyright (c) Microsoft. All rights reserved. | ||
// Licensed under the MIT license. See LICENSE file in the project root for full license information. | ||
// | ||
|
||
namespace Microsoft.Azure.Functions.PowerShellWorker.Durable | ||
{ | ||
using System; | ||
using System.Collections; | ||
using System.Management.Automation; | ||
|
||
// Contract for the orchestration invoker in the external Durable Functions SDK | ||
internal class ExternalInvoker : IExternalOrchestrationInvoker | ||
{ | ||
private readonly Func<PowerShell, object> _externalSDKInvokerFunction; | ||
|
||
public ExternalInvoker(Func<PowerShell, object> invokerFunction) | ||
{ | ||
_externalSDKInvokerFunction = invokerFunction; | ||
} | ||
|
||
// Invokes an orchestration using the external Durable SDK | ||
public Hashtable Invoke(IPowerShellServices powerShellServices) | ||
{ | ||
return (Hashtable)_externalSDKInvokerFunction.Invoke(powerShellServices.GetPowerShell()); | ||
} | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,16 @@ | ||
// | ||
// Copyright (c) Microsoft. All rights reserved. | ||
// Licensed under the MIT license. See LICENSE file in the project root for full license information. | ||
// | ||
|
||
namespace Microsoft.Azure.Functions.PowerShellWorker.Durable | ||
{ | ||
using System.Collections; | ||
|
||
// Contract interface for the orchestration invoker in the external Durable Functions SDK | ||
internal interface IExternalOrchestrationInvoker | ||
{ | ||
// Invokes an orchestration using the external Durable SDK | ||
Hashtable Invoke(IPowerShellServices powerShellServices); | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -11,58 +11,97 @@ namespace Microsoft.Azure.Functions.PowerShellWorker.Durable | |
using System.Linq; | ||
using System.Management.Automation; | ||
|
||
using PowerShellWorker.Utility; | ||
using Microsoft.Azure.Functions.PowerShellWorker.Durable.Actions; | ||
using Microsoft.Azure.Functions.PowerShellWorker.Utility; | ||
|
||
internal class OrchestrationInvoker : IOrchestrationInvoker | ||
{ | ||
public Hashtable Invoke(OrchestrationBindingInfo orchestrationBindingInfo, IPowerShellServices pwsh) | ||
private IExternalOrchestrationInvoker externalInvoker; | ||
|
||
public Hashtable Invoke( | ||
OrchestrationBindingInfo orchestrationBindingInfo, | ||
IPowerShellServices powerShellServices) | ||
{ | ||
try | ||
{ | ||
var outputBuffer = new PSDataCollection<object>(); | ||
var context = orchestrationBindingInfo.Context; | ||
if (powerShellServices.HasExternalDurableSDK()) | ||
{ | ||
return InvokeExternalDurableSDK(powerShellServices); | ||
} | ||
return InvokeInternalDurableSDK(orchestrationBindingInfo, powerShellServices); | ||
} | ||
catch (Exception ex) | ||
{ | ||
ex.Data.Add(Utils.IsOrchestrationFailureKey, true); | ||
throw; | ||
} | ||
finally | ||
{ | ||
powerShellServices.ClearStreamsAndCommands(); | ||
} | ||
} | ||
|
||
public Hashtable InvokeExternalDurableSDK(IPowerShellServices powerShellServices) | ||
{ | ||
return externalInvoker.Invoke(powerShellServices); | ||
} | ||
|
||
public Hashtable InvokeInternalDurableSDK( | ||
OrchestrationBindingInfo orchestrationBindingInfo, | ||
IPowerShellServices powerShellServices) | ||
{ | ||
var outputBuffer = new PSDataCollection<object>(); | ||
var context = orchestrationBindingInfo.Context; | ||
|
||
// context.History should never be null when initializing CurrentUtcDateTime | ||
var orchestrationStart = context.History.First( | ||
e => e.EventType == HistoryEventType.OrchestratorStarted); | ||
context.CurrentUtcDateTime = orchestrationStart.Timestamp.ToUniversalTime(); | ||
|
||
// context.History should never be null when initializing CurrentUtcDateTime | ||
var orchestrationStart = context.History.First( | ||
e => e.EventType == HistoryEventType.OrchestratorStarted); | ||
context.CurrentUtcDateTime = orchestrationStart.Timestamp.ToUniversalTime(); | ||
// Marks the first OrchestratorStarted event as processed | ||
orchestrationStart.IsProcessed = true; | ||
|
||
// Marks the first OrchestratorStarted event as processed | ||
orchestrationStart.IsProcessed = true; | ||
|
||
var asyncResult = pwsh.BeginInvoke(outputBuffer); | ||
// Finish initializing the Function invocation | ||
powerShellServices.AddParameter(orchestrationBindingInfo.ParameterName, context); | ||
powerShellServices.TracePipelineObject(); | ||
|
||
var (shouldStop, actions) = | ||
orchestrationBindingInfo.Context.OrchestrationActionCollector.WaitForActions(asyncResult.AsyncWaitHandle); | ||
var asyncResult = powerShellServices.BeginInvoke(outputBuffer); | ||
|
||
if (shouldStop) | ||
var (shouldStop, actions) = | ||
orchestrationBindingInfo.Context.OrchestrationActionCollector.WaitForActions(asyncResult.AsyncWaitHandle); | ||
|
||
if (shouldStop) | ||
{ | ||
// The orchestration function should be stopped and restarted | ||
powerShellServices.StopInvoke(); | ||
return CreateOrchestrationResult(isDone: false, actions, output: null, context.CustomStatus); | ||
} | ||
else | ||
{ | ||
try | ||
{ | ||
// The orchestration function should be stopped and restarted | ||
pwsh.StopInvoke(); | ||
return CreateOrchestrationResult(isDone: false, actions, output: null, context.CustomStatus); | ||
// The orchestration function completed | ||
powerShellServices.EndInvoke(asyncResult); | ||
var result = CreateReturnValueFromFunctionOutput(outputBuffer); | ||
return CreateOrchestrationResult(isDone: true, actions, output: result, context.CustomStatus); | ||
} | ||
else | ||
catch (Exception e) | ||
{ | ||
try | ||
{ | ||
// The orchestration function completed | ||
pwsh.EndInvoke(asyncResult); | ||
var result = FunctionReturnValueBuilder.CreateReturnValueFromFunctionOutput(outputBuffer); | ||
return CreateOrchestrationResult(isDone: true, actions, output: result, context.CustomStatus); | ||
} | ||
catch (Exception e) | ||
{ | ||
// The orchestrator code has thrown an unhandled exception: | ||
// this should be treated as an entire orchestration failure | ||
throw new OrchestrationFailureException(actions, context.CustomStatus, e); | ||
} | ||
// The orchestrator code has thrown an unhandled exception: | ||
// this should be treated as an entire orchestration failure | ||
throw new OrchestrationFailureException(actions, context.CustomStatus, e); | ||
} | ||
} | ||
finally | ||
} | ||
|
||
public static object CreateReturnValueFromFunctionOutput(IList<object> pipelineItems) | ||
{ | ||
if (pipelineItems == null || pipelineItems.Count <= 0) | ||
{ | ||
pwsh.ClearStreamsAndCommands(); | ||
return null; | ||
davidmrdavid marked this conversation as resolved.
Show resolved
Hide resolved
Comment on lines
-64
to
+101
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Just for clarity: the |
||
} | ||
|
||
return pipelineItems.Count == 1 ? pipelineItems[0] : pipelineItems.ToArray(); | ||
} | ||
|
||
private static Hashtable CreateOrchestrationResult( | ||
|
@@ -74,5 +113,10 @@ private static Hashtable CreateOrchestrationResult( | |
var orchestrationMessage = new OrchestrationMessage(isDone, actions, output, customStatus); | ||
return new Hashtable { { AzFunctionInfo.DollarReturn, orchestrationMessage } }; | ||
} | ||
|
||
public void SetExternalInvoker(IExternalOrchestrationInvoker externalInvoker) | ||
{ | ||
this.externalInvoker = externalInvoker; | ||
} | ||
} | ||
} |
Uh oh!
There was an error while loading. Please reload this page.