mirror of https://github.com/dapr/docs.git
1098 lines
34 KiB
Markdown
1098 lines
34 KiB
Markdown
---
|
|
type: docs
|
|
title: "Quickstart: Input & Output Bindings"
|
|
linkTitle: "Bindings"
|
|
weight: 75
|
|
description: "Get started with Dapr's Binding building block"
|
|
---
|
|
|
|
Let's take a look at Dapr's [Bindings building block]({{< ref bindings >}}). Using bindings, you can:
|
|
|
|
- Trigger your app with events coming in from external systems.
|
|
- Interface with external systems.
|
|
|
|
In this Quickstart, you schedule a batch script to run every 10 seconds using an input [Cron]({{< ref cron.md >}}) binding. The script processes a JSON file and outputs data to a SQL database using the [PostgreSQL]({{< ref postgresql.md >}}) Dapr binding.
|
|
|
|
<img src="/images/bindings-quickstart/bindings-quickstart.png" width=800 style="padding-bottom:15px;">
|
|
|
|
Select your preferred language-specific Dapr SDK before proceeding with the Quickstart.
|
|
|
|
{{< tabs "Python" "JavaScript" ".NET" "Java" "Go" >}}
|
|
<!-- Python -->
|
|
{{% codetab %}}
|
|
|
|
### Pre-requisites
|
|
|
|
For this example, you will need:
|
|
|
|
- [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started).
|
|
- [Python 3.7+ installed](https://www.python.org/downloads/).
|
|
<!-- IGNORE_LINKS -->
|
|
- [Docker Desktop](https://www.docker.com/products/docker-desktop)
|
|
<!-- END_IGNORE -->
|
|
|
|
### Step 1: Set up the environment
|
|
|
|
Clone the [sample provided in the Quickstarts repo](https://github.com/dapr/quickstarts/tree/master/bindings/python/sdk).
|
|
|
|
```bash
|
|
git clone https://github.com/dapr/quickstarts.git
|
|
```
|
|
|
|
### Step 2: Run PostgreSQL Docker container locally
|
|
|
|
Run the [PostgreSQL instance](https://www.postgresql.org/) locally in a Docker container on your machine. The Quickstart sample includes a Docker Compose file to locally customize, build, run, and initialize the `postgres` container with a default `orders` table.
|
|
|
|
In a terminal window, from the root of the Quickstarts clone directory, navigate to the `bindings/db` directory.
|
|
|
|
```bash
|
|
cd bindings/db
|
|
```
|
|
|
|
Run the following command to set up the container:
|
|
|
|
```bash
|
|
docker compose up
|
|
```
|
|
|
|
Verify that the container is running locally.
|
|
|
|
```bash
|
|
docker ps
|
|
```
|
|
|
|
The output should include:
|
|
|
|
```bash
|
|
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
|
|
55305d1d378b postgres "docker-entrypoint.s…" 3 seconds ago Up 2 seconds 0.0.0.0:5432->5432/tcp sql_db
|
|
```
|
|
|
|
### Step 3: Schedule a Cron job and write to the database
|
|
|
|
In a new terminal window, navigate to the SDK directory.
|
|
|
|
```bash
|
|
cd bindings/python/sdk/batch
|
|
```
|
|
|
|
Install the dependencies:
|
|
|
|
```bash
|
|
pip3 install -r requirements.txt
|
|
```
|
|
|
|
Run the `batch-sdk` service alongside a Dapr sidecar.
|
|
|
|
```bash
|
|
dapr run --app-id batch-sdk --app-port 50051 --resources-path ../../../components -- python3 app.py
|
|
```
|
|
|
|
> **Note**: Since Python3.exe is not defined in Windows, you may need to use `python app.py` instead of `python3 app.py`.
|
|
|
|
The code inside the `process_batch` function is executed every 10 seconds (defined in [`binding-cron.yaml`]({{< ref "#componentsbinding-cronyaml-component-file" >}}) in the `components` directory). The binding trigger looks for a route called via HTTP POST in your application by the Dapr sidecar.
|
|
|
|
```python
|
|
# Triggered by Dapr input binding
|
|
@app.route('/' + cron_binding_name, methods=['POST'])
|
|
def process_batch():
|
|
```
|
|
|
|
The `batch-sdk` service uses the PostgreSQL output binding defined in the [`binding-postgresql.yaml`]({{< ref "#componentbinding-postgresyaml-component-file" >}}) component to insert the `OrderId`, `Customer`, and `Price` records into the `orders` table.
|
|
|
|
```python
|
|
with DaprClient() as d:
|
|
sqlCmd = ('insert into orders (orderid, customer, price) values ' +
|
|
'(%s, \'%s\', %s)' % (order_line['orderid'],
|
|
order_line['customer'],
|
|
order_line['price']))
|
|
payload = {'sql': sqlCmd}
|
|
|
|
print(sqlCmd, flush=True)
|
|
|
|
try:
|
|
# Insert order using Dapr output binding via HTTP Post
|
|
resp = d.invoke_binding(binding_name=sql_binding, operation='exec',
|
|
binding_metadata=payload, data='')
|
|
return resp
|
|
except Exception as e:
|
|
print(e, flush=True)
|
|
raise SystemExit(e)
|
|
```
|
|
|
|
### Step 4: View the output of the job
|
|
|
|
Notice, as specified above, the code invokes the output binding with the `OrderId`, `Customer`, and `Price` as a payload.
|
|
|
|
Your output binding's `print` statement output:
|
|
|
|
```
|
|
== APP == Processing batch..
|
|
== APP == insert into orders (orderid, customer, price) values (1, 'John Smith', 100.32)
|
|
== APP == insert into orders (orderid, customer, price) values (2, 'Jane Bond', 15.4)
|
|
== APP == insert into orders (orderid, customer, price) values (3, 'Tony James', 35.56)
|
|
== APP == Finished processing batch
|
|
```
|
|
|
|
In a new terminal, verify the same data has been inserted into the database. Navigate to the `bindings/db` directory.
|
|
|
|
```bash
|
|
cd bindings/db
|
|
```
|
|
|
|
Run the following to start the interactive *psql* CLI:
|
|
|
|
```bash
|
|
docker exec -i -t postgres psql --username postgres -p 5432 -h localhost --no-password
|
|
```
|
|
|
|
At the `admin=#` prompt, change to the `orders` table:
|
|
|
|
```bash
|
|
\c orders;
|
|
```
|
|
|
|
At the `orders=#` prompt, select all rows:
|
|
|
|
```bash
|
|
select * from orders;
|
|
```
|
|
|
|
The output should look like this:
|
|
|
|
```
|
|
orderid | customer | price
|
|
---------+------------+--------
|
|
1 | John Smith | 100.32
|
|
2 | Jane Bond | 15.4
|
|
3 | Tony James | 35.56
|
|
```
|
|
|
|
#### `components\binding-cron.yaml` component file
|
|
|
|
When you execute the `dapr run` command and specify the component path, the Dapr sidecar:
|
|
|
|
- Initiates the Cron [binding building block]({{< ref bindings >}})
|
|
- Calls the binding endpoint (`batch`) every 10 seconds
|
|
|
|
The Cron `binding-cron.yaml` file included for this Quickstart contains the following:
|
|
|
|
```yaml
|
|
apiVersion: dapr.io/v1alpha1
|
|
kind: Component
|
|
metadata:
|
|
name: cron
|
|
namespace: quickstarts
|
|
spec:
|
|
type: bindings.cron
|
|
version: v1
|
|
metadata:
|
|
- name: schedule
|
|
value: "@every 10s" # valid cron schedule
|
|
- name: direction
|
|
value: "input" # direction of the cron binding
|
|
```
|
|
|
|
**Note:** The `metadata` section of `binding-cron.yaml` contains a [Cron expression]({{< ref cron.md >}}) that specifies how often the binding is invoked.
|
|
|
|
#### `component\binding-postgresql.yaml` component file
|
|
|
|
When you execute the `dapr run` command and specify the component path, the Dapr sidecar:
|
|
|
|
- Initiates the PostgreSQL [binding building block]({{< ref postgresql.md >}})
|
|
- Connects to PostgreSQL using the settings specified in the `binding-postgresql.yaml` file
|
|
|
|
With the `binding-postgresql.yaml` component, you can easily swap out the backend database [binding]({{< ref supported-bindings.md >}}) without making code changes.
|
|
|
|
The PostgreSQL `binding-postgresql.yaml` file included for this Quickstart contains the following:
|
|
|
|
```yaml
|
|
apiVersion: dapr.io/v1alpha1
|
|
kind: Component
|
|
metadata:
|
|
name: sqldb
|
|
namespace: quickstarts
|
|
spec:
|
|
type: bindings.postgresql
|
|
version: v1
|
|
metadata:
|
|
- name: url # Required
|
|
value: "user=postgres password=docker host=localhost port=5432 dbname=orders pool_min_conns=1 pool_max_conns=10"
|
|
- name: direction
|
|
value: "output" # direction of the postgresql binding
|
|
```
|
|
|
|
In the YAML file:
|
|
|
|
- `spec/type` specifies that PostgreSQL is used for this binding.
|
|
- `spec/metadata` defines the connection to the PostgreSQL instance used by the component.
|
|
|
|
{{% /codetab %}}
|
|
|
|
<!-- JavaScript -->
|
|
{{% codetab %}}
|
|
|
|
### Pre-requisites
|
|
|
|
For this example, you will need:
|
|
|
|
- [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started).
|
|
- [Latest Node.js installed](https://nodejs.org/download/).
|
|
<!-- IGNORE_LINKS -->
|
|
- [Docker Desktop](https://www.docker.com/products/docker-desktop)
|
|
<!-- END_IGNORE -->
|
|
|
|
### Step 1: Set up the environment
|
|
|
|
Clone the [sample provided in the Quickstarts repo](https://github.com/dapr/quickstarts/tree/master/bindings/javascript/sdk).
|
|
|
|
```bash
|
|
git clone https://github.com/dapr/quickstarts.git
|
|
```
|
|
|
|
### Step 2: Run PostgreSQL Docker container locally
|
|
|
|
Run the [PostgreSQL instance](https://www.postgresql.org/) locally in a Docker container on your machine. The Quickstart sample includes a Docker Compose file to locally customize, build, run, and initialize the `postgres` container with a default `orders` table.
|
|
|
|
In a terminal window, from the root of the Quickstarts clone directory, navigate to the `bindings/db` directory.
|
|
|
|
```bash
|
|
cd bindings/db
|
|
```
|
|
|
|
Run the following command to set up the container:
|
|
|
|
```bash
|
|
docker compose up
|
|
```
|
|
|
|
Verify that the container is running locally.
|
|
|
|
```bash
|
|
docker ps
|
|
```
|
|
|
|
The output should include:
|
|
|
|
```bash
|
|
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
|
|
55305d1d378b postgres "docker-entrypoint.s…" 3 seconds ago Up 2 seconds 0.0.0.0:5432->5432/tcp sql_db
|
|
```
|
|
|
|
### Step 3: Schedule a Cron job and write to the database
|
|
|
|
In a new terminal window, navigate to the SDK directory.
|
|
|
|
```bash
|
|
cd bindings/javascript/sdk/batch
|
|
```
|
|
|
|
Install the dependencies:
|
|
|
|
```bash
|
|
npm install
|
|
```
|
|
|
|
Run the `batch-sdk` service alongside a Dapr sidecar.
|
|
|
|
```bash
|
|
dapr run --app-id batch-sdk --app-port 5002 --dapr-http-port 3500 --resources-path ../../../components -- node index.js
|
|
```
|
|
|
|
The code inside the `process_batch` function is executed every 10 seconds (defined in [`binding-cron.yaml`]({{< ref "#componentsbinding-cronyaml-component-file" >}}) in the `components` directory). The binding trigger looks for a route called via HTTP POST in your application by the Dapr sidecar.
|
|
|
|
```javascript
|
|
async function start() {
|
|
await server.binding.receive(cronBindingName,processBatch);
|
|
await server.start();
|
|
}
|
|
```
|
|
|
|
The `batch-sdk` service uses the PostgreSQL output binding defined in the [`binding-postgresql.yaml`]({{< ref "##componentsbinding-postgresyaml-component-file" >}}) component to insert the `OrderId`, `Customer`, and `Price` records into the `orders` table.
|
|
|
|
```javascript
|
|
async function processBatch(){
|
|
const loc = '../../orders.json';
|
|
fs.readFile(loc, 'utf8', (err, data) => {
|
|
const orders = JSON.parse(data).orders;
|
|
orders.forEach(order => {
|
|
let sqlCmd = `insert into orders (orderid, customer, price) values (${order.orderid}, '${order.customer}', ${order.price});`;
|
|
let payload = `{ "sql": "${sqlCmd}" } `;
|
|
console.log(payload);
|
|
client.binding.send(postgresBindingName, "exec", "", JSON.parse(payload));
|
|
});
|
|
console.log('Finished processing batch');
|
|
});
|
|
return 0;
|
|
}
|
|
```
|
|
|
|
### Step 4: View the output of the job
|
|
|
|
Notice, as specified above, the code invokes the output binding with the `OrderId`, `Customer`, and `Price` as a payload.
|
|
|
|
Your output binding's `print` statement output:
|
|
|
|
```
|
|
== APP == Processing batch..
|
|
== APP == insert into orders (orderid, customer, price) values(1, 'John Smith', 100.32)
|
|
== APP == insert into orders (orderid, customer, price) values(2, 'Jane Bond', 15.4)
|
|
== APP == insert into orders (orderid, customer, price) values(3, 'Tony James', 35.56)
|
|
```
|
|
|
|
In a new terminal, verify the same data has been inserted into the database. Navigate to the `bindings/db` directory.
|
|
|
|
```bash
|
|
cd bindings/db
|
|
```
|
|
|
|
Run the following to start the interactive Postgres CLI:
|
|
|
|
```bash
|
|
docker exec -i -t postgres psql --username postgres -p 5432 -h localhost --no-password
|
|
```
|
|
|
|
At the `admin=#` prompt, change to the `orders` table:
|
|
|
|
```bash
|
|
\c orders;
|
|
```
|
|
|
|
At the `orders=#` prompt, select all rows:
|
|
|
|
```bash
|
|
select * from orders;
|
|
```
|
|
|
|
The output should look like this:
|
|
|
|
```
|
|
orderid | customer | price
|
|
---------+------------+--------
|
|
1 | John Smith | 100.32
|
|
2 | Jane Bond | 15.4
|
|
3 | Tony James | 35.56
|
|
```
|
|
|
|
#### `components\binding-cron.yaml` component file
|
|
|
|
When you execute the `dapr run` command and specify the component path, the Dapr sidecar:
|
|
|
|
- Initiates the Cron [binding building block]({{< ref bindings >}})
|
|
- Calls the binding endpoint (`batch`) every 10 seconds
|
|
|
|
The Cron `binding-cron.yaml` file included for this Quickstart contains the following:
|
|
|
|
```yaml
|
|
apiVersion: dapr.io/v1alpha1
|
|
kind: Component
|
|
metadata:
|
|
name: cron
|
|
namespace: quickstarts
|
|
spec:
|
|
type: bindings.cron
|
|
version: v1
|
|
metadata:
|
|
- name: schedule
|
|
value: "@every 10s" # valid cron schedule
|
|
- name: direction
|
|
value: "input" # direction of the cron binding
|
|
```
|
|
|
|
**Note:** The `metadata` section of `binding-cron.yaml` contains a [Cron expression]({{< ref cron.md >}}) that specifies how often the binding is invoked.
|
|
|
|
#### `component\binding-postgresql.yaml` component file
|
|
|
|
When you execute the `dapr run` command and specify the component path, the Dapr sidecar:
|
|
|
|
- Initiates the PostgreSQL [binding building block]({{< ref postgresql.md >}})
|
|
- Connects to PostgreSQL using the settings specified in the `binding-postgresql.yaml` file
|
|
|
|
With the `binding-postgresql.yaml` component, you can easily swap out the backend database [binding]({{< ref supported-bindings.md >}}) without making code changes.
|
|
|
|
The PostgreSQL `binding-postgresql.yaml` file included for this Quickstart contains the following:
|
|
|
|
```yaml
|
|
apiVersion: dapr.io/v1alpha1
|
|
kind: Component
|
|
metadata:
|
|
name: sqldb
|
|
namespace: quickstarts
|
|
spec:
|
|
type: bindings.postgresql
|
|
version: v1
|
|
metadata:
|
|
- name: url # Required
|
|
value: "user=postgres password=docker host=localhost port=5432 dbname=orders pool_min_conns=1 pool_max_conns=10"
|
|
- name: direction
|
|
value: "output" # direction of the postgresql binding
|
|
```
|
|
|
|
In the YAML file:
|
|
|
|
- `spec/type` specifies that PostgreSQL is used for this binding.
|
|
- `spec/metadata` defines the connection to the PostgreSQL instance used by the component.
|
|
|
|
{{% /codetab %}}
|
|
|
|
<!-- .NET -->
|
|
{{% codetab %}}
|
|
|
|
### Pre-requisites
|
|
|
|
For this example, you will need:
|
|
|
|
- [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started).
|
|
<!-- IGNORE_LINKS -->
|
|
- [Docker Desktop](https://www.docker.com/products/docker-desktop)
|
|
<!-- END_IGNORE -->
|
|
- [.NET 6](https://dotnet.microsoft.com/download/dotnet/6.0), [.NET 8](https://dotnet.microsoft.com/download/dotnet/8.0) or [.NET 9](https://dotnet.microsoft.com/download/dotnet/9.0) installed
|
|
|
|
**NOTE:** .NET 6 is the minimally supported version of .NET for the Dapr .NET SDK packages in this release. Only .NET 8 and .NET 9
|
|
will be supported in Dapr v1.16 and later releases.
|
|
|
|
### Step 1: Set up the environment
|
|
|
|
Clone the [sample provided in the Quickstarts repo](https://github.com/dapr/quickstarts/tree/master/bindings/csharp/sdk).
|
|
|
|
```bash
|
|
git clone https://github.com/dapr/quickstarts.git
|
|
```
|
|
|
|
### Step 2: Run PostgreSQL Docker container locally
|
|
|
|
Run the [PostgreSQL instance](https://www.postgresql.org/) locally in a Docker container on your machine. The Quickstart sample includes a Docker Compose file to locally customize, build, run, and initialize the `postgres` container with a default `orders` table.
|
|
|
|
In a terminal window, from the root of the Quickstarts clone directory, navigate to the `bindings/db` directory.
|
|
|
|
```bash
|
|
cd bindings/db
|
|
```
|
|
|
|
Run the following command to set up the container:
|
|
|
|
```bash
|
|
docker compose up
|
|
```
|
|
|
|
Verify that the container is running locally.
|
|
|
|
```bash
|
|
docker ps
|
|
```
|
|
|
|
The output should include:
|
|
|
|
```bash
|
|
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
|
|
55305d1d378b postgres "docker-entrypoint.s…" 3 seconds ago Up 2 seconds 0.0.0.0:5432->5432/tcp sql_db
|
|
```
|
|
|
|
### Step 3: Schedule a Cron job and write to the database
|
|
|
|
In a new terminal window, navigate to the SDK directory.
|
|
|
|
```bash
|
|
cd bindings/csharp/sdk/batch
|
|
```
|
|
|
|
Install the dependencies:
|
|
|
|
```bash
|
|
dotnet restore
|
|
dotnet build batch.csproj
|
|
```
|
|
|
|
Run the `batch-sdk` service alongside a Dapr sidecar.
|
|
|
|
```bash
|
|
dapr run --app-id batch-sdk --app-port 7002 --resources-path ../../../components -- dotnet run
|
|
```
|
|
|
|
The code inside the `process_batch` function is executed every 10 seconds (defined in [`binding-cron.yaml`]({{< ref "#componentsbinding-cronyaml-component-file" >}}) in the `components` directory). The binding trigger looks for a route called via HTTP POST in your application by the Dapr sidecar.
|
|
|
|
```csharp
|
|
app.MapPost("/" + cronBindingName, async () => {
|
|
// ...
|
|
});
|
|
```
|
|
|
|
The `batch-sdk` service uses the PostgreSQL output binding defined in the [`binding-postgresql.yaml`]({{< ref "#componentbinding-postgresyaml-component-file" >}}) component to insert the `OrderId`, `Customer`, and `Price` records into the `orders` table.
|
|
|
|
```csharp
|
|
// ...
|
|
string jsonFile = File.ReadAllText("../../../orders.json");
|
|
var ordersArray = JsonSerializer.Deserialize<Orders>(jsonFile);
|
|
using var client = new DaprClientBuilder().Build();
|
|
foreach(Order ord in ordersArray?.orders ?? new Order[] {}){
|
|
var sqlText = $"insert into orders (orderid, customer, price) values ({ord.OrderId}, '{ord.Customer}', {ord.Price});";
|
|
var command = new Dictionary<string,string>(){
|
|
{"sql",
|
|
sqlText}
|
|
};
|
|
// ...
|
|
}
|
|
|
|
// Insert order using Dapr output binding via Dapr Client SDK
|
|
await client.InvokeBindingAsync(bindingName: sqlBindingName, operation: "exec", data: "", metadata: command);
|
|
```
|
|
|
|
### Step 4: View the output of the job
|
|
|
|
Notice, as specified above, the code invokes the output binding with the `OrderId`, `Customer`, and `Price` as a payload.
|
|
|
|
Your output binding's `print` statement output:
|
|
|
|
```
|
|
== APP == Processing batch..
|
|
== APP == insert into orders (orderid, customer, price) values (1, 'John Smith', 100.32);
|
|
== APP == insert into orders (orderid, customer, price) values (2, 'Jane Bond', 15.4);
|
|
== APP == insert into orders (orderid, customer, price) values (3, 'Tony James', 35.56);
|
|
== APP == Finished processing batch
|
|
```
|
|
|
|
In a new terminal, verify the same data has been inserted into the database. Navigate to the `bindings/db` directory.
|
|
|
|
```bash
|
|
cd bindings/db
|
|
```
|
|
|
|
Run the following to start the interactive Postgres CLI:
|
|
|
|
```bash
|
|
docker exec -i -t postgres psql --username postgres -p 5432 -h localhost --no-password
|
|
```
|
|
|
|
At the `admin=#` prompt, change to the `orders` table:
|
|
|
|
```bash
|
|
\c orders;
|
|
```
|
|
|
|
At the `orders=#` prompt, select all rows:
|
|
|
|
```bash
|
|
select * from orders;
|
|
```
|
|
|
|
The output should look like this:
|
|
|
|
```
|
|
orderid | customer | price
|
|
---------+------------+--------
|
|
1 | John Smith | 100.32
|
|
2 | Jane Bond | 15.4
|
|
3 | Tony James | 35.56
|
|
```
|
|
|
|
#### `components\binding-cron.yaml` component file
|
|
|
|
When you execute the `dapr run` command and specify the component path, the Dapr sidecar:
|
|
|
|
- Initiates the Cron [binding building block]({{< ref bindings >}})
|
|
- Calls the binding endpoint (`batch`) every 10 seconds
|
|
|
|
The Cron `binding-cron.yaml` file included for this Quickstart contains the following:
|
|
|
|
```yaml
|
|
apiVersion: dapr.io/v1alpha1
|
|
kind: Component
|
|
metadata:
|
|
name: cron
|
|
namespace: quickstarts
|
|
spec:
|
|
type: bindings.cron
|
|
version: v1
|
|
metadata:
|
|
- name: schedule
|
|
value: "@every 10s" # valid cron schedule
|
|
- name: direction
|
|
value: "input" # direction of the cron binding
|
|
```
|
|
|
|
**Note:** The `metadata` section of `binding-cron.yaml` contains a [Cron expression]({{< ref cron.md >}}) that specifies how often the binding is invoked.
|
|
|
|
#### `component\binding-postgresql.yaml` component file
|
|
|
|
When you execute the `dapr run` command and specify the component path, the Dapr sidecar:
|
|
|
|
- Initiates the PostgreSQL [binding building block]({{< ref postgresql.md >}})
|
|
- Connects to PostgreSQL using the settings specified in the `binding-postgresql.yaml` file
|
|
|
|
With the `binding-postgresql.yaml` component, you can easily swap out the backend database [binding]({{< ref supported-bindings.md >}}) without making code changes.
|
|
|
|
The PostgreSQL `binding-postgresql.yaml` file included for this Quickstart contains the following:
|
|
|
|
```yaml
|
|
apiVersion: dapr.io/v1alpha1
|
|
kind: Component
|
|
metadata:
|
|
name: sqldb
|
|
namespace: quickstarts
|
|
spec:
|
|
type: bindings.postgresql
|
|
version: v1
|
|
metadata:
|
|
- name: url # Required
|
|
value: "user=postgres password=docker host=localhost port=5432 dbname=orders pool_min_conns=1 pool_max_conns=10"
|
|
- name: direction
|
|
value: "output" # direction of the postgresql binding
|
|
```
|
|
|
|
In the YAML file:
|
|
|
|
- `spec/type` specifies that PostgreSQL is used for this binding.
|
|
- `spec/metadata` defines the connection to the PostgreSQL instance used by the component.
|
|
|
|
{{% /codetab %}}
|
|
|
|
<!-- Java -->
|
|
{{% codetab %}}
|
|
|
|
### Pre-requisites
|
|
|
|
For this example, you will need:
|
|
|
|
- [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started).
|
|
- Java JDK 17 (or greater):
|
|
- [Oracle JDK](https://www.oracle.com/java/technologies/downloads), or
|
|
- OpenJDK
|
|
- [Apache Maven](https://maven.apache.org/install.html), version 3.x.
|
|
<!-- IGNORE_LINKS -->
|
|
- [Docker Desktop](https://www.docker.com/products/docker-desktop)
|
|
<!-- END_IGNORE -->
|
|
|
|
### Step 1: Set up the environment
|
|
|
|
Clone the [sample provided in the Quickstarts repo](https://github.com/dapr/quickstarts/tree/master/bindings/java/sdk).
|
|
|
|
```bash
|
|
git clone https://github.com/dapr/quickstarts.git
|
|
```
|
|
|
|
### Step 2: Run PostgreSQL Docker container locally
|
|
|
|
Run the [PostgreSQL instance](https://www.postgresql.org/) locally in a Docker container on your machine. The Quickstart sample includes a Docker Compose file to locally customize, build, run, and initialize the `postgres` container with a default `orders` table.
|
|
|
|
In a terminal window, from the root of the Quickstarts clone directory, navigate to the `bindings/db` directory.
|
|
|
|
```bash
|
|
cd bindings/db
|
|
```
|
|
|
|
Run the following command to set up the container:
|
|
|
|
```bash
|
|
docker compose up
|
|
```
|
|
|
|
Verify that the container is running locally.
|
|
|
|
```bash
|
|
docker ps
|
|
```
|
|
|
|
The output should include:
|
|
|
|
```bash
|
|
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
|
|
55305d1d378b postgres "docker-entrypoint.s…" 3 seconds ago Up 2 seconds 0.0.0.0:5432->5432/tcp sql_db
|
|
```
|
|
|
|
### Step 3: Schedule a Cron job and write to the database
|
|
|
|
In a new terminal window, navigate to the SDK directory.
|
|
|
|
```bash
|
|
cd bindings/java/sdk/batch
|
|
```
|
|
|
|
Install the dependencies:
|
|
|
|
```bash
|
|
mvn clean install
|
|
```
|
|
|
|
Run the `batch-sdk` service alongside a Dapr sidecar.
|
|
|
|
```bash
|
|
dapr run --app-id batch-sdk --app-port 8080 --resources-path ../../../components -- java -jar target/BatchProcessingService-0.0.1-SNAPSHOT.jar
|
|
```
|
|
|
|
The code inside the `process_batch` function is executed every 10 seconds (defined in [`binding-cron.yaml`]({{< ref "#componentsbinding-cronyaml-component-file" >}}) in the `components` directory). The binding trigger looks for a route called via HTTP POST in your application by the Dapr sidecar.
|
|
|
|
```java
|
|
@PostMapping(path = cronBindingPath, consumes = MediaType.ALL_VALUE)
|
|
public ResponseEntity<String> processBatch() throws IOException, Exception
|
|
```
|
|
|
|
The `batch-sdk` service uses the PostgreSQL output binding defined in the [`binding-postgresql.yaml`]({{< ref "#componentbinding-postgresyaml-component-file" >}}) component to insert the `OrderId`, `Customer`, and `Price` records into the `orders` table.
|
|
|
|
```java
|
|
try (DaprClient client = new DaprClientBuilder().build()) {
|
|
|
|
for (Order order : ordList.orders) {
|
|
String sqlText = String.format(
|
|
"insert into orders (orderid, customer, price) " +
|
|
"values (%s, '%s', %s);",
|
|
order.orderid, order.customer, order.price);
|
|
logger.info(sqlText);
|
|
|
|
Map<String, String> metadata = new HashMap<String, String>();
|
|
metadata.put("sql", sqlText);
|
|
|
|
// Invoke sql output binding using Dapr SDK
|
|
client.invokeBinding(sqlBindingName, "exec", null, metadata).block();
|
|
}
|
|
|
|
logger.info("Finished processing batch");
|
|
|
|
return ResponseEntity.ok("Finished processing batch");
|
|
}
|
|
```
|
|
|
|
### Step 4: View the output of the job
|
|
|
|
Notice, as specified above, the code invokes the output binding with the `OrderId`, `Customer`, and `Price` as a payload.
|
|
|
|
Your output binding's `print` statement output:
|
|
|
|
```
|
|
== APP == 2022-06-22 16:39:17.012 INFO 35772 --- [nio-8080-exec-4] c.s.c.BatchProcessingServiceController : Processing batch..
|
|
== APP == 2022-06-22 16:39:17.268 INFO 35772 --- [nio-8080-exec-4] c.s.c.BatchProcessingServiceController : insert into orders (orderid, customer, price) values (1, 'John Smith', 100.32);
|
|
== APP == 2022-06-22 16:39:17.838 INFO 35772 --- [nio-8080-exec-4] c.s.c.BatchProcessingServiceController : insert into orders (orderid, customer, price) values (2, 'Jane Bond', 15.4);
|
|
== APP == 2022-06-22 16:39:17.844 INFO 35772 --- [nio-8080-exec-4] c.s.c.BatchProcessingServiceController : insert into orders (orderid, customer, price) values (3, 'Tony James', 35.56);
|
|
== APP == 2022-06-22 16:39:17.848 INFO 35772 --- [nio-8080-exec-4] c.s.c.BatchProcessingServiceController : Finished processing batch
|
|
```
|
|
|
|
In a new terminal, verify the same data has been inserted into the database. Navigate to the `bindings/db` directory.
|
|
|
|
```bash
|
|
cd bindings/db
|
|
```
|
|
|
|
Run the following to start the interactive Postgres CLI:
|
|
|
|
```bash
|
|
docker exec -i -t postgres psql --username postgres -p 5432 -h localhost --no-password
|
|
```
|
|
|
|
At the `admin=#` prompt, change to the `orders` table:
|
|
|
|
```bash
|
|
\c orders;
|
|
```
|
|
|
|
At the `orders=#` prompt, select all rows:
|
|
|
|
```bash
|
|
select * from orders;
|
|
```
|
|
|
|
The output should look like this:
|
|
|
|
```
|
|
orderid | customer | price
|
|
---------+------------+--------
|
|
1 | John Smith | 100.32
|
|
2 | Jane Bond | 15.4
|
|
3 | Tony James | 35.56
|
|
```
|
|
|
|
#### `components\binding-cron.yaml` component file
|
|
|
|
When you execute the `dapr run` command and specify the component path, the Dapr sidecar:
|
|
|
|
- Initiates the Cron [binding building block]({{< ref bindings >}})
|
|
- Calls the binding endpoint (`batch`) every 10 seconds
|
|
|
|
The Cron `binding-cron.yaml` file included for this Quickstart contains the following:
|
|
|
|
```yaml
|
|
apiVersion: dapr.io/v1alpha1
|
|
kind: Component
|
|
metadata:
|
|
name: cron
|
|
namespace: quickstarts
|
|
spec:
|
|
type: bindings.cron
|
|
version: v1
|
|
metadata:
|
|
- name: schedule
|
|
value: "@every 10s" # valid cron schedule
|
|
- name: direction
|
|
value: "input" # direction of the cron binding
|
|
```
|
|
|
|
**Note:** The `metadata` section of `binding-cron.yaml` contains a [Cron expression]({{< ref cron.md >}}) that specifies how often the binding is invoked.
|
|
|
|
#### `component\binding-postgresql.yaml` component file
|
|
|
|
When you execute the `dapr run` command and specify the component path, the Dapr sidecar:
|
|
|
|
- Initiates the PostgreSQL [binding building block]({{< ref postgresql.md >}})
|
|
- Connects to PostgreSQL using the settings specified in the `binding-postgresql.yaml` file
|
|
|
|
With the `binding-postgresql.yaml` component, you can easily swap out the backend database [binding]({{< ref supported-bindings.md >}}) without making code changes.
|
|
|
|
The PostgreSQL `binding-postgresql.yaml` file included for this Quickstart contains the following:
|
|
|
|
```yaml
|
|
apiVersion: dapr.io/v1alpha1
|
|
kind: Component
|
|
metadata:
|
|
name: sqldb
|
|
namespace: quickstarts
|
|
spec:
|
|
type: bindings.postgresql
|
|
version: v1
|
|
metadata:
|
|
- name: url # Required
|
|
value: "user=postgres password=docker host=localhost port=5432 dbname=orders pool_min_conns=1 pool_max_conns=10"
|
|
- name: direction
|
|
value: "output" # direction of the postgresql binding
|
|
```
|
|
|
|
In the YAML file:
|
|
|
|
- `spec/type` specifies that PostgreSQL is used for this binding.
|
|
- `spec/metadata` defines the connection to the PostgreSQL instance used by the component.
|
|
|
|
{{% /codetab %}}
|
|
|
|
<!-- Go -->
|
|
{{% codetab %}}
|
|
|
|
### Pre-requisites
|
|
|
|
For this example, you will need:
|
|
|
|
- [Dapr CLI and initialized environment](https://docs.dapr.io/getting-started).
|
|
- [Latest version of Go](https://go.dev/dl/).
|
|
<!-- IGNORE_LINKS -->
|
|
- [Docker Desktop](https://www.docker.com/products/docker-desktop)
|
|
<!-- END_IGNORE -->
|
|
|
|
### Step 1: Set up the environment
|
|
|
|
Clone the [sample provided in the Quickstarts repo](https://github.com/dapr/quickstarts/tree/master/bindings/go/sdk).
|
|
|
|
```bash
|
|
git clone https://github.com/dapr/quickstarts.git
|
|
```
|
|
|
|
### Step 2: Run PostgreSQL Docker container locally
|
|
|
|
Run the [PostgreSQL instance](https://www.postgresql.org/) locally in a Docker container on your machine. The Quickstart sample includes a Docker Compose file to locally customize, build, run, and initialize the `postgres` container with a default `orders` table.
|
|
|
|
In a terminal window, from the root of the Quickstarts clone directory, navigate to the `bindings/db` directory.
|
|
|
|
```bash
|
|
cd bindings/db
|
|
```
|
|
|
|
Run the following command to set up the container:
|
|
|
|
```bash
|
|
docker compose up
|
|
```
|
|
|
|
Verify that the container is running locally.
|
|
|
|
```bash
|
|
docker ps
|
|
```
|
|
|
|
The output should include:
|
|
|
|
```bash
|
|
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
|
|
55305d1d378b postgres "docker-entrypoint.s…" 3 seconds ago Up 2 seconds 0.0.0.0:5432->5432/tcp sql_db
|
|
```
|
|
|
|
### Step 3: Schedule a Cron job and write to the database
|
|
|
|
In a new terminal window, navigate to the SDK directory.
|
|
|
|
```bash
|
|
cd bindings/go/sdk/batch
|
|
```
|
|
|
|
Install the dependencies:
|
|
|
|
```bash
|
|
go build .
|
|
```
|
|
|
|
Run the `batch-sdk` service alongside a Dapr sidecar.
|
|
|
|
```bash
|
|
dapr run --app-id batch-sdk --app-port 6002 --dapr-http-port 3502 --dapr-grpc-port 60002 --resources-path ../../../components -- go run .
|
|
```
|
|
|
|
The code inside the `process_batch` function is executed every 10 seconds (defined in [`binding-cron.yaml`]({{< ref "#componentsbinding-cronyaml-component-file" >}}) in the `components` directory). The binding trigger looks for a route called via HTTP POST in your application by the Dapr sidecar.
|
|
|
|
```go
|
|
// Triggered by Dapr input binding
|
|
r.HandleFunc("/"+cronBindingName, processBatch).Methods("POST")
|
|
```
|
|
|
|
The `batch-sdk` service uses the PostgreSQL output binding defined in the [`binding-postgresql.yaml`]({{< ref "#componentbinding-postgresyaml-component-file" >}}) component to insert the `OrderId`, `Customer`, and `Price` records into the `orders` table.
|
|
|
|
```go
|
|
func sqlOutput(order Order) (err error) {
|
|
|
|
client, err := dapr.NewClient()
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
ctx := context.Background()
|
|
|
|
sqlCmd := fmt.Sprintf("insert into orders (orderid, customer, price) values (%d, '%s', %s);", order.OrderId, order.Customer, strconv.FormatFloat(order.Price, 'f', 2, 64))
|
|
fmt.Println(sqlCmd)
|
|
|
|
// Insert order using Dapr output binding via Dapr SDK
|
|
in := &dapr.InvokeBindingRequest{
|
|
Name: sqlBindingName,
|
|
Operation: "exec",
|
|
Data: []byte(""),
|
|
Metadata: map[string]string{"sql": sqlCmd},
|
|
}
|
|
err = client.InvokeOutputBinding(ctx, in)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
return nil
|
|
}
|
|
```
|
|
|
|
### Step 4: View the output of the job
|
|
|
|
Notice, as specified above, the code invokes the output binding with the `OrderId`, `Customer`, and `Price` as a payload.
|
|
|
|
Your output binding's `print` statement output:
|
|
|
|
```
|
|
== APP == Processing batch..
|
|
== APP == insert into orders (orderid, customer, price) values(1, 'John Smith', 100.32)
|
|
== APP == insert into orders (orderid, customer, price) values(2, 'Jane Bond', 15.4)
|
|
== APP == insert into orders (orderid, customer, price) values(3, 'Tony James', 35.56)
|
|
```
|
|
|
|
In a new terminal, verify the same data has been inserted into the database. Navigate to the `bindings/db` directory.
|
|
|
|
```bash
|
|
cd bindings/db
|
|
```
|
|
|
|
Run the following to start the interactive Postgres CLI:
|
|
|
|
```bash
|
|
docker exec -i -t postgres psql --username postgres -p 5432 -h localhost --no-password
|
|
```
|
|
|
|
At the `admin=#` prompt, change to the `orders` table:
|
|
|
|
```bash
|
|
\c orders;
|
|
```
|
|
|
|
At the `orders=#` prompt, select all rows:
|
|
|
|
```bash
|
|
select * from orders;
|
|
```
|
|
|
|
The output should look like this:
|
|
|
|
```
|
|
orderid | customer | price
|
|
---------+------------+--------
|
|
1 | John Smith | 100.32
|
|
2 | Jane Bond | 15.4
|
|
3 | Tony James | 35.56
|
|
```
|
|
|
|
#### `components\binding-cron.yaml` component file
|
|
|
|
When you execute the `dapr run` command and specify the component path, the Dapr sidecar:
|
|
|
|
- Initiates the Cron [binding building block]({{< ref bindings >}})
|
|
- Calls the binding endpoint (`batch`) every 10 seconds
|
|
|
|
The Cron `binding-cron.yaml` file included for this Quickstart contains the following:
|
|
|
|
```yaml
|
|
apiVersion: dapr.io/v1alpha1
|
|
kind: Component
|
|
metadata:
|
|
name: cron
|
|
namespace: quickstarts
|
|
spec:
|
|
type: bindings.cron
|
|
version: v1
|
|
metadata:
|
|
- name: schedule
|
|
value: "@every 10s" # valid cron schedule
|
|
- name: direction
|
|
value: "input" # direction of the cron binding
|
|
```
|
|
|
|
**Note:** The `metadata` section of `binding-cron.yaml` contains a [Cron expression]({{< ref cron.md >}}) that specifies how often the binding is invoked.
|
|
|
|
#### `component\binding-postgresql.yaml` component file
|
|
|
|
When you execute the `dapr run` command and specify the component path, the Dapr sidecar:
|
|
|
|
- Initiates the PostgreSQL [binding building block]({{< ref postgresql.md >}})
|
|
- Connects to PostgreSQL using the settings specified in the `binding-postgresql.yaml` file
|
|
|
|
With the `binding-postgresql.yaml` component, you can easily swap out the backend database [binding]({{< ref supported-bindings.md >}}) without making code changes.
|
|
|
|
The PostgreSQL `binding-postgresql.yaml` file included for this Quickstart contains the following:
|
|
|
|
```yaml
|
|
apiVersion: dapr.io/v1alpha1
|
|
kind: Component
|
|
metadata:
|
|
name: sqldb
|
|
namespace: quickstarts
|
|
spec:
|
|
type: bindings.postgresql
|
|
version: v1
|
|
metadata:
|
|
- name: url # Required
|
|
value: "user=postgres password=docker host=localhost port=5432 dbname=orders pool_min_conns=1 pool_max_conns=10"
|
|
- name: direction
|
|
value: "output" # direction of the postgresql binding
|
|
```
|
|
|
|
In the YAML file:
|
|
|
|
- `spec/type` specifies that PostgreSQL is used for this binding.
|
|
- `spec/metadata` defines the connection to the PostgreSQL instance used by the component.
|
|
|
|
{{% /codetab %}}
|
|
|
|
{{< /tabs >}}
|
|
|
|
## Tell us what you think!
|
|
|
|
We're continuously working to improve our Quickstart examples and value your feedback. Did you find this quickstart helpful? Do you have suggestions for improvement?
|
|
|
|
Join the discussion in our [discord channel](https://discord.com/channels/778680217417809931/953427615916638238).
|
|
|
|
## Next steps
|
|
|
|
- Use Dapr Bindings with HTTP instead of an SDK.
|
|
- [Python](https://github.com/dapr/quickstarts/tree/master/bindings/python/http)
|
|
- [JavaScript](https://github.com/dapr/quickstarts/tree/master/bindings/javascript/http)
|
|
- [.NET](https://github.com/dapr/quickstarts/tree/master/bindings/csharp/http)
|
|
- [Java](https://github.com/dapr/quickstarts/tree/master/bindings/java/http)
|
|
- [Go](https://github.com/dapr/quickstarts/tree/master/bindings/go/http)
|
|
- Learn more about [Binding building block]({{< ref bindings >}})
|
|
|
|
{{< button text="Explore Dapr tutorials >>" page="getting-started/tutorials/_index.md" >}}
|