Update Relationship Tuples
This section will illustrate how to update relationship tuples.
Before You Start
- Node.js
- Go
- .NET
- Python
- CLI
- curl
- Deploy an instance of the OpenFGA server, and have ready the values for your setup: FGA_STORE_ID, FGA_API_HOST and, if needed, FGA_API_TOKEN.
- You have installed the SDK.
- You have configured the authorization model.
- You have loaded
FGA_STORE_ID
andFGA_API_HOST
as environment variables.
- Deploy an instance of the OpenFGA server, and have ready the values for your setup: FGA_STORE_ID, FGA_API_HOST and, if needed, FGA_API_TOKEN.
- You have installed the SDK.
- You have configured the authorization model.
- You have loaded
FGA_STORE_ID
andFGA_API_HOST
as environment variables.
- Deploy an instance of the OpenFGA server, and have ready the values for your setup: FGA_STORE_ID, FGA_API_HOST and, if needed, FGA_API_TOKEN.
- You have installed the SDK.
- You have configured the authorization model.
- You have loaded
FGA_STORE_ID
andFGA_API_HOST
as environment variables.
- Deploy an instance of the OpenFGA server, and have ready the values for your setup: FGA_STORE_ID, FGA_API_HOST and, if needed, FGA_API_TOKEN.
- You have installed the SDK.
- You have configured the authorization model.
- You have loaded
FGA_STORE_ID
andFGA_API_HOST
as environment variables.
- Deploy an instance of the OpenFGA server, and have ready the values for your setup: FGA_STORE_ID, FGA_API_HOST and, if needed, FGA_API_TOKEN.
- You have configured the authorization model.
- You have loaded
FGA_STORE_ID
andFGA_SERVER_URL
as environment variables.
- Deploy an instance of the OpenFGA server, and have ready the values for your setup: FGA_STORE_ID, FGA_API_HOST and, if needed, FGA_API_TOKEN.
- You have configured the authorization model.
- You have loaded
FGA_STORE_ID
andFGA_API_HOST
as environment variables.
Step By Step
Assume that you want to add user user:anne
to have relationship reader
with object document:Z
{
user: 'user:anne',
relation: 'reader',
object: 'document:Z',
}
01. Configure The OpenFGA API Client
Before calling the write API, you will need to configure the API client.
- Node.js
- Go
- .NET
- Python
- CLI
- curl
// import the SDK
const { OpenFgaClient } = require('@openfga/sdk');
// Initialize the SDK with no auth - see "How to setup SDK client" for more options
const fgaClient = new OpenFgaClient({
apiScheme: process.env.FGA_API_SCHEME, // Either "http" or "https", defaults to "https"
apiHost: process.env.FGA_API_HOST, // required, define without the scheme (e.g. api.fga.example instead of https://api.fga.example)
storeId: process.env.FGA_STORE_ID,
authorizationModelId: process.env.FGA_MODEL_ID, // Optional, can be overridden per request
});
import (
. "github.com/openfga/go-sdk/client"
"os"
)
func main() {
// Initialize the SDK with no auth - see "How to setup SDK client" for more options
fgaClient, err := NewSdkClient(&ClientConfiguration{
ApiScheme: os.Getenv("FGA_SCHEME"), // Either "http" or "https", defaults to "https"
ApiHost: os.Getenv("FGA_API_HOST"), // required, define without the scheme (e.g. api.fga.example instead of https://api.fga.example)
StoreId: os.Getenv("FGA_STORE_ID"), // optional, not needed for `CreateStore` and `ListStores`, required before calling for all other methods
AuthorizationModelId: openfga.PtrString(os.Getenv("FGA_MODEL_ID")), // Optional, can be overridden per request
})
if err != nil {
// .. Handle error
}
}
// import the SDK
using OpenFga.Sdk.Client;
using OpenFga.Sdk.Client.Model;
using OpenFga.Sdk.Model;
using Environment = System.Environment;
namespace Example;
class Example {
public static async Task Main() {
// Initialize the SDK with no auth - see "How to setup SDK client" for more options
var configuration = new ClientConfiguration() {
ApiScheme = Environment.GetEnvironmentVariable("FGA_API_SCHEME"), // Either "http" or "https", defaults to "https"
ApiHost = Environment.GetEnvironmentVariable("FGA_API_HOST"), // required, define without the scheme (e.g. api.fga.example instead of https://api.fga.example)
StoreId = Environment.GetEnvironmentVariable("FGA_STORE_ID"), // optional, not needed for `CreateStore` and `ListStores`, required before calling for all other methods
AuthorizationModelId = Environment.GetEnvironmentVariable("FGA_MODEL_ID"), // Optional, can be overridden per request
};
var fgaClient = new OpenFgaClient(configuration);
}
}
import os
import json
from openfga_sdk.client import ClientConfiguration
from openfga_sdk.client import OpenFgaClient
configuration = ClientConfiguration(
api_scheme = os.environ.get('FGA_API_SCHEME'), # Either "http" or "https", defaults to "https"
api_host = os.environ.get('FGA_API_HOST'), # required, define without the scheme (e.g. api.fga.example instead of https://api.fga.example)
store_id = os.environ.get('FGA_STORE_ID') # optional, not needed for `CreateStore` and `ListStores`, required before calling for all other methods
authorization_model_id = os.environ.get('FGA_MODEL_ID'), # Optional, can be overridden per request
)
# Enter a context with an instance of the OpenFgaClient
async with OpenFgaClient(configuration) as fga_client:
api_response = await fga_client.read_authorization_models()
await fga_client.close()
Set FGA_SERVER_URL according to the service you are using (e.g. https://api.fga.example)
To obtain the access token:
Set FGA_SERVER_URL according to the service you are using (e.g. https://api.fga.example)
02. Calling Write API To Add New Relationship Tuples
To add the relationship tuples, we can invoke the write API.
- Node.js
- Go
- .NET
- Python
- CLI
- curl
await fgaClient.write({
writes: [
{ user: 'user:anne', relation: 'reader', object: 'document:Z'}]
},
}, {
authorization_model_id: "1uHxCSuTP0VKPYSnkq1pbb1jeZw"
});
options := ClientWriteOptions{
AuthorizationModelId: openfga.PtrString("1uHxCSuTP0VKPYSnkq1pbb1jeZw"),
}
body := fgaClient.ClientWriteRequest{
Writes: &[]ClientTupleKey{
{
User: openfga.PtrString("user:anne"),
Relation: openfga.PtrString("reader"),
Object: openfga.PtrString("document:Z"),
}, } }
data, err := fgaClient.Write(context.Background()).Body(requestBody).Options(options).Execute()
if err != nil {
// .. Handle error
}
var options = new ClientListObjectsOptions {
AuthorizationModelId = "1uHxCSuTP0VKPYSnkq1pbb1jeZw",
};
var body = new ClientWriteRequest() {
Writes = new List<ClientTupleKey>() {
new() { User = "user:anne", Relation = "reader", Object = "document:Z" }
},
};
var response = await fgaClient.Write(body, options);
options = {
"authorization_model_id": "1uHxCSuTP0VKPYSnkq1pbb1jeZw"
}
body = ClientWriteRequest(
writes=[
ClientTuple(
user="user:anne",
relation="reader",
object="document:Z",
),
],
)
response = await fga_client.write(body, options)
fga tuple write --store-id=${FGA_STORE_ID} --model-id=1uHxCSuTP0VKPYSnkq1pbb1jeZw user:anne reader document:Z
curl -X POST $FGA_SERVER_URL/stores/$FGA_STORE_ID/write \
-H "Authorization: Bearer $FGA_API_TOKEN" \ # Not needed if service does not require authorization
-H "content-type: application/json" \
-d '{"writes": { "tuple_keys" : [{"user":"user:anne","relation":"reader","object":"document:Z"}] }, "authorization_model_id": "1uHxCSuTP0VKPYSnkq1pbb1jeZw"}'
03. Calling Write API To Delete Relationship Tuples
To delete relationship tuples, we can invoke the write API.
Assume that you want to delete user user:anne
's reader
relationship with object document:Z
{
user: 'user:anne',
relation: 'reader',
object: 'document:Z',
}
- Node.js
- Go
- .NET
- Python
- CLI
- curl
await fgaClient.write({
deletes: [
{ user: 'user:anne', relation: 'reader', object: 'document:Z'}]
},
}, {
authorization_model_id: "1uHxCSuTP0VKPYSnkq1pbb1jeZw"
});
options := ClientWriteOptions{
AuthorizationModelId: openfga.PtrString("1uHxCSuTP0VKPYSnkq1pbb1jeZw"),
}
body := fgaClient.ClientWriteRequest{
Deletes: &[]ClientTupleKey{
{
User: openfga.PtrString("user:anne"),
Relation: openfga.PtrString("reader"),
Object: openfga.PtrString("document:Z"),
}, } }
data, err := fgaClient.Write(context.Background()).Body(requestBody).Options(options).Execute()
if err != nil {
// .. Handle error
}
var options = new ClientListObjectsOptions {
AuthorizationModelId = "1uHxCSuTP0VKPYSnkq1pbb1jeZw",
};
var body = new ClientWriteRequest() {
Deletes = new List<ClientTupleKey>() {
new() { User = "user:anne", Relation = "reader", Object = "document:Z" }
},
};
var response = await fgaClient.Write(body, options);
options = {
"authorization_model_id": "1uHxCSuTP0VKPYSnkq1pbb1jeZw"
}
body = ClientWriteRequest(
deletes=[
ClientTuple(
user="user:anne",
relation="reader",
object="document:Z",
),
],
)
response = await fga_client.write(body, options)
fga tuple delete --store-id=${FGA_STORE_ID} user:anne reader document:Z
curl -X POST $FGA_SERVER_URL/stores/$FGA_STORE_ID/write \
-H "Authorization: Bearer $FGA_API_TOKEN" \ # Not needed if service does not require authorization
-H "content-type: application/json" \
-d '{"deletes": { "tuple_keys" : [{"user":"user:anne","relation":"reader","object":"document:Z"}] }, "authorization_model_id": "1uHxCSuTP0VKPYSnkq1pbb1jeZw"}'