Getting Started with TSG
This guide takes you from nothing to a running TSG participant: your own wallet, SSO bridge, control plane and data plane, joined to a dataspace somebody else operates.
Prerequisites
Tools
- Node.js 22+ — download
- kubectl — installation guide
Helm is not required.
Cluster
- Kubernetes 1.24+
- CloudNativePG 1.30 or newer
- An Ingress controller (or the Gateway API CRDs plus a controller)
- cert-manager, to issue the TLS certificates
Important: public HTTPS endpoints with real domains are required for DID document resolution and for connectors to reach each other.
Install the CLI
npm install -g @tsg-dsp/cli@latest
tsg --version
Step 1: Get your dataspace details
Whoever operates the dataspace you are joining gives you four things:
| What | Used for |
|---|---|
The authority's did:web: DID | The trust anchor your components accept. |
| The authority's domain | Where the credential type is served. |
| The credential type | What proves membership. |
| A pre-authorized code | What your wallet exchanges for your credential. |
Note: the TSG Playground at
https://playground.dataspac.esis being moved to this deployment model. Until that is done, follow the instructions there rather than the values in this guide.
Step 2: Write your configuration
Create participant.yaml:
apiVersion: tsg.dataspac.es/v1alpha1
kind: TsgDeployment
metadata:
name: my-org # ✏️ your deployment identity
spec:
namespace: tsg-my-org # ✏️ your Kubernetes namespace
# The trust domain you are joining. Stated, never derived: a DID guessed from
# the domain would differ from the one the authority's wallet actually serves.
dataspace:
name: example-dataspace # ✏️ from the authority
authority:
did: did:web:authority.example.com:tenants:authority # ✏️ from the authority
domain: authority.example.com # ✏️ from the authority
credentialType: ExampleCredential # ✏️ from the authority
admin:
username: tsg # ✏️ your admin username
email: platform@my-org.example # ✏️ your admin email
# Referenced, never rendered. See step 3.
passwordSecret:
name: tsg-admin
key: password
stacks:
- id: my-org # ✏️ your unique id
name: My Organization # ✏️ your display name
host: dataspace.my-org.example # ✏️ your domain
# Everything on one host under path prefixes: one certificate, one DNS
# record. Use `subdomain` for a host per component instead.
routing: path
participantSeeds:
- id: my-org # ✏️ your unique id
name: My Organization # ✏️ your display name
preAuthorizedCodeSecret:
name: tsg-my-org-preauth
key: code
components:
# A wallet and an SSO bridge are always deployed. A control plane is
# what makes you able to trade data rather than only hold credentials.
controlPlane:
enabled: true
dataPlanes:
http-data-plane: {}
useCaseApps:
dataspace-starter: {}
Point DNS at your ingress address before deploying: certificate issuance and DID resolution both depend on the host resolving.
Step 3: Create the Secrets
Rendered manifests only reference credentials; they never contain them. Two Secrets are needed here: the initial administrator password, and the pre-authorized code the authority gave you.
For production, supply them with your own tooling — SOPS, Sealed Secrets,
External Secrets, plain kubectl. To get going:
kubectl create namespace tsg-my-org
kubectl -n tsg-my-org create secret generic tsg-my-org-preauth \
--from-literal=code=YOUR_CODE_HERE
# Generates the rest, and leaves anything that already exists untouched
tsg secrets generate participant.yaml --apply
Step 4: Review, then deploy
kubectl config current-context # make sure this is the right cluster
tsg diff participant.yaml # what would change
tsg deploy participant.yaml # do it
deploy renders the manifests, shows the diff, applies in ordered waves, waits
for each component to become ready, and prunes anything a previous deployment
left behind. Nothing is applied if a referenced Secret or a cluster prerequisite
is missing.
Step 5: Verify
kubectl get pods -n tsg-my-org
tsg status participant.yaml
Your interfaces:
- SSO Bridge:
https://dataspace.my-org.example/ - Wallet:
https://dataspace.my-org.example/wallet/ - Control Plane:
https://dataspace.my-org.example/control-plane/ - Data Plane:
https://dataspace.my-org.example/http-data-plane/ - Dataspace Starter:
https://dataspace.my-org.example/dataspace-starter/
Sign in to the SSO Bridge with the administrator credentials. For anything
beyond a test deployment, enable two-factor authentication there, and consider
switching confidential service clients to private_key_jwt.
Step 6: Publish an HTTP dataset
Open Dataspace Starter. The deployment supplies its service URLs and selects
my-org as the participant tenant. Sign in with your SSO Bridge account.
For shared stacks, select the participant whose catalog you want to manage.
Open Datasets, choose New dataset, and select the registered HTTP data plane. Enter a title and the backend URL reachable from the data plane. Supply an authorization header if the backend requires one. These backend settings are private. Add a public OpenAPI specification URL to enable the Tester, then publish. The HTTP data plane does not read datasets from startup configuration.
Use Own Catalog to check the entry. From another participant, discover the provider and use Tester to negotiate a transfer and issue an HTTP request. Check that the response contains the expected backend data. Ready pods alone do not verify credential issuance, negotiation or data access.
See Publishing datasets for SDK automation, versions, metadata edits and credential replacement.
Next steps
- Publish your data. Dataset Configuration describes how what you offer becomes a DCAT catalog entry.
- Explore the control plane. Browse catalogs, negotiate, and watch transfers from its web interface.
- Deploy a whole dataspace. The Deployment Guide covers the ecosystem shape, with an authority and several participants in one cluster.
- Harden it. The
Configuration Reference
covers
private_key_jwt, 2FA, per-stack databases and digest pinning.
Troubleshooting
A prerequisite is missing. tsg deploy names the CRD and prints the command
that installs it. These are cluster-admin operations; TSG never performs them.
A Secret is missing. The preflight lists every Secret and key it could not find, before anything is applied. Create them, then re-run.
A component does not become ready. Nothing was pruned and the inventory
still records both the previous and the desired objects, so fix the cause and
re-run — no reset is needed. kubectl logs -n tsg-my-org deploy/<name> usually
says why.
Certificates stay pending. Check that DNS resolves your host to the ingress
address, then kubectl describe certificate -n tsg-my-org.
More in the troubleshooting guide.