Skip to content

v0.25.0

Choose a tag to compare

@hyoshi hyoshi released this 13 Oct 20:08
· 83 commits to main since this release
93b0c98

Added

  • A credential source can fail closed for the platforms it does not
    cover
    (#824). CredentialSource gains a keyword-only strict field
    (default False). With strict=True, a handler for a platform the source
    leaves at None raises the new CredentialSourceError (a RuntimeError
    naming the platform) instead of reading the operator's credentials file,
    environment or BYOD manifest. Without strict such a platform still uses
    the operator's own credentials, as before; this is now stated in
    docs/plugin-authoring.md. A nested use_credential_source keeps
    replacing the outer source; CredentialSource.merged_with(other) combines
    two explicitly. active_source_identity(platform) and call_source(...)
    are exported for hosts and built-in paths.
  • A plugin can override or suppress the callback-URL hint on its OAuth
    card.
    AccountOAuthConfig gains callback_hint (and a
    callback_hint_i18n locale table). The configure UI shows that text under
    the callback URL input instead of the generic "register this exact URL"
    hint, or no hint at all when it is "", so a provider whose flow is
    brokered no longer tells operators to register a redirect URI they do not
    own. Providers that leave it unset are unchanged. The list endpoint exposes
    it as oauth.callback_hint.
  • A plugin platform's label uses the name its provider declares (#826).
    The Reports card now labels a plugin:<distribution>:<provider> key (and
    the bare provider name) with the provider class's display_name,
    stripped and followed by (plugin), instead of title-casing the provider
    name, so brand casing survives. The name is read from the providers
    discovery already loaded; a provider that is not loaded, one registered
    from a different distribution, the legacy plugin:<distribution> key and a
    blank name keep the derived label. Built-in platforms and in-tree bridges
    are unchanged.

Changed

  • Errors raised by a credential source reach the MCP client curated
    (#824). Every call into a source's load_credentials() /
    oauth_credentials() is wrapped: the client sees
    credential source failed for <platform> (<ExceptionClass>), and only the
    platform and class name are logged, never the source's exception text. An
    auth failure raised by a source is still reported as an auth failure.
  • The tracking pre-flight snapshot cache is keyed by credential source
    (#824). The key is (customer_id, identity of the active google source),
    so two sources resolving to the same customer id within the TTL no longer
    share cached ad rows. An entry holds its source until it expires, so the
    identity cannot be reused meanwhile, and expired entries are dropped.
  • Without a credential source the Google Ads client factory is called as
    before #821
    (#824): oauth_credentials is passed only when a source
    supplies one, so a factory patched with the narrower signature works again.
  • The Google Ads client and credential resolution moved from
    mureo/mcp/_handlers_google_ads.py to the private
    mureo/mcp/_google_ads_client.py (#824); the old module re-exports the
    names. Code that patches load_google_ads_credentials,
    create_google_ads_client, byod_has, get_google_ads_client or
    runtime_google_ads_customer_ids on mureo.mcp._handlers_google_ads must
    patch them on mureo.mcp._google_ads_client instead.
  • The Meta Ads client and credential resolution moved from
    mureo/mcp/_handlers_meta_ads.py to the private
    mureo/mcp/_meta_ads_client.py, and the upload / creative handlers to
    mureo/mcp/_handlers_meta_ads_creatives.py (#840); the old module
    re-exports the names. Code that patches load_meta_ads_credentials,
    create_meta_ads_client, refresh_meta_token_if_needed, byod_has,
    byod_freshness, get_meta_ads_client, register_client_for_cleanup,
    current_meta_source, call_source or runtime_meta_account_ids on
    mureo.mcp._handlers_meta_ads must patch them on
    mureo.mcp._meta_ads_client instead.
  • Skills treat a namespaced built-in variant as the built-in platform
    (#825). A provider whose tools are <builtin_platform>_<suffix>_<operation>,
    with the same operation set and input schemas as the built-in
    <builtin_platform>_<operation> tools, now gets the full workflow and
    analysis instead of the best-effort plugin path; the skills call its tools
    with the prefix substituted. The match is derived from the live tool list.
    When the built-in and a variant are both present, the skills use the one
    whose credentials are configured and never call both for the same account.
    _mureo-shared defines the rule, every skill that names built-in tools
    points to it, and docs/plugin-authoring.md describes what mirroring a
    built-in surface requires.

Fixed

  • The learning-period reset check classifies a namespaced built-in variant
    like the built-in
    (#837). A tool named
    <builtin_platform>_<suffix>_<operation> is now matched against the
    built-in <builtin_platform>_<operation> tool, including its reset triggers
    and argument rules, so a bid-strategy, budget, keyword or reactivation
    change made through such a variant reaches the block_learning_resets /
    block_learning_resets_during_incident refusal and the post-call notice
    instead of being reported as a read or as not reset-triggering. A name that
    only shares a built-in platform prefix, with no built-in operation behind
    it, is no longer forced to "read": its declared readOnlyHint and then the
    read-only name pattern decide. Meta minor-unit conversion already applied
    to variants and is unchanged; a test now pins it.