Merge branch 'master' into master

This commit is contained in:
Aman Bhardwaj 2020-07-09 02:56:32 +00:00 committed by GitHub
commit 1ebf0671fc
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 391 additions and 125 deletions

View File

@ -21,6 +21,7 @@ Every binding has its own unique set of properties. Click the name link to see t
| Name | Input<br>Binding | Output<br>Binding | Status |
|------|:----------------:|:-----------------:|--------|
| [Cron (Scheduler)](../../reference/specs/bindings/cron.md) | ✅ | ✅ | Experimental |
| [HTTP](../../reference/specs/bindings/http.md) | | ✅ | Experimental |
| [Kafka](../../reference/specs/bindings/kafka.md) | ✅ | ✅ | Experimental |
| [Kubernetes Events](../../reference/specs/bindings/kubernetes.md) | ✅ | | Experimental |

View File

@ -1,61 +1,109 @@
# W3C tracing context for distributed tracing
# W3C trace context for distributed tracing
- [Background](#background)
- [Trace scenarios](#scenarios)
- [W3C trace headers](#w3c-trace-headers)
- [Trace context HTTP headers format](#trace-context-http-headers-format)
- [Trace context gRPC headers format](#trace-context-grpc-headers-format)
## Introduction
Dapr uses W3C trace context for distributed tracing for both service invocation and pub/sub messaging. Largely Dapr does all the heavy lifting of generating and propogating the trace context information and this can be sent to many different diagnostics tools for visualization and querying. There are only a very few cases where you, as a developer, need to either propagate a trace header or generate one.
## Background
Distributed tracing is a methodology implemented by tracing tools to follow, analyze and debug a transaction across multiple software components. Typically, a distributed trace traverses more than one service which requires it to be uniquely identifiable. Trace context propagation passes along this unique identification.
Distributed tracing is a methodology implemented by tracing tools to follow, analyze and debug a transaction across multiple software components. Typically, a distributed trace traverses more than one component which requires it to be uniquely identifiable across all participating systems. Trace context propagation passes along this unique identification.
Today, trace context propagation is implemented individually by each tracing vendor. In multi-vendor environments, this causes interoperability problems, such as:
In the past, trace context propagation has typically been implemented individually by each different tracing vendors. In multi-vendor environments, this causes interoperability problems, such as;
- Traces that are collected by different tracing vendors cannot be correlated as there is no shared unique identifier.
- Traces that cross boundaries between different tracing vendors can not be propagated as there is no uniformly agreed set of identification that is forwarded.
- Vendor specific metadata might be dropped by intermediaries.
- Cloud platform vendors, intermediaries and service providers, cannot guarantee to support trace context propagation as there is no standard to follow.
In the past, these problems did not have a significant impact as most applications were monitored by a single tracing vendor and stayed within the boundaries of a single platform provider. Today, an increasing number of applications are highly distributed and leverage multiple middleware services and cloud platforms.
In the past, these problems did not have a significant impact as most applications were monitored by a single tracing vendor and stayed within the boundaries of a single platform provider. Today, an increasing number of applications are distributed and leverage multiple middleware services and cloud platforms.
This transformation of modern applications calls for a distributed tracing context propagation standard.
This transformation of modern applications called for a distributed tracing context propagation standard. The [W3C trace context specification](https://www.w3.org/TR/trace-context/) defines a universally agreed-upon format for the exchange of trace context propagation data - referred to as trace context. Trace context solves the problems described above by;
[W3C trace context specification](https://www.w3.org/TR/trace-context/) defines a universally agreed-upon format for the exchange of trace context propagation data - referred to as trace context. Trace context solves the problems described above by
* Providing an unique identifier for individual traces and requests, allowing trace data of multiple providers to be linked together.
* Providing an agreed-upon mechanism to forward vendor-specific trace data and avoid broken traces when multiple tracing tools participate in a single transaction.
* Providing an industry standard that intermediaries, platforms, and hardware providers can support.
* providing an unique identifier for individual traces and requests, allowing trace data of multiple providers to be linked together.
* providing an agreed-upon mechanism to forward vendor-specific trace data and avoid broken traces when multiple tracing tools participate in a single transaction.
* providing an industry standard that intermediaries, platforms, and hardware providers can support.
A unified approach for propagating trace data improves visibility into the behavior of distributed applications, facilitating problem and performance analysis.
A unified approach for propagating trace data improves visibility into the behavior of distributed applications, facilitating problem and performance analysis. The interoperability provided by trace context is a prerequisite to manage modern micro-service based applications.
## Scenarios
There are two scenarios where you need to understand how tracing is used;
1. Dapr generates and propagates the trace context between services.
2. Dapr generates the trace context and you need to propagate the trace context to another service **or** you generate the trace context and Dapr propagates the trace context to a service.
### Dapr generates and propagates the trace context between services.
In these scenarios Dapr does all work for you. You do not need to create and propagate any trace headers. Dapr takes care of creating all trace headers and propogating them. Let's go through the scenarios with examples;
1. Single service invocation call (`service A -> service B` )
Dapr generates the trace headers in service A and these trace headers are propagated from service A to service B.
2. Multiple sequential service invocation calls ( `service A -> service B -> service C`)
Dapr generates the trace headers at the beginning of the request in service A and these trace headers are propagated from `service A-> service B -> service C` and so on to further Dapr enabled services.
3. Request is from external endpoint (`For example from a gateway service to a Dapr enabled service A`)
Dapr generates the trace headers in service A and these trace headers are propagated from service A to further Dapr enabled services `service A-> service B -> service C`. This is similar to above case 2.
4. Pub/sub messages
Dapr generates the trace headers in the published message topic and these trace headers are propagated to any services listening on that topic.
### You need to propagate or generate trace context between services
In these scenarios Dapr does some of the work for you and you need to either create or propagate trace headers.
1. Multiple service calls to different services from single service
When you are calling multiple services from a single service, for example from service A like this, you need to propagate the trace headers;
service A -> service B
[ .. some code logic ..]
service A -> service C
[ .. some code logic ..]
service A -> service D
[ .. some code logic ..]
In this case, when service A first calls service B, Dapr generates the trace headers in service A, and these trace headers are then propagated to service B. These trace headers are returned in the response from service B as part of response headers. However you need to propagate the returned trace context to the next services, service C and Service D, as Dapr does not know you want to reuse the same header.
To understand how to extract the trace headers from a response and add the trace headers into a request, see the [how to use trace context](../../howto/use-w3c-tracecontext/README.md) article.
2. You have chosen to generate your own trace context headers.
This is much more unusual. There may be occassions where you specifically chose to add W3C trace headers into a service call, for example if you have an existing application that does not currently use Dapr. In this case Dapr still propagates the trace context headers for you. If you decide to generate trace headers yourself, there are three ways this can be done :
1. You can use the industry standard OpenCensus/OpenTelemetry SDKs to generate trace headers and pass these trace headers to a Dapr enabled service. This is the preferred recommendation.
2. You can use a vendor SDK that provides a way to generate W3C trace headers such as DynaTrace SDK and pass these trace headers to a Dapr enabled service.
3. You can handcraft a trace context following [W3C trace context specification](https://www.w3.org/TR/trace-context/) and pass these trace headers to Dapr enabled service.
## W3C trace headers
Theses are the specific trace context headers that are generated and propagated by Dapr for HTTP and gRPC.
### Trace context HTTP headers format
When propogating a trace context header from an HTTP response to an HTTP request, these are the headers that you need to copy.
#### Traceparent Header
The traceparent header represents the incoming request in a tracing system in a common format, understood by all vendors.
Heres an example of a traceparent header.
`traceparent: 00-0af7651916cd43dd8448eb211c80319c-b7ad6b7169203331-01`
Refer traceparent fields details [here](https://www.w3.org/TR/trace-context/#traceparent-header)
The traceparent fields are detailed [here](https://www.w3.org/TR/trace-context/#traceparent-header)
#### Tracestate Header
The tracestate header includes the parent in a potentially vendor-specific format:
`tracestate: congo=t61rcWkgMzE`
Refer tracestate fields details [here](https://www.w3.org/TR/trace-context/#tracestate-header)
The tracestate fields are detailed [here](https://www.w3.org/TR/trace-context/#tracestate-header)
### Trace context gRPC headers format
In the gRPC API calls, trace context is passed through `grpc-trace-bin` header.
## Related Links
* [Observability sample](https://github.com/dapr/samples/tree/master/8.observability)
* [How-To: Set up Application Insights for distributed tracing](../../howto/use-w3c-tracecontext)
* [How-To: Set up Zipkin for distributed tracing](../../howto/diagnose-with-tracing/zipkin.md)
* [How To set up Application Insights for distributed tracing](../../howto/diagnose-with-tracing/azure-monitor.md)
* [How To set up Zipkin for distributed tracing](../../howto/diagnose-with-tracing/zipkin.md)
* [How to use Trace Context](../../howto/use-w3c-tracecontext)
* [W3C trace context specification](https://www.w3.org/TR/trace-context/)
* [Observability sample](https://github.com/dapr/samples/tree/master/8.observability)

View File

@ -8,7 +8,7 @@ Here you'll find a list of "How To" guides that walk you through accomplishing s
- [Pub/Sub](#pubsub)
- [Bindings](#bindings-and-triggers)
- [Actors](#actors)
- [Observerability](#observerability)
- [Observability](#observability)
- [Security](#security)
- [Middleware](#middleware)
- [Components](#components)
@ -48,7 +48,7 @@ For Actors How Tos see the SDK documentation
* [.NET Actors](https://github.com/dapr/dotnet-sdk/blob/master/docs/get-started-dapr-actor.md)
* [Java Actors](https://github.com/dapr/java-sdk)
## Observerability
## Observability
### Metric and logs
@ -59,7 +59,7 @@ For Actors How Tos see the SDK documentation
### Distributed Tracing
* [Diagnose your services with distributed tracing](./diagnose-with-tracing)
* [Trace calls across services](./use-w3c-tracecontext)
* [Use W3C Trace Context](./use-w3c-tracecontext)
## Security

View File

@ -8,3 +8,4 @@ The following list shows the supported secret stores by Dapr. The links here wil
* [GCP Secret Manager](./gcp-secret-manager.md)
* [Hashicorp Vault](./hashicorp-vault.md)
* [Kubernetes](./kubernetes.md)
* [Local JSON secret store (for Development)](./local-secret-store.md)

View File

@ -0,0 +1,98 @@
# Local secret store (for Development)
This document shows how to enable Local secret store using [Dapr Secrets Component](../../concepts/secrets/README.md) for Development scenarios in Standalone mode. This Dapr secret store component reads plain text JSON from a given file and does not use authentication.
> The Local secret store is in no way recommended for production environments.
## Contents
- [Create JSON file to hold the secrets](#create-json-file-to-hold-the-secrets)
- [Use Local secret store in Standalone mode](#use-local-secret-store-in-standalone-mode)
- [References](#references)
## Create JSON file to hold the secrets
This creates new JSON file to hold the secrets.
1. Create a json file (i.e. secrets.json) with the following contents:
```json
{
"redisPassword": "your redis passphrase"
}
```
## Use Local secret store in Standalone mode
This section walks you through how to enable an Local secret store to store a password to access a Redis state store in Standalone mode.
1. Create a file called localsecretstore.yaml in the components directory
Now create a Dapr localsecretstore component. Create a file called localsecretstore.yaml and add it to your components directory with the following content
```yaml
apiVersion: dapr.io/v1alpha1
kind: Component
metadata:
name: localsecretstore
namespace: default
spec:
type: secretstores.local.localsecretstore
metadata:
- name: secretsFile
value: [path to the secrets.json you created in the previous section]
- name: nestedSeparator
value: ":"
```
2. Create redis.yaml in the components directory with the content below
Create a statestore component file. This Redis component yaml shows how to use the `redisPassword` secret stored in a Local secret store called localsecretstore as a Redis connection password.
```yaml
apiVersion: dapr.io/v1alpha1
kind: Component
metadata:
name: statestore
namespace: default
spec:
type: state.redis
metadata:
- name: redisHost
value: "[redis]:6379"
- name: redisPassword
secretKeyRef:
name: redisPassword
key: redisPassword
auth:
secretStore: localsecretstore
```
3. Run your app
You can check that `secretstores.local.localsecretstore` component is loaded and redis server connects successfully by looking at the log output when using the dapr `run` command.
Here is the log when you run [HelloWorld sample](https://github.com/dapr/samples/tree/master/1.hello-world) with Local Secret secret store.
```bash
$ dapr run --app-id mynode --app-port 3000 --port 3500 node app.js
Starting Dapr with id mynode on port 3500
✅ You're up and running! Both Dapr and your app logs will appear here.
...
== DAPR == time="2019-09-25T17:57:37-07:00" level=info msg="loaded component localsecretstore (secretstores.local.localsecretstore)"
== APP == Node App listening on port 3000!
== DAPR == time="2019-09-25T17:57:38-07:00" level=info msg="loaded component statestore (state.redis)"
== DAPR == time="2019-09-25T17:57:38-07:00" level=info msg="loaded component messagebus (pubsub.redis)"
...
== DAPR == 2019/09/25 17:57:38 redis: connecting to [redis]:6379
== DAPR == 2019/09/25 17:57:38 redis: connected to [redis]:6379 (localAddr: x.x.x.x:62137, remAddr: x.x.x.x:6379)
...
```
## Related Links
- [Secrets Component](../../concepts/secrets/README.md)
- [Secrets API](../../reference/api/secrets_api.md)
- [Secrets API Samples](https://github.com/dapr/samples/blob/master/9.secretstore/README.md)

View File

@ -1,84 +1,35 @@
# Trace calls across services
# How to use trace context
Dapr uses W3C trace context for distributed tracing for both service invocation and pub/sub messaging. Dapr does all the heavy lifting of generating and propagating the trace context information and there are very few cases where you need to either propagate or create a trace context. First read scenarios in the [W3C trace context for distributed tracing](../../concepts/observability/W3C-traces.md) article to understand whether you need to propagate or create a trace context.
To view traces, read the [how to diagnose with tracing](../diagnose-with-tracing) article.
## Contents
- [Using trace context in Dapr](#using-trace-context-in-dapr)
- [How to pass a trace context](#how-to-pass-a-trace-context)
- [Configuring tracing in Dapr](#configuring-tracing-in-dapr)
- [Invoking Dapr with trace context](#invoking-dapr-with-trace-context)
- [How to retrieve trace context from a response](#how-to-retrieve-trace-context-from-a-response)
- [How to propagate trace context in a request](#how-to-propagate-trace-context-in-a-request)
- [How to create trace context](#how-to-create-trace-context)
- [Go](#create-trace-context-in-go)
- [Java](#create-trace-context-in-java)
- [Python](#create-trace-context-in-python)
- [NodeJS](#create-trace-context-in-nodejs)
- [C++](#create-trace-context-in-c++)
- [C#](#create-trace-context-in-c#)
- [Putting it all together with a Go Sample](#putting-it-all-together-with-a-go-sample)
- [Related Links](#related-links)
## Using trace context in Dapr
## How to retrieve trace context from a response
`Note: There are no helper methods exposed in Dapr SDKs to propagate and retrieve trace context. You need to use http/gRPC clients to propagate and retrieve trace headers through http headers and gRPC metadata.`
Dapr tracing is built on [OpenCensus](https://opencensus.io/introduction/) specification that supports official W3C HTTP tracing header.
### Retrieve trace context in Go
#### For HTTP calls
OpenCensus Go SDK provides [ochttp](https://pkg.go.dev/go.opencensus.io/plugin/ochttp/propagation/tracecontext?tab=doc) package that provides methods to retrieve trace context from http response.
For the gRPC tracing with OpenCensus, the details are [here](https://github.com/census-instrumentation/opencensus-specs/blob/master/trace/gRPC.md)
Dapr supports OpenCensus instrumentation of services when tracing configuration is enabled through a Dapr annotation. Once the tracing configuration is applied, you get instrumentation of traces and you can retrieve the trace correlation id from the standard W3C context headers.
You can also choose to pass the trace context explicitly, then Dapr uses the supplied trace context and propagates this all across the HTTP/gRPC call.
### How to pass a trace context
Since Dapr tracing uses OpenCensus, you set the trace context using OpenCensus SDK. OpenCensus supports several different programming languages.
| Language | SDK |
|:-------:|:----:|
| Go | [Link](https://pkg.go.dev/go.opencensus.io?tab=overview)
| Java | [Link](https://www.javadoc.io/doc/io.opencensus/opencensus-api/latest/index.html)
| C# | [Link](https://github.com/census-instrumentation/opencensus-csharp/)
| C++ | [Link](https://github.com/census-instrumentation/opencensus-cpp)
| Node.js | [Link](https://github.com/census-instrumentation/opencensus-node)
| Python | [Link](https://census-instrumentation.github.io/opencensus-python/trace/api/index.html)
### Let's go through an example using the [grpc app](../create-grpc-app) using the Go SDK.
#### 1. Get the OpenCensus Go SDK
Prerequisites: OpenCensus Go libraries require Go 1.8 or later. For details on installation go [here](https://pkg.go.dev/go.opencensus.io?tab=overview).
#### 2. Import the package "go.opencensus.io/trace"
`$ go get -u go.opencensus.io`
#### 3. Create trace context
When you want to pass the trace context, you are starting the trace spans. Since a distributed trace tracks the progression of a single user request as it is handled by the services and processes that make up an application, each step is called a `span` in the trace. Spans include metadata about the step, including the time spent in the step, called the spans latency.
Span is the unit step in a trace. Each span has a name, latency, status and additional metadata.
The code belows shows starting a span for a cache read and ending it when done:
To retrieve the trace context from HTTP response, you can use :
```go
ctx, span := trace.StartSpan(ctx, "cache.Get")
defer span.End()
// Do work to get from cache.
f := tracecontext.HTTPFormat{}
sc, ok := f.SpanContextFromRequest(req)
```
The `StartSpan` call returns two values. If you want to propagate trace context within your calls in the same process, you can use `context.Context` to propagate spans. The returned `span` has the fields 'TraceID' and 'SpanID'. You can read more on these fields usage [here](https://opencensus.io/tracing/span/)
When you call the Dapr API through HTTP/gRPC, you need to pass the trace context across processes or services. Across the network, OpenCensus provides different propagation methods for different protocols. You can read about the propagation package [here](https://godoc.org/go.opencensus.io/trace/propagation).
In our example, since these are gRPC calls, the OpenCensus binary propagation format is used.
#### 4. Passing the trace context to Dapr
##### For gRPC calls
First import the package 'go.opencensus.io/trace/propagation'.
Once imported, get the span context from the generated span (as mentioned in above step 3), and convert it to OpenCensus binary propagation format.
```go
traceContext := span.SpanContext()
traceContextBinary := propagation.Binary(traceContext)
```
You can then pass the trace context through [gRPC metadata]("google.golang.org/grpc/metadata") through `grpc-trace-bin` header.
```go
ctx = metadata.AppendToOutgoingContext(ctx, "grpc-trace-bin", string(traceContextBinary))
```
You can then pass this context `ctx` in Dapr gRPC calls as first parameter. For example `InvokeService`, context is passed in first parameter.
#### For gRPC calls
To retrieve the trace context header when the gRPC call is returned, you can pass the response header reference as gRPC call option which contains response headers:
```go
@ -98,31 +49,159 @@ client.InvokeService(ctx, &pb.InvokeServiceRequest{
grpc.Header(&responseHeader))
```
##### HTTP calls
### Retrieve trace context in C#
#### For HTTP calls
To retrieve the trace context from HTTP response, you can use [.NET API](https://docs.microsoft.com/en-us/dotnet/api/system.net.http.headers.httpresponseheaders?view=netcore-3.1) :
HTTP integration uses [Zipkins B3](https://github.com/openzipkin/b3-propagation) by default, but can be configured to use a custom propagation method by setting another `propagation.HTTPFormat`.
```csharp
// client is HttpClient. req is HttpRequestMessage
HttpResponseMessage response = await client.SendAsync(req);
IEnumerable<string> values1, values2;
string traceparentValue = "";
string tracestateValue = "";
if (response.Headers.TryGetValues("traceparent", out values1))
{
traceparentValue = values1.FirstOrDefault();
}
if (response.Headers.TryGetValues("tracestate", out values2))
{
tracestateValue = values2.FirstOrDefault();
}
```
For control over HTTP client headers, redirect policy, and other settings, you create a client. In this example, [net/http](net/http) is used for HTTP calls.
#### For gRPC calls
To retrieve the trace context from gRPC response, you can use [Grpc.Net.Client](https://www.nuget.org/packages/Grpc.Net.Client) ResponseHeadersAsync method.
```csharp
// client is Dapr proto client
using var call = client.InvokeServiceAsync(req);
var response = await call.ResponseAsync;
var headers = await call.ResponseHeadersAsync();
var tracecontext = headers.First(e => e.Key == "grpc-trace-bin");
```
Additional general details on calling gRPC services with .NET client [here](https://docs.microsoft.com/en-us/aspnet/core/grpc/client?view=aspnetcore-3.1).
## How to propagate trace context in a request
`Note: There are no helper methods exposed in Dapr SDKs to propagate and retrieve trace context. You need to use http/gRPC clients to propagate and retrieve trace headers through http headers and gRPC metadata.`
### Pass trace context in Go
#### For HTTP calls
OpenCensus Go SDK provides [ochttp](https://pkg.go.dev/go.opencensus.io/plugin/ochttp/propagation/tracecontext?tab=doc) package that provides methods to attach trace context in http request.
```go
f := &HTTPFormat{}
f := tracecontext.HTTPFormat{}
req, _ := http.NewRequest("GET", "http://localhost:3500/v1.0/invoke/mathService/method/api/v1/add", nil)
traceContext := span.SpanContext()
f.SpanContextToRequest(traceContext, req)
```
To retrieve the trace context when the HTTP request is returned, you can use :
#### For gRPC calls
```go
sc, ok := f.SpanContextFromRequest(req)
traceContext := span.SpanContext()
traceContextBinary := propagation.Binary(traceContext)
```
You can then pass the trace context through [gRPC metadata]("google.golang.org/grpc/metadata") through `grpc-trace-bin` header.
```go
ctx = metadata.AppendToOutgoingContext(ctx, "grpc-trace-bin", string(traceContextBinary))
```
See the [Dapr API reference](https://github.com/dapr/docs/tree/master/reference/api).
You can then continuing passing this go context `ctx` in subsequent Dapr gRPC calls as first parameter. For example `InvokeService`, context is passed in first parameter.
### Configuring tracing in Dapr
To enable tracing in Dapr, you need to first configure tracing.
Create adeployment config yaml e.g. `appconfig.yaml` with following configuration.
### Pass trace context in C#
#### For HTTP calls
To pass trace context in HTTP request, you can use [.NET API](https://docs.microsoft.com/en-us/dotnet/api/system.net.http.headers.httprequestheaders?view=netcore-3.1) :
```csharp
// client is HttpClient. req is HttpRequestMessage
req.Headers.Add("traceparent", traceparentValue);
req.Headers.Add("tracestate", tracestateValue);
HttpResponseMessage response = await client.SendAsync(req);
```
#### For gRPC calls
To pass the trace context in gRPC call metadata, you can use [Grpc.Net.Client](https://www.nuget.org/packages/Grpc.Net.Client) ResponseHeadersAsync method.
```csharp
// client is Dapr.Client.Autogen.Grpc.v1
var headers = new Metadata();
headers.Add("grpc-trace-bin", tracecontext);
using var call = client.InvokeServiceAsync(req, headers);
```
Additional general details on calling gRPC services with .NET client [here](https://docs.microsoft.com/en-us/aspnet/core/grpc/client?view=aspnetcore-3.1).
## How to create trace context
You can create a trace context using the recommended OpenCensus SDKs. OpenCensus supports several different programming languages.
| Language | SDK |
|:-------:|:----:|
| Go | [Link](https://pkg.go.dev/go.opencensus.io?tab=overview)
| Java | [Link](https://www.javadoc.io/doc/io.opencensus/opencensus-api/latest/index.html)
| C# | [Link](https://github.com/census-instrumentation/opencensus-csharp/)
| C++ | [Link](https://github.com/census-instrumentation/opencensus-cpp)
| Node.js | [Link](https://github.com/census-instrumentation/opencensus-node)
| Python | [Link](https://census-instrumentation.github.io/opencensus-python/trace/api/index.html)
### Create trace context in Go
#### 1. Get the OpenCensus Go SDK
Prerequisites: OpenCensus Go libraries require Go 1.8 or later. For details on installation go [here](https://pkg.go.dev/go.opencensus.io?tab=overview).
#### 2. Import the package "go.opencensus.io/trace"
`$ go get -u go.opencensus.io`
#### 3. Create trace context
```go
ctx, span := trace.StartSpan(ctx, "cache.Get")
defer span.End()
// Do work to get from cache.
```
### Create trace context in Java
```java
try (Scope ss = TRACER.spanBuilder("cache.Get").startScopedSpan()) {
}
```
### Create trace context in Python
```python
with tracer.span(name="cache.get") as span:
pass
```
### Create trace context in NodeJS
```nodejs
tracer.startRootSpan({name: 'cache.Get'}, rootSpan => {
});
```
### Create trace context in C++
```cplusplus
opencensus::trace::Span span = opencensus::trace::Span::StartSpan(
"cache.Get", nullptr, {&sampler});
```
### Create trace context in C#
```csharp
var span = tracer.SpanBuilder("cache.Get").StartScopedSpan();
```
## Putting it all together with a Go Sample
### Configure tracing in Dapr
First you need to enable tracing configuration in Dapr. This step is mentioned for completeness from enabling tracing to invoking Dapr with trace context.
Create a deployment config yaml e.g. `appconfig.yaml` with following configuration.
```yaml
apiVersion: dapr.io/v1alpha1
@ -146,22 +225,17 @@ You then set the following tracing annotation in your deployment YAML. You can a
dapr.io/config: "appconfig"
```
### Viewing traces
To view traces, you need to deploy OpenCensus supported exporters. This is independent of Dapr configuration.
Read [how-to-diagnose-with-tracing](../diagnose-with-tracing) to set up trace exporters.
### Invoking Dapr with trace context
As mentioned earlier in the [section](#Using-Trace-Context-in-Dapr), you can create the trace context and pass it when calling Dapr, or Dapr can generate trace context and pass it back to you.
As mentioned in `Scenarios` section in [W3C Trace Context for distributed tracing](../../concepts/observability/W3C-traces.md) that Dapr covers generating trace context and you do not need to explicitly create trace context.
If you choose to pass the trace context explicitly, then Dapr will use the passed trace context and propagate all across the HTTP/gRPC call.
However if you choose to pass the trace context explicitly, then Dapr will use the passed trace context and propagate all across the HTTP/gRPC call.
Using the [grpc app](../create-grpc-app) in the example and putting this all together, the following steps show you how to create a Dapr client and call the Save State operation passing the trace context:
Using the [grpc app](../create-grpc-app) in the example and putting this all together, the following steps show you how to create a Dapr client and call the InvokeService method passing the trace context:
The Rest code snippet and details, refer to the [grpc app](../create-grpc-app).
#### 1. Import the package
### 1. Import the package
```go
package main
@ -175,7 +249,7 @@ import (
)
```
#### 2. Create the client
### 2. Create the client
```go
// Get the Dapr port and create a connection
@ -191,7 +265,7 @@ import (
client := pb.NewDaprClient(conn)
```
#### 3. Invoke the InvokeService method With Trace Context
### 3. Invoke the InvokeService method With Trace Context
```go
// Create the Trace Context
@ -215,16 +289,15 @@ import (
})
```
That's it !. Now you can correlate the calls in your app and across services with Dapr using the same trace context.
To view traces, you can refer [how-to-diagnose-with-tracing](../diagnose-with-tracing)
You can now correlate the calls in your app and across services with Dapr using the same trace context.
## Related Links
* [Observability concepts](../../concepts/observability/traces.md)
* [Observability sample](https://github.com/dapr/samples/tree/master/8.observability)
* [W3C Trace Context for distributed tracing](../../concepts/observability/W3C-traces.md)
* [How-To: Set up Application Insights for distributed tracing](../../howto/diagnose-with-tracing/azure-monitor.md)
* [How-To: Set up Zipkin for distributed tracing](../../howto/diagnose-with-tracing/zipkin.md)
* [How to set up Application Insights for distributed tracing](../../howto/diagnose-with-tracing/azure-monitor.md)
* [How to set up Zipkin for distributed tracing](../../howto/diagnose-with-tracing/zipkin.md)
* [W3C trace context specification](https://www.w3.org/TR/trace-context/)
* [Observability sample](https://github.com/dapr/samples/tree/master/8.observability)

View File

@ -0,0 +1,45 @@
# Cron Binding Spec
```yaml
apiVersion: dapr.io/v1alpha1
kind: Component
metadata:
name: <NAME>
namespace: <NAMESPACE>
spec:
type: bindings.cron
metadata:
- name: schedule
value: "@every 15m" # valid cron schedule
```
## Schedule Format
The Dapr cron binding supports following formats:
| Character | Descriptor | Acceptable values |
|:---------:|-------------------|-----------------------------------------------|
| 1 | Second | 0 to 59, or * |
| 2 | Minute | 0 to 59, or * |
| 3 | Hour | 0 to 23, or * (UTC) |
| 4 | Day of the month | 1 to 31, or * |
| 5 | Month | 1 to 12, or * |
| 6 | Day of the week | 0 to 7 (where 0 and 7 represent Sunday), or * |
For example:
* `30 * * * * *` - every 30 seconds
* `0 15 * * * *` - every 15 minutes
* `0 30 3-6,20-23 * * *` - every hour on the half hour in the range 3-6am, 8-11pm
* `CRON_TZ=America/New_York 0 0 30 04 * * *` - every day at 4:30am New York time
> You can learn more about cron and the supported formats [here](https://en.wikipedia.org/wiki/Cron)
For ease of use, the Dapr cron binding also supports few shortcuts:
* `@every 15s` where `s` is seconds, `m` minutes, and `h` hours
* `@daily` or `@hourly` which runs at that period from the time the binding is initialized
## Programmability
The Dapr cron binding also supports `Invoke` method with `Delete` operation as an output binding which can be used to cancel existing schedule programmatically. For more about sending events see the [Output Bindings docs](https://github.com/dapr/docs/tree/master/howto/send-events-with-output-bindings).