Skip to content

release: v1.20.1 — credentials in the OAuth URLs refused, and kept out of several startup refusals - #309

Merged
takashi-matsuyama merged 1 commit into
mainfrom
release/v1.20.1
Oct 19, 2026
Merged

takashi-matsuyama merged 1 commit into
mainfrom
release/v1.20.1

Conversation

@takashi-matsuyama

Copy link
Copy Markdown
Member

Bump all packages 1.20.0 -> 1.20.1 and the pinned image tags (README,
quickstart + scaffold docker-compose). Ships the changes already on main since
v1.20.0:

  • fix(mcp): refuse userinfo in the OAuth resource and authorization-server URLs #302 auth.resource and the auth.authorizationServers entries are refused
    at startup when they carry userinfo - a user name, a password, or both. Since
    v1.13.0 neither was checked for it. A credential in either one was quoted by
    the startup refusals and by the allowInsecureHttp warning, and when the URL
    was otherwise accepted it was printed on the startup line and served in the
    RFC 9728 protected-resource metadata, which is unauthenticated by design. The
    refusal for a value that does not parse no longer quotes it, nor does the
    scheme refusal for an authorizationServers entry; an entry is named by its
    index (auth.authorizationServers[1]) instead.
  • fix: refuse a query or fragment in an issuer entry, and stop quoting two startup refusals #305 an auth.authorizationServers entry with a non-empty query or fragment
    is refused at startup. RFC 8414 defines an issuer identifier as having
    neither, and the metadata served the entry as given, so anything carried
    there was published with it.
  • fix: refuse a query or fragment in an issuer entry, and stop quoting two startup refusals #305 two startup refusals stop quoting the value they refuse. The kozou
    config check that refuses server.mcp.http.advertisedUrl with a query or a
    fragment now names the key alone, as startHttpServer's option already did.
    It had quoted the whole value since v1.18.0, and a query or fragment is where
    a token usually goes. An allowedHosts entry that is refused - as a URL, as a
    path, or because no hostname can be read from it - is now named by its index
    (allowedHosts[1]) rather than quoted, in the kozou config check and in
    startHttpServer alike. The same values are refused as before.

Behaviour changes for embedders and operators:

  • An OAuth config (server.mcp.http.auth, or startHttpServer's auth
    option) whose resource or authorizationServers entry carries userinfo, or
    whose authorizationServers entry carries a non-empty query or fragment, now
    fails at startup. Most such configs used to start. One that was already
    refused - for plaintext http, or for a query in resource - is now refused
    for the userinfo, or for the query in the entry, first.
  • The refusals listed above name a key or an index where they quoted a value;
    other refusals are unchanged. When KOZOU_MCP_HTTP_ALLOWED_HOSTS holds empty
    items, the index counts only the non-empty ones, so it can differ from the
    item's position in the variable (allowedHosts[N] in a refusal does not match the item's position in KOZOU_MCP_HTTP_ALLOWED_HOSTS when the list has empty items #308).

Not covered: a password made only of digits with no @ after it
(https://user:4321/mcp) parses as a host and a port, and cannot be told apart
from one, so such a value is still accepted as a host and a port.

…t of several startup refusals

Bump all packages 1.20.0 -> 1.20.1 and the pinned image tags (README,
quickstart + scaffold docker-compose). Ships the changes already on main since
v1.20.0:

- #302 `auth.resource` and the `auth.authorizationServers` entries are refused
  at startup when they carry userinfo - a user name, a password, or both. Since
  v1.13.0 neither was checked for it. A credential in either one was quoted by
  the startup refusals and by the `allowInsecureHttp` warning, and when the URL
  was otherwise accepted it was printed on the startup line and served in the
  RFC 9728 protected-resource metadata, which is unauthenticated by design. The
  refusal for a value that does not parse no longer quotes it, nor does the
  scheme refusal for an `authorizationServers` entry; an entry is named by its
  index (`auth.authorizationServers[1]`) instead.
- #305 an `auth.authorizationServers` entry with a non-empty query or fragment
  is refused at startup. RFC 8414 defines an issuer identifier as having
  neither, and the metadata served the entry as given, so anything carried
  there was published with it.
- #305 two startup refusals stop quoting the value they refuse. The `kozou`
  config check that refuses `server.mcp.http.advertisedUrl` with a query or a
  fragment now names the key alone, as `startHttpServer`'s option already did.
  It had quoted the whole value since v1.18.0, and a query or fragment is where
  a token usually goes. An `allowedHosts` entry that is refused - as a URL, as a
  path, or because no hostname can be read from it - is now named by its index
  (`allowedHosts[1]`) rather than quoted, in the `kozou` config check and in
  `startHttpServer` alike. The same values are refused as before.

Behaviour changes for embedders and operators:

- An OAuth config (`server.mcp.http.auth`, or `startHttpServer`'s `auth`
  option) whose `resource` or `authorizationServers` entry carries userinfo, or
  whose `authorizationServers` entry carries a non-empty query or fragment, now
  fails at startup. Most such configs used to start. One that was already
  refused - for plaintext http, or for a query in `resource` - is now refused
  for the userinfo, or for the query in the entry, first.
- The refusals listed above name a key or an index where they quoted a value;
  other refusals are unchanged. When `KOZOU_MCP_HTTP_ALLOWED_HOSTS` holds empty
  items, the index counts only the non-empty ones, so it can differ from the
  item's position in the variable (#308).

Not covered: a password made only of digits with no `@` after it
(`https://user:4321/mcp`) parses as a host and a port, and cannot be told apart
from one, so such a value is still accepted as a host and a port.
@takashi-matsuyama
takashi-matsuyama merged commit 74b6860 into main Oct 19, 2026
21 checks passed
@takashi-matsuyama
takashi-matsuyama deleted the release/v1.20.1 branch October 19, 2026 00:16
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant