From 31b2617d8fe6c624fb4e8777bfed6fd652b65826 Mon Sep 17 00:00:00 2001 From: Alberto Bastianello Date: Mon, 26 Jan 2026 11:44:48 +0100 Subject: [PATCH] added go docs --- STRUCTURE.md | 4 +- docs/developers/go/api-quick-reference.md | 52 +++++- docs/developers/go/cstore-integration.md | 107 +++++++++++++ docs/developers/go/index.md | 6 +- .../developers/go/quick-end-to-end-example.md | 83 +++++++++- docs/developers/go/r1fs-integration.md | 148 ++++++++++++++++++ 6 files changed, 387 insertions(+), 13 deletions(-) create mode 100644 docs/developers/go/cstore-integration.md create mode 100644 docs/developers/go/r1fs-integration.md diff --git a/STRUCTURE.md b/STRUCTURE.md index fef18ed..5bee635 100644 --- a/STRUCTURE.md +++ b/STRUCTURE.md @@ -55,7 +55,9 @@ 5.2.5. Simple auth - using SDK simple auth with the JavaScript SDK (Ale) 5.3. Go - using the Go SDK for Ratio1 (B) 5.3.1. Quick end-to-end example - a complete example of using the Go SDK (B) -5.3.1. API Quick Reference - detailed API documentation (B) +5.3.2. API Quick Reference - detailed API documentation (B) +5.3.3. CStore Integration - using CStore with the Go SDK (B) +5.3.4. R1FS Integration - using R1FS with the Go SDK (B) 5.4. The Sandbox - using the Ratio1 Sandbox for testing and development(B) 5.5. r1ctl - the kubectl for Ratio1 (AID) 5.5.1. r1ctl Overview - overview presentation with no details (AID) diff --git a/docs/developers/go/api-quick-reference.md b/docs/developers/go/api-quick-reference.md index 8506f8e..e3c7de1 100644 --- a/docs/developers/go/api-quick-reference.md +++ b/docs/developers/go/api-quick-reference.md @@ -6,12 +6,54 @@ description: detailed API documentation # API Quick Reference -## What this covers -- Core concepts and definitions for this topic. -- Practical guidance and recommended next steps. +## Package layout +- `github.com/Ratio1/edge_sdk_go/pkg/cstore` – CStore client (key/value + hash operations) +- `github.com/Ratio1/edge_sdk_go/pkg/r1fs` – R1FS client (file/object helpers) -## Notable date -- TBD (add a source link). +## Bootstrap (recommended) +Both clients can be initialised from the standard Ratio1 env vars: +- `EE_CHAINSTORE_API_URL` for CStore +- `EE_R1FS_API_URL` for R1FS + +```go +cs, err := cstore.NewFromEnv() +fs, err := r1fs.NewFromEnv() +``` + +## Error and “not found” semantics +- Most methods return Go `error` values for transport/protocol failures. +- When the upstream returns `null` for missing data, the SDK returns a `nil` item/document (with `err == nil`). + - CStore: `Get` / `HGet` can return `nil` + - R1FS: `GetYAML` can return `nil` + +## CStore highlights +- `Set(ctx, key, value, opts)` – store JSON-serialisable values +- `Get(ctx, key, out)` – fetch and decode values +- `HSet(ctx, hash, field, value, opts)` – set a field inside a hash key +- `HGet(ctx, hash, field, out)` / `HGetAll(ctx, hash)` – retrieve hash data +- `GetStatus(ctx)` – lightweight connectivity/status call + +## R1FS highlights +- `AddFileBase64(ctx, r, opts)` / `GetFileBase64(ctx, cid, secret)` – store and retrieve content +- `AddFile(ctx, r, opts)` / `GetFile(ctx, cid, secret)` – multipart upload + metadata lookup +- `AddYAML(ctx, data, opts)` / `GetYAML(ctx, cid, secret, out)` – YAML convenience helpers +- `CalculateJSONCID(ctx, data, seed, opts)` / `CalculatePickleCID(...)` – compute content IDs without storing +- `AddJSON(ctx, data, opts)` / `AddPickle(ctx, data, opts)` – store structured payloads directly +- `DeleteFile(ctx, cid, opts)` / `DeleteFiles(ctx, cids, opts)` – remove stored content + +## R1FS options +`r1fs.DataOptions` (used by upload/calculate endpoints): +- `Filename` – name associated with the uploaded payload +- `FilePath` – virtual path to store the payload under +- `Secret` – optional access secret (forwarded to the manager) +- `Nonce` – optional integer used by endpoints that support deterministic CID calculation + +`r1fs.DeleteOptions` (used by delete endpoints): +- `UnpinRemote` – request unpin on remote pinning backends +- `RunGC` – request garbage collection (`run_gc` / `run_gc_after_all`) +- `CleanupLocalFiles` – request local cleanup on the node ## Next steps +- See [CStore Integration](./cstore-integration) for a step-by-step KV flow. +- See [R1FS Integration](./r1fs-integration) for uploads/downloads. - Back to [Go](../). diff --git a/docs/developers/go/cstore-integration.md b/docs/developers/go/cstore-integration.md new file mode 100644 index 0000000..27dd79f --- /dev/null +++ b/docs/developers/go/cstore-integration.md @@ -0,0 +1,107 @@ +--- +title: CStore Integration +sidebar_position: 3 +description: using CStore with the Go SDK +--- + +# CStore Integration + +## What CStore is +CStore is the Ratio1 edge-node key/value store exposed via a REST manager API. +The Go SDK provides a small HTTP client with helpers for: +- key/value reads and writes +- hash operations (field maps under a single key) + +## Configure +Set the base URL for the node (or sandbox) you want to talk to: +- `EE_CHAINSTORE_API_URL` + +Example: +```bash +export EE_CHAINSTORE_API_URL="http://:/" +``` + +## Concepts +- **Key/value**: store one JSON document per key. +- **Hash**: store many JSON documents under a single “hash key”, addressed by **field**. +- **Missing data**: `Get` / `HGet` return `(nil, nil)` when the upstream returns `null` (treat as “not found”). + +## Patterns and best practices +- Always use a `context.Context` with timeouts for network calls. +- Use stable key prefixes (e.g. `app::`) so you can locate your data later. +- Keep values JSON-serialisable; the SDK encodes/decodes with `encoding/json`. + +## Bootstrap +```go +client, err := cstore.NewFromEnv() +``` + +## Key/value flow (Set + Get) +```go +type Counter struct { + Count int `json:"count"` +} + +if err := client.Set(ctx, "jobs:123", Counter{Count: 1}, nil); err != nil { + return err +} + +var out Counter +item, err := client.Get(ctx, "jobs:123", &out) +if err != nil { + return err +} +if item == nil { + // Key does not exist (upstream returned null). + return nil +} +``` + +## Hash flow (HSet + HGet + HGetAll) +```go +if err := client.HSet(ctx, "jobs", "123", map[string]any{"status": "queued"}, nil); err != nil { + return err +} + +var payload map[string]any +hashItem, err := client.HGet(ctx, "jobs", "123", &payload) +if err != nil { + return err +} +if hashItem == nil { + // Field does not exist (upstream returned null). + return nil +} + +all, err := client.HGetAll(ctx, "jobs") +if err != nil { + return err +} +_ = all +``` + +## Connectivity check +`GetStatus` is a lightweight way to validate connectivity and inspect keys reported by the manager: +```go +status, err := client.GetStatus(ctx) +if err != nil { + return err +} +if status != nil { + fmt.Println(status.Keys) +} +``` + +## Runnable example +The SDK repo includes a complete example: +```bash +go run ./examples/cstore +``` + +## Troubleshooting +- `cstore.NewFromEnv()` fails: verify `EE_CHAINSTORE_API_URL` is set and reachable. +- Decode errors: ensure the value stored under the key is valid JSON for the struct you pass to `Get`/`HGet`. + +## Next steps +- For file/object storage, see [R1FS Integration](./r1fs-integration). +- Back to [Go](../). diff --git a/docs/developers/go/index.md b/docs/developers/go/index.md index 6ece82f..4fdadc1 100644 --- a/docs/developers/go/index.md +++ b/docs/developers/go/index.md @@ -9,6 +9,8 @@ description: using the Go SDK for Ratio1 ## In this section - [Quick end-to-end example](./quick-end-to-end-example) - [API Quick Reference](./api-quick-reference) +- [CStore Integration](./cstore-integration) +- [R1FS Integration](./r1fs-integration) -## Notable date -- TBD (add a source link). +## SDK repository +- `github.com/Ratio1/edge_sdk_go` diff --git a/docs/developers/go/quick-end-to-end-example.md b/docs/developers/go/quick-end-to-end-example.md index d96bea2..f928706 100644 --- a/docs/developers/go/quick-end-to-end-example.md +++ b/docs/developers/go/quick-end-to-end-example.md @@ -6,12 +6,85 @@ description: a complete example of using the Go SDK # Quick end-to-end example -## What this covers -- Core concepts and definitions for this topic. -- Practical guidance and recommended next steps. +This page shows the smallest working flow to: +- configure the SDK via env vars +- connect to CStore and R1FS +- perform one call against each service -## Notable date -- TBD (add a source link). +## Prerequisites +- Go 1.20+ (recommended) +- A Ratio1 node (or sandbox) exposing the manager APIs: + - `EE_CHAINSTORE_API_URL` for CStore + - `EE_R1FS_API_URL` for R1FS + +## Configure (environment variables) +Set these before running the examples: +```bash +export EE_CHAINSTORE_API_URL="http://:/" +export EE_R1FS_API_URL="http://:/" +``` + +The SDK initialisers `cstore.NewFromEnv()` and `r1fs.NewFromEnv()` fail fast if the variables are missing. + +## Install +```bash +go get github.com/Ratio1/edge_sdk_go +``` + +## Run the upstream example +The SDK repo contains a ready-made program that validates the env vars and issues lightweight calls: +```bash +go run ./examples/runtime_modes +``` + +## Minimal code +```go +package main + +import ( + "context" + "fmt" + "log" + "time" + + "github.com/Ratio1/edge_sdk_go/pkg/cstore" + "github.com/Ratio1/edge_sdk_go/pkg/r1fs" +) + +func main() { + // Always use timeouts for network calls. + ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second) + defer cancel() + + cs, err := cstore.NewFromEnv() + if err != nil { + log.Fatalf("init cstore: %v", err) + } + fs, err := r1fs.NewFromEnv() + if err != nil { + log.Fatalf("init r1fs: %v", err) + } + + status, err := cs.GetStatus(ctx) + if err != nil { + log.Fatalf("cstore status: %v", err) + } + keyCount := 0 + if status != nil { + keyCount = len(status.Keys) + } + fmt.Printf("CStore keys: %d\n", keyCount) + + // Calculate a CID without storing anything. + cid, err := fs.CalculateJSONCID(ctx, map[string]any{"hello": "ratio1"}, 1, nil) + if err != nil { + log.Fatalf("r1fs calculate: %v", err) + } + fmt.Printf("Sample CID (not stored): %s\n", cid) +} +``` ## Next steps +- If you want key/value operations, continue with [CStore Integration](./cstore-integration). +- If you want file/object operations, continue with [R1FS Integration](./r1fs-integration). - Back to [Go](../). diff --git a/docs/developers/go/r1fs-integration.md b/docs/developers/go/r1fs-integration.md new file mode 100644 index 0000000..a76c9a3 --- /dev/null +++ b/docs/developers/go/r1fs-integration.md @@ -0,0 +1,148 @@ +--- +title: R1FS Integration +sidebar_position: 4 +description: using R1FS with the Go SDK +--- + +# R1FS Integration + +## What R1FS is +R1FS is the Ratio1 edge-node file/object storage layer (backed by the upstream IPFS manager). +The Go SDK provides helpers to: +- upload data and get back a CID +- resolve stored metadata (path, filename, optional meta) +- compute CIDs for JSON/pickle payloads without storing them + +## Configure +Set the base URL for the node (or sandbox) you want to talk to: +- `EE_R1FS_API_URL` + +Example: +```bash +export EE_R1FS_API_URL="http://:/" +``` + +## Concepts +- **CID**: content identifier returned by the service (used to download/resolve/delete). +- **Upload name vs path**: + - `DataOptions.Filename` is the name attached to uploads. + - `DataOptions.FilePath` is the (virtual) path you want the manager to store. + - Some endpoints require *one of them*; the SDK enforces this. +- **Secret**: optional access control token passed as `secret` to supported endpoints. +- **Nonce**: optional integer forwarded to endpoints that support deterministic CID derivation. + +## Patterns and best practices +- Always use a `context.Context` with timeouts for network calls. +- Use a predictable `FilePath` prefix like `my-app///...` for easier organisation. +- If you plan to delete data, design your paths so you can locate related CIDs (store an index in CStore, for example). + +## Bootstrap +```go +client, err := r1fs.NewFromEnv() +``` + +## Upload and download (base64 endpoints) +These endpoints send file contents base64-encoded inside JSON. They are convenient for small payloads. +```go +cid, err := client.AddFileBase64(ctx, bytes.NewReader([]byte("hello")), &r1fs.DataOptions{ + FilePath: "ratio1-sdk-demo/hello.txt", +}) +if err != nil { + return err +} + +data, filename, err := client.GetFileBase64(ctx, cid, "") +if err != nil { + return err +} +_ = data +_ = filename +``` + +## Multipart upload + metadata lookup +Use `/add_file` when you want a classic multipart upload. Then resolve where it was stored using `/get_file`. +```go +cid, err := client.AddFile(ctx, bytes.NewReader([]byte{0xca, 0xfe}), &r1fs.DataOptions{ + FilePath: "ratio1-sdk-demo/artifacts/artifact.bin", +}) +if err != nil { + return err +} + +loc, err := client.GetFile(ctx, cid, "") +if err != nil { + return err +} +fmt.Println("download path:", loc.Path, "filename:", loc.Filename) +``` + +## Store YAML and read it back +```go +yamlCID, err := client.AddYAML(ctx, map[string]any{"service": "r1fs"}, &r1fs.DataOptions{Filename: "config.yaml"}) +if err != nil { + return err +} + +var out map[string]any +_, err = client.GetYAML(ctx, yamlCID, "", &out) +if err != nil { + return err +} +``` + +## Store JSON / pickle directly +If you already have structured data, you can store it without manually serialising bytes: +```go +cid, err := client.AddJSON(ctx, map[string]any{"job": 123, "status": "queued"}, &r1fs.DataOptions{ + Filename: "job.json", +}) +if err != nil { + return err +} +_ = cid +``` + +## Calculate CIDs without storing content +Useful for deduplication and “pre-flight” checks. +```go +cid, err := client.CalculateJSONCID(ctx, map[string]any{"job": 123}, 42, &r1fs.DataOptions{ + Secret: "optional", +}) +if err != nil { + return err +} +_ = cid +``` + +## Delete content +R1FS exposes delete endpoints for a single CID or a list of CIDs. +```go +unpinRemote := true +runGC := false +cleanupLocal := true + +result, err := client.DeleteFile(ctx, cid, &r1fs.DeleteOptions{ + UnpinRemote: &unpinRemote, + RunGC: &runGC, + CleanupLocalFiles: &cleanupLocal, +}) +if err != nil { + return err +} +fmt.Println(result.Success, result.Message) +``` + +## Runnable example +The SDK repo includes a complete example: +```bash +go run ./examples/r1fs +``` + +## Troubleshooting +- `r1fs.NewFromEnv()` fails: verify `EE_R1FS_API_URL` is set and reachable. +- `filename or filepath is required`: pass `DataOptions.Filename` or `DataOptions.FilePath` for upload endpoints. +- `GetFileBase64` fails to decode: ensure the upstream returns a valid base64 payload. + +## Next steps +- For key/value storage, see [CStore Integration](./cstore-integration). +- Back to [Go](../).