diff --git a/src/arts/active-app/service-factories/perm.ts b/src/arts/active-app/service-factories/perm.ts index c91a5ac..78d135d 100644 --- a/src/arts/active-app/service-factories/perm.ts +++ b/src/arts/active-app/service-factories/perm.ts @@ -1,4 +1,5 @@ import { createActivePerms } from '$perm/active-permissions.svelte'; +import type { EngineHttp } from '$http'; import type { ActivePerms, ActivePermsOptions } from '$perm/types'; import type { AppServiceFactory } from '../services.ts'; @@ -11,22 +12,33 @@ import type { AppServiceFactory } from '../services.ts'; * `applyPermInvalidateOnIdentityChange` to react to identity changes. * * The factory wires `logger` and `clock` from the core, so decision - * cache TTL math runs on `App.Timers.clock`. The application still - * needs to provide `endpoint` (or a custom `fetcher`) — the perm - * client cannot work without a backend. + * cache TTL math runs on `App.Timers.clock`. If `App` declares an `http` + * service, this factory also wires `App.http` as the perm client's + * `http` transport so retry/timeout/auth hooks composed at the App + * level apply uniformly. Apps that prefer their own transport can pass + * `http` or `fetcher` explicitly in `options` — those win over the + * App-level default. + * + * The application still needs to provide `endpoint` — the perm client + * cannot work without a backend. */ export function defineActivePerm( options: Omit -): AppServiceFactory<'perm', readonly ['logger', 'timers'], readonly [], ActivePerms> { +): AppServiceFactory<'perm', readonly ['logger', 'timers'], readonly ['http'], ActivePerms> { return { name: 'perm', coreDependencies: ['logger', 'timers'], + serviceDependencies: ['http'], initMode: 'lazy', - create({ core }): ActivePerms { + create({ core, services }): ActivePerms { + const httpFromApp = services.http as EngineHttp | undefined; return createActivePerms({ ...options, logger: core.logger, - clock: options.clock ?? { now: () => core.timers.clock.now() } + clock: options.clock ?? { now: () => core.timers.clock.now() }, + // Caller-provided `http`/`fetcher` win; otherwise inherit + // `App.http` when declared. + http: options.http ?? (options.fetcher === undefined ? httpFromApp : undefined) }); }, dispose(instance) {