You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: articles/active-directory/develop/v2-oauth-ropc.md
+2-1Lines changed: 2 additions & 1 deletion
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -13,7 +13,7 @@ ms.workload: identity
13
13
ms.tgt_pltfrm: na
14
14
ms.devlang: na
15
15
ms.topic: conceptual
16
-
ms.date: 08/30/2019
16
+
ms.date: 10/11/2019
17
17
ms.author: ryanwi
18
18
ms.reviewer: hirsin
19
19
ms.custom: aaddev
@@ -30,6 +30,7 @@ Microsoft identity platform supports the [resource owner password credential (RO
30
30
> * Personal accounts that are invited to an Azure AD tenant can't use ROPC.
31
31
> * Accounts that don't have passwords can't sign in through ROPC. For this scenario, we recommend that you use a different flow for your app instead.
32
32
> * If users need to use multi-factor authentication (MFA) to log in to the application, they will be blocked instead.
33
+
> * ROPC is not supported in [hybrid identity federation](/azure/active-directory/hybrid/whatis-fed) scenarios (for example, Azure AD and ADFS used to authenticate on-premise accounts). If users are full-page redirected to an on-premises identity providers, Azure AD is not able to test the username and password against that identity provider. [Pass-through authentication](/azure/active-directory/hybrid/how-to-connect-pta) is supported with ROPC, however.
Copy file name to clipboardExpand all lines: articles/azure-functions/durable/durable-functions-bindings.md
+48-55Lines changed: 48 additions & 55 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -368,62 +368,62 @@ Any state changes made to an entity during its execution will be automatically p
368
368
369
369
Every entity function has a parameter type of `IDurableEntityContext`, which has the following members:
370
370
371
-
***EntityName**: Gets the name of the currently executing entity.
372
-
***EntityKey**: Gets the key of the currently executing entity.
373
-
***EntityId**: Gets the ID of the currently executing entity.
374
-
***OperationName**: gets the name of the current operation.
375
-
***IsNewlyConstructed**: returns `true` if the entity did not exist prior to the operation.
376
-
***GetState\<TState>()**: gets the current state of the entity. The `TState` parameter must be a primitive or JSON-serializeable type.
377
-
***SetState(object)**: updates the state of the entity. The `object` parameter must be a primitive or JSON-serializeable object.
378
-
***GetInput\<TInput>()**: gets the input for the current operation. The `TInput` type parameter must represent a primitive or JSON-serializeable type.
379
-
***Return(object)**: returns a value to the orchestration that called the operation. The `object` parameter must be a primitive or JSON-serializeable object.
380
-
***DestructOnExit()**: deletes the entity after finishing the current operation.
381
-
***SignalEntity(EntityId, string, object)**: sends a one-way message to an entity. The `object` parameter must be a primitive or JSON-serializeable object.
382
-
383
-
When using the class-based entity programming mode, the `IDurableEntityContext` object can be referenced using the `Entity.Current` thread-static property.
384
-
385
-
### Trigger sample - entity function
386
-
387
-
The following code is an example of a simple *Counter* entity implemented as a standard function. This function defines three *operations*, `add`, `reset`, and `get`, each of which operate on an integer state value, `currentValue`.
371
+
***EntityName**: the name of the currently executing entity.
372
+
***EntityKey**: the key of the currently executing entity.
373
+
***EntityId**: the ID of the currently executing entity.
374
+
***OperationName**: the name of the current operation.
375
+
***HasState**: whether the entity exists, that is, has some state.
376
+
***GetState\<TState>()**: gets the current state of the entity. If it does not already exist, it is created and initialized to `default<TState>`. The `TState` parameter must be a primitive or JSON-serializeable type.
377
+
***GetState\<TState>(initfunction)**: gets the current state of the entity. If it does not already exist, it is created by calling the provided `initfunction` parameter. The `TState` parameter must be a primitive or JSON-serializeable type.
378
+
***SetState(arg)**: creates or updates the state of the entity. The `arg` parameter must be a JSON-serializeable object or primitive.
379
+
***DeleteState()**: deletes the state of the entity.
380
+
***GetInput\<TInput>()**: gets the input for the current operation. The `TInput` type parameter must be a primitive or JSON-serializeable type.
381
+
***Return(arg)**: returns a value to the orchestration that called the operation. The `arg` parameter must be a primitive or JSON-serializeable object.
382
+
***SignalEntity(EntityId, operation, input)**: sends a one-way message to an entity. The `operation` parameter must be a non-null string, and the `input` parameter must be a primitive or JSON-serializeable object.
383
+
***CreateNewOrchestration(orchestratorFunctionName, input)**: starts a new orchestration. The `input` parameter must be a primitive or JSON-serializeable object.
384
+
385
+
The `IDurableEntityContext` object passed to the entity function can be accessed using the `Entity.Current` async-local property. This approach is convenient when using the class-based programming model.
386
+
387
+
### Trigger sample (function-based syntax)
388
+
389
+
The following code is an example of a simple *Counter* entity implemented as a durable function. This function defines three operations, `add`, `reset`, and `get`, each of which operate on an integer state.
For more information on the function-based syntax and how to use it, see [Function-Based Syntax](durable-functions-dotnet-entities.md#function-based-syntax).
414
411
415
-
The following example is an equivalent implementation of the previous `Counter` entity using .NET classes and methods.
412
+
### Trigger sample (class-based syntax)
413
+
414
+
The following example is an equivalent implementation of the `Counter` entity using classes and methods.
The state of this entity is an object of type `Counter`, which contains a field that stores the current value of the counter. To persist this object in storage, it is serialized and deserialized by the [Json.NET](https://www.newtonsoft.com/json) library.
436
+
437
+
For more information on the class-based syntax and how to use it, see [Defining entity classes](durable-functions-dotnet-entities.md#defining-entity-classes).
438
+
435
439
> [!NOTE]
436
440
> The function entry point method with the `[FunctionName]` attribute *must* be declared `static` when using entity classes. Non-static entry point methods may result in multiple object initialization and potentially other undefined behaviors.
437
441
438
-
Entity classes have special mechanisms for interacting with bindings and .NET dependency injection. For more information, see the [Durable Entities](durable-functions-entities.md) article.
442
+
Entity classes have special mechanisms for interacting with bindings and .NET dependency injection. For more information, see [Entity construction](durable-functions-dotnet-entities.md#entity-construction).
439
443
440
444
## Entity client
441
445
@@ -468,17 +472,15 @@ If you're using scripting languages (for example, *.csx* or *.js* files) for dev
468
472
469
473
In .NET functions, you typically bind to `IDurableEntityClient`, which gives you full access to all client APIs supported by Durable Entities. You can also bind to the `IDurableClient` interface, which provides access to client APIs for both entities and orchestrations. APIs on the client object include:
470
474
471
-
***ReadEntityStateAsync\<T>**: reads the state of an entity.
475
+
***ReadEntityStateAsync\<T>**: reads the state of an entity. It returns a response that indicates whether the target entity exists, and if so, what its state is.
472
476
***SignalEntityAsync**: sends a one-way message to an entity, and waits for it to be enqueued.
473
-
***SignalEntityAsync\<TEntityInterface>**: same as `SignalEntityAsync` but uses a generated proxy object of type `TEntityInterface`.
474
-
***CreateEntityProxy\<TEntityInterface>**: dynamically generates a dynamic proxy of type `TEntityInterface` for making type-safe calls to entities.
475
477
476
-
> [!NOTE]
477
-
> It's important to understand that the previous "signal" operations are all asynchronous. It is not possible to invoke an entity function and get back a return value from a client. Similarly, the `SignalEntityAsync` may return before the entity starts executing the operation. Only orchestrator functions can invoke entity functions synchronously and process return values.
478
+
There is no need to create the target entity before sending a signal - the entity state can be created from within the entity function that handles the signal.
478
479
479
-
The `SignalEntityAsync` APIs require specifying the unique identifier of the entity as an `EntityId`. These APIs also optionally take the name of the entity operation as a `string` and the payload of the operation as a JSON-serializeable `object`. If the target entity does not exist, it will be created automatically with the specified entity ID.
480
+
> [!NOTE]
481
+
> It's important to understand that the "signals" sent from the client are simply enqueued, to be processed asynchronously at a later time. In particular, the `SignalEntityAsync` usually returns before the entity even starts the operation, and it is not possible to get back the return value or observe exceptions. If stronger guarantees are required (e.g. for workflows), *orchestrator functions* should be used, which can wait for entity operations to complete, and can process return values and observe exceptions.
480
482
481
-
### Client sample (untyped)
483
+
### Example: client signals entity directly
482
484
483
485
Here is an example queue-triggered function that invokes a "Counter" entity.
484
486
@@ -495,16 +497,16 @@ public static Task Run(
495
497
}
496
498
```
497
499
498
-
### Client sample (typed)
500
+
### Example: client signals entity via interface
499
501
500
-
It's possible to generate a proxy object for type-safe access to entity operations. To generate a type-safe proxy, the entity type must implement an interface. For example, suppose the `Counter` entity mentioned earlier implemented an `ICounter` interface, defined as follows:
502
+
Where possible, we recommend [accessing entities through interfaces](durable-functions-dotnet-entities.md#accessing-entities-through-interfaces) because it provides more type checking. For example, suppose the `Counter` entity mentioned earlier implemented an `ICounter` interface, defined as follows:
501
503
502
504
```csharp
503
505
publicinterfaceICounter
504
506
{
505
507
voidAdd(intamount);
506
508
voidReset();
507
-
intGet();
509
+
Task<int>Get();
508
510
}
509
511
510
512
publicclassCounter : ICounter
@@ -513,7 +515,7 @@ public class Counter : ICounter
513
515
}
514
516
```
515
517
516
-
Client code could then use `SignalEntityAsync<TEntityInterface>`and specify the `ICounter` interface as the type parameter to generate a type-safe proxy. This use of type-safe proxies is demonstrated in the following code sample:
518
+
Client code can then use `SignalEntityAsync<ICounter>` to generate a type-safe proxy:
517
519
518
520
```csharp
519
521
[FunctionName("UserDeleteAvailable")]
@@ -527,28 +529,19 @@ public static async Task AddValueClient(
527
529
}
528
530
```
529
531
530
-
In the previous example, the `proxy` parameter is a dynamically generated instance of `ICounter`, which internally translates the call to `Add` into the equivalent (untyped) call to `SignalEntityAsync`.
531
-
532
-
There are a few rules for defining entity interfaces:
533
-
534
-
* The type parameter `TEntityInterface` in `SignalEntityAsync<TEntityInterface>` must be an interface.
535
-
* Entity interfaces must only define methods.
536
-
* Entity interface methods must not define more than one parameter.
537
-
* Entity interface methods must return `void`, `Task`, or `Task<T>` where `T` is some return value.
538
-
* Entity interfaces must have exactly one concrete implementation class within the same assembly (that is, the entity class).
539
-
540
-
If any of these rules are violated, an `InvalidOperationException` will be thrown at runtime. The exception message will explain which rule was broken.
532
+
The `proxy` parameter is a dynamically generated instance of `ICounter`, which internally translates the call to `Add` into the equivalent (untyped) call to `SignalEntityAsync`.
541
533
542
534
> [!NOTE]
543
535
> The `SignalEntityAsync` APIs represent one-way operations. If an entity interfaces returns `Task<T>`, the value of the `T` parameter will always be null or `default`.
544
536
545
-
<aname="host-json"></a>
537
+
In particular, it does not make sense to signal the `Get` operation, as no value is returned. Instead, clients can use either `ReadStateAsync` to access the counter state directly, or can start an orchestrator function that calls the `Get` operation.
0 commit comments