Skip to content

Support read/write of object data #2314

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
wants to merge 1 commit into from
Closed

Conversation

andriyko
Copy link

@andriyko andriyko commented Apr 9, 2025

This PR introduces object data support to SpiceDB, allowing storage and retrieval of arbitrary object metadata alongside relationships. This feature aims to solve the dual-write problem of maintaining consistency between SpiceDB and application databases.

Related PRs:
authzed/api#136
authzed/authzed-go#311

Background

Several feature requests in SpiceDB relate to the dual-write problem:

Features

  1. Storage Layer (Note: PostgreSQL only)

    • Added object_data table using PostgreSQL JSONB type
    • Implemented schema migration with appropriate indexes and constraints
    • Support for both resource and subject object metadata
    • Bulk operations with batch processing
  2. API Extensions

    • Added object data support to key PermissionsService APIs:
      • ReadRelationships
      • WriteRelationships
      • LookupResources
      • LookupSubjects
      • ImportBulkRelationships
      • ExportBulkRelationships
    • Maintained backward compatibility by making object_data optional
    • Uses protobuf Struct format for flexible data storage

Implementation Details

  • Object data is stored using PostgreSQL's JSONB type
  • Added indexes for query performance
  • Test coverage for new functionality

Migration

The changes are backward compatible:

  • Existing relationships remain unaffected
  • Object data is optional in all APIs
  • New schema migrations handle the addition of object_data table

Example Usage

Write schema

grpcurl -plaintext -H 'Authorization: Bearer somerandomkeyhere' -d '{
  "schema": "definition user {}\ndefinition document {\nrelation writer: user\nrelation viewer: user\npermission write = writer\npermission view = viewer + writer\n }"
}' localhost:50051 authzed.api.v1.SchemaService/WriteSchema

Write relationships

grpcurl -plaintext -H 'Authorization: Bearer somerandomkeyhere' -d '{
  "includeObjectData": true,
  "updates": [{
    "operation": "OPERATION_CREATE",
    "relationship": {
      "resource": {
        "objectType": "document",
        "objectId": "doc2",
        "objectData": {
          "metadata": {
            "size": 100240,
            "parent": {"folder": "folder1"}
          }
        }
      },
      "relation": "viewer",
      "subject": {
        "object": {
          "objectType": "user",
          "objectId": "bob",
          "objectData": {
            "name": "Bob",
            "email": "bob@user.com"
          }
        }
      }
    }
  }]
}' localhost:50051 authzed.api.v1.PermissionsService/WriteRelationships

Read relationships

grpcurl -plaintext -H 'Authorization: Bearer somerandomkeyhere' -d '{
  "includeObjectData": true,
  "relationshipFilter": {
    "resourceType": "document"
  }
}' localhost:50051 authzed.api.v1.PermissionsService/ReadRelationships

Lookup operations

grpcurl -plaintext -H 'Authorization: Bearer somerandomkeyhere' -d '{
  "includeObjectData": true,
  "resource": {
    "object_type": "document",
    "object_id": "doc1"
  },
  "permission": "view",
  "subject_object_type": "user"
}' localhost:50051 authzed.api.v1.PermissionsService/LookupSubjects

Export relationships

grpcurl -plaintext -H 'Authorization: Bearer somerandomkeyhere' -d '{
  "includeObjectData": true
}' localhost:50051 authzed.api.v1.PermissionsService/ExportBulkRelationships

Import relationships

grpcurl -plaintext -H 'Authorization: Bearer somerandomkeyhere' -d '{
  "relationships": [
    {
      "resource": {
        "objectType": "document",
        "objectId": "doc102",
        "objectData": {"name": "doc102"}
      },
      "relation": "viewer",
      "subject": {
        "object": {
          "objectType": "user",
          "objectId": "bob102",
          "objectData": {
            "email": "bob102@user.com",
            "name": "Bob102"
          }
        }
      }
    }
  ]
}' localhost:50051 authzed.api.v1.PermissionsService/ImportBulkRelationships

implement of object data storage
@andriyko andriyko requested a review from a team as a code owner April 9, 2025 15:55
Copy link

github-actions bot commented Apr 9, 2025

CLA Assistant Lite bot All contributors have signed the CLA ✍️ ✅

@github-actions github-actions bot added area/CLI Affects the command line area/api v1 Affects the v1 API area/datastore Affects the storage system area/dependencies Affects dependencies area/tooling Affects the dev or user toolchain (e.g. tests, ci, build tools) labels Apr 9, 2025
@andriyko
Copy link
Author

andriyko commented Apr 9, 2025

I have read the CLA Document and I hereby sign the CLA

@tstirrat15
Copy link
Contributor

How does this solve the dual-write problem? SpiceDB is not and will not be a good key/value store - it's optimized around the access patterns of permission checks. It won't make a good application database and we don't necessarily want to encourage folks using it that way.

@andriyko andriyko closed this Apr 14, 2025
@github-actions github-actions bot locked and limited conversation to collaborators Apr 14, 2025
@tstirrat15 tstirrat15 reopened this Apr 14, 2025
@tstirrat15
Copy link
Contributor

@andriyko I wanted to reopen this and say that we appreciate the work that you put into this and that my question was genuine - I don't want to dismiss what you've put forward out of hand.

@tstirrat15
Copy link
Contributor

I chatted with Andriy out of band - I do think this solves an interesting problem that SpiceDB doesn't otherwise have a solution for, which is using SpiceDB without dealing with the dual-write problem. Perhaps this idea could be turned into an optional extension of SpiceDB? I'm going to re-close in the meantime, though.

@tstirrat15 tstirrat15 closed this Apr 15, 2025
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
area/api v1 Affects the v1 API area/CLI Affects the command line area/datastore Affects the storage system area/dependencies Affects dependencies area/tooling Affects the dev or user toolchain (e.g. tests, ci, build tools)
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants