Files
wehub-resource-sync a9cd7750f4
CI / unit-test (push) Has been cancelled
CI / detect-changes (push) Has been cancelled
CI / build (push) Has been cancelled
Publish docs via GitHub Pages / Deploy docs (push) Has been cancelled
CI / test-harness (push) Has been cancelled
CI / generate-e2e-matrix (push) Has been cancelled
CI / e2e (push) Has been cancelled
CI / build-ui (push) Has been cancelled
Release Drafter / update_release_draft (push) Has been cancelled
UI v2 Integration CI / E2E (Integration) (push) Has been cancelled
UI v2 CI / Lint, Format & Test (push) Has been cancelled
UI v2 CI / E2E (Mocked) (push) Has been cancelled
chore: import upstream snapshot with attribution
2026-07-13 12:37:56 +08:00

273 lines
10 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
---
description: "Build Conductor workers in Go with type-safe task definitions and workflow management."
---
# Go SDK
!!! info "Source"
GitHub: [conductor-oss/go-sdk](https://github.com/conductor-oss/go-sdk) | Report issues and contribute on GitHub.
## Installation
1. Initialize your module. e.g.:
```shell
mkdir hello_world
cd hello_world
go mod init hello_world
```
2. Get the SDK:
```shell
go get github.com/conductor-sdk/conductor-go
```
## Hello World
In this repo you will find a basic "Hello World" under [examples/hello_world](https://github.com/conductor-oss/go-sdk/blob/main/examples/hello_world/).
Let's analyze the app in 3 steps.
> [!note]
> You will need an up & running Conductor Server.
>
> For details on how to run Conductor take a look at [our guide](https://conductor-oss.github.io/conductor/devguide/running/deploy.html).
>
> The examples expect the server to be listening on http://localhost:8080.
### Step 1: Creating the workflow by code
The "greetings" workflow is going to be created by code and registered in Conductor.
Check the `CreateWorkflow` function in [examples/hello_world/src/workflow.go](https://github.com/conductor-oss/go-sdk/blob/main/examples/hello_world/src/workflow.go).
```go
func CreateWorkflow(executor *executor.WorkflowExecutor) *workflow.ConductorWorkflow {
wf := workflow.NewConductorWorkflow(executor).
Name("greetings").
Version(1).
Description("Greetings workflow - Greets a user by their name").
TimeoutPolicy(workflow.TimeOutWorkflow, 600)
greet := workflow.NewSimpleTask("greet", "greet_ref").
Input("person_to_be_greated", "${workflow.input.name}")
wf.Add(greet)
wf.OutputParameters(map[string]interface{}{
"greetings": greet.OutputRef("hello"),
})
return wf
}
```
In the above code first we create a workflow by calling `workflow.NewConductorWorkflow(..)` and set its properties `Name`, `Version`, `Description` and `TimeoutPolicy`.
Then we create a [Simple Task](https://orkes.io/content/reference-docs/worker-task) of type `"greet"` with reference name `"greet_ref"` and add it to the workflow. That task gets the workflow input `"name"` as an input with key `"person_to_be_greated"`.
> [!note]
>`"person_to_be_greated"` is too verbose! Why would you name it like that?
>
> It's just to make it clear that the workflow input is not passed automatically.
>
> The worker will get the actual value of the workflow input because of this mapping `Input("person_to_be_greated", "${workflow.input.name}")` in the workflow definition.
>
>Expressions like `"${workflow.input.name}"` will be replaced by their value during execution.
Last but not least, the output of the workflow is set by calling `wf.OutputParameters(..)`.
The value of `"greetings"` is going to be whatever `"hello"` is in the output of the executed `"greet"` task, e.g.: if the task output is:
```
{
"hello" : "Hello, John"
}
```
The expected workflow output will be:
```
{
"greetings": "Hello, John"
}
```
The Go code translates to this JSON defininition. You can view this in your Conductor server after registering the workflow.
```json
{
"schemaVersion": 2,
"name": "greetings",
"description": "Greetings workflow - Greets a user by their name",
"version": 1,
"tasks": [
{
"name": "greet",
"taskReferenceName": "greet_ref",
"type": "SIMPLE",
"inputParameters": {
"name": "${workflow.input.name}"
}
}
],
"outputParameters": {
"Greetings": "${greet_ref.output.greetings}"
},
"timeoutPolicy": "TIME_OUT_WF",
"timeoutSeconds": 600
}
```
> [!note]
> Workflows can also be registered using the API. Using the JSON you can make the following request:
> ```shell
> curl -X POST -H "Content-Type:application/json" \
> http://localhost:8080/api/metadata/workflow -d @greetings_workflow.json
> ```
In [Step 3](#step-3-running-the-application) you will see how to create an instance of `executor.WorkflowExecutor`.
### Step 2: Creating the worker
A worker is a function with a specific task to perform.
In this example the worker just uses the input `person_to_be_greated` to say hello, as you can see in [examples/hello_world/src/worker.go](https://github.com/conductor-oss/go-sdk/blob/main/examples/hello_world/src/worker.go).
```go
func Greet(task *model.Task) (interface{}, error) {
return map[string]interface{}{
"hello": "Hello, " + fmt.Sprintf("%v", task.InputData["person_to_be_greated"]),
}, nil
}
```
To learn more about workers take a look at [Writing Workers with the Go SDK](https://github.com/conductor-oss/go-sdk/blob/main/docs/workers_sdk.md).
> [!note]
> A single workflow can have task workers written in different languages and deployed anywhere, making your workflow polyglot and distributed!
### Step 3: Running the application
The application is going to start the Greet worker (to execute tasks of type "greet") and it will register the workflow created in [step 1](#step-1-creating-the-workflow-by-code).
To begin with, let's take a look at the variable declaration in [examples/hello_world/main.go](https://github.com/conductor-oss/go-sdk/blob/main/examples/hello_world/main.go).
```go
var (
apiClient = client.NewAPIClientFromEnv()
taskRunner = worker.NewTaskRunnerWithApiClient(apiClient)
workflowExecutor = executor.NewWorkflowExecutor(apiClient)
)
```
First we create an `APIClient` instance. This is a REST client.
We need to provide the correct settings to our client. In this example, `client.NewAPIClientFromEnv()` is used, which initializes a new client by reading the settings from the following environment variables: `CONDUCTOR_SERVER_URL`, `CONDUCTOR_AUTH_KEY`, and `CONDUCTOR_AUTH_SECRET`.
`CONDUCTOR_CLIENT_HTTP_TIMEOUT` lets you configure the HTTP timeout for our client, in seconds. If not set, defaults to 30 seconds.
> [!tip]
> For advanced configuration options and detailed examples see the [API Client Configuration Guide](https://github.com/conductor-oss/go-sdk/blob/main/docs/api_client/README.md).
Now let's take a look at the `main` function:
```go
func main() {
// Start the Greet Worker. This worker will process "greet" tasks.
taskRunner.StartWorker("greet", hello_world.Greet, 1, time.Millisecond*100)
// This is used to register the Workflow, it's a one-time process. You can comment from here
wf := hello_world.CreateWorkflow(workflowExecutor)
err := wf.Register(true)
if err != nil {
log.Error(err.Error())
return
}
// Till Here after registering the workflow
// Start the greetings workflow
id, err := workflowExecutor.StartWorkflow(
&model.StartWorkflowRequest{
Name: "greetings",
Version: 1,
Input: map[string]string{
"name": "Gopher",
},
},
)
if err != nil {
log.Error(err.Error())
return
}
log.Info("Started workflow with Id: ", id)
// Get a channel to monitor the workflow execution -
// Note: This is useful in case of short duration workflows that completes in few seconds.
channel, _ := workflowExecutor.MonitorExecution(id)
run := <-channel
log.Info("Output of the workflow: ", run.Output)
}
```
The `taskRunner` uses the `apiClient` to poll for work and complete tasks. It also starts the worker and handles concurrency and polling intervals for us based on the configuration provided.
That simple line `taskRunner.StartWorker("greet", hello_world.Greet, 1, time.Millisecond*100)` is all that's needed to get our Greet worker up & running and processing tasks of type `"greet"`.
The `workflowExecutor` gives us an abstraction on top of the `apiClient` to manage workflows. It is used under the hood by `ConductorWorkflow` to register the workflow and it's also used to start and monitor the execution.
#### Running the example with a local Conductor OSS server:
```shell
export CONDUCTOR_SERVER_URL="http://localhost:8080/api"
cd examples
go run hello_world/main.go
```
#### Running the example with an [Orkes developer account](https://developer.orkescloud.com).
```shell
export CONDUCTOR_SERVER_URL="https://developer.orkescloud.com/api"
export CONDUCTOR_AUTH_KEY="..."
export CONDUCTOR_AUTH_SECRET="..."
cd examples
go run hello_world/main.go
```
> [!note]
> Orkes Conductor requires authentication. [Get a key and secret from the server](https://orkes.io/content/how-to-videos/access-key-and-secret) to set those variables.
The above commands should give an output similar to
```shell
INFO[0000] Updated poll interval for task: greet, to: 100ms
INFO[0000] Started 1 worker(s) for taskName greet, polling in interval of 100 ms
INFO[0000] Started workflow with Id:14a9fcc5-3d74-11ef-83dc-acde48001122
INFO[0000] Output of the workflow:map[Greetings:Hello, Gopher]
```
## Deprecated Methods
Some methods in the SDK client interfaces are now deprecated. Theyve been replaced with newer methods that follow more consistent naming. Please refer to our [Migration Guide](https://github.com/conductor-oss/go-sdk/blob/main/docs/migration_guide.md) for detailed information on how to update your code.
# Further Reading
- [Writing Workers with the Go SDK](https://github.com/conductor-oss/go-sdk/blob/main/docs/workers_sdk.md)
- [Authoring Workflows with the Go SDK](https://github.com/conductor-oss/go-sdk/blob/main/docs/workflow_sdk.md)
- [Logging Configuration](https://github.com/conductor-oss/go-sdk/blob/main/docs/logger_sdk.md)
- [Migration Guide: Deprecated Methods](https://github.com/conductor-oss/go-sdk/blob/main/docs/migration_guide.md)
- [API Client Configuration](https://github.com/conductor-oss/go-sdk/blob/main/docs/api_client/README.md) - Complete guide to API client setup, authentication, and proxy configuration
- [TLS Configuration Guide](https://github.com/conductor-oss/go-sdk/blob/main/docs/api_client/tls_configuration.md) - TLS/SSL configuration for self-signed certificates and mTLS
## Examples
Browse all examples on GitHub: [conductor-oss/go-sdk/examples](https://github.com/conductor-oss/go-sdk/tree/main/examples)
| Example | Type |
|---|---|
| [Readme](https://github.com/conductor-oss/go-sdk/blob/main/examples/README.md) | file |
| [Api Gateway](https://github.com/conductor-oss/go-sdk/tree/main/examples/api_gateway) | directory |
| [Hello World](https://github.com/conductor-oss/go-sdk/tree/main/examples/hello_world) | directory |
| [Workflow](https://github.com/conductor-oss/go-sdk/tree/main/examples/workflow) | directory |