This release includes 2 breaking changes for platform teams planning a safe upgrade.
✓ No known CVEs patched in this version
Topics
+11 more
Affected surfaces
ReleasePort's take
Moderate signalThe `/learn` slash command has been restored as an operational skill with persistence and approval constraints, while the `auth setup --web` CLI command has been removed in favor of a unified authentication flow within the `mureo configure` UI.
Why it matters: Restoring /learn enables persisted learning workflows; removing auth setup --web forces all users to adopt the new UI‑based authentication, eliminating legacy command paths.
Summary
AI summary/learn slash command restored and auth setup --web removed
Changes in this release
| Type | Severity | Summary | CVE |
|---|---|---|---|
| Feature | Medium |
Restored `/learn` slash command as an operational skill with persistence and approval constraints. Restored `/learn` slash command as an operational skill with persistence and approval constraints. Source: llm_adapter@2026-05-21 Confidence: high |
— |
| Feature | Medium |
Configured official mureo logo and dark mode for `mureo configure` UI with cohesive design-system tokens. Configured official mureo logo and dark mode for `mureo configure` UI with cohesive design-system tokens. Source: llm_adapter@2026-05-21 Confidence: high |
— |
| Feature | Medium |
Introduced `mureo providers confirm <id>` command and UI button to finalize hosted‑connector verification, disabling native tools only after confirmation. Introduced `mureo providers confirm <id>` command and UI button to finalize hosted‑connector verification, disabling native tools only after confirmation. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Feature | Medium |
Added `mureo configure` Web UI (Phase 1) with localhost server, CSRF protection, CSP headers, and env‑var credential writer. Added `mureo configure` Web UI (Phase 1) with localhost server, CSRF protection, CSP headers, and env‑var credential writer. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Feature | Low |
Added Google Ads OAuth‑scope guidance in the auth step to prevent insufficient‑scope errors. Added Google Ads OAuth‑scope guidance in the auth step to prevent insufficient‑scope errors. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Feature | Low |
Removed `auth setup --web` command; unified authentication flow into `mureo configure` UI. Removed `auth setup --web` command; unified authentication flow into `mureo configure` UI. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Feature | Low |
Added per‑platform native↔official toggle in the dashboard with validation and restart guidance. Added per‑platform native↔official toggle in the dashboard with validation and restart guidance. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Feature | Low |
Clarified host selector labels in the configure UI for Claude Code vs. Desktop app and added unavailability note for credential‑guard hook on Desktop. Clarified host selector labels in the configure UI for Claude Code vs. Desktop app and added unavailability note for credential‑guard hook on Desktop. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Feature | Low |
Implemented plugin → MCP tool exposure via new `MCPToolProvider` protocol, allowing third‑party plugins to publish tools as `mcp__mureo__*`. Implemented plugin → MCP tool exposure via new `MCPToolProvider` protocol, allowing third‑party plugins to publish tools as `mcp__mureo__*`. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Feature | Low |
Added `mureo providers` CLI commands (`list`, `add`, `remove`) for managing official MCP providers with idempotent and dry‑run support. Added `mureo providers` CLI commands (`list`, `add`, `remove`) for managing official MCP providers with idempotent and dry‑run support. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Feature | Low |
Made workflow skills provider‑aware to fall back gracefully when native tools are disabled by official providers. Made workflow skills provider‑aware to fall back gracefully when native tools are disabled by official providers. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Performance | Medium |
Phase 3 plugin packaging migrated slash commands to skills, dropped `learn` entirely. Phase 3 plugin packaging migrated slash commands to skills, dropped `learn` entirely. Source: llm_adapter@2026-05-21 Confidence: low |
— |
| Bugfix | High |
Prevented dead config entry for official Meta Ads provider on Claude Code; now requires manual connector setup via Claude.ai. Prevented dead config entry for official Meta Ads provider on Claude Code; now requires manual connector setup via Claude.ai. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Bugfix | High |
Fixed official Google Ads provider registration so credentials are collected and injected correctly, making the provider usable. Fixed official Google Ads provider registration so credentials are collected and injected correctly, making the provider usable. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Bugfix | Medium |
Corrected Meta hosted MCP handling on Claude Code to use Claude.ai connector instead of failing `/mcp` registration. Corrected Meta hosted MCP handling on Claude Code to use Claude.ai connector instead of failing `/mcp` registration. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Bugfix | Medium |
Fixed official/native precedence when mureo MCP is configured after an official provider, ensuring deterministic tool source selection. Fixed official/native precedence when mureo MCP is configured after an official provider, ensuring deterministic tool source selection. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Bugfix | Medium |
Resolved GA4 wizard input saving issue so credentials are persisted correctly. Resolved GA4 wizard input saving issue so credentials are persisted correctly. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Bugfix | Medium |
Fixed dashboard “mureo integrations” list to include Search Console and exclude GA4 (official only). Fixed dashboard “mureo integrations” list to include Search Console and exclude GA4 (official only). Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Bugfix | Medium |
Corrected BYOD/demo relative windows calculation so demo data remains non‑empty over time. Corrected BYOD/demo relative windows calculation so demo data remains non‑empty over time. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Bugfix | Medium |
Ensured auto‑disable of mureo native tools when adding an official provider, with atomic config updates and env‑var handling. Ensured auto‑disable of mureo native tools when adding an official provider, with atomic config updates and env‑var handling. Source: granite4.1:30b@2026-05-22-audit Confidence: low |
— |
| Other | Low |
affected_surface affected_surface Source: llm_adapter@2026-05-21 Confidence: low |
— |
Full changelog
Fixed — /learn slash command restored (regression from #77)
- Phase 3 plugin packaging (#77) migrated every
.claude/commands/*.mdslash command into an operational skill underskills/+ the bundledmureo/_data/skills/, but droppedlearnentirely (deleted.claude/commands/learn.md, never created alearnskill)./learnbecame uninvocable while every other workflow command kept working, even though README/docs still document it. Restored as an operational skill (skills/learn/+ byte-identical bundled copy):name: learn(no_prefix → appears in the picker), saves insights to../_mureo-pro-diagnosis/SKILL.md(scaffolding that canonical-only knowledge base on first use), approval-required and append-only, never Claude memory or secrets/PII.
Changed — mureo configure visual refresh + official mureo logo
- The configure Web UI got a cohesive design-system pass (refined spacing/type/color tokens, light and dark via
prefers-color-scheme, crafted cards/buttons/focus states, system fonts only — strict CSP, no web fonts/CDN/build). The header now shows the official mureo wordmark (bundledlogo.png/logo-dark.png, scheme-swapped). CSS-only; everydata-*/data-i18nhook and EN/JA parity preserved.
Added — Google Ads OAuth-scope guidance in the auth step
- The Web UI Google Ads auth step and
docs/authentication.mdnow explain that a reused refresh token must carry the Google Ads scopehttps://www.googleapis.com/auth/adwordsor API calls fail withACCESS_TOKEN_SCOPE_INSUFFICIENT, with a link to the official Google scope reference. mureo's own OAuth already requests it; the note prevents the failure when users supply a hand-minted token.
Fixed — Meta hosted MCP on Claude Code goes through the Claude.ai connector (supersedes the earlier "/mcp register" Unreleased note)
- A prior Unreleased change had
mureo configure/mureo providers add/ the wizard registermeta-ads-officialinto~/.claude.jsonon Claude Code and tell the user to finish OAuth via/mcp→ Authenticate. Real-environment verification proved this cannot work: Meta's hosted MCP (https://mcp.facebook.com/ads) does not support OAuth Dynamic Client Registration, so Claude Code's/mcpOAuth fails withSDK auth failed: The provided redirect_uris are not registered for this client. Registering it locally only creates an unauthenticatable user-scope server. Corrected behavior: on Claude Code, mureo now does not register Meta locally at all —install_provider/mureo providers addreturnmanual_required(no~/.claude.jsonwrite, no subprocess) and the UI/CLI point the user to add Meta as a Claude.ai account connector (claude.ai → Settings → Connectors → Add custom connector →https://mcp.facebook.com/ads; Anthropic brokers the Meta Business sign-in there, requires a paid plan, then works account-wide in Claude Code and Claude Desktop and surfaces asmcp__claude_ai_MetaAds__*). mureo-native Meta is still not auto-disabled (nothing registered/verified — native steps aside only viamureo providers confirmonce the connector is verified Connected; no-strand preserved). Claude Desktop is unchanged (manual_required, Settings → Connectors). This re-aligns with the "no dead config entry / Connectors" behavior described in the bullets below; the intervening "/mcp register on Code" wording is withdrawn.
Docs — mureo configure is now the documented front door; auth setup --web removed
mureo auth setup --webwas removed (its browser credential flow is now part of the unifiedmureo configureUI). README and docs (cli.md,authentication.md,getting-started.md/.ja.md,byod.md/.ja.md,architecture.md) updated: everyauth setup --webreference now points tomureo configure(or terminalmureo auth setup). README gained a top-of-"Choose your setup" quickstart —pip install mureo+mureo configure— enumerating what the browser UI does (host pick, basic setup, OAuth/credentials, official MCP providers, native↔official toggle, Demo/BYOD).
Fixed — official/native precedence when mureo MCP is configured after an official provider
MUREO_DISABLE_<PLATFORM>(which makes the mureo-native MCP step aside so an official provider is the single source for a platform) was only auto-set bymureo providers addwhen amcpServers.mureoblock already existed. A user who registered the official provider first and configured the mureo MCP later ended up with native + official both active and no deterministic precedence (tool ambiguity).install_mureo_mcp(the path both basic-setup and the dashboard use) now backfills the disable env, after the mureo block is written, for already-registered pipx/npm official providers (google-ads-official, ga4-official) detected by a pure host-config registry read. Meta (hosted) is intentionally out of backfill scope — detecting it needs a networkclaude mcp listprobe that must not run on the basic-setup path; Meta native↔official is the explicitmureo providers confirm/ dashboard native-toggle (both gate on the verified connector — no-strand preserved). Best-effort and idempotent (never raises, never invents a mureo block); Search Console is never disabled. Works for both Claude Code (~/.claude.json) and Claude Desktop (claude_desktop_config.json).- Web-UI per-platform native↔official toggle — the dashboard now shows, per official provider (when the mureo MCP is configured), the current tool source for that platform and a button to switch.
POST /api/providers/native-togglesets/unsetsMUREO_DISABLE_<PLATFORM>;statusexposes the per-platform state. Switching to official is allowed only when the official path is actually usable (pipx/npm provider registered, or Meta connector verified Connected) — refused with an actionable message otherwise; switching back to native is always allowed (the un-strand path). Restart Claude to apply (the flag is read once at MCP start). Host-aware (Code + Desktop), EN + JA.
Fixed — GA4 wizard inputs were collected but never saved
- The configure-UI auth wizard's GA4 step rendered the service-account-path / project-id inputs and a "Done" button whose handler only advanced the wizard — the entered values were discarded, so
GOOGLE_APPLICATION_CREDENTIALS/GOOGLE_PROJECT_IDwere never written tocredentials.jsonand the officialga4-officialMCP launched unauthenticated (same class as the earlier Google Ads bug). The Done handler now POSTs each value through the allow-listed/api/credentials/env-varwriter (into thega4section) before advancing, only proceeding if every write succeeds (otherwise it surfaces a save-failed message and stays on the step). Host-accurate labels + saving/failure status added (EN + JA).
Changed — host selector clarity + Desktop-unavailable credential-guard hook note
- The configure-UI host selector labels were ambiguous (
Claude Code (terminal)implied terminal-only). Relabelled toClaude Code (CLI, Desktop app)vsClaude Desktop app (Chat, Cowork)so users running Claude Code inside the Desktop app correctly pick the Claude Code option (which targets~/.claude.json). Japanese punctuation made consistent (fullwidth、). - The credential-guard hook has no surface on Claude Desktop (
install_auth_hookis anoop:unsupported_on_desktopthere). The basic-setup list (wizard and dashboard) now appends "(not available on the Desktop app)" / "(デスクトップアプリでは利用できません)" to that row when the chosen host is Claude Desktop, instead of implying it can be installed.
Fixed — dashboard "mureo integrations" listed GA4 (not native) and omitted Search Console
- The configure-UI dashboard's mureo integrations section listed
Google Ads / Meta Ads / GA4. mureo ships no native GA4 tools (GA4 is official-provider-only), so GA4 did not belong there; meanwhile the genuinely mureo-native Search Console was missing (only a sub-note under Google Ads). GA4's presence came from thega4credentials.json section, which actually stores the official GA4 MCP's service-account env — not a mureo-native integration. - Removed the GA4 row; added a Search Console row. Search Console has no own credentials section (it reuses the Google Ads Google OAuth — adwords + webmasters scopes), so the row is status-only: it shows configured the moment the wizard's Search Console / Google sign-in is done (driven by the existing
credentials_oauth.googlesignal) and has no standalone Remove (a note directs removal to the Google Ads row, since the sign-in is shared).
Fixed — official Meta Ads provider registered a dead entry on Claude Code
- Adding the official Meta Ads MCP (
meta-ads-official, hosted athttps://mcp.facebook.com/ads) on Claude Code wrote a raw{"type":"http","url":…}entry into~/.claude.jsonand setMUREO_DISABLE_META_ADS=1. But Meta's hosted MCP has no OAuth Dynamic Client Registration, so Claude Code can never connect that raw entry (✗ Failed to connect) — while mureo-native Meta was disabled, leaving the user with zero Meta capability (the model fell back to a mureo-native "credentials not found" error). The Desktop path already short-circuited this; the Code path and themureo providers addCLI did not. - Claude Code, the
mureo providers addCLI, and Claude Desktop now treathosted_httpproviders consistently: no dead config entry is written and mureo-native tools are NOT auto-disabled (auto-disabling before the official path is verified strands the user). The result ismanual_required, and the UI/CLI now point the user to Claude's account-level Connectors (the working path mureo cannot create programmatically). Connectors setup guidance is host-accurate — terminal (Claude Code) vs Claude Desktop have genuinely different steps — EN + JA.mureo providers removestill self-heals a staleMUREO_DISABLE_<PLATFORM>left by the old logic so native Meta comes back. mureo providers confirm <id>(new) + a Web UI "I've connected it — finalize" button close the post-setup coexistence gap: once the official hosted connector is verified Connected (parsed fromclaude mcp list), the overlappingMUREO_DISABLE_<PLATFORM>is set so the model stops calling the credential-less mureo-native tools. Native is only disabled after the official path is confirmed working — never before (no stranding). Claude Desktop returnsmanual(no programmatic signal there; the user verifies in Settings → Connectors). Theclaude mcp listprobe is timeout-bounded so an unreachable endpoint can't hang the call.- The dashboard's Official MCP providers list previously showed
meta-ads-officialas permanently✗(mureo never registers a hosted connector in the config file). It now reflects the real account-level Connector state: a newPOST /api/providers/hosted-statusendpoint (lazily fetched, cached) flips the row to✓once the Connector is Connected. The probe is a SEPARATE endpoint, intentionally not folded into/api/status, so it never slows every status poll. Hosted rows never get a Remove button (mureo cannot unregister an account Connector).
Fixed — official Google Ads provider was registered but unusable
- Selecting the official Google Ads MCP from the
mureo configureWeb UI registered the provider but left it unable to authenticate: (1) the wizard's Developer-Token + Google OAuth step only ran for the mureo-native provider choice, so picking official skipped credential collection entirely; and (2) the registeredmcpServers["google-ads-official"]block carried noenv, while the upstreamgoogle-ads-mcpreads its config only from environment variables (never mureo's~/.mureo/credentials.json). Net effect: "✓ registered" then "✗ Failed to connect". - The Web UI auth step now runs for both native and official Google Ads (same Developer Token + OAuth refresh token), the wizard now orders
authbeforeproviders_installso credentials exist when the block is written, andinstall_providerresolves the credential env fromcredentials.json(closed allow-list, reverse of the per-var writer) and injects it into the registered provider block — Claude Code (~/.claude.json) and Claude Desktop alike. Meta's hosted MCP is correctly excluded (it authenticates via browser OAuth on first connect; no env to inject). Credential values are redacted from anyclaude mcp add-jsonfailure message before it can reach a log line.
Added — mureo configure Web UI (Issue #88, Phase 1: localhost setup wizard)
mureo configure— local Web UI for non-engineer onboarding. Spawns a stdlib-only HTTP server bound to127.0.0.1(ephemeral port by default;--portto pin;--no-browserto suppress auto-open;--timeout-secondsfor idle exit). Renders a single Japanese settings page with cards for current status, official MCP providers (add/remove via the auditedmureo.providers.config_writerhelpers), OAuth handoff stubs, and an allow-listed env-var writer that routes throughmureo.auth_setup.save_credentials(mode0o600). Defense-in-depth: hard-coded localhost bind, Host-header validation on every route (DNS-rebinding defense), per-process CSRF (secrets.token_urlsafe(32)+secrets.compare_digest), full CSP /X-Content-Type-Options/X-Frame-Options: DENY/Referrer-Policy: no-referrerheaders, 16 KiB POST cap, basename allow-list for static assets, 405 responses for unsupported HTTP methods. Stdlib only — no Flask/FastAPI/jinja2 dependency added (regression-pinned bytest_pyproject_does_not_depend_on_web_framework).
Added — plugin → MCP tool exposure (Issue #89 follow-up)
mureo.mcp.tool_provider: newMCPToolProvideropt-in secondary Protocol (mcp_tools()+async handle_mcp_tool()) andcollect_plugin_tools(). A third-party provider discovered via themureo.providersentry-point group that also satisfiesMCPToolProvidernow has its operations published asmcp__mureo__*tools. A provider that does not implement it is still discovered and skill-matched, just not exposed (graceful). Added to the stable plugin ABI (seedocs/ABI-stability.md§1).mureo/mcp/server.py: purely additive wiring — built-in platforms keep their static tool list and are not routed through the plugin path (no double-exposure). With no third-party plugins installed, the tool list and behaviour are byte-identical to before. Built-in tool names are reserved (a colliding plugin tool is dropped, built-ins win); plugin↔plugin collisions are first-wins; a broken/malicious plugin (construct /mcp_tools()/ non-async handler / wholesale discovery failure) is skipped with aPluginToolWarningand can never crash the server or starve other plugins.- Docs:
plugin-authoring.md§3 "Exposing operations as MCP tools",mcp-server.md"Plugin-Provided Tools",ABI-stability.mdupdated.
Fixed — BYOD/demo relative windows silently went empty over time
- The CSV-backed BYOD/demo clients resolved relative MCP query windows (
LAST_7_DAYS, …) againstdate.today(). The demo dataset has fixed historical dates, so as wall-clock time moved past it the demo silently returned[]—LAST_7_DAYSfirst, then every window — making Meta insights / anomaly checks / Search Console appear broken even though the data was present. _period_to_rangenow accepts an optionalanchor; the BYOD/demo metrics readers anchor relative windows on the dataset's own latest date (same span, ending at the most recent available day) so the demo stays non-empty regardless of the current date.anchor=Nonepreserves the exact legacy wall-clock behaviour, so live-API and non-demo callers are completely unaffected.
Added — mureo providers CLI (Issue #86, Phase 1: Claude Code)
mureo providers list / add / remove— one-command install of the official platform MCP servers into Claude Code's~/.claude/settings.json. mureo owns both package acquisition and config registration.addis idempotent;add --allinstalls every catalog entry and continues past per-provider failures (non-zero exit overall).--dry-runprints the plannedpipx/npmargv (or, for hosted endpoints, the "no local install step" notice) plus the JSON delta without touching disk or subprocess.removeonly edits the settings file (it does not uninstall the underlying pipx/npm package; no-op for hosted-HTTP entries which have none).- Phase 1 catalog (3 entries):
- Google Ads (
google-ads-official,pipxfromgithub.com/googleads/google-ads-mcp— env-var Client Library config, no OAuth Proxy / ADC modes in Phase 1). - Meta Ads (
meta-ads-official, hosted HTTP athttps://mcp.facebook.com/ads— Meta's official "Meta Ads AI Connectors" announced 2026-04-29; interactive Meta Business OAuth in the browser on first connect, no Meta Developer App, no API tokens, no env vars to pre-populate; currently in public beta and free). - GA4 (
ga4-official,pipx install analytics-mcpfromgithub.com/googleanalytics/google-analytics-mcp— service-account JSON viaGOOGLE_APPLICATION_CREDENTIALS, read-only Reporting + Admin APIs).
- Google Ads (
- New
mureo/providers/package:catalog.py(frozenProviderSpec+ immutable Phase 1 catalog with threeinstall_kindfamilies:pipx,npm,hosted_http),installer.py(list-form subprocess withpipx/npmexecutable allow-list — noshell=True, noenv=kwarg;hosted_httpshort-circuits subprocess entirely),config_writer.py(atomicos.replacefrom a same-dir.tmp.<pid>file with0o600mode and fd-fsync + best-effort parent-dir fsync; refuses to overwrite malformed-JSON existing settings viaConfigWriteError),coexistence.py(warning when an official provider overlaps with a mureo-native platform),mureo_env.py(per-platformMUREO_DISABLE_*env-var writers). - Auto-disable mureo's native tool family when an official provider for an overlapping platform is added (extension to Phase 1, per Founder Q1/Q2 review).
mureo providers add google-ads-officialnow also writesmcpServers.mureo.env.MUREO_DISABLE_GOOGLE_ADS="1"(and analogous keys for Meta Ads / GA4) in the same atomicos.replacethat adds the official provider — no torn-write window. The mureo MCP server reads these env vars once at import time and excludes the matching tool family from_ALL_TOOLSand the dispatch table; the comparison is exact-string== "1"(any other value keeps tools enabled).mureo providers remove <id>pops the matching env var. Search Console is intentionally exempt — mureo remains canonical for SC, noMUREO_DISABLE_SEARCH_CONSOLEis honored. When nomcpServers.mureoblock exists, the CLI registers the official provider as before and emits a degraded coexistence note pointing atmureo setup claude-code. - Workflow skills are now provider-aware when an official MCP is installed. Skills under
mureo/_data/skills/(daily-check,rescue,search-term-cleanup,budget-rebalance,creative-refresh,competitive-scan,weekly-report,sync-state,onboard) keep mureo native tool names as the primary path — so existing users runningmureo setup claude-codesee zero behavior change. The skills now also instruct the LLM to fall back to the official MCP's equivalent tools when mureo's tools for that platform are unavailable (i.e.MUREO_DISABLE_<PLATFORM>=1is set because the user ranmureo providers add <id>), and to gracefully skip mureo-only value-add features (anomaly detection, RSA asset audit,result_indicatoranalysis, rule-based scoring, etc.) with a user-facing note pointing back tomureo setup claude-codefor full coverage. - Phase 2 (Cursor / Codex / Gemini config writing for official providers) is deferred to a separate Issue. Search Console intentionally remains out of the catalog — mureo's native MCP stays canonical.
Breaking Changes
- Removed `mureo auth setup --web` CLI flag and its associated browser credential flow; all authentication now occurs via the unified `mureo configure` Web UI.
- /learn slash command was deleted in Phase 3 plugin packaging and is now restored as an operational skill.
Weekly OSS security release digest.
The CVE patches and breaking changes that affected production tools this week. One email, every Sunday.
No spam, unsubscribe anytime.
Share this release
About logly/mureo
Framework for AI agents (Claude Code, Cursor, Codex, Gemini) to operate Google Ads, Meta Ads, and Search Console. Grounded in a local STRATEGY.md — not metric-chasing. Defense-in-depth security, local-first. Apache 2.0.
Related context
Related tools
Beta — feedback welcome: [email protected]