CLI + MCP · 100% open source · MIT

Simple connectors for your agent. From the terminal.

An open source collection of connectors: one CLI and one MCP so Claude, Cursor, n8n or your shell can use Search Console, GA4, Google Ads and Workspace. Google first; more coming. Read-only, with errors that explain how to fix themselves.

Example terminal session with the CONCAT CLI: npx @lucasleguizamo/concat login / signed in · ana@example.com / concat connect gsc / authorizing webmasters.readonly ... / probe sites.list → 3 properties · connected / concat gsc striking-distance --site onconcat.com / QUERY POS IMPR +CLK / invoices with n8n 11.4 1,840 ~96 / whatsapp smb bot 9.7 920 ~61 / n8n vs make 14.2 2,310 ~48 / 3 of 41 · pos 8-20 · 28 d · non-brand

Sample data

demo / same question, two gateways

What changes when the gateway thinks in tasks.

On the left, what usually happens with a generic MCP wrapper. On the right, CONCAT. The session is illustrative.

typical MCP wrapper

tools/list
43 tools registered (get_*, list_*, batch_* ...)
gsc_query {"rowLimit": 25000}
[{"keys":["invoices with n8n"],"clicks":4,"impressions":1840,"ctr":0.0021,"position":11.4},
{"keys":["whatsapp smb bot"],"clicks":2,"impressions":920,"ctr":0.0022, ...
... 24,998 more rows
status
connected
gsc_query
Error 403: The caller does not have permission
  • 40+ tools
  • Raw dump
  • Fake "connected"
  • Opaque 403

CONCAT

concat tools
striking_distance · cannibalization · content_decay · ctr_gaps · gsc_ga4_join
concat gsc striking-distance --site onconcat.com
3 opportunities · +205 potential clicks / 28 d
concat calendar events
exit 5 · scope_lost
{ "error": "scope_lost", "module": "calendar",
"message": "Calendar lost its read permission.",
"fix": "Reconnect only that module; the others stay live.",
"next_action": "reconnect_module",
"url": "https://gw.onconcat.com/connect/calendar" }
  • 5 task tools
  • Compact output
  • Connected = the probe returned data
  • Error with next_action and URL

The task tools (striking distance, cannibalization, content decay, CTR gaps, GSC↔GA4 join) ship in v1.1 on top of the GSC and GA4 modules. Today the gateway already exposes the base read tools.

01 / problem

Connecting an agent to Google is expensive and blind today.

  1. Forty tools, zero judgement

    Wrappers register one tool per API method. The agent spends its context choosing instead of solving.

  2. Raw dumps

    Thousands of unsummarized JSON rows. The model drowns in data and you pay for the tokens.

  3. A "connected" that lies

    Login finishes and the dashboard says OK. The first query comes back empty and nobody knows why.

  4. A 403 with no way out

    Forbidden. Neither you nor the agent know which permission is missing, or which Google screen fixes it.

  5. Too many permissions

    Write scopes from day one, and refresh tokens in a .env the agent itself can read.

02 / solution

A gateway between your agent and Google.

You sign in once. The gateway stores the encrypted refresh token and the agent only receives a gateway token. Each service is a module with its own scopes, probe and tools.

Agent → Gateway → Google. OAuth 2.1 toward the agent, Google OAuth toward the service.

Phase A

First to be verified

Native modules. The first ones to pass Google's verification.

  • Search Console

    Your email must be a user of the property.

    scope webmasters.readonly

    • gsc_list_sites
    • gsc_performance
    • gsc_list_sitemaps
  • Google Analytics 4

    Viewer role on the property.

    scope analytics.readonly

    • ga4_list_properties
    • ga4_daily_report
  • Google Ads

    Account access, or the MCC login-customer-id.

    scope adwords

    • ads_list_customers
    • ads_search
  • People

    Profile and contacts.

    scope userinfo.profile

Beta

Sensitive scopes

Work in testing with an invite list. Need a demo video and a justification per scope.

  • Calendar

    Calendars and events.

    scope calendar.events.readonly

  • Docs

    Read documents.

    scope documents.readonly

  • Sheets

    Values and metadata.

    scope spreadsheets.readonly

  • Slides

    Read presentations.

    scope presentations.readonly

Closed beta

Restricted scopes

Require the CASA security assessment, renewed every 12 months. Test list only.

  • Gmail

    Restricted scope.

    scope gmail.readonly

  • Drive

    Restricted scope.

    scope drive.readonly

  • Chat

    Restricted scope.

    scope chat.messages.readonly

v1.1 · task tools

Five questions, five tools. Not forty wrappers.

  • striking_distanceQueries at position 8-20 with clicks to win.
  • cannibalizationPages competing with each other for the same query.
  • content_decayWhich pages lose traffic, and why.
  • ctr_gapsCTR below the site's own curve.
  • gsc_ga4_joinGSC↔GA4 join with a reported match_rate.

03 / how it works

From zero to data in four steps.

  1. Login

    Once. Browser with PKCE; on a machine without a browser, device code. The token lives in the OS keychain.

    shell
    npx -y @lucasleguizamo/concat@1 login
  2. Connect a module

    Incremental authorization: each module asks only for its read scopes, when you connect it.

    shell
    concat connect gsc ga4
  3. Probe

    "Connected" means the list call returned data. If it comes back empty, the status says exactly what to do.

    concat status
    gsc connected sites.list → 3
    ga4 no_resources accountSummaries → 0
    fix: GA4 → Admin → Access management → add your email as Viewer
  4. Use it in your agent

    Two doors, one catalog. The MCP host does the OAuth; the CLI serves n8n, CI or any agent with a shell.

    Claude Code
    claude mcp add --transport http concat https://gw.onconcat.com/mcp
    Cursor · mcp.json
    {
      "mcpServers": {
        "concat": { "url": "https://gw.onconcat.com/mcp" }
      }
    }
    CLI
    concat gsc performance --site sc-domain:onconcat.com --by query

04 / why concat

Four decisions that are not up for negotiation.

  • Read-only, and tokens the agent never sees

    v1 asks only for read scopes. Refresh tokens are encrypted with AES-256-GCM. Writing will be a per-module permission, audited and revocable.

    readOnlyHint: true
  • Open source and self-host

    MIT license. Run your own gateway with your own Google Cloud project, or use the instance CONCAT operates.

    LICENSE: MIT
  • Actionable errors

    Every failure carries message, fix and next_action. It names the Google screen that fixes the permission and, when it applies, the URL to reconnect.

    next_action: "reconnect_module"
  • MCP and CLI, one surface

    The CLI is a thin MCP client. Its subcommands are generated from tools/list: a new tool shows up on both doors without a release.

    gsc_performance → concat gsc performance

05 / pricing

Free if you host it. Hosted is in beta.

Self-host

Free

MIT license

  • All modules and tools
  • Your Google Cloud project and your verification
  • Your Postgres and your vault key
  • Quotas are those of your own project
View on GitHub

Hosted

Beta

Waitlist

  • Instance operated by CONCAT at gw.onconcat.com
  • No Google project or infrastructure of your own
  • Modules by phase, as Google verifies them
  • Price to be defined; joining the list costs nothing
Join the waitlist

06 / next step

Connect your first module from a terminal.

Open source, MIT. Try the CLI or point your MCP host at the CONCAT instance.