From 2dab5f2dada8728062a88061d57d33a8555607ff Mon Sep 17 00:00:00 2001 From: Hannah Hunter Date: Wed, 15 Jan 2025 13:32:47 -0500 Subject: [PATCH 01/18] clarify that self-hosted can work in production too Signed-off-by: Hannah Hunter --- daprdocs/content/en/concepts/overview.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/concepts/overview.md b/daprdocs/content/en/concepts/overview.md index 7613042ff..fb1e31502 100644 --- a/daprdocs/content/en/concepts/overview.md +++ b/daprdocs/content/en/concepts/overview.md @@ -76,7 +76,7 @@ Dapr exposes its HTTP and gRPC APIs as a sidecar architecture, either as a conta ## Hosting environments Dapr can be hosted in multiple environments, including: -- Self-hosted on a Windows/Linux/macOS machine for local development +- Self-hosted on a Windows/Linux/macOS machine for local development and in production - On Kubernetes or clusters of physical or virtual machines in production ### Self-hosted local development From 26145a05857f1615c7640f4822a37096d05066d0 Mon Sep 17 00:00:00 2001 From: Elena Kolevska Date: Wed, 22 Jan 2025 00:17:53 +0000 Subject: [PATCH 02/18] Updates errors reference Signed-off-by: Elena Kolevska --- .../error-codes/error-codes-reference.md | 270 +++++++++++------- 1 file changed, 162 insertions(+), 108 deletions(-) diff --git a/daprdocs/content/en/developing-applications/error-codes/error-codes-reference.md b/daprdocs/content/en/developing-applications/error-codes/error-codes-reference.md index 314bf67c4..053899653 100644 --- a/daprdocs/content/en/developing-applications/error-codes/error-codes-reference.md +++ b/daprdocs/content/en/developing-applications/error-codes/error-codes-reference.md @@ -6,145 +6,199 @@ description: "List of gRPC and HTTP error codes in Dapr and their descriptions" weight: 20 --- -The following tables list the error codes returned by Dapr runtime: +The following tables list the error codes returned by Dapr runtime. +The error codes are returned in the response body of an HTTP request or in the `ErrorInfo` section of a gRPC Status response, if one is present. +An effort is underway to enrich all gRPC error responses according to the [Richer Error Model]({{< ref grpc-error-codes.md#richer-grpc-error-model >}}). Error codes without a corresponding gRPC code indicate errors that have not yet been updated to this model yet. ### Actors API -| Error Code | Description | -| -------------------------------- | ------------------------------------------ | -| ERR_ACTOR_INSTANCE_MISSING | Error when an actor instance is missing. | -| ERR_ACTOR_RUNTIME_NOT_FOUND | Error the actor instance. | -| ERR_ACTOR_REMINDER_CREATE | Error creating a reminder for an actor. | -| ERR_ACTOR_REMINDER_DELETE | Error deleting a reminder for an actor. | -| ERR_ACTOR_TIMER_CREATE | Error creating a timer for an actor. | -| ERR_ACTOR_TIMER_DELETE | Error deleting a timer for an actor. | -| ERR_ACTOR_REMINDER_GET | Error getting a reminder for an actor. | -| ERR_ACTOR_INVOKE_METHOD | Error invoking a method on an actor. | -| ERR_ACTOR_STATE_DELETE | Error deleting the state for an actor. | -| ERR_ACTOR_STATE_GET | Error getting the state for an actor. | -| ERR_ACTOR_STATE_TRANSACTION_SAVE | Error storing actor state transactionally. | -| ERR_ACTOR_REMINDER_NON_HOSTED | Error setting reminder for an actor. | +| HTTP Code | gRPC Code | Description | +| ---------------------------------- | --------- | ----------------------------------------------------------------------- | +| `ERR_ACTOR_INSTANCE_MISSING` | | Missing actor instance | +| `ERR_ACTOR_INVOKE_METHOD` | | Error invoking actor method | +| `ERR_ACTOR_RUNTIME_NOT_FOUND` | | Actor runtime not found | +| `ERR_ACTOR_STATE_GET` | | Error getting actor state | +| `ERR_ACTOR_STATE_TRANSACTION_SAVE` | | Error saving actor transaction | +| `ERR_ACTOR_REMINDER_CREATE` | | Error creating actor reminder | +| `ERR_ACTOR_REMINDER_DELETE` | | Error deleting actor reminder | +| `ERR_ACTOR_REMINDER_GET` | | Error getting actor reminder | +| `ERR_ACTOR_REMINDER_NON_HOSTED` | | Reminder operation on non-hosted actor type | +| `ERR_ACTOR_TIMER_CREATE` | | Error creating actor timer | +| `ERR_ACTOR_NO_APP_CHANNEL` | | App channel not initialized | +| `ERR_ACTOR_STACK_DEPTH` | | Maximum actor call stack depth exceeded | +| `ERR_ACTOR_NO_PLACEMENT` | | Placement service not configured | +| `ERR_ACTOR_RUNTIME_CLOSED` | | Actor runtime is closed | +| `ERR_ACTOR_NAMESPACE_REQUIRED` | | Actors must have a namespace configured when running in Kubernetes mode | +| `ERR_ACTOR_NO_ADDRESS` | | No address found for actor | + ### Workflows API -| Error Code | Description | -| -------------------------------- | ----------------------------------------------------------- | -| ERR_GET_WORKFLOW | Error getting workflow. | -| ERR_START_WORKFLOW | Error starting the workflow. | -| ERR_PAUSE_WORKFLOW | Error pausing the workflow. | -| ERR_RESUME_WORKFLOW | Error resuming the workflow. | -| ERR_TERMINATE_WORKFLOW | Error terminating the workflow. | -| ERR_PURGE_WORKFLOW | Error purging workflow. | -| ERR_RAISE_EVENT_WORKFLOW | Error raising an event within the workflow. | -| ERR_WORKFLOW_COMPONENT_MISSING | Error when a workflow component is missing a configuration. | -| ERR_WORKFLOW_COMPONENT_NOT_FOUND | Error when a workflow component is not found. | -| ERR_WORKFLOW_EVENT_NAME_MISSING | Error when the event name for a workflow is missing. | -| ERR_WORKFLOW_NAME_MISSING | Error when the workflow name is missing. | -| ERR_INSTANCE_ID_INVALID | Error invalid workflow instance ID provided. | -| ERR_INSTANCE_ID_NOT_FOUND | Error workflow instance ID not found. | -| ERR_INSTANCE_ID_PROVIDED_MISSING | Error workflow instance ID was provided but missing. | -| ERR_INSTANCE_ID_TOO_LONG | Error workflow instance ID exceeds allowable length. | +| HTTP Code | gRPC Code | Description | +| ---------------------------------- | --------- | --------------------------------------------------------------------------------------- | +| `ERR_GET_WORKFLOW` | | Error getting workflow | +| `ERR_START_WORKFLOW` | | Error starting workflow | +| `ERR_PAUSE_WORKFLOW` | | Error pausing workflow | +| `ERR_RESUME_WORKFLOW` | | Error resuming workflow | +| `ERR_TERMINATE_WORKFLOW` | | Error terminating workflow | +| `ERR_PURGE_WORKFLOW` | | Error purging workflow | +| `ERR_RAISE_EVENT_WORKFLOW` | | Error raising event in workflow | +| `ERR_WORKFLOW_COMPONENT_MISSING` | | Missing workflow component | +| `ERR_WORKFLOW_COMPONENT_NOT_FOUND` | | Workflow component not found | +| `ERR_WORKFLOW_EVENT_NAME_MISSING` | | Missing workflow event name | +| `ERR_WORKFLOW_NAME_MISSING` | | Workflow name not configured | +| `ERR_INSTANCE_ID_INVALID` | | Invalid workflow instance ID. (Only alphanumeric and underscore characters are allowed) | +| `ERR_INSTANCE_ID_NOT_FOUND` | | Workflow instance ID not found | +| `ERR_INSTANCE_ID_PROVIDED_MISSING` | | Missing workflow instance ID | +| `ERR_INSTANCE_ID_TOO_LONG` | | Workflow instance ID too long | -### State Management API -| Error Code | Description | -| ------------------------------------- | ------------------------------------------------------------------------- | -| ERR_STATE_STORE_NOT_FOUND | Error referencing a state store not found. | -| ERR_STATE_STORES_NOT_CONFIGURED | Error no state stores configured. | -| ERR_NOT_SUPPORTED_STATE_OPERATION | Error transaction requested on a state store with no transaction support. | -| ERR_STATE_GET | Error getting a state for state store. | -| ERR_STATE_DELETE | Error deleting a state from state store. | -| ERR_STATE_SAVE | Error saving a state in state store. | -| ERR_STATE_TRANSACTION | Error encountered during state transaction. | -| ERR_STATE_BULK_GET | Error performing bulk retrieval of state entries. | -| ERR_STATE_QUERY | Error querying the state store. | -| ERR_STATE_STORE_NOT_CONFIGURED | Error state store is not configured. | -| ERR_STATE_STORE_NOT_SUPPORTED | Error state store is not supported. | -| ERR_STATE_STORE_TOO_MANY_TRANSACTIONS | Error exceeded maximum allowable transactions. | +### State management API + +| HTTP Code | gRPC Code | Description | +| --------------------------------------- | --------------------------------------- | ----------------------------------------- | +| `ERR_STATE_TRANSACTION` | | Error in state transaction | +| `ERR_STATE_SAVE` | | Error saving state | +| `ERR_STATE_GET` | | Error getting state | +| `ERR_STATE_DELETE` | | Error deleting state | +| `ERR_STATE_BULK_DELETE` | | Error deleting state in bulk | +| `ERR_STATE_BULK_GET` | | Error getting state in bulk | +| `ERR_NOT_SUPPORTED_STATE_OPERATION` | | Operation not supported in transaction | +| `ERR_STATE_QUERY` | `DAPR_STATE_QUERY_FAILED` | Error querying state | +| `ERR_STATE_STORE_NOT_FOUND` | `DAPR_STATE_NOT_FOUND` | State store not found | +| `ERR_STATE_STORE_NOT_CONFIGURED` | `DAPR_STATE_NOT_CONFIGURED` | State store not configured | +| `ERR_STATE_STORE_NOT_SUPPORTED` | `DAPR_STATE_TRANSACTIONS_NOT_SUPPORTED` | State store does not support transactions | +| `ERR_STATE_STORE_NOT_SUPPORTED` | `DAPR_STATE_QUERYING_NOT_SUPPORTED` | State store does not support querying | +| `ERR_STATE_STORE_TOO_MANY_TRANSACTIONS` | `DAPR_STATE_TOO_MANY_TRANSACTIONS` | Too many operations per transaction | +| `ERR_MALFORMED_REQUEST` | `DAPR_STATE_ILLEGAL_KEY` | Invalid key | + ### Configuration API -| Error Code | Description | -| -------------------------------------- | -------------------------------------------- | -| ERR_CONFIGURATION_GET | Error retrieving configuration. | -| ERR_CONFIGURATION_STORE_NOT_CONFIGURED | Error configuration store is not configured. | -| ERR_CONFIGURATION_STORE_NOT_FOUND | Error configuration store not found. | -| ERR_CONFIGURATION_SUBSCRIBE | Error subscribing to a configuration. | -| ERR_CONFIGURATION_UNSUBSCRIBE | Error unsubscribing from a configuration. | +| HTTP Code | gRPC Code | Description | +| ---------------------------------------- | --------- | -------------------------------------- | +| `ERR_CONFIGURATION_GET` | | Error getting configuration | +| `ERR_CONFIGURATION_STORE_NOT_CONFIGURED` | | Configuration store not configured | +| `ERR_CONFIGURATION_STORE_NOT_FOUND` | | Configuration store not found | +| `ERR_CONFIGURATION_SUBSCRIBE` | | Error subscribing to configuration | +| `ERR_CONFIGURATION_UNSUBSCRIBE` | | Error unsubscribing from configuration | + ### Crypto API -| Error Code | Description | -| ----------------------------------- | ------------------------------------------ | -| ERR_CRYPTO | General crypto building block error. | -| ERR_CRYPTO_KEY | Error related to a crypto key. | -| ERR_CRYPTO_PROVIDER_NOT_FOUND | Error specified crypto provider not found. | -| ERR_CRYPTO_PROVIDERS_NOT_CONFIGURED | Error no crypto providers configured. | +| HTTP Code | gRPC Code | Description | +| ------------------------------------- | --------- | ------------------------------- | +| `ERR_CRYPTO` | | Error in crypto operation | +| `ERR_CRYPTO_KEY` | | Error retrieving crypto key | +| `ERR_CRYPTO_PROVIDER_NOT_FOUND` | | Crypto provider not found | +| `ERR_CRYPTO_PROVIDERS_NOT_CONFIGURED` | | Crypto providers not configured | + ### Secrets API -| Error Code | Description | -| -------------------------------- | ---------------------------------------------------- | -| ERR_SECRET_STORES_NOT_CONFIGURED | Error that no secret store is configured. | -| ERR_SECRET_STORE_NOT_FOUND | Error that specified secret store is not found. | -| ERR_SECRET_GET | Error retrieving the specified secret. | -| ERR_PERMISSION_DENIED | Error access denied due to insufficient permissions. | +| HTTP Code | gRPC Code | Description | +| ---------------------------------- | --------- | --------------------------- | +| `ERR_SECRET_GET` | | Error getting secret | +| `ERR_SECRET_STORE_NOT_FOUND` | | Secret store not found | +| `ERR_SECRET_STORES_NOT_CONFIGURED` | | Secret store not configured | +| `ERR_PERMISSION_DENIED` | | Permission denied by policy | -### Pub/Sub API -| Error Code | Description | -| --------------------------- | -------------------------------------------------------- | -| ERR_PUBSUB_NOT_FOUND | Error referencing the Pub/Sub component in Dapr runtime. | -| ERR_PUBSUB_PUBLISH_MESSAGE | Error publishing a message. | -| ERR_PUBSUB_FORBIDDEN | Error message forbidden by access controls. | -| ERR_PUBSUB_CLOUD_EVENTS_SER | Error serializing Pub/Sub event envelope. | -| ERR_PUBSUB_EMPTY | Error empty Pub/Sub. | -| ERR_PUBSUB_NOT_CONFIGURED | Error Pub/Sub component is not configured. | -| ERR_PUBSUB_REQUEST_METADATA | Error with metadata in Pub/Sub request. | -| ERR_PUBSUB_EVENTS_SER | Error serializing Pub/Sub events. | -| ERR_PUBLISH_OUTBOX | Error publishing message to the outbox. | -| ERR_TOPIC_NAME_EMPTY | Error topic name for Pub/Sub message is empty. | +### Pub/Sub and messaging errors + +| HTTP Code | gRPC Code | Description | +| ----------------------------- | -------------------------------------- | -------------------------------------- | +| `ERR_PUBSUB_EMPTY` | `DAPR_PUBSUB_NAME_EMPTY` | Pubsub name is empty | +| `ERR_PUBSUB_NOT_FOUND` | `DAPR_PUBSUB_NOT_FOUND` | Pubsub not found | +| `ERR_PUBSUB_NOT_FOUND` | `DAPR_PUBSUB_TEST_NOT_FOUND` | Pubsub not found | +| `ERR_PUBSUB_NOT_CONFIGURED` | `DAPR_PUBSUB_NOT_CONFIGURED` | Pubsub not configured | +| `ERR_TOPIC_NAME_EMPTY` | `DAPR_PUBSUB_TOPIC_NAME_EMPTY` | Topic name is empty | +| `ERR_PUBSUB_FORBIDDEN` | `DAPR_PUBSUB_FORBIDDEN` | Access to topic forbidden for APP ID | +| `ERR_PUBSUB_PUBLISH_MESSAGE` | `DAPR_PUBSUB_PUBLISH_MESSAGE` | Error publishing message | +| `ERR_PUBSUB_REQUEST_METADATA` | `DAPR_PUBSUB_METADATA_DESERIALIZATION` | Error deserializing metadata | +| `ERR_PUBSUB_CLOUD_EVENTS_SER` | `DAPR_PUBSUB_CLOUD_EVENT_CREATION` | Error creating CloudEvent | +| `ERR_PUBSUB_EVENTS_SER` | `DAPR_PUBSUB_MARSHAL_ENVELOPE` | Error marshalling Cloud Event envelope | +| `ERR_PUBSUB_EVENTS_SER` | `DAPR_PUBSUB_MARSHAL_EVENTS` | Error marshalling events to bytes | +| `ERR_PUBSUB_EVENTS_SER` | `DAPR_PUBSUB_UNMARSHAL_EVENTS` | Error unmarshalling events | +| `ERR_PUBLISH_OUTBOX` | | Error publishing message to outbox | + ### Conversation API -| Error Code | Description | -| ------------------------------- | ----------------------------------------------- | -| ERR_INVOKE_OUTPUT_BINDING | Error invoking an output binding. | -| ERR_DIRECT_INVOKE | Error in direct invocation. | -| ERR_CONVERSATION_INVALID_PARMS | Error invalid parameters for conversation. | -| ERR_CONVERSATION_INVOKE | Error invoking the conversation. | -| ERR_CONVERSATION_MISSING_INPUTS | Error missing required inputs for conversation. | -| ERR_CONVERSATION_NOT_FOUND | Error conversation not found. | +| HTTP Code | gRPC Code | Description | +| --------------------------------- | --------- | --------------------------------------------- | +| `ERR_CONVERSATION_INVALID_PARMS` | | Invalid parameters for conversation component | +| `ERR_CONVERSATION_INVOKE` | | Error invoking conversation | +| `ERR_CONVERSATION_MISSING_INPUTS` | | Missing inputs for conversation | +| `ERR_CONVERSATION_NOT_FOUND` | | Conversation not found | + + +### Service Invocation / Direct Messaging API + +| HTTP Code | gRPC Code | Description | +| ------------------- | --------- | ---------------------- | +| `ERR_DIRECT_INVOKE` | | Error invoking service | + + +### Bindings API + +| HTTP Code | gRPC Code | Description | +| --------------------------- | --------- | ----------------------------- | +| `ERR_INVOKE_OUTPUT_BINDING` | | Error invoking output binding | + ### Distributed Lock API -| Error Code | Description | -| ----------------------------- | ----------------------------------- | -| ERR_TRY_LOCK | Error attempting to acquire a lock. | -| ERR_UNLOCK | Error attempting to release a lock. | -| ERR_LOCK_STORE_NOT_CONFIGURED | Error lock store is not configured. | -| ERR_LOCK_STORE_NOT_FOUND | Error lock store not found. | +| HTTP Code | gRPC Code | Description | +| ------------------------------- | --------- | ------------------------- | +| `ERR_LOCK_STORE_NOT_CONFIGURED` | | Lock store not configured | +| `ERR_LOCK_STORE_NOT_FOUND` | | Lock store not found | +| `ERR_TRY_LOCK` | | Error acquiring lock | +| `ERR_UNLOCK` | | Error releasing lock | + ### Healthz -| Error Code | Description | -| ----------------------------- | --------------------------------------------------------------- | -| ERR_HEALTH_NOT_READY | Error that Dapr is not ready. | -| ERR_HEALTH_APPID_NOT_MATCH | Error the app-id does not match expected value in health check. | -| ERR_OUTBOUND_HEALTH_NOT_READY | Error outbound connection health is not ready. | +| HTTP Code | gRPC Code | Description | +| ------------------------------- | --------- | --------------------------- | +| `ERR_HEALTH_NOT_READY` | | Dapr not ready | +| `ERR_HEALTH_APPID_NOT_MATCH` | | Dapr App ID does not match | +| `ERR_OUTBOUND_HEALTH_NOT_READY` | | Dapr outbound not ready | + ### Common -| Error Code | Description | -| -------------------------- | ------------------------------------------------ | -| ERR_API_UNIMPLEMENTED | Error API is not implemented. | -| ERR_APP_CHANNEL_NIL | Error application channel is nil. | -| ERR_BAD_REQUEST | Error client request is badly formed or invalid. | -| ERR_BODY_READ | Error reading body. | -| ERR_INTERNAL | Internal server error encountered. | -| ERR_MALFORMED_REQUEST | Error with a malformed request. | -| ERR_MALFORMED_REQUEST_DATA | Error request data is malformed. | -| ERR_MALFORMED_RESPONSE | Error response data is malformed. | +| HTTP Code | gRPC Code | Description | +| ---------------------------- | --------- | -------------------------- | +| `ERR_API_UNIMPLEMENTED` | | API not implemented | +| `ERR_APP_CHANNEL_NIL` | | App channel is nil | +| `ERR_BAD_REQUEST` | | Bad request | +| `ERR_BODY_READ` | | Error reading request body | +| `ERR_INTERNAL` | | Internal error | +| `ERR_MALFORMED_REQUEST` | | Malformed request | +| `ERR_MALFORMED_REQUEST_DATA` | | Malformed request data | +| `ERR_MALFORMED_RESPONSE` | | Malformed response | + + +### Scheduler/Jobs API + +| HTTP Code | gRPC Code | Description | +| ------------------------------- | ------------------------------- | -------------------------------------- | +| `DAPR_SCHEDULER_SCHEDULE_JOB` | `DAPR_SCHEDULER_SCHEDULE_JOB` | Error scheduling job | +| `DAPR_SCHEDULER_JOB_NAME` | `DAPR_SCHEDULER_JOB_NAME` | Job name should only be set in the url | +| `DAPR_SCHEDULER_JOB_NAME_EMPTY` | `DAPR_SCHEDULER_JOB_NAME_EMPTY` | Job name is empty | +| `DAPR_SCHEDULER_GET_JOB` | `DAPR_SCHEDULER_GET_JOB` | Error getting job | +| `DAPR_SCHEDULER_LIST_JOBS` | `DAPR_SCHEDULER_LIST_JOBS` | Error listing jobs | +| `DAPR_SCHEDULER_DELETE_JOB` | `DAPR_SCHEDULER_DELETE_JOB` | Error deleting job | +| `DAPR_SCHEDULER_EMPTY` | `DAPR_SCHEDULER_EMPTY` | Required argument is empty | +| `DAPR_SCHEDULER_SCHEDULE_EMPTY` | `DAPR_SCHEDULER_SCHEDULE_EMPTY` | No schedule provided for job | + + +### Generic + +| HTTP Code | gRPC Code | Description | +| --------- | --------- | ------------- | +| `ERROR` | `ERROR` | Generic error | ## Next steps From ce1c07e072278bc8e1e9923532da8b0d94dcd962 Mon Sep 17 00:00:00 2001 From: Elena Kolevska Date: Wed, 22 Jan 2025 00:24:30 +0000 Subject: [PATCH 03/18] Adds quotes Signed-off-by: Elena Kolevska --- .../error-codes/error-codes-reference.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/error-codes/error-codes-reference.md b/daprdocs/content/en/developing-applications/error-codes/error-codes-reference.md index 053899653..e0dc6b4c1 100644 --- a/daprdocs/content/en/developing-applications/error-codes/error-codes-reference.md +++ b/daprdocs/content/en/developing-applications/error-codes/error-codes-reference.md @@ -8,7 +8,7 @@ weight: 20 The following tables list the error codes returned by Dapr runtime. The error codes are returned in the response body of an HTTP request or in the `ErrorInfo` section of a gRPC Status response, if one is present. -An effort is underway to enrich all gRPC error responses according to the [Richer Error Model]({{< ref grpc-error-codes.md#richer-grpc-error-model >}}). Error codes without a corresponding gRPC code indicate errors that have not yet been updated to this model yet. +An effort is underway to enrich all gRPC error responses according to the [Richer Error Model]({{< ref "grpc-error-codes.md#richer-grpc-error-model" >}}). Error codes without a corresponding gRPC code indicate errors that have not yet been updated to this model yet. ### Actors API From ed8c9529e64a0a4e871d89ef2b5713a0db85b0f6 Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Wed, 22 Jan 2025 05:40:13 -0600 Subject: [PATCH 04/18] Added .NET example to the job scheduling documentation Signed-off-by: Whit Waldo --- ...owto-schedule-and-handle-triggered-jobs.md | 97 ++++++++++++++++++- 1 file changed, 96 insertions(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index 0a5dba3b1..d08c4d13c 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -20,7 +20,102 @@ When you [run `dapr init` in either self-hosted mode or on Kubernetes]({{< ref i In your code, set up and schedule jobs within your application. -{{< tabs "Go" >}} +{{< tabs ".NET" "Go" >}} + +{{% codetab %}} + + + +The following .NET SDK code sample schedules the job named `prod-db-backup`. Our job data will contain information +about the database we're seeking to make regular backups of. Over the course of this example, we'll do the following: +- Define types used in the rest of the example +- Register an endpoint during application startup that handles all job trigger invocations on the service +- Register the job with Dapr + +In the following example, we'll create some records that we'll serialize and register alongside the job so the information +is available when the job is triggered in the future: +- The name of the backup task (`db-backup`) +- The backup task's `Metadata`, including: + - The database name (`DBName`) + - The database location (`BackupLocation`) + +Create an ASP.NET Core project and add the latest version of `Dapr.Jobs` from NuGet. While it's not strictly necessary +for your project to use the `Microsoft.NET.Sdk.Web` SDK to create jobs, as of the time this documentation is authored, +only the service that schedules a job will receive trigger invocations for it. As those invocations expect an endpoint +registered that can handle the job trigger, and that requires the `Microsoft.NET.Sdk.Web` SDK, it's recommended that you +use an ASP.NET Core project for this purpose. + +We'll start by defining some types to +persist our backup job data and apply our own JSON property name attributes to the properties so they're consistent +with other language examples. + +```cs +//Define the types that we'll represent the job data with +internal sealed record BackupJobData([property: JsonPropertyName("task")] string Task, [property: JsonPropertyName("metadata")] BackupMetadata Metadata); +internal sealed record BackupMetadata([property: JsonPropertyName("DBName")]string DatabaseName, [property: JsonPropertyName("BackupLocation")] string BackupLocation); +``` + +Next, we'll set up a handler as part of our application setup that will be called anytime a job is triggered on our +application. It's the responsibility of this handler to identify how jobs should be processed based on the job name provided. + +This works by registering a handler with ASP.NET Core at `/job/` where `` is parameterized and simply +passed into this handler delegate, meeting Dapr's expectation that an endpoint is available to handle triggered named jobs. + +Populate your `Program.cs` file with the following: + +```cs +using System.Text; +using System.Text.Json; +using Dapr.Jobs; +using Dapr.Jobs.Extensions; +using Dapr.Jobs.Models; +using Dapr.Jobs.Models.Responses; + +var builder = WebApplication.CreateBuilder(args); +builder.Services.AddDaprJobsClient(); +var app = builder.Build(); + +//Registers an endpoint to receive and process triggered jobs +var cancellationTokenSource = new CancellationTokenSource(TimeSpan.FromSeconds(5)); +app.MapDaprScheduledJobHandler((string jobName, DaprJobDetails jobDetails, ILogger logger, CancellationToken cancellationToken) => { + logger?.LogInformation("Received trigger invocation for job '{jobName}'", jobName); + switch (jobName) + { + case "prod-db-backup": + // Deserialize the job payload metadata + var jobData = JsonSerializer.Deserialize(jobDetails.Payload); + + // Process the backup operation - we assume this is implemented elsewhere in your code + await BackupDatabaseAsync(jobData, cancellationToken); + break; + } +}, cancellationTokenSource.Token); + +await app.RunAsync(); +``` + +Finally, the job itself needs to be registered with Dapr so it can be triggered at a later point in time. This could happen +by injecting a `DaprJobsClient` into a class and executing as part of an inbound operation to your application, but for +our purposes, we'll just put it at the bottom of our `Program.cs` file we started above. Because we'll be using the +`DaprJobsClient` we registered with dependency injection, we need to start by creating a scope so we can access it. + +```cs +//Create a scope so we can access the registered DaprJobsClient +await using scope = app.Services.CreateAsyncScope(); +var daprJobsClient = scope.ServiceProvider.GetRequiredService(); + +//Create the payload we wish to present alongside our future job triggers +var jobData = new BackupJobData("db-backup", new BackupMetadata("my-prod-db", "/backup-dir")); + +//Serialize our payload to UTF-8 bytes +var serializedJobData = JsonSerializer.SerializeToUtf8Bytes(jobData); + +//Schedule our backup job to run every minute, but only repeat 10 times +await daprJobsClient.ScheduleJobAsync("prod-db-backup", DaprJobSchedule.FromDuration(TimeSpan.FromMinutes(1)), + serializedJobData, repeats: 10); +``` + +{{% /codetab %}} {{% codetab %}} From 91a8ebed2152d80ae01ea74544c4574985432475 Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Wed, 22 Jan 2025 12:58:57 -0600 Subject: [PATCH 05/18] Actors do not support gRPC today Signed-off-by: Whit Waldo --- .../building-blocks/actors/actors-features-concepts.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/actors/actors-features-concepts.md b/daprdocs/content/en/developing-applications/building-blocks/actors/actors-features-concepts.md index e486b3243..da5261298 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/actors/actors-features-concepts.md +++ b/daprdocs/content/en/developing-applications/building-blocks/actors/actors-features-concepts.md @@ -57,7 +57,7 @@ This simplifies some choices, but also carries some consideration: ## Actor communication -You can interact with Dapr to invoke the actor method by calling HTTP/gRPC endpoint. +You can interact with Dapr to invoke the actor method by calling the HTTP endpoint. ```bash POST/GET/PUT/DELETE http://localhost:3500/v1.0/actors/// From ec449fd43cb9e7f54be3ae5ae02ec31038a150ab Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Wed, 22 Jan 2025 13:17:00 -0600 Subject: [PATCH 06/18] Update daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md Co-authored-by: Hannah Hunter <94493363+hhunter-ms@users.noreply.github.com> Signed-off-by: Whit Waldo --- .../jobs/howto-schedule-and-handle-triggered-jobs.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index d08c4d13c..d55a2ee18 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -26,7 +26,7 @@ In your code, set up and schedule jobs within your application. -The following .NET SDK code sample schedules the job named `prod-db-backup`. Our job data will contain information +The following .NET SDK code sample schedules the job named `prod-db-backup`. The job data contains information about the database we're seeking to make regular backups of. Over the course of this example, we'll do the following: - Define types used in the rest of the example - Register an endpoint during application startup that handles all job trigger invocations on the service From 82e43c686523d146249e9980d93a9ed87b10bae8 Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Wed, 22 Jan 2025 13:17:18 -0600 Subject: [PATCH 07/18] Update daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md Co-authored-by: Hannah Hunter <94493363+hhunter-ms@users.noreply.github.com> Signed-off-by: Whit Waldo --- .../jobs/howto-schedule-and-handle-triggered-jobs.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index d55a2ee18..60a6a152d 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -27,7 +27,7 @@ In your code, set up and schedule jobs within your application. The following .NET SDK code sample schedules the job named `prod-db-backup`. The job data contains information -about the database we're seeking to make regular backups of. Over the course of this example, we'll do the following: +about the database that you'll be seeking to backup regularly. Over the course of this example, you'll: - Define types used in the rest of the example - Register an endpoint during application startup that handles all job trigger invocations on the service - Register the job with Dapr From a08c30d51056a8b7ff23a7207b1c5bea493d9f9d Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Wed, 22 Jan 2025 13:17:31 -0600 Subject: [PATCH 08/18] Update daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md Co-authored-by: Hannah Hunter <94493363+hhunter-ms@users.noreply.github.com> Signed-off-by: Whit Waldo --- .../jobs/howto-schedule-and-handle-triggered-jobs.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index 60a6a152d..cb53236e5 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -32,7 +32,7 @@ about the database that you'll be seeking to backup regularly. Over the course o - Register an endpoint during application startup that handles all job trigger invocations on the service - Register the job with Dapr -In the following example, we'll create some records that we'll serialize and register alongside the job so the information +In the following example, you'll create records that you'll serialize and register alongside the job so the information is available when the job is triggered in the future: - The name of the backup task (`db-backup`) - The backup task's `Metadata`, including: From 9b61304f0f8905ce1f4a9f7a0545c0e01f4bdc7c Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Wed, 22 Jan 2025 13:20:20 -0600 Subject: [PATCH 09/18] Update daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md Co-authored-by: Hannah Hunter <94493363+hhunter-ms@users.noreply.github.com> Signed-off-by: Whit Waldo --- .../jobs/howto-schedule-and-handle-triggered-jobs.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index cb53236e5..fc10a1fe7 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -55,7 +55,7 @@ internal sealed record BackupJobData([property: JsonPropertyName("task")] string internal sealed record BackupMetadata([property: JsonPropertyName("DBName")]string DatabaseName, [property: JsonPropertyName("BackupLocation")] string BackupLocation); ``` -Next, we'll set up a handler as part of our application setup that will be called anytime a job is triggered on our +Next, set up a handler as part of your application setup that will be called anytime a job is triggered on your application. It's the responsibility of this handler to identify how jobs should be processed based on the job name provided. This works by registering a handler with ASP.NET Core at `/job/` where `` is parameterized and simply From c1700c7887ebf925c7bbb9f8cf868d35d6787b24 Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Wed, 22 Jan 2025 13:20:35 -0600 Subject: [PATCH 10/18] Update daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md Co-authored-by: Hannah Hunter <94493363+hhunter-ms@users.noreply.github.com> Signed-off-by: Whit Waldo --- .../jobs/howto-schedule-and-handle-triggered-jobs.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index fc10a1fe7..b7fe9a59c 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -58,7 +58,7 @@ internal sealed record BackupMetadata([property: JsonPropertyName("DBName")]stri Next, set up a handler as part of your application setup that will be called anytime a job is triggered on your application. It's the responsibility of this handler to identify how jobs should be processed based on the job name provided. -This works by registering a handler with ASP.NET Core at `/job/` where `` is parameterized and simply +This works by registering a handler with ASP.NET Core at `/job/`, where `` is parameterized and passed into this handler delegate, meeting Dapr's expectation that an endpoint is available to handle triggered named jobs. Populate your `Program.cs` file with the following: From ad5bbe5dc5ded7c70a7c3555387bb19c8d40a54a Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Wed, 22 Jan 2025 13:20:51 -0600 Subject: [PATCH 11/18] Update daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md Co-authored-by: Hannah Hunter <94493363+hhunter-ms@users.noreply.github.com> Signed-off-by: Whit Waldo --- .../jobs/howto-schedule-and-handle-triggered-jobs.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index b7fe9a59c..e4ff4f1ac 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -96,7 +96,7 @@ await app.RunAsync(); Finally, the job itself needs to be registered with Dapr so it can be triggered at a later point in time. This could happen by injecting a `DaprJobsClient` into a class and executing as part of an inbound operation to your application, but for -our purposes, we'll just put it at the bottom of our `Program.cs` file we started above. Because we'll be using the +this example's purposes, it'll go at the bottom of the `Program.cs` file you started above. Because you'll be using the `DaprJobsClient` we registered with dependency injection, we need to start by creating a scope so we can access it. ```cs From 6b2fc525a15977fb46fae7385e60e0e8dc56fe0d Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Wed, 22 Jan 2025 13:21:05 -0600 Subject: [PATCH 12/18] Update daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md Co-authored-by: Hannah Hunter <94493363+hhunter-ms@users.noreply.github.com> Signed-off-by: Whit Waldo --- .../jobs/howto-schedule-and-handle-triggered-jobs.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index e4ff4f1ac..34b3b8ecc 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -97,7 +97,7 @@ await app.RunAsync(); Finally, the job itself needs to be registered with Dapr so it can be triggered at a later point in time. This could happen by injecting a `DaprJobsClient` into a class and executing as part of an inbound operation to your application, but for this example's purposes, it'll go at the bottom of the `Program.cs` file you started above. Because you'll be using the -`DaprJobsClient` we registered with dependency injection, we need to start by creating a scope so we can access it. +`DaprJobsClient` you registered with dependency injection, start by creating a scope so you can access it. ```cs //Create a scope so we can access the registered DaprJobsClient From 88847bda2b9fe6ce310b959fa0f12c0021bc00ba Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Wed, 22 Jan 2025 13:21:53 -0600 Subject: [PATCH 13/18] Update daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md Co-authored-by: Hannah Hunter <94493363+hhunter-ms@users.noreply.github.com> Signed-off-by: Whit Waldo --- .../jobs/howto-schedule-and-handle-triggered-jobs.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index 34b3b8ecc..cd50392f3 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -94,7 +94,7 @@ app.MapDaprScheduledJobHandler((string jobName, DaprJobDetails jobDetails, ILogg await app.RunAsync(); ``` -Finally, the job itself needs to be registered with Dapr so it can be triggered at a later point in time. This could happen +Finally, the job itself needs to be registered with Dapr so it can be triggered at a later point in time. You can do this by injecting a `DaprJobsClient` into a class and executing as part of an inbound operation to your application, but for this example's purposes, it'll go at the bottom of the `Program.cs` file you started above. Because you'll be using the `DaprJobsClient` you registered with dependency injection, start by creating a scope so you can access it. From 8f335cc75ecc817c75111a15a5cbd3a3ed8152dd Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Wed, 22 Jan 2025 13:22:13 -0600 Subject: [PATCH 14/18] Update daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md Co-authored-by: Hannah Hunter <94493363+hhunter-ms@users.noreply.github.com> Signed-off-by: Whit Waldo --- .../jobs/howto-schedule-and-handle-triggered-jobs.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index cd50392f3..8ae8e5c94 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -45,7 +45,7 @@ only the service that schedules a job will receive trigger invocations for it. A registered that can handle the job trigger, and that requires the `Microsoft.NET.Sdk.Web` SDK, it's recommended that you use an ASP.NET Core project for this purpose. -We'll start by defining some types to +Start by defining types to persist our backup job data and apply our own JSON property name attributes to the properties so they're consistent with other language examples. From 9c6756722820e7cfdee55abdfb1bbefd085c486a Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Wed, 22 Jan 2025 13:22:34 -0600 Subject: [PATCH 15/18] Update daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md Co-authored-by: Hannah Hunter <94493363+hhunter-ms@users.noreply.github.com> Signed-off-by: Whit Waldo --- .../jobs/howto-schedule-and-handle-triggered-jobs.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index 8ae8e5c94..b34d34a9a 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -42,7 +42,7 @@ is available when the job is triggered in the future: Create an ASP.NET Core project and add the latest version of `Dapr.Jobs` from NuGet. While it's not strictly necessary for your project to use the `Microsoft.NET.Sdk.Web` SDK to create jobs, as of the time this documentation is authored, only the service that schedules a job will receive trigger invocations for it. As those invocations expect an endpoint -registered that can handle the job trigger, and that requires the `Microsoft.NET.Sdk.Web` SDK, it's recommended that you +that can handle the job trigger and requires the `Microsoft.NET.Sdk.Web` SDK, it's recommended that you use an ASP.NET Core project for this purpose. Start by defining types to From cea7a7e938512d7ec95bbd8846eb000cf4575d1e Mon Sep 17 00:00:00 2001 From: Elena Kolevska Date: Wed, 22 Jan 2025 22:34:01 +0000 Subject: [PATCH 16/18] Apply suggestions from code review Co-authored-by: Hannah Hunter <94493363+hhunter-ms@users.noreply.github.com> Signed-off-by: Elena Kolevska --- .../error-codes/error-codes-reference.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/daprdocs/content/en/developing-applications/error-codes/error-codes-reference.md b/daprdocs/content/en/developing-applications/error-codes/error-codes-reference.md index e0dc6b4c1..494a123ef 100644 --- a/daprdocs/content/en/developing-applications/error-codes/error-codes-reference.md +++ b/daprdocs/content/en/developing-applications/error-codes/error-codes-reference.md @@ -7,8 +7,8 @@ weight: 20 --- The following tables list the error codes returned by Dapr runtime. -The error codes are returned in the response body of an HTTP request or in the `ErrorInfo` section of a gRPC Status response, if one is present. -An effort is underway to enrich all gRPC error responses according to the [Richer Error Model]({{< ref "grpc-error-codes.md#richer-grpc-error-model" >}}). Error codes without a corresponding gRPC code indicate errors that have not yet been updated to this model yet. +The error codes are returned in the response body of an HTTP request or in the `ErrorInfo` section of a gRPC status response, if one is present. +An effort is underway to enrich all gRPC error responses according to the [Richer Error Model]({{< ref "grpc-error-codes.md#richer-grpc-error-model" >}}). Error codes without a corresponding gRPC code indicate those errors have not yet been updated to this model. ### Actors API From 7f6daad698642c021fd24c34511beaec49b96eae Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Thu, 23 Jan 2025 12:01:19 -0600 Subject: [PATCH 17/18] Updated to use inline-note Signed-off-by: Whit Waldo --- .../jobs/howto-schedule-and-handle-triggered-jobs.md | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index b34d34a9a..be61fbdfa 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -39,15 +39,16 @@ is available when the job is triggered in the future: - The database name (`DBName`) - The database location (`BackupLocation`) -Create an ASP.NET Core project and add the latest version of `Dapr.Jobs` from NuGet. While it's not strictly necessary +Create an ASP.NET Core project and add the latest version of `Dapr.Jobs` from NuGet. + +> **Note:** While it's not strictly necessary for your project to use the `Microsoft.NET.Sdk.Web` SDK to create jobs, as of the time this documentation is authored, only the service that schedules a job will receive trigger invocations for it. As those invocations expect an endpoint that can handle the job trigger and requires the `Microsoft.NET.Sdk.Web` SDK, it's recommended that you use an ASP.NET Core project for this purpose. -Start by defining types to -persist our backup job data and apply our own JSON property name attributes to the properties so they're consistent -with other language examples. +Start by defining types to persist our backup job data and apply our own JSON property name attributes to the properties +so they're consistent with other language examples. ```cs //Define the types that we'll represent the job data with From 073973c5d3dc1c7ba71d6eb8dd87eed216a05fa9 Mon Sep 17 00:00:00 2001 From: Whit Waldo Date: Thu, 23 Jan 2025 12:02:35 -0600 Subject: [PATCH 18/18] Updated to remove future tense Signed-off-by: Whit Waldo --- .../jobs/howto-schedule-and-handle-triggered-jobs.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md index be61fbdfa..f85758708 100644 --- a/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md +++ b/daprdocs/content/en/developing-applications/building-blocks/jobs/howto-schedule-and-handle-triggered-jobs.md @@ -43,7 +43,7 @@ Create an ASP.NET Core project and add the latest version of `Dapr.Jobs` from Nu > **Note:** While it's not strictly necessary for your project to use the `Microsoft.NET.Sdk.Web` SDK to create jobs, as of the time this documentation is authored, -only the service that schedules a job will receive trigger invocations for it. As those invocations expect an endpoint +only the service that schedules a job receives trigger invocations for it. As those invocations expect an endpoint that can handle the job trigger and requires the `Microsoft.NET.Sdk.Web` SDK, it's recommended that you use an ASP.NET Core project for this purpose.