@fungi.computer/puffball 0.0.0-stage → 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +443 -2
- package/dist/app-api.d.ts +7 -0
- package/dist/app-api.js +61 -0
- package/dist/app-backend-binding-vocabulary.d.ts +299 -0
- package/dist/app-backend-binding-vocabulary.js +257 -0
- package/dist/app-backend-bindings.d.ts +21 -0
- package/dist/app-backend-bindings.js +47 -0
- package/dist/app-declaration.d.ts +46 -0
- package/dist/app-declaration.js +115 -0
- package/dist/app-event-facts.d.ts +40 -0
- package/dist/app-event-facts.js +28 -0
- package/dist/app-method-context.d.ts +109 -0
- package/dist/app-method-context.js +9 -0
- package/dist/app-method-runtime.d.ts +86 -0
- package/dist/app-method-runtime.js +122 -0
- package/dist/app-origin-paths.d.ts +6 -0
- package/dist/app-origin-paths.js +6 -0
- package/dist/app-vocabulary.d.ts +189 -0
- package/dist/app-vocabulary.js +103 -0
- package/dist/app.d.ts +379 -0
- package/dist/app.js +71 -0
- package/dist/artifact-dispositions.d.ts +115 -0
- package/dist/artifact-dispositions.js +234 -0
- package/dist/assets.d.ts +54 -0
- package/dist/assets.js +89 -0
- package/dist/backend.d.ts +41 -0
- package/dist/backend.js +29 -0
- package/dist/background-replay.d.ts +115 -0
- package/dist/background-replay.js +175 -0
- package/dist/buyer-references.d.ts +69 -0
- package/dist/buyer-references.js +154 -0
- package/dist/cloudflare-assets.d.ts +48 -0
- package/dist/cloudflare-assets.js +105 -0
- package/dist/cloudflare.d.ts +254 -0
- package/dist/cloudflare.js +1619 -0
- package/dist/effect.d.ts +73 -0
- package/dist/effect.js +325 -0
- package/dist/git-representation.d.ts +13 -0
- package/dist/git-representation.js +16 -0
- package/dist/inbox.d.ts +132 -0
- package/dist/inbox.js +81 -0
- package/dist/index.d.ts +31 -0
- package/dist/index.js +85 -0
- package/dist/internal/app-description.d.ts +14 -0
- package/dist/internal/app-description.js +98 -0
- package/dist/internal/app-release-artifact-reader.d.ts +26 -0
- package/dist/internal/app-release-artifact-reader.js +1 -0
- package/dist/internal/app-release-contract.d.ts +540 -0
- package/dist/internal/app-release-contract.js +169 -0
- package/dist/internal/app-release-schema.d.ts +1676 -0
- package/dist/internal/app-release-schema.js +386 -0
- package/dist/internal/app-release-store.d.ts +47 -0
- package/dist/internal/app-release-store.js +1 -0
- package/dist/internal/background-sync.d.ts +7 -0
- package/dist/internal/background-sync.js +10 -0
- package/dist/internal/deterministic-memory-app-release-store.d.ts +14 -0
- package/dist/internal/deterministic-memory-app-release-store.js +319 -0
- package/dist/internal/failure.d.ts +2 -0
- package/dist/internal/failure.js +9 -0
- package/dist/internal/immutable-release-material.d.ts +3 -0
- package/dist/internal/immutable-release-material.js +13 -0
- package/dist/internal/promise-app-release-store-adapter.d.ts +9 -0
- package/dist/internal/promise-app-release-store-adapter.js +65 -0
- package/dist/internal/promise-artifact-reader-adapter.d.ts +9 -0
- package/dist/internal/promise-artifact-reader-adapter.js +18 -0
- package/dist/internal/public-route-sql.d.ts +10 -0
- package/dist/internal/public-route-sql.js +239 -0
- package/dist/internal/public-website-authority.d.ts +338 -0
- package/dist/internal/public-website-authority.js +50 -0
- package/dist/internal/public-website-delivery.d.ts +59 -0
- package/dist/internal/public-website-delivery.js +232 -0
- package/dist/internal/public-website-fetch.d.ts +8 -0
- package/dist/internal/public-website-fetch.js +54 -0
- package/dist/internal/release-transition-material.d.ts +3 -0
- package/dist/internal/release-transition-material.js +11 -0
- package/dist/internal/verified-artifact-snapshot.d.ts +41 -0
- package/dist/internal/verified-artifact-snapshot.js +91 -0
- package/dist/public-route-moderation.d.ts +83 -0
- package/dist/public-route-moderation.js +236 -0
- package/dist/public-route-policy.d.ts +51 -0
- package/dist/public-route-policy.js +88 -0
- package/dist/public-routes.d.ts +34 -0
- package/dist/public-routes.js +136 -0
- package/dist/publisher.d.ts +61 -0
- package/dist/publisher.js +16 -0
- package/dist/safety-takedown.d.ts +56 -0
- package/dist/safety-takedown.js +146 -0
- package/dist/seller-closure-notice.d.ts +14 -0
- package/dist/seller-closure-notice.js +14 -0
- package/dist/seller-closure.d.ts +15 -0
- package/dist/seller-closure.js +31 -0
- package/dist/testing.d.ts +8 -0
- package/dist/testing.js +47 -0
- package/docs/api/README.md +26 -0
- package/docs/api/app-backend-binding-vocabulary.md +276 -0
- package/docs/api/app-backend-bindings.md +141 -0
- package/docs/api/app-event-facts.md +110 -0
- package/docs/api/app-method-context.md +166 -0
- package/docs/api/app-method-runtime.md +330 -0
- package/docs/api/backend.md +108 -0
- package/docs/api/background-replay.md +516 -0
- package/docs/api/cloudflare.md +1044 -0
- package/docs/api/effect.md +2429 -0
- package/docs/api/git-representation.md +56 -0
- package/docs/api/inbox.md +289 -0
- package/docs/api/index.md +2868 -0
- package/docs/api/publisher.md +147 -0
- package/docs/api/testing.md +31 -0
- package/package.json +158 -3
|
@@ -0,0 +1,239 @@
|
|
|
1
|
+
/** Only trusted column expressions enter DDL; all request values are bound. */
|
|
2
|
+
export function routeKeySql(column) {
|
|
3
|
+
const slug = `CASE WHEN substr(${column},1,1)='/' THEN substr(${column},2) ELSE ${column} END`;
|
|
4
|
+
return `replace(replace(replace(replace(replace(replace(replace(${slug},'-',''),'_',''),'1','i'),'l','i'),'0','o'),'5','s'),'3','e')`;
|
|
5
|
+
}
|
|
6
|
+
/** Immutable Surface metadata and database-enforced policy comparison key. */
|
|
7
|
+
export const publicSurfaceTableSql = `
|
|
8
|
+
CREATE TABLE app_release_public_surfaces (
|
|
9
|
+
public_surface_id TEXT PRIMARY KEY,
|
|
10
|
+
app_id TEXT NOT NULL REFERENCES app_release_apps(app_id),
|
|
11
|
+
stable_route TEXT NOT NULL,
|
|
12
|
+
route_key TEXT NOT NULL CHECK(route_key = ${routeKeySql("stable_route")}),
|
|
13
|
+
publisher_team_id TEXT NOT NULL CHECK(length(publisher_team_id) BETWEEN 1 AND 256),
|
|
14
|
+
publisher_user_id TEXT NOT NULL CHECK(length(publisher_user_id) BETWEEN 1 AND 256),
|
|
15
|
+
authority_kind TEXT NOT NULL CHECK(authority_kind IN ('customer','platform')),
|
|
16
|
+
request_key TEXT NOT NULL CHECK(length(request_key) BETWEEN 1 AND 256),
|
|
17
|
+
UNIQUE(publisher_team_id,request_key)
|
|
18
|
+
) STRICT;
|
|
19
|
+
`.replaceAll("\n", " ");
|
|
20
|
+
/** Shared by the Surface insertion and the transition trigger's eligibility view. */
|
|
21
|
+
const surfaceEligibilitySql = `
|
|
22
|
+
NOT EXISTS (SELECT 1 FROM app_release_safety_takedowns a
|
|
23
|
+
WHERE a.app_id=s.app_id AND a.stable_route=s.stable_route)
|
|
24
|
+
AND
|
|
25
|
+
NOT EXISTS (
|
|
26
|
+
SELECT 1 FROM app_release_surface_retirements x
|
|
27
|
+
WHERE x.public_surface_id=s.public_surface_id
|
|
28
|
+
)
|
|
29
|
+
AND NOT EXISTS (
|
|
30
|
+
SELECT 1 FROM app_release_team_route_blocks b
|
|
31
|
+
WHERE b.team_id=s.publisher_team_id AND b.route_key=s.route_key
|
|
32
|
+
)
|
|
33
|
+
AND (c.route_key IS NOT NULL OR NOT EXISTS (
|
|
34
|
+
SELECT 1 FROM app_release_route_holds h
|
|
35
|
+
WHERE h.route_key=s.route_key AND h.until_s>unixepoch()
|
|
36
|
+
))
|
|
37
|
+
AND (c.route_key IS NULL OR
|
|
38
|
+
(c.public_surface_id=s.public_surface_id AND c.state='held'))
|
|
39
|
+
AND (s.authority_kind='platform' OR c.public_surface_id=s.public_surface_id OR
|
|
40
|
+
(SELECT count(*) FROM app_release_route_claims own
|
|
41
|
+
JOIN app_release_public_surfaces owned_surface ON owned_surface.public_surface_id=own.public_surface_id
|
|
42
|
+
WHERE own.team_id=s.publisher_team_id AND owned_surface.authority_kind='customer')<policy.max_team_routes)
|
|
43
|
+
AND (
|
|
44
|
+
(s.authority_kind='platform' AND EXISTS (
|
|
45
|
+
SELECT 1 FROM app_release_platform_routes p
|
|
46
|
+
WHERE p.stable_route=s.stable_route AND p.app_id=s.app_id
|
|
47
|
+
))
|
|
48
|
+
OR
|
|
49
|
+
(s.authority_kind='customer' AND EXISTS (
|
|
50
|
+
SELECT 1 FROM app_release_team_publishers p
|
|
51
|
+
WHERE p.app_id=s.app_id AND p.team_id=s.publisher_team_id
|
|
52
|
+
AND p.source_provider='artifacts' AND p.source_repository=p.app_id
|
|
53
|
+
AND p.source_branch='main' AND p.template_app_id IS NOT NULL
|
|
54
|
+
AND p.template_app_id<>p.app_id AND p.template_seed_revision IS NOT NULL
|
|
55
|
+
) AND (
|
|
56
|
+
c.public_surface_id=s.public_surface_id OR (
|
|
57
|
+
NOT EXISTS (SELECT 1 FROM app_release_platform_routes p
|
|
58
|
+
WHERE p.route_key=s.route_key)
|
|
59
|
+
AND NOT EXISTS (
|
|
60
|
+
SELECT 1 FROM app_release_reserved_route_keys k
|
|
61
|
+
WHERE (k.match_kind='exact' AND k.route_key=s.route_key)
|
|
62
|
+
OR (k.match_kind='prefix' AND
|
|
63
|
+
substr(s.route_key,1,length(k.route_key))=k.route_key
|
|
64
|
+
AND NOT EXISTS (SELECT 1 FROM app_release_route_brand_exceptions x WHERE x.route_key=s.route_key))
|
|
65
|
+
)
|
|
66
|
+
)
|
|
67
|
+
))
|
|
68
|
+
)`;
|
|
69
|
+
/** One write: pre-check custody and bound unused rows before minting any Surface. */
|
|
70
|
+
export const insertPublicSurfaceSql = `
|
|
71
|
+
WITH candidate(public_surface_id,app_id,stable_route,route_key,
|
|
72
|
+
publisher_team_id,publisher_user_id,authority_kind,request_key)
|
|
73
|
+
AS (VALUES (?,?,?,?,?,?,?,?))
|
|
74
|
+
INSERT INTO app_release_public_surfaces
|
|
75
|
+
(public_surface_id,app_id,stable_route,route_key,publisher_team_id,publisher_user_id,authority_kind,request_key)
|
|
76
|
+
SELECT s.public_surface_id,s.app_id,s.stable_route,s.route_key,
|
|
77
|
+
s.publisher_team_id,s.publisher_user_id,s.authority_kind,s.request_key
|
|
78
|
+
FROM candidate s
|
|
79
|
+
JOIN app_release_route_policy policy ON policy.singleton=1
|
|
80
|
+
LEFT JOIN app_release_route_claims c ON c.route_key=s.route_key
|
|
81
|
+
WHERE ${surfaceEligibilitySql}
|
|
82
|
+
AND (SELECT count(*) FROM app_release_public_surfaces unused
|
|
83
|
+
WHERE unused.app_id=s.app_id AND NOT EXISTS (
|
|
84
|
+
SELECT 1 FROM app_release_transitions t
|
|
85
|
+
WHERE t.public_surface_id=unused.public_surface_id
|
|
86
|
+
AND t.operation_kind IN ('promotion','rollback')
|
|
87
|
+
))<policy.max_unused_surfaces_per_app
|
|
88
|
+
ON CONFLICT DO NOTHING
|
|
89
|
+
RETURNING *`;
|
|
90
|
+
/** Current route custody is separate from immutable Surface and transition history. */
|
|
91
|
+
export const publicRouteSchemaSql = [
|
|
92
|
+
`CREATE TABLE app_release_route_policy (
|
|
93
|
+
singleton INTEGER PRIMARY KEY CHECK(singleton=1),
|
|
94
|
+
version INTEGER NOT NULL,
|
|
95
|
+
digest TEXT NOT NULL,
|
|
96
|
+
config_json TEXT NOT NULL CHECK(json_valid(config_json)),
|
|
97
|
+
max_team_routes INTEGER NOT NULL CHECK(max_team_routes>0),
|
|
98
|
+
max_unused_surfaces_per_app INTEGER NOT NULL CHECK(max_unused_surfaces_per_app>0)
|
|
99
|
+
) STRICT;`,
|
|
100
|
+
`CREATE TABLE app_release_reserved_route_keys (
|
|
101
|
+
word TEXT NOT NULL,
|
|
102
|
+
route_key TEXT NOT NULL CHECK(route_key = ${routeKeySql("word")}),
|
|
103
|
+
match_kind TEXT NOT NULL CHECK(match_kind IN ('exact','prefix')),
|
|
104
|
+
PRIMARY KEY(route_key,match_kind)
|
|
105
|
+
) STRICT;`,
|
|
106
|
+
`CREATE TABLE app_release_route_brand_exceptions (
|
|
107
|
+
word TEXT NOT NULL,
|
|
108
|
+
route_key TEXT PRIMARY KEY CHECK(route_key = ${routeKeySql("word")})
|
|
109
|
+
) STRICT;`,
|
|
110
|
+
`CREATE TABLE app_release_platform_routes (
|
|
111
|
+
stable_route TEXT NOT NULL,
|
|
112
|
+
route_key TEXT PRIMARY KEY CHECK(route_key = ${routeKeySql("stable_route")}),
|
|
113
|
+
app_id TEXT NOT NULL
|
|
114
|
+
) STRICT;`,
|
|
115
|
+
`CREATE TABLE app_release_route_claims (
|
|
116
|
+
route_key TEXT PRIMARY KEY CHECK(route_key = ${routeKeySql("stable_route")}),
|
|
117
|
+
stable_route TEXT NOT NULL,
|
|
118
|
+
public_surface_id TEXT NOT NULL UNIQUE REFERENCES app_release_public_surfaces(public_surface_id),
|
|
119
|
+
team_id TEXT NOT NULL,
|
|
120
|
+
user_id TEXT NOT NULL,
|
|
121
|
+
first_transition_id TEXT NOT NULL REFERENCES app_release_transitions(transition_id),
|
|
122
|
+
claimed_at INTEGER NOT NULL,
|
|
123
|
+
state TEXT NOT NULL CHECK(state IN ('held','removing')),
|
|
124
|
+
removal_operation_id TEXT,
|
|
125
|
+
CHECK((state='removing') = (removal_operation_id IS NOT NULL))
|
|
126
|
+
) STRICT;`,
|
|
127
|
+
`CREATE INDEX app_release_route_claims_team ON app_release_route_claims(team_id);`,
|
|
128
|
+
`CREATE TABLE app_release_route_holds (
|
|
129
|
+
route_key TEXT PRIMARY KEY CHECK(route_key = ${routeKeySql("stable_route")}),
|
|
130
|
+
stable_route TEXT NOT NULL,
|
|
131
|
+
until_s INTEGER NOT NULL,
|
|
132
|
+
cause TEXT NOT NULL CHECK(cause IN ('operator-release','erasure')),
|
|
133
|
+
operation_id TEXT NOT NULL
|
|
134
|
+
) STRICT;`,
|
|
135
|
+
`CREATE TABLE app_release_surface_retirements (
|
|
136
|
+
public_surface_id TEXT PRIMARY KEY REFERENCES app_release_public_surfaces(public_surface_id),
|
|
137
|
+
operation_id TEXT NOT NULL
|
|
138
|
+
) STRICT;`,
|
|
139
|
+
`CREATE TABLE app_release_team_route_blocks (
|
|
140
|
+
team_id TEXT NOT NULL,
|
|
141
|
+
route_key TEXT NOT NULL CHECK(route_key = ${routeKeySql("stable_route")}),
|
|
142
|
+
stable_route TEXT NOT NULL,
|
|
143
|
+
removal_operation_id TEXT NOT NULL,
|
|
144
|
+
PRIMARY KEY(team_id,route_key)
|
|
145
|
+
) STRICT;`,
|
|
146
|
+
`CREATE TABLE app_release_route_operations (
|
|
147
|
+
operation_id TEXT PRIMARY KEY,
|
|
148
|
+
kind TEXT NOT NULL CHECK(kind IN ('unlist-and-release','re-allow')),
|
|
149
|
+
public_surface_id TEXT NOT NULL,
|
|
150
|
+
app_id TEXT NOT NULL,
|
|
151
|
+
team_id TEXT NOT NULL,
|
|
152
|
+
stable_route TEXT NOT NULL,
|
|
153
|
+
route_key TEXT NOT NULL CHECK(route_key = ${routeKeySql("stable_route")}),
|
|
154
|
+
reason TEXT NOT NULL CHECK(length(reason) BETWEEN 1 AND 1000),
|
|
155
|
+
initiated_by TEXT NOT NULL,
|
|
156
|
+
created_at INTEGER NOT NULL,
|
|
157
|
+
removal_operation_id TEXT,
|
|
158
|
+
state TEXT NOT NULL CHECK(state IN ('pending','complete','superseded-by-erasure')),
|
|
159
|
+
completed_at INTEGER,
|
|
160
|
+
CHECK((kind='re-allow') = (removal_operation_id IS NOT NULL))
|
|
161
|
+
) STRICT;`,
|
|
162
|
+
`CREATE INDEX app_release_route_operations_pending ON app_release_route_operations(state,operation_id);`,
|
|
163
|
+
`CREATE TABLE app_release_route_operation_steps (
|
|
164
|
+
operation_id TEXT NOT NULL REFERENCES app_release_route_operations(operation_id),
|
|
165
|
+
phase TEXT NOT NULL CHECK(phase IN ('prepared','completed')),
|
|
166
|
+
operator_id TEXT NOT NULL,
|
|
167
|
+
recorded_at INTEGER NOT NULL,
|
|
168
|
+
PRIMARY KEY(operation_id,phase)
|
|
169
|
+
) STRICT;`,
|
|
170
|
+
`CREATE VIEW app_release_selection_ready AS
|
|
171
|
+
SELECT s.public_surface_id, s.app_id, s.stable_route, s.route_key,
|
|
172
|
+
s.publisher_team_id AS team_id, s.publisher_user_id AS user_id,
|
|
173
|
+
r.release_id,
|
|
174
|
+
CASE WHEN c.public_surface_id=s.public_surface_id AND c.state='held'
|
|
175
|
+
THEN 1 ELSE 0 END AS already_held
|
|
176
|
+
FROM app_release_public_surfaces s
|
|
177
|
+
JOIN app_release_releases r ON r.app_id=s.app_id
|
|
178
|
+
JOIN app_release_release_verifications v
|
|
179
|
+
ON v.release_id=r.release_id AND v.artifact_digest=r.artifact_digest
|
|
180
|
+
JOIN app_release_route_policy policy ON policy.singleton=1
|
|
181
|
+
LEFT JOIN app_release_route_claims c ON c.route_key=s.route_key
|
|
182
|
+
WHERE ${surfaceEligibilitySql}
|
|
183
|
+
AND NOT EXISTS (
|
|
184
|
+
SELECT 1 FROM app_release_transitions revoked
|
|
185
|
+
WHERE revoked.operation_kind='revocation' AND revoked.release_id=r.release_id
|
|
186
|
+
);`,
|
|
187
|
+
`CREATE TRIGGER app_release_selection_claim_before
|
|
188
|
+
BEFORE INSERT ON app_release_transitions
|
|
189
|
+
WHEN NEW.operation_kind IN ('promotion','rollback')
|
|
190
|
+
BEGIN
|
|
191
|
+
SELECT CASE WHEN NOT EXISTS (
|
|
192
|
+
SELECT 1 FROM app_release_selection_ready e
|
|
193
|
+
WHERE e.public_surface_id=NEW.public_surface_id
|
|
194
|
+
AND e.release_id=NEW.release_id
|
|
195
|
+
AND (NEW.operation_kind='promotion' OR
|
|
196
|
+
(e.already_held=1 AND EXISTS (
|
|
197
|
+
SELECT 1 FROM app_release_transitions prior
|
|
198
|
+
WHERE prior.public_surface_id=NEW.public_surface_id
|
|
199
|
+
AND prior.release_id=NEW.release_id
|
|
200
|
+
AND prior.operation_kind IN ('promotion','rollback')
|
|
201
|
+
)))
|
|
202
|
+
) THEN RAISE(ABORT,'publication_claim_refused') END;
|
|
203
|
+
END;`,
|
|
204
|
+
`CREATE TRIGGER app_release_selection_claim_after
|
|
205
|
+
AFTER INSERT ON app_release_transitions
|
|
206
|
+
WHEN NEW.operation_kind IN ('promotion','rollback')
|
|
207
|
+
BEGIN
|
|
208
|
+
INSERT INTO app_release_route_claims
|
|
209
|
+
(route_key,stable_route,public_surface_id,team_id,user_id,first_transition_id,claimed_at,state)
|
|
210
|
+
SELECT e.route_key,e.stable_route,e.public_surface_id,e.team_id,e.user_id,
|
|
211
|
+
NEW.transition_id,unixepoch(),'held'
|
|
212
|
+
FROM app_release_selection_ready e
|
|
213
|
+
WHERE e.public_surface_id=NEW.public_surface_id
|
|
214
|
+
AND e.release_id=NEW.release_id AND e.already_held=0
|
|
215
|
+
AND NEW.operation_kind='promotion'
|
|
216
|
+
AND EXISTS (
|
|
217
|
+
SELECT 1 FROM app_release_transitions t
|
|
218
|
+
WHERE t.transition_id=NEW.transition_id
|
|
219
|
+
AND t.operation_kind=NEW.operation_kind
|
|
220
|
+
AND t.idempotency_key=NEW.idempotency_key
|
|
221
|
+
AND t.release_id=NEW.release_id
|
|
222
|
+
AND t.public_surface_id=NEW.public_surface_id
|
|
223
|
+
);
|
|
224
|
+
SELECT CASE WHEN NOT EXISTS (
|
|
225
|
+
SELECT 1 FROM app_release_route_claims c
|
|
226
|
+
JOIN app_release_public_surfaces s ON s.public_surface_id=c.public_surface_id
|
|
227
|
+
WHERE c.public_surface_id=NEW.public_surface_id
|
|
228
|
+
AND c.route_key=s.route_key AND c.team_id=s.publisher_team_id
|
|
229
|
+
AND c.state='held'
|
|
230
|
+
) THEN RAISE(ABORT,'publication_claim_missing') END;
|
|
231
|
+
END;`,
|
|
232
|
+
]
|
|
233
|
+
.map((statement) => statement.replaceAll("\n", " "))
|
|
234
|
+
.join("\n");
|
|
235
|
+
/** Operator replay history preserves original Surface attribution. */
|
|
236
|
+
export const platformOwnerReplaySchemaSql = `
|
|
237
|
+
CREATE TABLE app_release_platform_owner_replays (sequence INTEGER PRIMARY KEY AUTOINCREMENT, public_surface_id TEXT NOT NULL, app_id TEXT NOT NULL, stable_route TEXT NOT NULL, owner_team_id TEXT NOT NULL, publisher_user_id TEXT NOT NULL, operator_user_id TEXT NOT NULL, recorded_at INTEGER NOT NULL) STRICT;
|
|
238
|
+
CREATE INDEX app_release_platform_owner_replays_app ON app_release_platform_owner_replays(app_id);
|
|
239
|
+
`;
|
|
@@ -0,0 +1,338 @@
|
|
|
1
|
+
import * as Effect from "effect/Effect";
|
|
2
|
+
import * as Schema from "effect/Schema";
|
|
3
|
+
import type { AppReleaseStoreResult, PromiseAppReleaseStore, ReleaseId, StableRoute } from "./app-release-contract.js";
|
|
4
|
+
import type { AppReleaseStore, AppReleaseStorePortFailure } from "./app-release-store.js";
|
|
5
|
+
/** Private atomic route, selection, and selected Release delivery facts. */
|
|
6
|
+
export type PublicWebsiteAuthority = Schema.Schema.Type<typeof authoritySchema>;
|
|
7
|
+
/** One atomic route authority query, optionally pinned to a previously selected Release. */
|
|
8
|
+
export type PublicWebsiteAuthorityRequest = Readonly<{
|
|
9
|
+
readonly stableRoute: StableRoute;
|
|
10
|
+
readonly expectedReleaseId?: ReleaseId;
|
|
11
|
+
}>;
|
|
12
|
+
export type PromisePublicWebsiteAuthorityReader = (requests: readonly PublicWebsiteAuthorityRequest[]) => Promise<AppReleaseStoreResult<readonly PublicWebsiteAuthority[]>>;
|
|
13
|
+
export type EffectPublicWebsiteAuthorityReader = (requests: readonly PublicWebsiteAuthorityRequest[]) => Effect.Effect<readonly PublicWebsiteAuthority[], AppReleaseStorePortFailure>;
|
|
14
|
+
declare const authoritySchema: Schema.Union<readonly [Schema.Struct<{
|
|
15
|
+
readonly kind: Schema.Literal<"absent">;
|
|
16
|
+
}>, Schema.Struct<{
|
|
17
|
+
readonly kind: Schema.Literal<"ambiguous">;
|
|
18
|
+
}>, Schema.Struct<{
|
|
19
|
+
readonly kind: Schema.Literal<"unselected">;
|
|
20
|
+
readonly app: Schema.Struct<{
|
|
21
|
+
readonly appId: Schema.refine<import("./app-release-contract.js").AppId, Schema.String>;
|
|
22
|
+
}>;
|
|
23
|
+
readonly surface: Schema.Struct<{
|
|
24
|
+
readonly publicSurfaceId: Schema.refine<import("./app-release-contract.js").PublicSurfaceId, Schema.String>;
|
|
25
|
+
readonly appId: Schema.refine<import("./app-release-contract.js").AppId, Schema.String>;
|
|
26
|
+
readonly stableRoute: Schema.refine<StableRoute, Schema.String>;
|
|
27
|
+
}>;
|
|
28
|
+
}>, Schema.Struct<{
|
|
29
|
+
readonly kind: Schema.Literal<"selected">;
|
|
30
|
+
readonly app: Schema.Struct<{
|
|
31
|
+
readonly appId: Schema.refine<import("./app-release-contract.js").AppId, Schema.String>;
|
|
32
|
+
}>;
|
|
33
|
+
readonly surface: Schema.Struct<{
|
|
34
|
+
readonly publicSurfaceId: Schema.refine<import("./app-release-contract.js").PublicSurfaceId, Schema.String>;
|
|
35
|
+
readonly appId: Schema.refine<import("./app-release-contract.js").AppId, Schema.String>;
|
|
36
|
+
readonly stableRoute: Schema.refine<StableRoute, Schema.String>;
|
|
37
|
+
}>;
|
|
38
|
+
readonly releaseId: Schema.refine<ReleaseId, Schema.String>;
|
|
39
|
+
readonly currentReleaseId: Schema.refine<ReleaseId, Schema.String>;
|
|
40
|
+
readonly sequence: Schema.Number;
|
|
41
|
+
readonly release: Schema.Union<readonly [Schema.Struct<{
|
|
42
|
+
readonly kind: Schema.Literal<"found">;
|
|
43
|
+
readonly release: Schema.Struct<{
|
|
44
|
+
readonly releaseId: Schema.refine<ReleaseId, Schema.String>;
|
|
45
|
+
readonly appId: Schema.refine<import("./app-release-contract.js").AppId, Schema.String>;
|
|
46
|
+
readonly artifact: Schema.Struct<{
|
|
47
|
+
readonly artifactRef: Schema.refine<import("./app-release-contract.js").ArtifactRef, Schema.String>;
|
|
48
|
+
readonly artifactDigest: Schema.refine<import("./app-release-contract.js").Sha256Digest, Schema.String>;
|
|
49
|
+
readonly provenance: Schema.Struct<{
|
|
50
|
+
readonly sourceRevision: Schema.refine<import("./app-release-contract.js").SourceRevision, Schema.String>;
|
|
51
|
+
readonly sourceTreeDigest: Schema.refine<import("./app-release-contract.js").Sha256Digest, Schema.String>;
|
|
52
|
+
readonly buildRecipeDigest: Schema.refine<import("./app-release-contract.js").Sha256Digest, Schema.String>;
|
|
53
|
+
}>;
|
|
54
|
+
}>;
|
|
55
|
+
}>;
|
|
56
|
+
readonly verification: Schema.Union<readonly [Schema.Struct<{
|
|
57
|
+
readonly kind: Schema.Literal<"verified">;
|
|
58
|
+
readonly digest: Schema.refine<import("./app-release-contract.js").Sha256Digest, Schema.String>;
|
|
59
|
+
readonly mediaType: Schema.Literal<"application/vnd.fungi.app+json">;
|
|
60
|
+
readonly description: Schema.Struct<{
|
|
61
|
+
readonly format: Schema.Literal<"fungi-app-v1">;
|
|
62
|
+
readonly ui: Schema.NullOr<Schema.Struct<{
|
|
63
|
+
readonly artifactRef: Schema.refine<import("./app-release-contract.js").ArtifactRef, Schema.String>;
|
|
64
|
+
readonly digest: Schema.refine<import("./app-release-contract.js").Sha256Digest, Schema.String>;
|
|
65
|
+
readonly mediaType: Schema.Literals<readonly ["text/html; charset=utf-8", "application/vnd.fungi.app-backend+json", "application/vnd.fungi.app-assets+json"]>;
|
|
66
|
+
readonly version: Schema.String;
|
|
67
|
+
readonly byteLength: Schema.Number;
|
|
68
|
+
}>>;
|
|
69
|
+
readonly backend: Schema.NullOr<Schema.Struct<{
|
|
70
|
+
readonly artifact: Schema.Struct<{
|
|
71
|
+
readonly artifactRef: Schema.refine<import("./app-release-contract.js").ArtifactRef, Schema.String>;
|
|
72
|
+
readonly digest: Schema.refine<import("./app-release-contract.js").Sha256Digest, Schema.String>;
|
|
73
|
+
readonly mediaType: Schema.Literals<readonly ["text/html; charset=utf-8", "application/vnd.fungi.app-backend+json", "application/vnd.fungi.app-assets+json"]>;
|
|
74
|
+
readonly version: Schema.String;
|
|
75
|
+
readonly byteLength: Schema.Number;
|
|
76
|
+
}>;
|
|
77
|
+
readonly profile: Schema.Struct<{
|
|
78
|
+
readonly runtime: Schema.Struct<{
|
|
79
|
+
readonly kind: Schema.Literal<"durable-facet">;
|
|
80
|
+
readonly stateSchema: Schema.Number;
|
|
81
|
+
}>;
|
|
82
|
+
readonly compatibilityDate: Schema.String;
|
|
83
|
+
readonly exportName: Schema.String;
|
|
84
|
+
}>;
|
|
85
|
+
}>>;
|
|
86
|
+
readonly declaration: Schema.withDecodingDefaultType<Schema.Codec<Readonly<{
|
|
87
|
+
api?: import("../app-vocabulary.js").AppApi;
|
|
88
|
+
displayName?: string | undefined;
|
|
89
|
+
capabilities: readonly import("../app-vocabulary.js").AppCapabilityId[];
|
|
90
|
+
calls?: readonly Readonly<{
|
|
91
|
+
appId: string;
|
|
92
|
+
methods: readonly string[];
|
|
93
|
+
}>[] | undefined;
|
|
94
|
+
guidance?: string | undefined;
|
|
95
|
+
handlers: readonly import("../app-vocabulary.js").AppHandler[];
|
|
96
|
+
receives?: readonly "git.push"[] | undefined;
|
|
97
|
+
icon?: string;
|
|
98
|
+
roles: readonly import("../app-vocabulary.js").AppRole[];
|
|
99
|
+
storage?: readonly import("../app-vocabulary.js").AppStorageKey[] | undefined;
|
|
100
|
+
commands?: readonly import("../app-vocabulary.js").AppDeclaredCommand[] | undefined;
|
|
101
|
+
gills?: readonly import("@fungi.computer/gills").AppDeclaredGill[] | undefined;
|
|
102
|
+
backend?: Readonly<{
|
|
103
|
+
bindings: readonly import("../app-backend-binding-vocabulary.js").AppBackendBinding[];
|
|
104
|
+
sync?: Readonly<{
|
|
105
|
+
method: string;
|
|
106
|
+
}>;
|
|
107
|
+
}> | undefined;
|
|
108
|
+
}>, Readonly<{
|
|
109
|
+
api?: import("../app-vocabulary.js").AppApi;
|
|
110
|
+
displayName?: string | undefined;
|
|
111
|
+
capabilities: readonly import("../app-vocabulary.js").AppCapabilityId[];
|
|
112
|
+
calls?: readonly Readonly<{
|
|
113
|
+
appId: string;
|
|
114
|
+
methods: readonly string[];
|
|
115
|
+
}>[] | undefined;
|
|
116
|
+
guidance?: string | undefined;
|
|
117
|
+
handlers: readonly import("../app-vocabulary.js").AppHandler[];
|
|
118
|
+
receives?: readonly "git.push"[] | undefined;
|
|
119
|
+
icon?: string;
|
|
120
|
+
roles: readonly import("../app-vocabulary.js").AppRole[];
|
|
121
|
+
storage?: readonly import("../app-vocabulary.js").AppStorageKey[] | undefined;
|
|
122
|
+
commands?: readonly import("../app-vocabulary.js").AppDeclaredCommand[] | undefined;
|
|
123
|
+
gills?: readonly import("@fungi.computer/gills").AppDeclaredGill[] | undefined;
|
|
124
|
+
backend?: Readonly<{
|
|
125
|
+
bindings: readonly import("../app-backend-binding-vocabulary.js").AppBackendBinding[];
|
|
126
|
+
sync?: Readonly<{
|
|
127
|
+
method: string;
|
|
128
|
+
}>;
|
|
129
|
+
}> | undefined;
|
|
130
|
+
}>, never, never>, never>;
|
|
131
|
+
}>;
|
|
132
|
+
}>, Schema.Struct<{
|
|
133
|
+
readonly kind: Schema.Literal<"unverified">;
|
|
134
|
+
}>]>;
|
|
135
|
+
readonly revocation: Schema.Union<readonly [Schema.Struct<{
|
|
136
|
+
readonly kind: Schema.Literal<"active">;
|
|
137
|
+
}>, Schema.Struct<{
|
|
138
|
+
readonly kind: Schema.Literal<"revoked">;
|
|
139
|
+
}>]>;
|
|
140
|
+
}>, Schema.Struct<{
|
|
141
|
+
readonly kind: Schema.Literal<"absent">;
|
|
142
|
+
}>]>;
|
|
143
|
+
}>]>;
|
|
144
|
+
export declare const decodePublicWebsiteAuthorityStoreResult: (input: unknown, options?: import("effect/SchemaAST").ParseOptions) => import("effect/Result").Result<{
|
|
145
|
+
readonly kind: "success";
|
|
146
|
+
readonly value: readonly ({
|
|
147
|
+
readonly kind: "absent";
|
|
148
|
+
} | {
|
|
149
|
+
readonly kind: "ambiguous";
|
|
150
|
+
} | {
|
|
151
|
+
readonly kind: "unselected";
|
|
152
|
+
readonly app: {
|
|
153
|
+
readonly appId: import("./app-release-contract.js").AppId;
|
|
154
|
+
};
|
|
155
|
+
readonly surface: {
|
|
156
|
+
readonly publicSurfaceId: import("./app-release-contract.js").PublicSurfaceId;
|
|
157
|
+
readonly appId: import("./app-release-contract.js").AppId;
|
|
158
|
+
readonly stableRoute: StableRoute;
|
|
159
|
+
};
|
|
160
|
+
} | {
|
|
161
|
+
readonly kind: "selected";
|
|
162
|
+
readonly app: {
|
|
163
|
+
readonly appId: import("./app-release-contract.js").AppId;
|
|
164
|
+
};
|
|
165
|
+
readonly surface: {
|
|
166
|
+
readonly publicSurfaceId: import("./app-release-contract.js").PublicSurfaceId;
|
|
167
|
+
readonly appId: import("./app-release-contract.js").AppId;
|
|
168
|
+
readonly stableRoute: StableRoute;
|
|
169
|
+
};
|
|
170
|
+
readonly releaseId: ReleaseId;
|
|
171
|
+
readonly currentReleaseId: ReleaseId;
|
|
172
|
+
readonly sequence: number;
|
|
173
|
+
readonly release: {
|
|
174
|
+
readonly kind: "found";
|
|
175
|
+
readonly release: {
|
|
176
|
+
readonly releaseId: ReleaseId;
|
|
177
|
+
readonly appId: import("./app-release-contract.js").AppId;
|
|
178
|
+
readonly artifact: {
|
|
179
|
+
readonly artifactRef: import("./app-release-contract.js").ArtifactRef;
|
|
180
|
+
readonly artifactDigest: import("./app-release-contract.js").Sha256Digest;
|
|
181
|
+
readonly provenance: {
|
|
182
|
+
readonly sourceRevision: import("./app-release-contract.js").SourceRevision;
|
|
183
|
+
readonly sourceTreeDigest: import("./app-release-contract.js").Sha256Digest;
|
|
184
|
+
readonly buildRecipeDigest: import("./app-release-contract.js").Sha256Digest;
|
|
185
|
+
};
|
|
186
|
+
};
|
|
187
|
+
};
|
|
188
|
+
readonly verification: {
|
|
189
|
+
readonly kind: "verified";
|
|
190
|
+
readonly digest: import("./app-release-contract.js").Sha256Digest;
|
|
191
|
+
readonly mediaType: "application/vnd.fungi.app+json";
|
|
192
|
+
readonly description: {
|
|
193
|
+
readonly format: "fungi-app-v1";
|
|
194
|
+
readonly ui: {
|
|
195
|
+
readonly artifactRef: import("./app-release-contract.js").ArtifactRef;
|
|
196
|
+
readonly digest: import("./app-release-contract.js").Sha256Digest;
|
|
197
|
+
readonly mediaType: "text/html; charset=utf-8" | "application/vnd.fungi.app-backend+json" | "application/vnd.fungi.app-assets+json";
|
|
198
|
+
readonly version: string;
|
|
199
|
+
readonly byteLength: number;
|
|
200
|
+
} | null;
|
|
201
|
+
readonly backend: {
|
|
202
|
+
readonly artifact: {
|
|
203
|
+
readonly artifactRef: import("./app-release-contract.js").ArtifactRef;
|
|
204
|
+
readonly digest: import("./app-release-contract.js").Sha256Digest;
|
|
205
|
+
readonly mediaType: "text/html; charset=utf-8" | "application/vnd.fungi.app-backend+json" | "application/vnd.fungi.app-assets+json";
|
|
206
|
+
readonly version: string;
|
|
207
|
+
readonly byteLength: number;
|
|
208
|
+
};
|
|
209
|
+
readonly profile: {
|
|
210
|
+
readonly runtime: {
|
|
211
|
+
readonly kind: "durable-facet";
|
|
212
|
+
readonly stateSchema: number;
|
|
213
|
+
};
|
|
214
|
+
readonly compatibilityDate: string;
|
|
215
|
+
readonly exportName: string;
|
|
216
|
+
};
|
|
217
|
+
} | null;
|
|
218
|
+
readonly declaration: Readonly<{
|
|
219
|
+
api?: Readonly<{
|
|
220
|
+
methods: Readonly<Record<string, Readonly<{
|
|
221
|
+
description: string;
|
|
222
|
+
input: object;
|
|
223
|
+
output: object;
|
|
224
|
+
effect: "read" | "write" | "external";
|
|
225
|
+
requires: readonly import("../app-vocabulary.js").AppCapabilityId[];
|
|
226
|
+
pending?: true | undefined;
|
|
227
|
+
hidden?: true | undefined;
|
|
228
|
+
anonymous?: true | undefined;
|
|
229
|
+
}>>>;
|
|
230
|
+
toolFamily?: Readonly<{
|
|
231
|
+
name: string;
|
|
232
|
+
list: string;
|
|
233
|
+
call: string;
|
|
234
|
+
}>;
|
|
235
|
+
events?: Readonly<Record<string, Readonly<{
|
|
236
|
+
description: string;
|
|
237
|
+
payload: object;
|
|
238
|
+
}>>>;
|
|
239
|
+
}>;
|
|
240
|
+
displayName?: string | undefined;
|
|
241
|
+
capabilities: readonly import("../app-vocabulary.js").AppCapabilityId[];
|
|
242
|
+
calls?: readonly Readonly<{
|
|
243
|
+
appId: string;
|
|
244
|
+
methods: readonly string[];
|
|
245
|
+
}>[] | undefined;
|
|
246
|
+
guidance?: string | undefined;
|
|
247
|
+
handlers: readonly import("../app-vocabulary.js").AppHandler[];
|
|
248
|
+
receives?: readonly "git.push"[] | undefined;
|
|
249
|
+
icon?: string;
|
|
250
|
+
roles: readonly import("../app-vocabulary.js").AppRole[];
|
|
251
|
+
storage?: readonly Readonly<{
|
|
252
|
+
key: string;
|
|
253
|
+
scopes: readonly import("../app-vocabulary.js").AppStorageScope[];
|
|
254
|
+
maxBytes: number;
|
|
255
|
+
}>[] | undefined;
|
|
256
|
+
commands?: readonly Readonly<{
|
|
257
|
+
id: string;
|
|
258
|
+
title: string;
|
|
259
|
+
category: string;
|
|
260
|
+
description?: string | undefined;
|
|
261
|
+
sigil?: string | undefined;
|
|
262
|
+
projections?: Readonly<{
|
|
263
|
+
bindings?: (Readonly<{
|
|
264
|
+
order?: number | undefined;
|
|
265
|
+
}> & Readonly<{
|
|
266
|
+
values: readonly string[];
|
|
267
|
+
}>) | undefined;
|
|
268
|
+
agent?: (Readonly<{
|
|
269
|
+
order?: number | undefined;
|
|
270
|
+
}> & Readonly<{
|
|
271
|
+
keybind?: string | undefined;
|
|
272
|
+
}>) | undefined;
|
|
273
|
+
help?: Readonly<{
|
|
274
|
+
order?: number | undefined;
|
|
275
|
+
}> | undefined;
|
|
276
|
+
menu?: Readonly<{
|
|
277
|
+
order?: number | undefined;
|
|
278
|
+
}> | undefined;
|
|
279
|
+
palette?: Readonly<{
|
|
280
|
+
order?: number | undefined;
|
|
281
|
+
}> | undefined;
|
|
282
|
+
slash?: (Readonly<{
|
|
283
|
+
order?: number | undefined;
|
|
284
|
+
}> & Readonly<{
|
|
285
|
+
aliases: readonly string[];
|
|
286
|
+
}>) | undefined;
|
|
287
|
+
}> | undefined;
|
|
288
|
+
}>[] | undefined;
|
|
289
|
+
gills?: readonly Readonly<{
|
|
290
|
+
id: string;
|
|
291
|
+
source: string;
|
|
292
|
+
title: string;
|
|
293
|
+
params?: readonly Readonly<{
|
|
294
|
+
key: string;
|
|
295
|
+
label: string;
|
|
296
|
+
kind: "computer" | "repository" | "branch";
|
|
297
|
+
required: boolean;
|
|
298
|
+
options?: string | undefined;
|
|
299
|
+
}>[] | undefined;
|
|
300
|
+
watch?: import("@fungi.computer/gills").AppGillWatch | undefined;
|
|
301
|
+
desktop?: Readonly<{
|
|
302
|
+
sizes: readonly import("@fungi.computer/gills").AppGillDesktopSize[];
|
|
303
|
+
}> | undefined;
|
|
304
|
+
}>[] | undefined;
|
|
305
|
+
backend?: Readonly<{
|
|
306
|
+
bindings: readonly Readonly<{
|
|
307
|
+
name: import("../app-backend-binding-vocabulary.js").AppBackendBindingName;
|
|
308
|
+
operations: readonly string[];
|
|
309
|
+
}>[];
|
|
310
|
+
sync?: Readonly<{
|
|
311
|
+
method: string;
|
|
312
|
+
}>;
|
|
313
|
+
}> | undefined;
|
|
314
|
+
}>;
|
|
315
|
+
};
|
|
316
|
+
} | {
|
|
317
|
+
readonly kind: "unverified";
|
|
318
|
+
};
|
|
319
|
+
readonly revocation: {
|
|
320
|
+
readonly kind: "active";
|
|
321
|
+
} | {
|
|
322
|
+
readonly kind: "revoked";
|
|
323
|
+
};
|
|
324
|
+
} | {
|
|
325
|
+
readonly kind: "absent";
|
|
326
|
+
};
|
|
327
|
+
})[];
|
|
328
|
+
} | {
|
|
329
|
+
readonly kind: "failure";
|
|
330
|
+
readonly failure: {
|
|
331
|
+
readonly kind: "unavailable";
|
|
332
|
+
};
|
|
333
|
+
}, Schema.SchemaError>;
|
|
334
|
+
export declare function registerPromisePublicWebsiteAuthorityReader(store: PromiseAppReleaseStore, reader: PromisePublicWebsiteAuthorityReader): PromiseAppReleaseStore;
|
|
335
|
+
export declare function getPromisePublicWebsiteAuthorityReader(store: PromiseAppReleaseStore): PromisePublicWebsiteAuthorityReader | undefined;
|
|
336
|
+
export declare function registerEffectPublicWebsiteAuthorityReader(store: AppReleaseStore, reader: EffectPublicWebsiteAuthorityReader): AppReleaseStore;
|
|
337
|
+
export declare function getEffectPublicWebsiteAuthorityReader(store: AppReleaseStore): EffectPublicWebsiteAuthorityReader | undefined;
|
|
338
|
+
export {};
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import * as Effect from "effect/Effect";
|
|
2
|
+
import * as Schema from "effect/Schema";
|
|
3
|
+
import { publicSurfaceSchema, appSchema, releaseIdSchema, releaseLifecycleSchema, } from "./app-release-schema.js";
|
|
4
|
+
const promiseReaders = new WeakMap();
|
|
5
|
+
const effectReaders = new WeakMap();
|
|
6
|
+
const authoritySchema = Schema.Union([
|
|
7
|
+
Schema.Struct({ kind: Schema.Literal("absent") }),
|
|
8
|
+
Schema.Struct({ kind: Schema.Literal("ambiguous") }),
|
|
9
|
+
Schema.Struct({
|
|
10
|
+
kind: Schema.Literal("unselected"),
|
|
11
|
+
app: appSchema,
|
|
12
|
+
surface: publicSurfaceSchema,
|
|
13
|
+
}),
|
|
14
|
+
Schema.Struct({
|
|
15
|
+
kind: Schema.Literal("selected"),
|
|
16
|
+
app: appSchema,
|
|
17
|
+
surface: publicSurfaceSchema,
|
|
18
|
+
releaseId: releaseIdSchema,
|
|
19
|
+
currentReleaseId: releaseIdSchema,
|
|
20
|
+
sequence: Schema.Number.pipe(Schema.check(Schema.isInt()), Schema.check(Schema.isGreaterThan(0))),
|
|
21
|
+
release: releaseLifecycleSchema,
|
|
22
|
+
}),
|
|
23
|
+
]);
|
|
24
|
+
const authorityStoreResultSchema = Schema.Union([
|
|
25
|
+
Schema.Struct({
|
|
26
|
+
kind: Schema.Literal("success"),
|
|
27
|
+
value: Schema.Array(authoritySchema),
|
|
28
|
+
}),
|
|
29
|
+
Schema.Struct({
|
|
30
|
+
kind: Schema.Literal("failure"),
|
|
31
|
+
failure: Schema.Struct({ kind: Schema.Literal("unavailable") }),
|
|
32
|
+
}),
|
|
33
|
+
]);
|
|
34
|
+
export const decodePublicWebsiteAuthorityStoreResult = Schema.decodeUnknownResult(authorityStoreResultSchema, {
|
|
35
|
+
onExcessProperty: "error",
|
|
36
|
+
});
|
|
37
|
+
export function registerPromisePublicWebsiteAuthorityReader(store, reader) {
|
|
38
|
+
promiseReaders.set(store, reader);
|
|
39
|
+
return store;
|
|
40
|
+
}
|
|
41
|
+
export function getPromisePublicWebsiteAuthorityReader(store) {
|
|
42
|
+
return promiseReaders.get(store);
|
|
43
|
+
}
|
|
44
|
+
export function registerEffectPublicWebsiteAuthorityReader(store, reader) {
|
|
45
|
+
effectReaders.set(store, reader);
|
|
46
|
+
return store;
|
|
47
|
+
}
|
|
48
|
+
export function getEffectPublicWebsiteAuthorityReader(store) {
|
|
49
|
+
return effectReaders.get(store);
|
|
50
|
+
}
|