replicas-mcp 0.2.1 → 0.2.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -20,7 +20,7 @@ For MCP clients that require a remote server URL instead of stdio, use the strea
20
20
  }
21
21
  ```
22
22
 
23
- Get your API key from [Settings](https://tryreplicas.com/dashboard?section=platform-apikeys).
23
+ Get your API key from [Settings > API Keys](https://tryreplicas.com/dashboard/settings?tab=api-keys).
24
24
 
25
25
  ## Tools
26
26
 
package/dist/index.js CHANGED
@@ -7367,7 +7367,7 @@ var PLANS = {
7367
7367
  "Unlimited automations",
7368
7368
  "Higher API rate limits",
7369
7369
  "Warm pools and warm hooks",
7370
- "Auto-upgraded sandbox resources (32 GB disk, 16 GB memory)",
7370
+ "Auto-upgraded sandbox resources (4 vCPU, 32 GB disk, 16 GB memory)",
7371
7371
  "Shared Slack support channel"
7372
7372
  ]
7373
7373
  },
@@ -7398,6 +7398,1113 @@ var SANDBOX_LIFECYCLE = {
7398
7398
  AUTO_DELETE_MINUTES: -1,
7399
7399
  SSH_TOKEN_EXPIRATION_MINUTES: 3 * 60
7400
7400
  };
7401
+ function buildPaths(homeDir) {
7402
+ return {
7403
+ HOME_DIR: homeDir,
7404
+ WORKSPACES_DIR: `${homeDir}/workspaces`,
7405
+ REPLICAS_DIR: `${homeDir}/.replicas`,
7406
+ REPLICAS_FILES_DIR: `${homeDir}/.replicas/files`,
7407
+ REPLICAS_RUNTIME_ENV_FILE: `${homeDir}/.replicas/runtime-env.sh`
7408
+ };
7409
+ }
7410
+ var DAYTONA_PATHS = buildPaths("/home/ubuntu");
7411
+ var E2B_PATHS = buildPaths("/home/user");
7412
+
7413
+ // ../shared/src/default-skills/replicas-agent/abilities/docker.ts
7414
+ var SECTION = `### Docker
7415
+ Start and use the Docker daemon in Replicas workspaces. Docker is pre-installed but the daemon does not auto-start.
7416
+
7417
+ **Reference:** \`references/DOCKER.md\`
7418
+
7419
+ Use this when:
7420
+ - You need to run \`docker\` or \`docker compose\` commands
7421
+ - You need to build or run Docker containers
7422
+ - Your task involves containerized services or Docker-based workflows`;
7423
+ var REFERENCE = `# Docker
7424
+
7425
+ Docker is pre-installed in Replicas workspaces, but the daemon does **not** auto-start. You must start it manually before running any \`docker\` or \`docker compose\` commands.
7426
+
7427
+ ## Starting the Docker Daemon
7428
+
7429
+ \`\`\`bash
7430
+ sudo service docker start
7431
+ \`\`\`
7432
+
7433
+ After starting, verify the daemon is running:
7434
+
7435
+ \`\`\`bash
7436
+ docker info
7437
+ \`\`\`
7438
+
7439
+ ## Important Notes
7440
+
7441
+ - **Start once per session.** The daemon stays running until the workspace shuts down. You do not need to restart it between commands.
7442
+ - **Check before starting.** If you are unsure whether the daemon is already running, check first to avoid an unnecessary restart:
7443
+ \`\`\`bash
7444
+ docker info > /dev/null 2>&1 || sudo service docker start
7445
+ \`\`\`
7446
+ - **Sudo is required** for starting the daemon, but regular \`docker\` commands run without sudo (the user is in the \`docker\` group).
7447
+ `;
7448
+ var DOCKER_ABILITY = {
7449
+ label: "Docker",
7450
+ description: "Start the daemon, build/run containers, drive `docker compose`.",
7451
+ bullet: "- Using Docker (starting the daemon, running containers, docker compose)",
7452
+ section: SECTION,
7453
+ referenceFile: { name: "DOCKER.md", content: REFERENCE }
7454
+ };
7455
+
7456
+ // ../shared/src/default-skills/replicas-agent/abilities/github.ts
7457
+ var SECTION2 = `### GitHub
7458
+ Use the pre-authenticated \`gh\` CLI for pull requests, issues, actions, and API calls.
7459
+
7460
+ **Reference:** \`references/GITHUB.md\`
7461
+
7462
+ Use this when:
7463
+ - You need to create, review, or manage pull requests
7464
+ - You need to interact with GitHub issues or actions
7465
+ - You need to use the GitHub API for advanced operations
7466
+ - You need to include images in PR descriptions`;
7467
+ var REFERENCE2 = `# GitHub Integration
7468
+
7469
+ This guide covers how to interact with GitHub from within your Replicas workspace.
7470
+
7471
+ ## Prerequisites
7472
+
7473
+ The \`gh\` CLI is pre-installed and authenticated in your workspace. You can verify this:
7474
+
7475
+ \`\`\`bash
7476
+ gh auth status
7477
+ \`\`\`
7478
+
7479
+ If authenticated, you can immediately use \`gh\` for all GitHub operations. No additional setup is needed.
7480
+
7481
+ ## Using the \`gh\` CLI
7482
+
7483
+ The GitHub CLI (\`gh\`) is the recommended way to interact with GitHub. It handles authentication, pagination, and API formatting automatically.
7484
+
7485
+ ### Pull Requests
7486
+
7487
+ \`\`\`bash
7488
+ # Create a PR
7489
+ gh pr create --title "Title" --body "Description"
7490
+
7491
+ # List open PRs
7492
+ gh pr list
7493
+
7494
+ # View a specific PR
7495
+ gh pr view 123
7496
+
7497
+ # Review/check PR status
7498
+ gh pr checks 123
7499
+
7500
+ # Merge a PR
7501
+ gh pr merge 123
7502
+ \`\`\`
7503
+
7504
+ ### Issues
7505
+
7506
+ \`\`\`bash
7507
+ # Create an issue
7508
+ gh issue create --title "Title" --body "Description"
7509
+
7510
+ # View an issue
7511
+ gh issue view 123
7512
+
7513
+ # List issues
7514
+ gh issue list
7515
+
7516
+ # Close an issue
7517
+ gh issue close 123
7518
+
7519
+ # Add a comment
7520
+ gh issue comment 123 --body "Your comment"
7521
+ \`\`\`
7522
+
7523
+ ### Repository Operations
7524
+
7525
+ \`\`\`bash
7526
+ # View repo info
7527
+ gh repo view
7528
+
7529
+ # Clone a repo
7530
+ gh repo clone owner/repo
7531
+
7532
+ # List releases
7533
+ gh release list
7534
+ \`\`\`
7535
+
7536
+ ### GitHub Actions / Checks
7537
+
7538
+ \`\`\`bash
7539
+ # List workflow runs
7540
+ gh run list
7541
+
7542
+ # View a specific run
7543
+ gh run view RUN_ID
7544
+
7545
+ # Watch a run in progress
7546
+ gh run watch RUN_ID
7547
+
7548
+ # Re-run failed jobs
7549
+ gh run rerun RUN_ID --failed
7550
+ \`\`\`
7551
+
7552
+ ### GitHub API (Advanced)
7553
+
7554
+ For operations not covered by \`gh\` subcommands, use the API directly:
7555
+
7556
+ \`\`\`bash
7557
+ # GET request
7558
+ gh api repos/owner/repo/pulls/123/comments
7559
+
7560
+ # POST request
7561
+ gh api repos/owner/repo/issues/123/comments -f body="Comment text"
7562
+
7563
+ # GraphQL query
7564
+ gh api graphql -f query='{ repository(owner: "owner", name: "repo") { issues(first: 10) { nodes { title number } } } }'
7565
+ \`\`\`
7566
+
7567
+ ### Working with PR Reviews
7568
+
7569
+ \`\`\`bash
7570
+ # View PR comments
7571
+ gh api repos/owner/repo/pulls/123/comments
7572
+
7573
+ # View PR review comments
7574
+ gh api repos/owner/repo/pulls/123/reviews
7575
+
7576
+ # Submit a review
7577
+ gh pr review 123 --approve
7578
+ gh pr review 123 --request-changes --body "Changes needed"
7579
+ \`\`\`
7580
+
7581
+ ## Image Uploads in PRs
7582
+
7583
+ GitHub does NOT have a public API for uploading images to PRs/issues. When you need to include images:
7584
+ - Do NOT use placeholder image URLs
7585
+ - Do NOT commit screenshots as files to the repository
7586
+ - Upload images to Imgur (or another external host) and use the returned URLs in your PR markdown
7587
+ - If you were triggered from Slack, also upload the images to the Slack thread so the user can see them directly
7588
+ `;
7589
+ var GITHUB_ABILITY = {
7590
+ label: "GitHub",
7591
+ description: "Pre-authenticated `gh` CLI for PRs, issues, releases, and GraphQL.",
7592
+ bullet: "- Interacting with GitHub (creating PRs, managing issues, using the API, etc.)",
7593
+ section: SECTION2,
7594
+ referenceFile: { name: "GITHUB.md", content: REFERENCE2 }
7595
+ };
7596
+
7597
+ // ../shared/src/default-skills/replicas-agent/abilities/google.ts
7598
+ var SECTION3 = `### Google Workspace (Docs, Sheets, Forms, Drive)
7599
+ Create and edit Google Docs, Sheets, and Forms via the Replicas gateway. Files are owned by Replicas \u2014 the integration cannot access pre-existing Google content created outside of it.
7600
+
7601
+ **Reference:** \`references/GOOGLE.md\`
7602
+
7603
+ Use this when:
7604
+ - You need to create or edit a Google Doc, Sheet, or Form
7605
+ - You need to share, rename, move, or delete a Replicas-created Google file
7606
+ - You need to read responses from a Replicas-created Google Form`;
7607
+ var REFERENCE3 = `# Google Workspace (Docs, Sheets, Forms, Drive)
7608
+
7609
+ This guide covers how to create and edit Google Docs, Sheets, and Forms \u2014 plus do basic Drive file operations \u2014 from inside a Replicas workspace, using the monolith as a gateway to Google's APIs.
7610
+
7611
+ ## Prerequisites
7612
+
7613
+ The integration is configured at the org or user level by the Replicas admin. From inside a workspace you don't have a Google access token directly; instead you call the monolith's \`/v1/gdrive/*\` endpoints, authenticated with your workspace's engine secret. The monolith refreshes the org's (or user's) Google access token and proxies the call.
7614
+
7615
+ Quick check that the integration is connected:
7616
+
7617
+ \`\`\`bash
7618
+ curl -s -X GET "$MONOLITH_URL/v1/gdrive/credentials" \\
7619
+ -H "Authorization: Bearer $REPLICAS_ENGINE_SECRET" \\
7620
+ -H "X-Workspace-Id: $WORKSPACE_ID"
7621
+ \`\`\`
7622
+
7623
+ - If \`hasCredentials\` is \`true\`: you're good to go.
7624
+ - If \`hasCredentials\` is \`false\`: Google has not been connected for this org. Ask the user to go to **Settings \u2192 Integrations \u2192 Google** in the [Replicas dashboard](https://replicas.dev) and connect a Google account. Do not attempt Google operations until it's connected.
7625
+
7626
+ Standard auth headers used by every call below:
7627
+
7628
+ \`\`\`
7629
+ Authorization: Bearer $REPLICAS_ENGINE_SECRET
7630
+ X-Workspace-Id: $WORKSPACE_ID
7631
+ \`\`\`
7632
+
7633
+ For brevity the examples below use a shell variable:
7634
+
7635
+ \`\`\`bash
7636
+ GDRIVE_AUTH=(-H "Authorization: Bearer $REPLICAS_ENGINE_SECRET" -H "X-Workspace-Id: $WORKSPACE_ID")
7637
+ \`\`\`
7638
+
7639
+ ## Important constraint: drive.file scope
7640
+
7641
+ The integration uses the **sensitive-tier \`drive.file\` scope**. That means Replicas can only read and edit Google files **it created itself**. It **cannot**:
7642
+
7643
+ - Read or edit a user's pre-existing Google Docs, Sheets, or Forms \u2014 even ones that were shared with the connected Google account.
7644
+ - List or search the user's broader Drive.
7645
+ - Touch any file that was not created via these gateway endpoints.
7646
+
7647
+ If the user asks you to edit an existing doc that Replicas didn't create, tell them this constraint and offer to create a new doc that mirrors what they want.
7648
+
7649
+ ## Google Docs
7650
+
7651
+ ### Create a new doc
7652
+
7653
+ \`\`\`bash
7654
+ curl -s -X POST "$MONOLITH_URL/v1/gdrive/docs" "\${GDRIVE_AUTH[@]}" \\
7655
+ -H "Content-Type: application/json" \\
7656
+ -d '{"title":"Meeting notes 2026-05-14"}'
7657
+ \`\`\`
7658
+
7659
+ Returns the full Doc object; grab \`.documentId\` for follow-up calls.
7660
+
7661
+ ### Read a doc
7662
+
7663
+ \`\`\`bash
7664
+ curl -s "$MONOLITH_URL/v1/gdrive/docs/$DOC_ID" "\${GDRIVE_AUTH[@]}"
7665
+ \`\`\`
7666
+
7667
+ Returns the full document structure \u2014 \`body.content\` is an ordered list of structural elements (paragraphs, tables, etc.) with character indexes you can target for edits.
7668
+
7669
+ ### Edit a doc (batchUpdate)
7670
+
7671
+ The Docs API edits use a list of [structural requests](https://developers.google.com/workspace/docs/api/reference/rest/v1/documents/request). Insert text, then style it; or insert tables, images, page breaks, etc.
7672
+
7673
+ \`\`\`bash
7674
+ curl -s -X POST "$MONOLITH_URL/v1/gdrive/docs/$DOC_ID/batchUpdate" "\${GDRIVE_AUTH[@]}" \\
7675
+ -H "Content-Type: application/json" \\
7676
+ -d '{
7677
+ "requests": [
7678
+ { "insertText": { "location": { "index": 1 }, "text": "Hello, world!\\n" } }
7679
+ ]
7680
+ }'
7681
+ \`\`\`
7682
+
7683
+ Common request types:
7684
+
7685
+ - \`insertText\` \u2014 insert plain text at a given index
7686
+ - \`deleteContentRange\` \u2014 delete a range
7687
+ - \`replaceAllText\` \u2014 find-and-replace
7688
+ - \`updateTextStyle\` \u2014 bold/italic/colors/fonts/sizes for a range
7689
+ - \`updateParagraphStyle\` \u2014 headings (\`HEADING_1\`..\`HEADING_6\`), alignment, spacing
7690
+ - \`createParagraphBullets\` \u2014 turn paragraphs into bulleted/numbered lists
7691
+ - \`insertTable\` \u2014 insert a table
7692
+ - \`insertInlineImage\` \u2014 insert an image from a URL
7693
+
7694
+ Edits are verbose but powerful. Prefer batching many requests into a single \`batchUpdate\` call rather than making many round trips \u2014 it's faster and keeps the doc state consistent.
7695
+
7696
+ ## Google Sheets
7697
+
7698
+ ### Create a new spreadsheet
7699
+
7700
+ \`\`\`bash
7701
+ curl -s -X POST "$MONOLITH_URL/v1/gdrive/sheets" "\${GDRIVE_AUTH[@]}" \\
7702
+ -H "Content-Type: application/json" \\
7703
+ -d '{"title":"Q2 metrics"}'
7704
+ \`\`\`
7705
+
7706
+ Returns the full Spreadsheet object; grab \`.spreadsheetId\`.
7707
+
7708
+ ### Read a range of cells
7709
+
7710
+ \`\`\`bash
7711
+ # Range is in A1 notation, e.g. "Sheet1!A1:C10"
7712
+ curl -s "$MONOLITH_URL/v1/gdrive/sheets/$SHEET_ID/values/$(printf %s 'Sheet1!A1:C10' | jq -sRr @uri)" \\
7713
+ "\${GDRIVE_AUTH[@]}"
7714
+ \`\`\`
7715
+
7716
+ ### Write a range of cells
7717
+
7718
+ \`\`\`bash
7719
+ curl -s -X PUT \\
7720
+ "$MONOLITH_URL/v1/gdrive/sheets/$SHEET_ID/values/$(printf %s 'Sheet1!A1:B2' | jq -sRr @uri)?valueInputOption=USER_ENTERED" \\
7721
+ "\${GDRIVE_AUTH[@]}" \\
7722
+ -H "Content-Type: application/json" \\
7723
+ -d '{
7724
+ "range": "Sheet1!A1:B2",
7725
+ "majorDimension": "ROWS",
7726
+ "values": [
7727
+ ["Name", "Revenue"],
7728
+ ["Q1", "=SUM(B3:B100)"]
7729
+ ]
7730
+ }'
7731
+ \`\`\`
7732
+
7733
+ \`valueInputOption=USER_ENTERED\` makes formulas evaluate as if a human typed them. Use \`RAW\` to write literal strings.
7734
+
7735
+ ### Bulk operations (formatting, charts, new tabs, etc.)
7736
+
7737
+ \`\`\`bash
7738
+ curl -s -X POST "$MONOLITH_URL/v1/gdrive/sheets/$SHEET_ID/batchUpdate" "\${GDRIVE_AUTH[@]}" \\
7739
+ -H "Content-Type: application/json" \\
7740
+ -d '{ "requests": [ { "addSheet": { "properties": { "title": "Raw data" } } } ] }'
7741
+ \`\`\`
7742
+
7743
+ \`batchUpdate\` accepts an array of [Sheets API requests](https://developers.google.com/workspace/sheets/api/reference/rest/v4/spreadsheets/request) \u2014 addSheet, updateSheetProperties, repeatCell, addChart, autoResizeDimensions, etc.
7744
+
7745
+ ## Google Forms
7746
+
7747
+ ### Create a new form
7748
+
7749
+ \`\`\`bash
7750
+ curl -s -X POST "$MONOLITH_URL/v1/gdrive/forms" "\${GDRIVE_AUTH[@]}" \\
7751
+ -H "Content-Type: application/json" \\
7752
+ -d '{"title":"Customer feedback"}'
7753
+ \`\`\`
7754
+
7755
+ Returns the form. Grab \`.formId\`.
7756
+
7757
+ ### Add questions / edit form structure
7758
+
7759
+ The Forms API uses its own \`batchUpdate\`:
7760
+
7761
+ \`\`\`bash
7762
+ curl -s -X POST "$MONOLITH_URL/v1/gdrive/forms/$FORM_ID/batchUpdate" "\${GDRIVE_AUTH[@]}" \\
7763
+ -H "Content-Type: application/json" \\
7764
+ -d '{
7765
+ "requests": [
7766
+ {
7767
+ "createItem": {
7768
+ "item": {
7769
+ "title": "How likely are you to recommend us?",
7770
+ "questionItem": {
7771
+ "question": {
7772
+ "required": true,
7773
+ "scaleQuestion": { "low": 0, "high": 10, "lowLabel": "Not at all", "highLabel": "Very likely" }
7774
+ }
7775
+ }
7776
+ },
7777
+ "location": { "index": 0 }
7778
+ }
7779
+ }
7780
+ ]
7781
+ }'
7782
+ \`\`\`
7783
+
7784
+ See the [Forms API Request reference](https://developers.google.com/workspace/forms/api/reference/rest/v1/forms/request) for all supported request types \u2014 text questions, multiple choice, checkboxes, scale, grid, date, time, file upload, section breaks, branching logic, quiz settings, etc.
7785
+
7786
+ ### Read responses
7787
+
7788
+ \`\`\`bash
7789
+ curl -s "$MONOLITH_URL/v1/gdrive/forms/$FORM_ID/responses" "\${GDRIVE_AUTH[@]}"
7790
+ \`\`\`
7791
+
7792
+ Pagination: pass \`?pageToken=...&pageSize=...\` to walk through responses.
7793
+
7794
+ ## Drive operations (only on Replicas-created files)
7795
+
7796
+ ### Share a file with a person
7797
+
7798
+ \`\`\`bash
7799
+ curl -s -X POST "$MONOLITH_URL/v1/gdrive/files/$FILE_ID/permissions" "\${GDRIVE_AUTH[@]}" \\
7800
+ -H "Content-Type: application/json" \\
7801
+ -d '{
7802
+ "type": "user",
7803
+ "role": "writer",
7804
+ "emailAddress": "alice@example.com",
7805
+ "sendNotificationEmail": true
7806
+ }'
7807
+ \`\`\`
7808
+
7809
+ Roles: \`reader\`, \`commenter\`, \`writer\`. Types: \`user\`, \`group\`, \`domain\`, \`anyone\`.
7810
+
7811
+ ### Make a file viewable by anyone with the link
7812
+
7813
+ \`\`\`bash
7814
+ curl -s -X POST "$MONOLITH_URL/v1/gdrive/files/$FILE_ID/permissions" "\${GDRIVE_AUTH[@]}" \\
7815
+ -H "Content-Type: application/json" \\
7816
+ -d '{ "type": "anyone", "role": "reader" }'
7817
+ \`\`\`
7818
+
7819
+ ### List existing permissions
7820
+
7821
+ \`\`\`bash
7822
+ curl -s "$MONOLITH_URL/v1/gdrive/files/$FILE_ID/permissions" "\${GDRIVE_AUTH[@]}"
7823
+ \`\`\`
7824
+
7825
+ ### Rename / move a file
7826
+
7827
+ \`\`\`bash
7828
+ curl -s -X PATCH "$MONOLITH_URL/v1/gdrive/files/$FILE_ID" "\${GDRIVE_AUTH[@]}" \\
7829
+ -H "Content-Type: application/json" \\
7830
+ -d '{"name":"Final report.docx"}'
7831
+ \`\`\`
7832
+
7833
+ To move into a folder, also pass \`addParents\` and \`removeParents\` as query parameters per [Drive API docs](https://developers.google.com/workspace/drive/api/reference/rest/v3/files/update).
7834
+
7835
+ ### Get file metadata
7836
+
7837
+ \`\`\`bash
7838
+ curl -s "$MONOLITH_URL/v1/gdrive/files/$FILE_ID?fields=id,name,mimeType,webViewLink,parents,modifiedTime" \\
7839
+ "\${GDRIVE_AUTH[@]}"
7840
+ \`\`\`
7841
+
7842
+ \`webViewLink\` is the human-shareable URL that opens in Google Docs/Sheets/Forms.
7843
+
7844
+ ### Delete a file
7845
+
7846
+ \`\`\`bash
7847
+ curl -s -X DELETE "$MONOLITH_URL/v1/gdrive/files/$FILE_ID" "\${GDRIVE_AUTH[@]}"
7848
+ \`\`\`
7849
+
7850
+ ### List Replicas-created files
7851
+
7852
+ \`\`\`bash
7853
+ curl -s "$MONOLITH_URL/v1/gdrive/files?pageSize=50" "\${GDRIVE_AUTH[@]}"
7854
+ \`\`\`
7855
+
7856
+ Pass \`?q=...\` to filter using [Drive API search syntax](https://developers.google.com/workspace/drive/api/guides/search-files). Only files the app created or was granted access to will appear.
7857
+
7858
+ ## Tips
7859
+
7860
+ - **Always return the \`webViewLink\`** to the user when you create or edit a file so they can open it. Get it from \`/v1/gdrive/files/$FILE_ID?fields=webViewLink\` or from \`documents.documentId\` \u2192 \`https://docs.google.com/document/d/$ID/edit\`.
7861
+ - **Batch your edits.** A single \`batchUpdate\` with 20 requests beats 20 round-trips.
7862
+ - **Watch error responses.** A 412 from the gateway means the org has no Google credentials connected \u2014 tell the user to connect Google in the dashboard. Other 4xx responses come straight from Google and usually explain the issue clearly.
7863
+ `;
7864
+ var GOOGLE_ABILITY = {
7865
+ label: "Google Workspace",
7866
+ description: "Create / edit Docs, Sheets, Forms, and Drive files via the Replicas gateway.",
7867
+ bullet: "- Interacting with Google Workspace (creating and editing Docs, Sheets, and Forms, sharing files, reading form responses, etc.)",
7868
+ section: SECTION3,
7869
+ referenceFile: { name: "GOOGLE.md", content: REFERENCE3 }
7870
+ };
7871
+
7872
+ // ../shared/src/default-skills/replicas-agent/abilities/linear.ts
7873
+ var SECTION4 = `### Linear
7874
+ Fetch issues, update state, add comments, and search via the Linear GraphQL API.
7875
+
7876
+ **Reference:** \`references/LINEAR.md\`
7877
+
7878
+ Use this when:
7879
+ - You encounter a Linear issue link and need to understand the task
7880
+ - You need to update an issue's state (e.g. mark as done)
7881
+ - You need to comment on or search for Linear issues`;
7882
+ var REFERENCE4 = `# Linear Integration
7883
+
7884
+ This guide covers how to interact with Linear from within your Replicas workspace.
7885
+
7886
+ ## Prerequisites
7887
+
7888
+ Check if the \`LINEAR_ACCESS_TOKEN\` environment variable is set:
7889
+
7890
+ \`\`\`bash
7891
+ echo "\${LINEAR_ACCESS_TOKEN:+set}"
7892
+ \`\`\`
7893
+
7894
+ - If **set**: Your workspace has Linear access. You can use the Linear GraphQL API as described below.
7895
+ - If **not set**: Linear has not been configured for this workspace. The user needs to connect Linear in the [Replicas dashboard](https://replicas.dev) under their organization's integration settings. Let the user know and do not attempt Linear operations.
7896
+
7897
+ ## Using the Linear API
7898
+
7899
+ Linear uses a GraphQL API at \`https://api.linear.app/graphql\`. All requests use the \`$LINEAR_ACCESS_TOKEN\` for authentication.
7900
+
7901
+ ### Fetching an Issue
7902
+
7903
+ If you encounter a Linear issue link (e.g. \`https://linear.app/team/issue/ENG-123\`), the identifier is the last path segment (\`ENG-123\`).
7904
+
7905
+ \`\`\`bash
7906
+ curl -s -X POST https://api.linear.app/graphql \\
7907
+ -H "Authorization: Bearer $LINEAR_ACCESS_TOKEN" \\
7908
+ -H "Content-Type: application/json" \\
7909
+ -d '{
7910
+ "query": "query { issues(filter: { identifier: { eq: \\"ENG-123\\" } }) { nodes { id identifier title description state { name } assignee { name } parent { identifier title description } } } }"
7911
+ }'
7912
+ \`\`\`
7913
+
7914
+ ### Updating Issue State
7915
+
7916
+ \`\`\`bash
7917
+ curl -s -X POST https://api.linear.app/graphql \\
7918
+ -H "Authorization: Bearer $LINEAR_ACCESS_TOKEN" \\
7919
+ -H "Content-Type: application/json" \\
7920
+ -d '{
7921
+ "query": "mutation { issueUpdate(id: \\"ISSUE_UUID\\", input: { stateId: \\"STATE_UUID\\" }) { success issue { identifier state { name } } } }"
7922
+ }'
7923
+ \`\`\`
7924
+
7925
+ To find available states, query: \`query { workflowStates { nodes { id name } } }\`
7926
+
7927
+ ### Adding a Comment
7928
+
7929
+ \`\`\`bash
7930
+ curl -s -X POST https://api.linear.app/graphql \\
7931
+ -H "Authorization: Bearer $LINEAR_ACCESS_TOKEN" \\
7932
+ -H "Content-Type: application/json" \\
7933
+ -d '{
7934
+ "query": "mutation { commentCreate(input: { issueId: \\"ISSUE_UUID\\", body: \\"Your comment here\\" }) { success comment { id } } }"
7935
+ }'
7936
+ \`\`\`
7937
+
7938
+ ### Searching Issues
7939
+
7940
+ \`\`\`bash
7941
+ curl -s -X POST https://api.linear.app/graphql \\
7942
+ -H "Authorization: Bearer $LINEAR_ACCESS_TOKEN" \\
7943
+ -H "Content-Type: application/json" \\
7944
+ -d '{
7945
+ "query": "query { issueSearch(query: \\"search terms\\", first: 10) { nodes { identifier title state { name } } } }"
7946
+ }'
7947
+ \`\`\`
7948
+
7949
+ ### Other Operations
7950
+
7951
+ The Linear GraphQL API supports creating issues, managing projects, labels, cycles, and more. For the full schema and documentation, see: https://developers.linear.app/docs/graphql/working-with-the-graphql-api
7952
+ `;
7953
+ var LINEAR_ABILITY = {
7954
+ label: "Linear",
7955
+ description: "Fetch issues, post comments, update states via the Linear GraphQL API.",
7956
+ bullet: "- Interacting with Linear (fetching issues, updating state, commenting, etc.)",
7957
+ section: SECTION4,
7958
+ referenceFile: { name: "LINEAR.md", content: REFERENCE4 }
7959
+ };
7960
+
7961
+ // ../shared/src/default-skills/replicas-agent/abilities/media.ts
7962
+ var SECTION5 = `### Media
7963
+ Share screenshots, screen recordings, generated diagrams, and audio clips inline in the Replicas chat (and as references in external messages).
7964
+
7965
+ **Reference:** \`references/MEDIA.md\`
7966
+
7967
+ Use this when:
7968
+ - You produce a screenshot, recording, generated image, or audio clip the user should see
7969
+ - You record video output (browser automation, screen capture) \u2014 including the recommended aspect ratio and FPS
7970
+ - You need to embed media in a Slack/Linear/GitHub message AND keep a referenceable copy in the Replicas dashboard`;
7971
+ var REFERENCE5 = `# Media (Screenshots, Recordings, Audio)
7972
+
7973
+ This guide covers how to share screenshots, screen recordings, generated diagrams, and audio clips with the user inline in the Replicas chat.
7974
+
7975
+ ## Prerequisites
7976
+
7977
+ The \`replicas\` CLI is pre-installed and authenticated in your workspace. No additional setup is needed.
7978
+
7979
+ ## When to upload
7980
+
7981
+ Upload to Replicas in these cases \u2014 and **only** these cases:
7982
+
7983
+ 1. **Media you produce.** Any screenshot, screen recording, generated diagram, or audio clip you create that the user might want to see. Upload before doing anything else with the file (analyzing, deleting, sending elsewhere). This applies even when you're also sending the file to Slack, Linear, GitHub, etc.
7984
+ 2. **Files the user explicitly asks you to upload.** If the user sends or points at a file (image, video, audio) and asks you to upload it, run \`replicas media upload\`. Otherwise leave it alone \u2014 files in the workspace the user did not ask about should not be auto-uploaded as media.
7985
+ 3. **Anything you plan to share externally (Slack, Linear, GitHub, etc.).** Upload to Replicas *in addition to* the platform's native upload. Never as a replacement.
7986
+
7987
+ If none of these apply, don't upload.
7988
+
7989
+ ## Uploading
7990
+
7991
+ \`\`\`bash
7992
+ replicas media upload <path-to-file> [<path-to-file> ...]
7993
+ \`\`\`
7994
+
7995
+ Pass one or more file paths. Uploading several files in a single invocation is preferred over running the command repeatedly \u2014 it's faster and keeps the output grouped.
7996
+
7997
+ For each file, the CLI prints two lines:
7998
+
7999
+ 1. \`![filename](<api-url>)\` \u2014 the chat embed (renders inline in Replicas chat only; see below).
8000
+ 2. \`View in Replicas: <deep-link>\` \u2014 a per-file dashboard URL of the form \`https://tryreplicas.com/workspaces/<workspace-id>?mode=media&media=<media-id>\` that opens directly to that specific file.
8001
+
8002
+ Match each "View in Replicas" line to the embed line directly above it \u2014 that's the deep link for that file.
8003
+
8004
+ ## How to use the output
8005
+
8006
+ ### CRITICAL: the markdown embed URL is for Replicas chat only
8007
+
8008
+ The URL inside \`![filename](...)\` points at \`api.tryreplicas.com/v1/media/<id>\`. This is **not a public URL** \u2014 it requires the Replicas chat's authenticated session, which resolves it to a presigned download. Anywhere else (Slack, Linear, GitHub, a browser tab the user opens directly, a customer copy-pasting from chat), it returns \`{"error":"Missing authorization token"}\` and renders as a broken image.
8009
+
8010
+ **Never paste this URL outside your Replicas chat reply.** Not in Slack messages, not in Linear comments, not in PR descriptions or commit messages, not in external docs \u2014 nowhere a non-Replicas surface will render it.
8011
+
8012
+ ### Always render dashboard URLs as \`[View in Replicas](<url>)\` hyperlinks
8013
+
8014
+ Whenever you share a workspace dashboard URL \u2014 in chat or anywhere else \u2014 format it as a markdown hyperlink labeled **View in Replicas**:
8015
+
8016
+ \`\`\`markdown
8017
+ [View in Replicas](https://tryreplicas.com/workspaces/<workspace-id>?mode=media&media=<media-id>)
8018
+ \`\`\`
8019
+
8020
+ Never paste the raw URL. Raw URLs look unpolished.
8021
+
8022
+ Two flavors of dashboard URL the CLI gives you:
8023
+
8024
+ - **Per-file deep link** (default \u2014 what \`replicas media upload\` prints): \`...?mode=media&media=<media-id>\` opens the dashboard scrolled to that specific file. Use this whenever you're linking to *one* file.
8025
+ - **Media tab link** (no \`media=\` param): \`...?mode=media\` opens the workspace's media tab listing all files. Use this only when you're pointing at the collection, not a specific file (rare \u2014 you almost always have a specific file in mind).
8026
+
8027
+ ### In your Replicas chat reply
8028
+
8029
+ Include each markdown embed line **verbatim** where you want that file to render inline. The chat substitutes each one with an embedded image, video, or audio player. Multiple embeds can appear in a single reply.
8030
+
8031
+ After (or alongside) the embeds, include a \`[View in Replicas](<deep-link>)\` hyperlink for each file using the per-file URL the CLI printed for that file. This lets the user jump to the specific item in the media tab.
8032
+
8033
+ ### On external platforms (Slack, Linear, GitHub, etc.)
8034
+
8035
+ Do **both** of these \u2014 neither alone is sufficient:
8036
+
8037
+ 1. Upload the raw bytes via that platform's own upload API (Slack \`files.upload\`, Linear attachments, Imgur for GitHub PR/issue images, etc.) so the recipient actually sees the media.
8038
+ 2. Include a \`[View in Replicas](<deep-link>)\` hyperlink \u2014 use the per-file deep link the CLI printed for that file (\`...?mode=media&media=<media-id>\`), so the recipient lands directly on that specific item.
8039
+
8040
+ Do **not** include the \`![filename](https://api.tryreplicas.com/...)\` markdown embed in external messages. It will render as a broken image / 401 for the recipient.
8041
+
8042
+ ## Recording defaults
8043
+
8044
+ When you record video (browser automation, screen capture, etc.):
8045
+
8046
+ - **Aspect ratio:** 16:9 (1920\xD71080 or 1280\xD7720)
8047
+ - **Frame rate:** 60 FPS or whatever the user specifies
8048
+
8049
+ Tools like Playwright default to a low frame rate that produces choppy playback \u2014 explicitly configure recording dimensions and FPS:
8050
+
8051
+ \`\`\`ts
8052
+ const context = await browser.newContext({
8053
+ recordVideo: { dir: './videos', size: { width: 1280, height: 720 } },
8054
+ });
8055
+ \`\`\`
8056
+
8057
+ For \`ffmpeg\` screen captures, pass \`-r 30\` (or \`-r 60\`) to set the frame rate.
8058
+
8059
+ ## Supported formats
8060
+
8061
+ Auto-detected from the filename extension:
8062
+
8063
+ | Extension | Kind |
8064
+ |---|---|
8065
+ | \`png\`, \`jpg\`, \`jpeg\`, \`webp\` | image |
8066
+ | \`mp4\`, \`webm\` | video |
8067
+ | \`mp3\`, \`wav\` | audio |
8068
+
8069
+ For other extensions, pass \`--kind image|video|audio\` explicitly. The kind applies to every file in that invocation, so group files of the same kind together:
8070
+
8071
+ \`\`\`bash
8072
+ replicas media upload diagram.svg --kind image
8073
+ replicas media upload chart-a.svg chart-b.svg --kind image
8074
+ \`\`\`
8075
+
8076
+ ## Options
8077
+
8078
+ - \`--kind <image|video|audio>\` \u2014 override auto-detection
8079
+ - \`--session-id <id>\` \u2014 associate the upload with a specific session
8080
+ `;
8081
+ var MEDIA_ABILITY = {
8082
+ label: "Media",
8083
+ description: "Share screenshots, recordings, generated images, and audio clips.",
8084
+ bullet: "- Sharing media (screenshots, screen recordings, generated diagrams, audio clips) \u2014 including in your Replicas chat reply and to external platforms",
8085
+ section: SECTION5,
8086
+ referenceFile: { name: "MEDIA.md", content: REFERENCE5 }
8087
+ };
8088
+
8089
+ // ../shared/src/default-skills/replicas-agent/abilities/previews.ts
8090
+ var SECTION6 = `### Previews
8091
+ Expose locally running services (web apps, APIs, databases) as public preview URLs so humans can interact with them directly.
8092
+
8093
+ **Reference:** \`references/PREVIEWS.md\`
8094
+
8095
+ Use this when:
8096
+ - You need to start a service that a human should view or interact with
8097
+ - The task involves UI work that benefits from human review
8098
+ - You are verifying frontend/backend integrations visually`;
8099
+ var REFERENCE6 = `# Preview URLs
8100
+
8101
+ When you run services on ports \u2014 such as a web app, API server, or database \u2014 humans may want to interact with them directly. You can expose your locally running services as public preview URLs.
8102
+
8103
+ ## Running Services for Preview
8104
+
8105
+ Services must run as detached background processes so they survive after your command session ends. Do not leave them attached to a foreground terminal.
8106
+
8107
+ Some potential methods:
8108
+ \`\`\`bash
8109
+ # Start a detached service with logging
8110
+ setsid -f bash -lc 'cd /path/to/app && exec yarn dev >> /tmp/app.log 2>&1'
8111
+
8112
+ # For daemons like Docker
8113
+ nohup dockerd > /tmp/dockerd.log 2>&1 &
8114
+ \`\`\`
8115
+
8116
+ After starting a service:
8117
+ 1. Verify the process is running: \`pgrep -af 'yarn dev'\`
8118
+ 2. Check logs for readiness: \`tail -f /tmp/app.log\`
8119
+ 3. Confirm it's actually serving: \`curl -s http://localhost:3000\` (or appropriate health check)
8120
+ 4. Only create the preview after the service is healthy
8121
+
8122
+ If a prior detached process exists on the same port, stop it before restarting.
8123
+
8124
+ ## Creating Previews
8125
+
8126
+ \`\`\`bash
8127
+ # Expose a local port as a public URL
8128
+ replicas preview create <port>
8129
+
8130
+ # Expose a port with authentication (requires Replicas login to access)
8131
+ replicas preview create <port> --authenticated
8132
+
8133
+ # List all active preview URLs
8134
+ replicas preview list
8135
+ \`\`\`
8136
+
8137
+ The \`create\` command prints the public URL. You can also read all active previews from \`~/.replicas/preview-ports.json\`.
8138
+
8139
+ ## Authenticated vs Unauthenticated Previews
8140
+
8141
+ Previews can optionally require cookie-based authentication. When \`--authenticated\` is set, only users who are logged in to replicas.dev can access the preview.
8142
+
8143
+ **When to use \`--authenticated\`:**
8144
+ - Frontends / web apps that humans will view directly in their browser. Since the user is already logged in to replicas.dev, the auth cookie is automatically present and the preview works seamlessly.
8145
+
8146
+ **When NOT to use \`--authenticated\`:**
8147
+ - Backend APIs and other services that are called by frontend code. The frontend runs in the user's browser under a different origin, so it cannot forward the Replicas auth cookie to the backend. Making backends authenticated will cause cross-service requests to fail with 401 errors.
8148
+
8149
+ **Rule of thumb:** Make frontend previews authenticated, leave backend/API previews unauthenticated.
8150
+
8151
+ ## Cross-Service References
8152
+
8153
+ When you expose multiple services that reference each other, you must update their configuration so they use preview URLs instead of \`localhost\`.
8154
+
8155
+ **Example:** You run a React frontend on port 3000 that makes API calls to a backend on port 8585.
8156
+
8157
+ 1. Create previews for both:
8158
+ \`\`\`bash
8159
+ replicas preview create 8585
8160
+ # Output: https://8585-<hash>.replicas.dev
8161
+ replicas preview create 3000 --authenticated
8162
+ # Output: https://3000-<hash>.replicas.dev
8163
+ \`\`\`
8164
+
8165
+ 2. Update the frontend's environment so its API base URL points to the backend's **preview URL**, not \`localhost:8585\`. For example, set \`REACT_APP_API_URL=https://8585-<hash>.replicas.dev\` or update the relevant config file.
8166
+
8167
+ **Why?** The frontend works on \`localhost\` for you because both services run on the same machine. But a human viewing the preview is on a different machine \u2014 requests to \`localhost:8585\` from their browser will fail. They need the public preview URL instead.
8168
+
8169
+ ## When to Create Previews
8170
+
8171
+ - After starting any service that a human should be able to view or interact with
8172
+ - When verifying frontend/backend integrations visually
8173
+ - When the task involves UI work that benefits from human review
8174
+
8175
+ It is your responsibility to make previews work for outsiders as well as they work for you on localhost. If at any time you need to see the public URLs that have been created, read \`~/.replicas/preview-ports.json\`.
8176
+ `;
8177
+ var PREVIEWS_ABILITY = {
8178
+ label: "Previews",
8179
+ description: "Expose locally running services on public preview URLs for humans.",
8180
+ bullet: "- Creating preview URLs for locally running services",
8181
+ section: SECTION6,
8182
+ referenceFile: { name: "PREVIEWS.md", content: REFERENCE6 }
8183
+ };
8184
+
8185
+ // ../shared/src/default-skills/replicas-agent/abilities/replicas.ts
8186
+ var SECTION7 = `### Replicas (in-workspace CLI)
8187
+ Take action *with* Replicas itself \u2014 manage automations, environments (variables, files), repos, and \`replicas.json\` config \u2014 using the pre-installed, pre-authenticated \`replicas\` CLI.
8188
+
8189
+ **Reference:** \`references/REPLICAS.md\`
8190
+
8191
+ Use this when:
8192
+ - The user asks you to create, edit, run, or delete an automation
8193
+ - The user asks you to manage environments, environment variables, or environment files
8194
+ - The user asks "what envs / repos / automations do I have?"
8195
+ - The user asks you to scaffold a \`replicas.json\` / \`replicas.yaml\` in a repo`;
8196
+ var REFERENCE7 = `# Replicas (in-workspace CLI)
8197
+
8198
+ This guide covers how to take action *with* Replicas itself from inside a Replicas workspace \u2014 managing automations, environments (and their variables/files), repos, previews, and the user's \`replicas.json\` config \u2014 using the pre-installed \`replicas\` CLI.
8199
+
8200
+ When the user asks _about_ Replicas (concepts, pricing, how a feature works), check https://docs.replicas.dev first. When the user asks you to _do_ something in their Replicas org, this is the file to use.
8201
+
8202
+ ## Prerequisites
8203
+
8204
+ The CLI is pre-installed in every workspace and pre-authenticated using the workspace's engine secret. You do **not** need to log in or set an API key. Verify:
8205
+
8206
+ \`\`\`bash
8207
+ replicas whoami
8208
+ \`\`\`
8209
+
8210
+ Expected output (in agent mode):
8211
+
8212
+ \`\`\`
8213
+ Workspace identity:
8214
+ Workspace ID: <uuid>
8215
+ Organization ID: <uuid>
8216
+ \`\`\`
8217
+
8218
+ If you get "Not logged in", the workspace is misconfigured \u2014 surface this to the user instead of trying to work around it.
8219
+
8220
+ In agent mode the CLI hides commands that don't make sense for in-workspace agents (\`login\`, \`logout\`, \`codex-auth\`, \`claude-auth\`, \`org switch\`, \`config\`, \`interact\`, \`code\`, replica/workspace top-level CRUD). What you have is:
8221
+
8222
+ | Command | What it does |
8223
+ | --- | --- |
8224
+ | \`replicas whoami\` | Print the workspace + org identity |
8225
+ | \`replicas init\` | Create a \`replicas.json\` / \`replicas.yaml\` in the current directory |
8226
+ | \`replicas connect <name>\` | SSH into another workspace (requires user creds \u2014 usually only useful when scripting locally) |
8227
+ | \`replicas repos\` | List repos connected to the org |
8228
+ | \`replicas environment ...\` | Manage environments, env vars, env files |
8229
+ | \`replicas automation ...\` | Manage automations (cron + GitHub event triggers) |
8230
+ | \`replicas preview ...\` | Register / list preview URLs (covered in \`PREVIEWS.md\`) |
8231
+ | \`replicas media ...\` | Upload screenshots, videos, audio (covered in \`MEDIA.md\`) |
8232
+
8233
+ \`replicas <command> --help\` is always the source of truth for flags.
8234
+
8235
+ ## Picking the right command for the user's request
8236
+
8237
+ | User says... | Run |
8238
+ | --- | --- |
8239
+ | "What environments do I have?" | \`replicas environment list\` |
8240
+ | "Add API key X to my staging env" | \`replicas environment vars set <env> <KEY> <VALUE>\` |
8241
+ | "Make me a \`.env\` file in the workspace with these vars" | \`replicas environment files set <env> .env --content "..."\` |
8242
+ | "Create a new env for my \`acme/web\` repo" | \`replicas environment create <name> -r acme/web\` |
8243
+ | "What automations do I have?" | \`replicas automation list\` |
8244
+ | "Run my nightly automation now" | \`replicas automation run <id>\` |
8245
+ | "Make an automation that runs every weekday at 9am" | \`replicas automation create\` (interactive) or \`--trigger-cron "0 9 * * 1-5"\` |
8246
+ | "Make an automation that runs when a PR opens on \`acme/web\`" | \`replicas automation create ... --trigger-github pull_request.opened --trigger-github-repos acme/web\` |
8247
+ | "What repos are connected?" | \`replicas repos\` |
8248
+ | "Set up a \`replicas.json\` in this repo" | \`replicas init\` (\`-y\` for YAML) |
8249
+
8250
+ ## Environments
8251
+
8252
+ Environments are the org-scoped *primitives* workspaces are built from. Each environment can bind to one repository (or repository set), carry environment variables, project files, enabled skills, and MCP servers. The \`Global\` environment is special \u2014 its vars/files/skills/MCPs apply to *every* workspace in the org, but it has no repo binding and can't back a workspace on its own.
8253
+
8254
+ ### List / get / create / edit / delete
8255
+
8256
+ \`\`\`bash
8257
+ replicas environment list
8258
+ replicas environment get <id-or-name> # use "global" for the Global env
8259
+ replicas environment create [name] \\
8260
+ --description "..." \\
8261
+ --repository <repo-name-or-id> \\
8262
+ --system-prompt "..."
8263
+ replicas environment edit <id-or-name> \\
8264
+ --name "..." --description "..." \\
8265
+ --repository <repo-name-or-id> # pass empty string to unbind
8266
+ replicas environment delete <id-or-name> [--force]
8267
+ \`\`\`
8268
+
8269
+ Notes:
8270
+ - Environments resolve by **name or UUID**. \`global\` is an alias for the org's Global env.
8271
+ - Non-global envs need a repo (or repo set) to back a workspace. If you \`create\` without \`--repository\`, the CLI prompts; in non-interactive contexts pass \`-r\`.
8272
+ - \`edit\` on the Global env is rejected by the API \u2014 manage its contents through the \`vars\` / \`files\` subcommands instead.
8273
+
8274
+ ### Environment variables
8275
+
8276
+ \`\`\`bash
8277
+ replicas environment vars list <env>
8278
+ replicas environment vars set <env> <KEY> <VALUE> # upsert (create or update)
8279
+ replicas environment vars delete <env> <KEY|VARIABLE_ID> [--force]
8280
+ \`\`\`
8281
+
8282
+ \`vars set\` is upsert: if a variable with that key already exists, it's updated; otherwise created. The CLI accepts either the variable's \`key\` or its UUID for \`delete\`.
8283
+
8284
+ These variables are injected into every workspace built from this environment as actual \`env\` vars \u2014 perfect for API keys, feature flags, etc. Anything you want available to the agent's tools (Claude, codex, your code, etc.) goes here.
8285
+
8286
+ ### Environment files
8287
+
8288
+ Files materialize on the workspace filesystem when a workspace starts, at the destination path you specify. Use this for things like \`.env\` files at the repo root, dotfiles in \`~\`, prompt files for agents, etc.
8289
+
8290
+ \`\`\`bash
8291
+ replicas environment files list <env>
8292
+ replicas environment files set <env> <destination-path> --content "..." # inline
8293
+ replicas environment files set <env> <destination-path> --file <local-path> # from local file
8294
+ replicas environment files set <env> <destination-path> --file <local-path> --name "Friendly name"
8295
+ replicas environment files delete <env> <destination-path|FILE_ID> [--force]
8296
+ \`\`\`
8297
+
8298
+ Constraints:
8299
+ - Each file is capped at 64KB.
8300
+ - \`set\` is upsert (matched by destination path).
8301
+ - The display \`--name\` defaults to the basename of the destination path; override only if it would be unclear in the dashboard list.
8302
+
8303
+ ## Automations
8304
+
8305
+ Automations are saved prompts with one or more triggers (cron schedules and/or GitHub events). When fired, they create a workspace using the configured environment and run the prompt with the user's coding agent.
8306
+
8307
+ ### List / get / run / delete
8308
+
8309
+ \`\`\`bash
8310
+ replicas automation list
8311
+ replicas automation get <id>
8312
+ replicas automation run <id> # cron-triggered automations only
8313
+ replicas automation delete <id> [--force]
8314
+ \`\`\`
8315
+
8316
+ ### Create
8317
+
8318
+ Either fully flag-driven or fully interactive \u2014 the CLI prompts for anything you don't pass.
8319
+
8320
+ \`\`\`bash
8321
+ # Cron trigger
8322
+ replicas automation create "Nightly typecheck" \\
8323
+ --prompt "Run \\\`bun typecheck\\\` and report any new errors" \\
8324
+ --environment <env-name-or-id> \\
8325
+ --trigger-cron "0 4 * * *" \\
8326
+ --trigger-cron-timezone "America/New_York"
8327
+
8328
+ # GitHub trigger (filter to specific repos)
8329
+ replicas automation create "Review my PRs" \\
8330
+ --prompt "Leave a code review on this PR" \\
8331
+ --environment <env-name-or-id> \\
8332
+ --trigger-github pull_request.opened \\
8333
+ --trigger-github-repos acme/web,acme/api
8334
+
8335
+ # Disable on creation
8336
+ replicas automation create ... --disabled
8337
+
8338
+ # Workspace lifecycle
8339
+ replicas automation create ... --lifecycle delete_when_done
8340
+ replicas automation create ... --lifecycle delete_after_inactivity --auto-stop-minutes 30
8341
+ \`\`\`
8342
+
8343
+ When the user says "make me an automation that...", default to **picking the environment for them by listing the available envs** and asking only when the user hasn't already pinned one. Same for repos in GitHub triggers. Don't pepper the user with questions you can answer by reading the existing config.
8344
+
8345
+ ### Edit
8346
+
8347
+ \`\`\`bash
8348
+ replicas automation edit <id> \\
8349
+ --name "..." \\
8350
+ --prompt "..." \\
8351
+ --enabled true|false \\
8352
+ --environment <env-name-or-id> \\
8353
+ --trigger-cron "0 4 * * *" # replaces existing triggers
8354
+ \`\`\`
8355
+
8356
+ \`replicas automation edit <id>\` with no flags drops into interactive mode.
8357
+
8358
+ ## Repositories
8359
+
8360
+ Read-only listing of repos connected to the org. Use when the user asks "what repos can I use?", or to validate a \`--repository\` value before passing it to \`environment create\` / \`automation create\`:
8361
+
8362
+ \`\`\`bash
8363
+ replicas repos
8364
+ \`\`\`
8365
+
8366
+ Repos are connected via the GitHub integration in the dashboard \u2014 not from the CLI. If the user wants a repo connected, point them at the dashboard rather than trying to do it yourself.
8367
+
8368
+ ## \`replicas.json\` / \`replicas.yaml\`
8369
+
8370
+ \`replicas init\` creates a starter config in the current directory. \`-y\` writes YAML, \`-f\` overwrites an existing file. This file controls per-repo workspace setup (warm hooks, start hooks, organization scoping for GitHub triggers). When the user asks to "set up Replicas in this repo", run \`replicas init\` and then edit the generated file based on what they need.
8371
+
8372
+ ## When NOT to use the CLI
8373
+
8374
+ - **Don't use the CLI to reach into other tools' state** (Linear, Slack, GitHub) \u2014 those have dedicated skill references in this directory.
8375
+ - **Don't try to install Replicas, log in, or switch orgs** \u2014 those flows are user-facing and aren't available in agent mode anyway.
8376
+ - **Don't create workspaces** from inside an existing workspace just to run a command. You're already in one.
8377
+
8378
+ ## Common errors
8379
+
8380
+ - \`Missing Replicas-Org-Id header\` \u2192 the workspace is hitting an older monolith that doesn't yet recognize agent auth on this endpoint. Surface this to the user; don't try to work around it by faking headers.
8381
+ - \`Workspace not found\` \u2192 the workspace was deleted while you were running. Stop and tell the user.
8382
+ - \`An environment with this name already exists\` \u2192 use \`environment edit\` instead, or pick a different name.
8383
+ - \`Cannot delete the global environment\` \u2192 there is exactly one Global env per org and it's permanent. Manage its *contents* (\`vars\`, \`files\`) instead.
8384
+ `;
8385
+ var REPLICAS_ABILITY = {
8386
+ label: "Replicas",
8387
+ description: "Teach the agent about Replicas itself \u2014 automations, environments, the in-workspace CLI.",
8388
+ // No bullet — help_instructions covers the `replicas` CLI surface in detail.
8389
+ bullet: "",
8390
+ section: SECTION7,
8391
+ referenceFile: { name: "REPLICAS.md", content: REFERENCE7 },
8392
+ locked: true
8393
+ };
8394
+
8395
+ // ../shared/src/default-skills/replicas-agent/abilities/slack.ts
8396
+ var SECTION8 = `### Slack
8397
+ Send messages, read threads, search conversations, and upload files via the Slack Web API.
8398
+
8399
+ **Reference:** \`references/SLACK.md\`
8400
+
8401
+ Use this when:
8402
+ - You need to send a message to a Slack channel or thread
8403
+ - You need to read or fetch a Slack conversation
8404
+ - You encounter a Slack message link and need to retrieve its content
8405
+ - The task asks you to notify, update, or communicate via Slack`;
8406
+ var REFERENCE8 = `# Slack Integration
8407
+
8408
+ This guide covers how to interact with Slack from within your Replicas workspace.
8409
+
8410
+ ## Prerequisites
8411
+
8412
+ Check if the \`SLACK_BOT_TOKEN\` environment variable is set:
8413
+
8414
+ \`\`\`bash
8415
+ echo "\${SLACK_BOT_TOKEN:+set}"
8416
+ \`\`\`
8417
+
8418
+ - If **set**: Your workspace has Slack access. You can use the Slack Web API as described below.
8419
+ - If **not set**: Slack has not been configured for this workspace. The user needs to connect Slack in the [Replicas dashboard](https://replicas.dev) under their organization's integration settings. Let the user know and do not attempt Slack operations.
8420
+
8421
+ ## Using the Slack API
8422
+
8423
+ All requests use the \`$SLACK_BOT_TOKEN\` for authentication via the Slack Web API.
8424
+
8425
+ ### Fetching a Thread from a Slack Link
8426
+
8427
+ If you encounter a Slack message link (e.g. \`https://team.slack.com/archives/C0123ABC/p1234567890123456\`), extract the channel ID and thread timestamp:
8428
+
8429
+ - **Channel ID**: The segment after \`/archives/\` (e.g. \`C0123ABC\`)
8430
+ - **Thread TS**: The \`p\` value with a dot inserted before the last 6 digits (e.g. \`p1234567890123456\` -> \`1234567890.123456\`)
8431
+
8432
+ \`\`\`bash
8433
+ curl -s "https://slack.com/api/conversations.replies?channel=CHANNEL_ID&ts=THREAD_TS" \\
8434
+ -H "Authorization: Bearer $SLACK_BOT_TOKEN"
8435
+ \`\`\`
8436
+
8437
+ ### Sending a Message
8438
+
8439
+ \`\`\`bash
8440
+ curl -s -X POST "https://slack.com/api/chat.postMessage" \\
8441
+ -H "Authorization: Bearer $SLACK_BOT_TOKEN" \\
8442
+ -H "Content-Type: application/json" \\
8443
+ -d '{
8444
+ "channel": "CHANNEL_ID",
8445
+ "text": "Your message here",
8446
+ "thread_ts": "OPTIONAL_THREAD_TS"
8447
+ }'
8448
+ \`\`\`
8449
+
8450
+ Omit \`thread_ts\` to post a new message to the channel. Include it to reply in a thread.
8451
+
8452
+ ### Searching Messages
8453
+
8454
+ \`\`\`bash
8455
+ curl -s "https://slack.com/api/search.messages?query=YOUR_SEARCH_QUERY" \\
8456
+ -H "Authorization: Bearer $SLACK_BOT_TOKEN"
8457
+ \`\`\`
8458
+
8459
+ ### Uploading Files
8460
+
8461
+ \`\`\`bash
8462
+ curl -s -X POST "https://slack.com/api/files.uploadV2" \\
8463
+ -H "Authorization: Bearer $SLACK_BOT_TOKEN" \\
8464
+ -F "channel_id=CHANNEL_ID" \\
8465
+ -F "file=@/path/to/file" \\
8466
+ -F "title=File title"
8467
+ \`\`\`
8468
+
8469
+ ### Other Operations
8470
+
8471
+ You can list channels, read channel history, add reactions, and perform any other operation supported by the Slack Web API using the same authentication pattern.
8472
+
8473
+ For full API documentation, see: https://docs.slack.dev/apis/web-api/
8474
+ `;
8475
+ var SLACK_ABILITY = {
8476
+ label: "Slack",
8477
+ description: "Send messages, read threads, search conversations, upload files.",
8478
+ bullet: "- Interacting with Slack (sending messages, reading threads, etc.)",
8479
+ section: SECTION8,
8480
+ referenceFile: { name: "SLACK.md", content: REFERENCE8 }
8481
+ };
8482
+
8483
+ // ../shared/src/default-skills/replicas-agent/registry.ts
8484
+ var REPLICAS_AGENT_ABILITY_REGISTRY = {
8485
+ replicas: REPLICAS_ABILITY,
8486
+ docker: DOCKER_ABILITY,
8487
+ github: GITHUB_ABILITY,
8488
+ google: GOOGLE_ABILITY,
8489
+ linear: LINEAR_ABILITY,
8490
+ media: MEDIA_ABILITY,
8491
+ previews: PREVIEWS_ABILITY,
8492
+ slack: SLACK_ABILITY
8493
+ };
8494
+ var REPLICAS_AGENT_ABILITIES = Object.keys(
8495
+ REPLICAS_AGENT_ABILITY_REGISTRY
8496
+ );
8497
+
8498
+ // ../shared/src/routes/preferences.ts
8499
+ var DEFAULT_REPLICAS_AGENT_ABILITIES = Object.fromEntries(
8500
+ REPLICAS_AGENT_ABILITIES.map((key) => [key, true])
8501
+ );
8502
+ var DEFAULT_DEFAULT_SKILLS = {
8503
+ replicas_agent: {
8504
+ enabled: true,
8505
+ abilities: { ...DEFAULT_REPLICAS_AGENT_ABILITIES }
8506
+ }
8507
+ };
7401
8508
 
7402
8509
  // ../shared/src/replicas-config.ts
7403
8510
  var import_yaml = __toESM(require_dist());
@@ -7407,6 +8514,29 @@ var DEFAULT_WARM_HOOK_TIMEOUT_MS = 5 * 60 * 1e3;
7407
8514
  var MAX_WARM_HOOK_TIMEOUT_MS = 15 * 60 * 1e3;
7408
8515
  var HOOK_EXEC_MAX_BUFFER_BYTES = 10 * 1024 * 1024;
7409
8516
 
8517
+ // ../shared/src/engine/types.ts
8518
+ var CLAUDE_OPUS_1M_MODEL = "opus[1m]";
8519
+ var LEGACY_CLAUDE_OPUS_1M_MODEL = "opus-1m";
8520
+ var MODEL_LABELS = {
8521
+ sonnet: "Sonnet 4.5",
8522
+ opus: "Opus 4.7",
8523
+ [CLAUDE_OPUS_1M_MODEL]: "Opus 4.7 (1M)",
8524
+ [LEGACY_CLAUDE_OPUS_1M_MODEL]: "Opus 4.7 (1M)",
8525
+ haiku: "Haiku 4.5",
8526
+ "gpt-5.5": "GPT-5.5",
8527
+ "gpt-5.4": "GPT-5.4",
8528
+ "gpt-5.4-mini": "GPT-5.4 Mini",
8529
+ "gpt-5.3-codex": "GPT-5.3 Codex",
8530
+ "gpt-5.3-codex-spark": "GPT-5.3 Codex Spark",
8531
+ "gpt-5.2-codex": "GPT-5.2 Codex",
8532
+ "gpt-5.2": "GPT-5.2",
8533
+ "gpt-5.1-codex-max": "GPT-5.1 Codex Max",
8534
+ "gpt-5.1-codex": "GPT-5.1 Codex",
8535
+ "gpt-5.1": "GPT-5.1",
8536
+ "gpt-5-codex": "GPT-5 Codex",
8537
+ "gpt-5": "GPT-5"
8538
+ };
8539
+
7410
8540
  // ../shared/src/routes/workspaces.ts
7411
8541
  var WORKSPACE_FILE_UPLOAD_MAX_SIZE_BYTES = 20 * 1024 * 1024;
7412
8542
  var WORKSPACE_FILE_CONTENT_MAX_SIZE_BYTES = 1 * 1024 * 1024;
@@ -7879,6 +9009,37 @@ function parseClaudeEvents(events, parentToolUseId) {
7879
9009
  }
7880
9010
  }
7881
9011
  });
9012
+ filteredEvents.forEach((event) => {
9013
+ if (event.type === "replicas-tool-input-request") {
9014
+ const payload = event.payload;
9015
+ if (!payload.toolUseId || !payload.requestId) return;
9016
+ if (!Array.isArray(payload.options) && !Array.isArray(payload.questions)) return;
9017
+ const toolInfo = toolCallMap.get(payload.toolUseId);
9018
+ if (!toolInfo) return;
9019
+ const message = messages[toolInfo.messageIndex];
9020
+ if (!message || message.type !== "tool_call") return;
9021
+ message.inputRequest = {
9022
+ requestId: payload.requestId,
9023
+ status: "pending",
9024
+ options: payload.options,
9025
+ questions: payload.questions
9026
+ };
9027
+ }
9028
+ if (event.type === "replicas-tool-input-resolved") {
9029
+ const payload = event.payload;
9030
+ if (!payload.toolUseId || !payload.selectionId) return;
9031
+ const toolInfo = toolCallMap.get(payload.toolUseId);
9032
+ if (!toolInfo) return;
9033
+ const message = messages[toolInfo.messageIndex];
9034
+ if (!message || message.type !== "tool_call" || !message.inputRequest) return;
9035
+ message.inputRequest = {
9036
+ ...message.inputRequest,
9037
+ status: payload.selectionId === "aborted" ? "aborted" : "resolved",
9038
+ selectionId: payload.selectionId,
9039
+ selectionSummary: payload.selectionSummary
9040
+ };
9041
+ }
9042
+ });
7882
9043
  filteredEvents.forEach((event) => {
7883
9044
  if (event.type === "claude-user") {
7884
9045
  const content = event.payload.message?.content || [];
@@ -7974,7 +9135,7 @@ function result(data, isError = false) {
7974
9135
  }
7975
9136
  var server = new McpServer({
7976
9137
  name: "replicas-mcp",
7977
- version: "0.2.1"
9138
+ version: "0.2.2"
7978
9139
  });
7979
9140
  var registerTool = server.registerTool.bind(server);
7980
9141
  registerTool(
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "replicas-mcp",
3
- "version": "0.2.1",
3
+ "version": "0.2.2",
4
4
  "license": "UNLICENSED",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",
package/src/index.ts CHANGED
@@ -57,7 +57,7 @@ type RegisterToolFn = (
57
57
 
58
58
  const server = new McpServer({
59
59
  name: 'replicas-mcp',
60
- version: '0.2.1',
60
+ version: '0.2.2',
61
61
  });
62
62
 
63
63
  const registerTool = server.registerTool.bind(server) as RegisterToolFn;