Skip to content

v1.1.1

Choose a tag to compare

@github-actions github-actions released this 07 Oct 00:46
· 189 commits to main since this release
0722c21

Fixed

  • The logger writes an Error passed in its data as its type, message,
    stack, code and cause chain. It wrote {}, so a logged failure such
    as the scaffold's seeding error carried no detail.
  • settlePendingLocalInvoices picks its invoices at random rather than
    oldest first, so an invoice that fails to settle on every run (an
    amount the provider disputes, a grant that throws) no longer holds back
    every invoice behind it, and starts no settle after deadlineMs
    (default 45 s), reporting the rest as deferred.
  • The payment-poll item's callback route answers { ok } only. It
    returned the settle summary, with each failure's message, to an
    unauthenticated caller.
  • The scaffold's assistant route answered every request with 429: its
    stand-in model example/echo-1 had no registered price, so admission
    refused it as unknown_model. The scaffold registers the stand-in at
    no cost, and the route answers a refusal only the deployment can fix
    with 503 and one the workspace can fix by paying with 402, and lets a
    failure other than a refused guard through instead of answering 401.
  • The stub chat model refuses to reply in a production build, so a
    deployment that never bound a real model in lib/chat-model.ts fails
    loudly instead of billing its users for an echo.
    INTELLIGO_ALLOW_STUB_MODEL=1, or allowInProduction in code, lets a
    deployment meant to run on it do so.
  • Stripe amounts for ISK, UGX and MNT. Stripe takes these in hundredths
    although none are in use, and they were sent as whole units — a charge
    at a hundredth of its price, or refused under Stripe's minimum. Credit
    checkout now converts through the new toStripeMinor, and amounts read
    back from Stripe (the payment-failed email, the admin revenue totals)
    through fromStripeMinor, both in @intelligo-dev/core/money. toMinor
    keeps the whole units local payment rails take.
  • A Stripe subscription that ended stays ended. A payment failure that
    arrives after customer.subscription.deleted no longer marks it
    past_due (which kept the paid plan), and the deletion drops the row's
    Stripe id. A plan granted to a workspace whose Stripe subscription
    ended — a local payment, grantPlan — now gets its period and lapses,
    instead of being taken for one Stripe still bills.
  • Quota admission no longer needs a second database connection inside its
    transaction. A billing settings cache miss read the settings through the
    shared pool while the transaction held its connection, so a pool full of
    admissions waited on each other forever. The settings are read first.
  • The database pool waits at most 15 seconds for a connection, so an
    exhausted pool fails requests instead of hanging the process, and logs
    an idle connection the server dropped instead of letting the unhandled
    error end the process. DATABASE_POOL_MAX sizes it (default 10).
  • A chat turn stopped mid-reply is charged for the step that was running.
    The finished steps were the only usage settled, so a reply stopped
    before its first step finished — every one-step turn — settled at
    zero while the provider billed it. The step in flight is now estimated
    from its prompt and what it had streamed.

Security

  • Better-Auth's organization endpoints that the team and workspace
    services wrap (create, update, delete, invite, accept, reject, cancel,
    remove, update role, leave) answer 404 over HTTP. Called directly they
    skipped the plan's member and workspace limits and the
    beforeDeleteWorkspace hook that cancels the subscription. The
    services, and set-active from the workspace switcher, are unaffected.
    A product that called these through authClient.organization calls the
    services instead.
  • A password reset ends every session that was open before it
    (revokeSessionsOnPasswordReset).
  • AUTH_IP_HEADERS and AUTH_TRUSTED_PROXIES tell the auth rate limiter
    where the client address is: without them, an app behind more than one
    proxy resolved no address and put every client in one bucket.
  • The scaffold's next.config.mjs sends frame-ancestors 'none',
    X-Frame-Options, X-Content-Type-Options, Referrer-Policy and
    Strict-Transport-Security on every response. An existing app adds the
    headers() block to its own config (intelligo upgrade --check shows
    the template changed).

Changed

  • A workspace that is its owner's only one cannot be deleted, and no one
    can leave their only workspace (last_workspace from the workspace and
    team services, with messages in workspace-settings and
    team-settings). With none left, the next page created a new personal
    workspace, and with it a new start for whatever the product grants one.

Upgrading

Run intelligo sync team-settings workspace-settings app-shell payment-poll chat for the new error messages, the callback route and the seam notes. Copy
the headers() block from the scaffold's next.config.mjs into your own.
A production deployment that runs on the stub chat model sets
INTELLIGO_ALLOW_STUB_MODEL=1; one behind more than one proxy sets
AUTH_IP_HEADERS / AUTH_TRUSTED_PROXIES. Code that called Better-Auth's
organization endpoints from the browser (authClient.organization.*,
other than setActive) calls the team and workspace services instead.