Service twin · API + UI
Google Drive
Test document agents that find, organize, edit, and share files across team drives.
API + UIspec-groundedREST · MCP · CLI
Terminal
$ uv tool install blobfish-cli
$ blobfish twin login
$ blobfish twin-runs create --twins googledrive --ttl 60 --waitWhat’s inside
A deterministic, seeded, resettable replica: every operation below executes real state transitions against the twin’s own SQLite state — reads are hash-invariant, writes produce inspectable diffs, and reset restores the seed baseline.
Seeded entities
| Entity | Table | Fields | About |
|---|---|---|---|
| about | abouts | 14 | Information about the user, the user's Drive, and system capabilities. |
| access_proposal | access_proposals | 7 | Manage outstanding access proposals on a file. |
| accessproposal | accessproposals | 6 | Inferred from operation parameters (spec has no named schema). |
| app | apps | 24 | The `apps` resource provides a list of apps that a user has installed, with information about each app's supported MIME types, file extensi… |
| app_list | app_lists | 5 | A list of third-party applications which the user has installed or given access to Google Drive. |
| approval | approvals | 10 | Metadata for an approval. An approval is a review or approve process for a Drive item. |
| approval_list | approval_lists | 4 | The response of an approvals list request. |
| approve_approval_request | approve_approval_requests | 2 | Request for approving an approval as a reviewer. |
| cancel_approval_request | cancel_approval_requests | 2 | Request for cancelling an approval as an initiator. |
| change | changes | 2 | Inferred from operation parameters (spec has no named schema). |
| change_list | change_lists | 5 | A list of changes for a user. |
| channel | channels | 10 | A notification channel used to watch for resource changes. |
| comment | comments | 14 | A comment on a file. Some resource methods (such as `comments.update`) require a `commentId`. Use the `comments.list` method to retrieve th… |
| comment_approval_request | comment_approval_requests | 2 | Request for commenting on an approval. |
| comment_list | comment_lists | 4 | A list of comments on a file. |
| decline_approval_request | decline_approval_requests | 2 | Request for declining an approval as a reviewer. |
| drive | drives | 12 | Representation of a shared drive. Some resource methods (such as `drives.update`) require a `driveId`. Use the `drives.list` method to retr… |
| drive_list | drive_lists | 4 | A list of shared drives. |
| file | files | 48 | The metadata for a file. Some resource methods (such as `files.update`) require a `fileId`. Use the `files.list` method to retrieve the ID … |
| file_list | file_lists | 5 | A list of files. |
| generate_cse_token_response | generate_cse_token_responses | 5 | JWT and associated metadata used to generate CSE files. |
| generated_id | generated_ids | 4 | A list of generated file IDs which can be provided in create requests. |
| label_list | label_lists | 4 | A list of labels applied to a file. |
| list_access_proposals_response | list_access_proposals_responses | 3 | The response to an access proposal list request. |
| modify_labels_request | modify_labels_requests | 3 | A request to modify the set of labels on a file. This request may contain many modifications that will either all succeed or all fail atomi… |
| modify_labels_response | modify_labels_responses | 3 | Response to a `ModifyLabels` request. This contains only those labels which were added or updated by the request. |
| operation | operations | 6 | This resource represents a long-running operation that is the result of a network API call. |
| permission | permissions | 16 | A permission for a file. A permission grants a user, group, domain, or the world access to a file or a folder hierarchy. For more informati… |
| permission_list | permission_lists | 4 | A list of permissions for a file. |
| reassign_approval_request | reassign_approval_requests | 4 | Request for reassigning an approval. Reviewers can be added or replaced, but not removed. |
| reply | replies | 11 | A reply to a comment on a file. Some resource methods (such as `replies.update`) require a `replyId`. Use the `replies.list` method to retr… |
| reply_list | reply_lists | 4 | A list of replies to a comment on a file. |
| resolve_access_proposal_request | resolve_access_proposal_requests | 5 | Request message for resolving an AccessProposal on a file. |
| revision | revisions | 14 | The metadata for a revision to a file. Some resource methods (such as `revisions.update`) require a `revisionId`. Use the `revisions.list` … |
| revision_list | revision_lists | 4 | A list of revisions of a file. |
| start_approval_request | start_approval_requests | 5 | Allows creating an approval on a file. |
| start_page_token | start_page_tokens | 3 | |
| team_drive | team_drives | 11 | Deprecated: use the drive collection instead. Next ID: 33 |
| team_drive_list | team_drive_lists | 4 | A list of Team Drives. |
| teamdrive | teamdrives | 2 | Inferred from operation parameters (spec has no named schema). |
Three surfaces, one state
Mount Google Drive in a twin environment and the same seeded state serves vendor-shaped REST operations, an MCP endpoint for tool calling, and a generated bf-twin CLI — with copy-on-write sessions per rollout and a one-call reset to the seed baseline. Prefer raw HTTP? The same create works with curl:
API
$ curl -sS -X POST https://blobfish.ai/api/v1/twin/environments \
-H "X-API-Key: $BLOBFISH_API_KEY" -H "Content-Type: application/json" \
-d '{"services":["googledrive"],"ttl_minutes":60}'Known limitations
Spec-grounded surface with synthetic seeded values; operations outside the spec are not mounted.