@panorama-industries/effect-vercel-blob 0.0.0-stage → 0.2.0
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 +13 -2
- package/dist/client.d.ts +8 -0
- package/dist/client.d.ts.map +1 -0
- package/dist/client.js +8 -0
- package/dist/client.js.map +1 -0
- package/dist/contracts/blob-client.d.ts +67 -0
- package/dist/contracts/blob-client.d.ts.map +1 -0
- package/dist/contracts/blob-client.js +11 -0
- package/dist/contracts/blob-client.js.map +1 -0
- package/dist/contracts/blob-config.d.ts +114 -0
- package/dist/contracts/blob-config.d.ts.map +1 -0
- package/dist/contracts/blob-config.js +7 -0
- package/dist/contracts/blob-config.js.map +1 -0
- package/dist/contracts/blob-domain.d.ts +336 -0
- package/dist/contracts/blob-domain.d.ts.map +1 -0
- package/dist/contracts/blob-domain.js +152 -0
- package/dist/contracts/blob-domain.js.map +1 -0
- package/dist/contracts/blob-errors.d.ts +125 -0
- package/dist/contracts/blob-errors.d.ts.map +1 -0
- package/dist/contracts/blob-errors.js +114 -0
- package/dist/contracts/blob-errors.js.map +1 -0
- package/dist/contracts/blob-signed-urls.d.ts +83 -0
- package/dist/contracts/blob-signed-urls.d.ts.map +1 -0
- package/dist/contracts/blob-signed-urls.js +10 -0
- package/dist/contracts/blob-signed-urls.js.map +1 -0
- package/dist/contracts/blob-store.d.ts +153 -0
- package/dist/contracts/blob-store.d.ts.map +1 -0
- package/dist/contracts/blob-store.js +15 -0
- package/dist/contracts/blob-store.js.map +1 -0
- package/dist/contracts/blob-uploads.d.ts +101 -0
- package/dist/contracts/blob-uploads.d.ts.map +1 -0
- package/dist/contracts/blob-uploads.js +17 -0
- package/dist/contracts/blob-uploads.js.map +1 -0
- package/dist/implementation/blob-client-live.d.ts +37 -0
- package/dist/implementation/blob-client-live.d.ts.map +1 -0
- package/dist/implementation/blob-client-live.js +213 -0
- package/dist/implementation/blob-client-live.js.map +1 -0
- package/dist/implementation/blob-config-live.d.ts +49 -0
- package/dist/implementation/blob-config-live.d.ts.map +1 -0
- package/dist/implementation/blob-config-live.js +82 -0
- package/dist/implementation/blob-config-live.js.map +1 -0
- package/dist/implementation/blob-live.d.ts +16 -0
- package/dist/implementation/blob-live.d.ts.map +1 -0
- package/dist/implementation/blob-live.js +16 -0
- package/dist/implementation/blob-live.js.map +1 -0
- package/dist/implementation/blob-signed-urls-live.d.ts +12 -0
- package/dist/implementation/blob-signed-urls-live.d.ts.map +1 -0
- package/dist/implementation/blob-signed-urls-live.js +92 -0
- package/dist/implementation/blob-signed-urls-live.js.map +1 -0
- package/dist/implementation/blob-store-live.d.ts +18 -0
- package/dist/implementation/blob-store-live.d.ts.map +1 -0
- package/dist/implementation/blob-store-live.js +364 -0
- package/dist/implementation/blob-store-live.js.map +1 -0
- package/dist/implementation/blob-uploads-live.d.ts +11 -0
- package/dist/implementation/blob-uploads-live.d.ts.map +1 -0
- package/dist/implementation/blob-uploads-live.js +218 -0
- package/dist/implementation/blob-uploads-live.js.map +1 -0
- package/dist/index.d.ts +15 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +15 -0
- package/dist/index.js.map +1 -0
- package/dist/internal/blob-errors.d.ts +79 -0
- package/dist/internal/blob-errors.d.ts.map +1 -0
- package/dist/internal/blob-errors.js +196 -0
- package/dist/internal/blob-errors.js.map +1 -0
- package/dist/internal/blob-request.d.ts +255 -0
- package/dist/internal/blob-request.d.ts.map +1 -0
- package/dist/internal/blob-request.js +291 -0
- package/dist/internal/blob-request.js.map +1 -0
- package/dist/internal/callback.d.ts +70 -0
- package/dist/internal/callback.d.ts.map +1 -0
- package/dist/internal/callback.js +141 -0
- package/dist/internal/callback.js.map +1 -0
- package/dist/internal/client-token.d.ts +65 -0
- package/dist/internal/client-token.d.ts.map +1 -0
- package/dist/internal/client-token.js +80 -0
- package/dist/internal/client-token.js.map +1 -0
- package/dist/internal/env.d.ts +34 -0
- package/dist/internal/env.d.ts.map +1 -0
- package/dist/internal/env.js +61 -0
- package/dist/internal/env.js.map +1 -0
- package/dist/internal/multipart.d.ts +110 -0
- package/dist/internal/multipart.d.ts.map +1 -0
- package/dist/internal/multipart.js +290 -0
- package/dist/internal/multipart.js.map +1 -0
- package/dist/internal/presign.d.ts +123 -0
- package/dist/internal/presign.d.ts.map +1 -0
- package/dist/internal/presign.js +345 -0
- package/dist/internal/presign.js.map +1 -0
- package/dist/internal/store-id.d.ts +38 -0
- package/dist/internal/store-id.d.ts.map +1 -0
- package/dist/internal/store-id.js +54 -0
- package/dist/internal/store-id.js.map +1 -0
- package/dist/internal/urls.d.ts +26 -0
- package/dist/internal/urls.d.ts.map +1 -0
- package/dist/internal/urls.js +33 -0
- package/dist/internal/urls.js.map +1 -0
- package/dist/internal/wire.d.ts +55 -0
- package/dist/internal/wire.d.ts.map +1 -0
- package/dist/internal/wire.js +64 -0
- package/dist/internal/wire.js.map +1 -0
- package/dist/internal/write-headers.d.ts +56 -0
- package/dist/internal/write-headers.d.ts.map +1 -0
- package/dist/internal/write-headers.js +82 -0
- package/dist/internal/write-headers.js.map +1 -0
- package/dist/testing/index.d.ts +2 -0
- package/dist/testing/index.d.ts.map +1 -0
- package/dist/testing/index.js +2 -0
- package/dist/testing/index.js.map +1 -0
- package/dist/testing/test-blob-store.d.ts +134 -0
- package/dist/testing/test-blob-store.d.ts.map +1 -0
- package/dist/testing/test-blob-store.js +718 -0
- package/dist/testing/test-blob-store.js.map +1 -0
- package/package.json +65 -3
- package/src/client.ts +11 -0
- package/src/contracts/blob-client.ts +121 -0
- package/src/contracts/blob-config.ts +64 -0
- package/src/contracts/blob-domain.ts +304 -0
- package/src/contracts/blob-errors.ts +161 -0
- package/src/contracts/blob-signed-urls.ts +112 -0
- package/src/contracts/blob-store.ts +258 -0
- package/src/contracts/blob-uploads.ts +151 -0
- package/src/implementation/blob-client-live.ts +387 -0
- package/src/implementation/blob-config-live.ts +145 -0
- package/src/implementation/blob-live.ts +30 -0
- package/src/implementation/blob-signed-urls-live.ts +121 -0
- package/src/implementation/blob-store-live.ts +528 -0
- package/src/implementation/blob-uploads-live.ts +326 -0
- package/src/index.ts +18 -0
- package/src/internal/blob-errors.ts +325 -0
- package/src/internal/blob-request.ts +617 -0
- package/src/internal/callback.ts +200 -0
- package/src/internal/client-token.ts +132 -0
- package/src/internal/env.ts +128 -0
- package/src/internal/multipart.ts +526 -0
- package/src/internal/presign.ts +477 -0
- package/src/internal/store-id.ts +69 -0
- package/src/internal/urls.ts +42 -0
- package/src/internal/wire.ts +80 -0
- package/src/internal/write-headers.ts +118 -0
- package/src/testing/index.ts +1 -0
- package/src/testing/test-blob-store.ts +1136 -0
|
@@ -0,0 +1,152 @@
|
|
|
1
|
+
import { Data, Schema } from "effect";
|
|
2
|
+
/** Whether a blob is readable by anyone with its URL (`public`) or only with credentials. */
|
|
3
|
+
export const BlobAccess = Schema.Literals(["public", "private"]);
|
|
4
|
+
/**
|
|
5
|
+
* Identifier of a Blob store without its `store_` prefix, as sent in `x-vercel-blob-store-id` and
|
|
6
|
+
* used in blob host names. Case-sensitive.
|
|
7
|
+
*/
|
|
8
|
+
export const StoreId = Schema.String.check(Schema.isPattern(/^(?!store_)[^\s_]+$/)).pipe(Schema.brand("StoreId"));
|
|
9
|
+
/** Longest pathname a write accepts: the provider limit minus room for Vercel's suffixes. */
|
|
10
|
+
export const maximumPathnameLength = 950;
|
|
11
|
+
/**
|
|
12
|
+
* Where a write stores a blob inside its store, such as `avatars/user-1.png`: non-empty, at most
|
|
13
|
+
* {@link maximumPathnameLength} characters, and without `//`.
|
|
14
|
+
*
|
|
15
|
+
* Reads and deletes take any pathname or blob URL as a plain string, because stored pathnames may
|
|
16
|
+
* be longer once a random suffix is added.
|
|
17
|
+
*/
|
|
18
|
+
export const BlobPathname = Schema.String.check(Schema.isMinLength(1), Schema.isMaxLength(maximumPathnameLength), Schema.makeFilter((pathname) => !pathname.includes("//"), {
|
|
19
|
+
expected: 'a pathname without "//"',
|
|
20
|
+
})).pipe(Schema.brand("BlobPathname"));
|
|
21
|
+
/** Version tag of a blob's content, used for conditional writes, deletes and reads. */
|
|
22
|
+
export const ETag = Schema.NonEmptyString.pipe(Schema.brand("ETag"));
|
|
23
|
+
/** Position of a part in a multipart upload: an integer from 1 to 10000. */
|
|
24
|
+
export const PartNumber = Schema.Int.check(Schema.isBetween({ minimum: 1, maximum: 10_000 })).pipe(Schema.brand("PartNumber"));
|
|
25
|
+
/** A stored blob as returned by writes. */
|
|
26
|
+
export class PutBlobResult extends Schema.Class("@effect-vercel/blob/PutBlobResult")({
|
|
27
|
+
url: Schema.URL,
|
|
28
|
+
/** The URL with `?download=1`, which makes browsers download instead of display. */
|
|
29
|
+
downloadUrl: Schema.URL,
|
|
30
|
+
pathname: Schema.String,
|
|
31
|
+
contentType: Schema.String,
|
|
32
|
+
contentDisposition: Schema.String,
|
|
33
|
+
etag: ETag,
|
|
34
|
+
}) {
|
|
35
|
+
}
|
|
36
|
+
/** Everything known about a stored blob. */
|
|
37
|
+
export class BlobMetadata extends Schema.Class("@effect-vercel/blob/BlobMetadata")({
|
|
38
|
+
url: Schema.URL,
|
|
39
|
+
downloadUrl: Schema.URL,
|
|
40
|
+
pathname: Schema.String,
|
|
41
|
+
/** Size in bytes. */
|
|
42
|
+
size: Schema.Int,
|
|
43
|
+
uploadedAt: Schema.DateTimeUtc,
|
|
44
|
+
contentType: Schema.String,
|
|
45
|
+
contentDisposition: Schema.String,
|
|
46
|
+
cacheControl: Schema.String,
|
|
47
|
+
etag: ETag,
|
|
48
|
+
}) {
|
|
49
|
+
}
|
|
50
|
+
/** One entry of a listing. */
|
|
51
|
+
export class ListedBlob extends Schema.Class("@effect-vercel/blob/ListedBlob")({
|
|
52
|
+
url: Schema.URL,
|
|
53
|
+
downloadUrl: Schema.URL,
|
|
54
|
+
pathname: Schema.String,
|
|
55
|
+
size: Schema.Int,
|
|
56
|
+
uploadedAt: Schema.DateTimeUtc,
|
|
57
|
+
etag: ETag,
|
|
58
|
+
}) {
|
|
59
|
+
}
|
|
60
|
+
/** One page of a listing, in lexicographic pathname order. */
|
|
61
|
+
export class ListPage extends Schema.Class("@effect-vercel/blob/ListPage")({
|
|
62
|
+
blobs: Schema.Array(ListedBlob),
|
|
63
|
+
/** Fully qualified folder pathnames directly under the prefix; empty unless `mode` is `folded`. */
|
|
64
|
+
folders: Schema.Array(Schema.String),
|
|
65
|
+
/** Pass to the next `list` call to continue; none on the last page. */
|
|
66
|
+
cursor: Schema.Option(Schema.String),
|
|
67
|
+
hasMore: Schema.Boolean,
|
|
68
|
+
}) {
|
|
69
|
+
}
|
|
70
|
+
/** A folder created with `createFolder`. */
|
|
71
|
+
export class CreateFolderResult extends Schema.Class("@effect-vercel/blob/CreateFolderResult")({
|
|
72
|
+
url: Schema.URL,
|
|
73
|
+
/** The folder pathname, ending in `/`. */
|
|
74
|
+
pathname: Schema.String,
|
|
75
|
+
}) {
|
|
76
|
+
}
|
|
77
|
+
/** Metadata of a blob read with `get`, from its response headers. */
|
|
78
|
+
export class FetchedBlob extends Schema.Class("@effect-vercel/blob/FetchedBlob")({
|
|
79
|
+
url: Schema.URL,
|
|
80
|
+
downloadUrl: Schema.URL,
|
|
81
|
+
pathname: Schema.String,
|
|
82
|
+
contentDisposition: Schema.String,
|
|
83
|
+
cacheControl: Schema.String,
|
|
84
|
+
/** `Last-Modified`, or the time of the read when the response had none. */
|
|
85
|
+
uploadedAt: Schema.DateTimeUtc,
|
|
86
|
+
etag: Schema.String,
|
|
87
|
+
}) {
|
|
88
|
+
}
|
|
89
|
+
/** Constructors and matchers for {@link GetBlobResult}. */
|
|
90
|
+
export const GetBlobResult = Data.taggedEnum();
|
|
91
|
+
/**
|
|
92
|
+
* A multipart upload in progress. Every write option is kept so parts and completion send the same
|
|
93
|
+
* headers as creation; the value can be serialized and resumed by another process.
|
|
94
|
+
*/
|
|
95
|
+
export class MultipartUpload extends Schema.Class("@effect-vercel/blob/MultipartUpload")({
|
|
96
|
+
pathname: BlobPathname,
|
|
97
|
+
/** Identifies the blob object being assembled. */
|
|
98
|
+
key: Schema.String,
|
|
99
|
+
uploadId: Schema.String,
|
|
100
|
+
access: BlobAccess,
|
|
101
|
+
addRandomSuffix: Schema.optionalKey(Schema.Boolean),
|
|
102
|
+
allowOverwrite: Schema.optionalKey(Schema.Boolean),
|
|
103
|
+
contentType: Schema.optionalKey(Schema.String),
|
|
104
|
+
/** In seconds, as sent on the wire. */
|
|
105
|
+
cacheControlMaxAge: Schema.optionalKey(Schema.Int),
|
|
106
|
+
}) {
|
|
107
|
+
}
|
|
108
|
+
/** A part uploaded to a multipart upload, needed to complete it. */
|
|
109
|
+
export class UploadedPart extends Schema.Class("@effect-vercel/blob/UploadedPart")({
|
|
110
|
+
etag: Schema.String,
|
|
111
|
+
partNumber: PartNumber,
|
|
112
|
+
}) {
|
|
113
|
+
}
|
|
114
|
+
/** Operations a signed token can delegate. */
|
|
115
|
+
export const DelegationOperation = Schema.Literals(["get", "head", "put", "delete"]);
|
|
116
|
+
/** Query parameters that authorize one presigned request instead of a bearer token. */
|
|
117
|
+
export class PresignedUrlPayload extends Schema.Class("@effect-vercel/blob/PresignedUrlPayload")({
|
|
118
|
+
/** Public part of the signed token; the store id is read from it. */
|
|
119
|
+
delegationToken: Schema.String,
|
|
120
|
+
/** HMAC-SHA256 (base64url) of the request's canonical string, keyed by the client signing token. */
|
|
121
|
+
signature: Schema.String,
|
|
122
|
+
/** Signed constraints, sent as query parameters. */
|
|
123
|
+
params: Schema.Record(Schema.String, Schema.String),
|
|
124
|
+
}) {
|
|
125
|
+
}
|
|
126
|
+
/** A short-lived token, issued by the Blob API, from which presigned URLs are signed locally. */
|
|
127
|
+
export class SignedToken extends Schema.Class("@effect-vercel/blob/SignedToken")({
|
|
128
|
+
/** Public; embedded in every presigned URL. */
|
|
129
|
+
delegationToken: Schema.String,
|
|
130
|
+
/** Secret HMAC key for presigning. Never send it to clients. */
|
|
131
|
+
clientSigningToken: Schema.Redacted(Schema.String),
|
|
132
|
+
validUntil: Schema.DateTimeUtc,
|
|
133
|
+
}) {
|
|
134
|
+
}
|
|
135
|
+
/** A token that lets a browser upload one pathname directly (`vercel_blob_client_…`). */
|
|
136
|
+
export const ClientToken = Schema.String.check(Schema.isPattern(/^vercel_blob_client_/)).pipe(Schema.brand("ClientToken"));
|
|
137
|
+
/** The blob store's notification that a browser upload finished. */
|
|
138
|
+
export class UploadCompleted extends Schema.Class("@effect-vercel/blob/UploadCompleted")({
|
|
139
|
+
blob: PutBlobResult,
|
|
140
|
+
/** Data the server attached when it authorized the upload. */
|
|
141
|
+
tokenPayload: Schema.Option(Schema.String),
|
|
142
|
+
}) {
|
|
143
|
+
}
|
|
144
|
+
/** What a browser asks for when it starts an upload through an upload route. */
|
|
145
|
+
export class UploadRequest extends Schema.Class("@effect-vercel/blob/UploadRequest")({
|
|
146
|
+
pathname: Schema.String,
|
|
147
|
+
/** Data the browser sent along, such as a form id; untrusted. */
|
|
148
|
+
clientPayload: Schema.Option(Schema.String),
|
|
149
|
+
multipart: Schema.Boolean,
|
|
150
|
+
}) {
|
|
151
|
+
}
|
|
152
|
+
//# sourceMappingURL=blob-domain.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"blob-domain.js","sourceRoot":"","sources":["../../src/contracts/blob-domain.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
import { Schema } from "effect";
|
|
2
|
+
declare const BlobNotFound_base: Schema.Class<BlobNotFound, Schema.TaggedStruct<"BlobNotFound", {
|
|
3
|
+
/** The pathname or URL that was requested. */
|
|
4
|
+
readonly locator: Schema.String;
|
|
5
|
+
}>, import("effect/Cause").YieldableError>;
|
|
6
|
+
/** The blob does not exist (`not_found`). */
|
|
7
|
+
export declare class BlobNotFound extends BlobNotFound_base {
|
|
8
|
+
}
|
|
9
|
+
declare const BlobStoreNotFound_base: Schema.Class<BlobStoreNotFound, Schema.TaggedStruct<"BlobStoreNotFound", {}>, import("effect/Cause").YieldableError>;
|
|
10
|
+
/** The store addressed by the credentials does not exist (`store_not_found`). */
|
|
11
|
+
export declare class BlobStoreNotFound extends BlobStoreNotFound_base {
|
|
12
|
+
}
|
|
13
|
+
declare const BlobStoreSuspended_base: Schema.Class<BlobStoreSuspended, Schema.TaggedStruct<"BlobStoreSuspended", {}>, import("effect/Cause").YieldableError>;
|
|
14
|
+
/** The store has been suspended, for example for exceeding the Hobby quota (`store_suspended`). */
|
|
15
|
+
export declare class BlobStoreSuspended extends BlobStoreSuspended_base {
|
|
16
|
+
}
|
|
17
|
+
declare const BlobStoreUnavailable_base: Schema.Class<BlobStoreUnavailable, Schema.TaggedStruct<"BlobStoreUnavailable", {
|
|
18
|
+
readonly reason: Schema.Union<readonly [typeof BlobStoreNotFound, typeof BlobStoreSuspended]>;
|
|
19
|
+
}>, import("effect/Cause").YieldableError>;
|
|
20
|
+
/** The store cannot serve any request. */
|
|
21
|
+
export declare class BlobStoreUnavailable extends BlobStoreUnavailable_base {
|
|
22
|
+
}
|
|
23
|
+
declare const BlobPreconditionFailed_base: Schema.Class<BlobPreconditionFailed, Schema.TaggedStruct<"BlobPreconditionFailed", {}>, import("effect/Cause").YieldableError>;
|
|
24
|
+
/** A conditional write or delete found a different ETag than `ifMatch` (`precondition_failed`). */
|
|
25
|
+
export declare class BlobPreconditionFailed extends BlobPreconditionFailed_base {
|
|
26
|
+
}
|
|
27
|
+
declare const ContentTypeNotAllowed_base: Schema.Class<ContentTypeNotAllowed, Schema.TaggedStruct<"ContentTypeNotAllowed", {
|
|
28
|
+
readonly message: Schema.String;
|
|
29
|
+
}>, import("effect/Cause").YieldableError>;
|
|
30
|
+
/** The upload's media type is not among the token's `allowedContentTypes`. */
|
|
31
|
+
export declare class ContentTypeNotAllowed extends ContentTypeNotAllowed_base {
|
|
32
|
+
}
|
|
33
|
+
declare const FileTooLarge_base: Schema.Class<FileTooLarge, Schema.TaggedStruct<"FileTooLarge", {
|
|
34
|
+
readonly message: Schema.String;
|
|
35
|
+
}>, import("effect/Cause").YieldableError>;
|
|
36
|
+
/** The upload is larger than `maximumSizeInBytes`, checked locally or by the store. */
|
|
37
|
+
export declare class FileTooLarge extends FileTooLarge_base {
|
|
38
|
+
}
|
|
39
|
+
declare const PathnameMismatch_base: Schema.Class<PathnameMismatch, Schema.TaggedStruct<"PathnameMismatch", {
|
|
40
|
+
readonly message: Schema.String;
|
|
41
|
+
}>, import("effect/Cause").YieldableError>;
|
|
42
|
+
/** The upload's pathname differs from the one the client token was issued for. */
|
|
43
|
+
export declare class PathnameMismatch extends PathnameMismatch_base {
|
|
44
|
+
}
|
|
45
|
+
declare const ClientTokenExpired_base: Schema.Class<ClientTokenExpired, Schema.TaggedStruct<"ClientTokenExpired", {}>, import("effect/Cause").YieldableError>;
|
|
46
|
+
/** The client token's `validUntil` has passed. */
|
|
47
|
+
export declare class ClientTokenExpired extends ClientTokenExpired_base {
|
|
48
|
+
}
|
|
49
|
+
declare const BlobUploadRejected_base: Schema.Class<BlobUploadRejected, Schema.TaggedStruct<"BlobUploadRejected", {
|
|
50
|
+
readonly reason: Schema.Union<readonly [typeof ContentTypeNotAllowed, typeof FileTooLarge, typeof PathnameMismatch, typeof ClientTokenExpired]>;
|
|
51
|
+
}>, import("effect/Cause").YieldableError>;
|
|
52
|
+
/** The store refused an upload because it breaks a constraint of its token. */
|
|
53
|
+
export declare class BlobUploadRejected extends BlobUploadRejected_base {
|
|
54
|
+
}
|
|
55
|
+
declare const BlobClientTokenNotAllowed_base: Schema.Class<BlobClientTokenNotAllowed, Schema.TaggedStruct<"BlobClientTokenNotAllowed", {
|
|
56
|
+
readonly message: Schema.String;
|
|
57
|
+
}>, import("effect/Cause").YieldableError>;
|
|
58
|
+
/**
|
|
59
|
+
* The operation needs a read-write or OIDC token and was called with a client token
|
|
60
|
+
* (`client_token_not_allowed`), such as `rename`.
|
|
61
|
+
*/
|
|
62
|
+
export declare class BlobClientTokenNotAllowed extends BlobClientTokenNotAllowed_base {
|
|
63
|
+
}
|
|
64
|
+
declare const BlobOidcEnvironmentNotAllowed_base: Schema.Class<BlobOidcEnvironmentNotAllowed, Schema.TaggedStruct<"BlobOidcEnvironmentNotAllowed", {
|
|
65
|
+
readonly message: Schema.String;
|
|
66
|
+
}>, import("effect/Cause").YieldableError>;
|
|
67
|
+
/**
|
|
68
|
+
* The project enables OIDC for Blob but not for the environment the token was issued in
|
|
69
|
+
* (`oidc_environment_not_allowed`). Enable it in the store's settings or use a read-write token.
|
|
70
|
+
*/
|
|
71
|
+
export declare class BlobOidcEnvironmentNotAllowed extends BlobOidcEnvironmentNotAllowed_base {
|
|
72
|
+
}
|
|
73
|
+
declare const BlobReadWriteTokenRequired_base: Schema.Class<BlobReadWriteTokenRequired, Schema.TaggedStruct<"BlobReadWriteTokenRequired", {
|
|
74
|
+
readonly operation: Schema.String;
|
|
75
|
+
}>, import("effect/Cause").YieldableError>;
|
|
76
|
+
/**
|
|
77
|
+
* The operation signs with the store's read-write token, and none is configured. OIDC is not
|
|
78
|
+
* enough for client tokens and their callbacks; set `BLOB_READ_WRITE_TOKEN`.
|
|
79
|
+
*/
|
|
80
|
+
export declare class BlobReadWriteTokenRequired extends BlobReadWriteTokenRequired_base {
|
|
81
|
+
}
|
|
82
|
+
declare const BlobPresignFailed_base: Schema.Class<BlobPresignFailed, Schema.TaggedStruct<"BlobPresignFailed", {
|
|
83
|
+
readonly message: Schema.String;
|
|
84
|
+
}>, import("effect/Cause").YieldableError>;
|
|
85
|
+
/** A presigned URL could not be signed: the token's scope or the options do not allow it. */
|
|
86
|
+
export declare class BlobPresignFailed extends BlobPresignFailed_base {
|
|
87
|
+
}
|
|
88
|
+
declare const SignatureMissing_base: Schema.Class<SignatureMissing, Schema.TaggedStruct<"SignatureMissing", {}>, import("effect/Cause").YieldableError>;
|
|
89
|
+
/** The `x-vercel-signature` header is absent. */
|
|
90
|
+
export declare class SignatureMissing extends SignatureMissing_base {
|
|
91
|
+
}
|
|
92
|
+
declare const SignatureInvalid_base: Schema.Class<SignatureInvalid, Schema.TaggedStruct<"SignatureInvalid", {}>, import("effect/Cause").YieldableError>;
|
|
93
|
+
/** The `x-vercel-signature` header does not match the body. */
|
|
94
|
+
export declare class SignatureInvalid extends SignatureInvalid_base {
|
|
95
|
+
}
|
|
96
|
+
declare const EventMalformed_base: Schema.Class<EventMalformed, Schema.TaggedStruct<"EventMalformed", {
|
|
97
|
+
readonly message: Schema.String;
|
|
98
|
+
}>, import("effect/Cause").YieldableError>;
|
|
99
|
+
/** The request body is not a known upload event, or not JSON. */
|
|
100
|
+
export declare class EventMalformed extends EventMalformed_base {
|
|
101
|
+
}
|
|
102
|
+
declare const WebhookPublicKeyMissing_base: Schema.Class<WebhookPublicKeyMissing, Schema.TaggedStruct<"WebhookPublicKeyMissing", {}>, import("effect/Cause").YieldableError>;
|
|
103
|
+
/** The presigned flow has no webhook public key: set `BLOB_WEBHOOK_PUBLIC_KEY`. */
|
|
104
|
+
export declare class WebhookPublicKeyMissing extends WebhookPublicKeyMissing_base {
|
|
105
|
+
}
|
|
106
|
+
declare const BlobUploadEventRejected_base: Schema.Class<BlobUploadEventRejected, Schema.TaggedStruct<"BlobUploadEventRejected", {
|
|
107
|
+
readonly reason: Schema.Union<readonly [typeof SignatureMissing, typeof SignatureInvalid, typeof EventMalformed, typeof WebhookPublicKeyMissing]>;
|
|
108
|
+
}>, import("effect/Cause").YieldableError>;
|
|
109
|
+
/**
|
|
110
|
+
* An upload route received a request it must refuse. Respond with a 4xx: the blob store retries an
|
|
111
|
+
* upload-completed callback that does not get a 200.
|
|
112
|
+
*/
|
|
113
|
+
export declare class BlobUploadEventRejected extends BlobUploadEventRejected_base {
|
|
114
|
+
}
|
|
115
|
+
declare const BlobUploadAuthorizationFailed_base: Schema.Class<BlobUploadAuthorizationFailed, Schema.TaggedStruct<"BlobUploadAuthorizationFailed", {
|
|
116
|
+
/** The route's status code; none when the request failed before a response. */
|
|
117
|
+
readonly status: Schema.Option<Schema.Int>;
|
|
118
|
+
readonly message: Schema.String;
|
|
119
|
+
readonly cause: Schema.optional<Schema.Defect>;
|
|
120
|
+
}>, import("effect/Cause").YieldableError>;
|
|
121
|
+
/** The browser could not get a client token or presigned URL from the upload route. */
|
|
122
|
+
export declare class BlobUploadAuthorizationFailed extends BlobUploadAuthorizationFailed_base {
|
|
123
|
+
}
|
|
124
|
+
export {};
|
|
125
|
+
//# sourceMappingURL=blob-errors.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"blob-errors.d.ts","sourceRoot":"","sources":["../../src/contracts/blob-errors.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,QAAQ,CAAC;;IAI9B,8CAA8C;;;AAFhD,6CAA6C;AAC7C,qBAAa,YAAa,SAAQ,iBAGhC;CAAG;;AAEL,iFAAiF;AACjF,qBAAa,iBAAkB,SAAQ,sBAGtC;CAAG;;AAEJ,mGAAmG;AACnG,qBAAa,kBAAmB,SAAQ,uBAGvC;CAAG;;;;AAEJ,0CAA0C;AAC1C,qBAAa,oBAAqB,SAAQ,yBAKzC;CAAG;;AAEJ,mGAAmG;AACnG,qBAAa,sBAAuB,SAAQ,2BAG3C;CAAG;;;;AAEJ,8EAA8E;AAC9E,qBAAa,qBAAsB,SAAQ,0BAK1C;CAAG;;;;AAEJ,uFAAuF;AACvF,qBAAa,YAAa,SAAQ,iBAEhC;CAAG;;;;AAEL,kFAAkF;AAClF,qBAAa,gBAAiB,SAAQ,qBAEpC;CAAG;;AAEL,kDAAkD;AAClD,qBAAa,kBAAmB,SAAQ,uBAGvC;CAAG;;;;AAEJ,+EAA+E;AAC/E,qBAAa,kBAAmB,SAAQ,uBAUvC;CAAG;;;;AAEJ;;;GAGG;AACH,qBAAa,yBAA0B,SAAQ,8BAK9C;CAAG;;;;AAEJ;;;GAGG;AACH,qBAAa,6BAA8B,SAAQ,kCAKlD;CAAG;;;;AAEJ;;;GAGG;AACH,qBAAa,0BAA2B,SAAQ,+BAK/C;CAAG;;;;AAEJ,6FAA6F;AAC7F,qBAAa,iBAAkB,SAAQ,sBAKtC;CAAG;;AAEJ,iDAAiD;AACjD,qBAAa,gBAAiB,SAAQ,qBAGrC;CAAG;;AAEJ,+DAA+D;AAC/D,qBAAa,gBAAiB,SAAQ,qBAGrC;CAAG;;;;AAEJ,iEAAiE;AACjE,qBAAa,cAAe,SAAQ,mBAElC;CAAG;;AAEL,mFAAmF;AACnF,qBAAa,uBAAwB,SAAQ,4BAG5C;CAAG;;;;AAEJ;;;GAGG;AACH,qBAAa,uBAAwB,SAAQ,4BAU5C;CAAG;;IAMA,+EAA+E;;;;;AAJnF,uFAAuF;AACvF,qBAAa,6BAA8B,SAAQ,kCAQlD;CAAG"}
|
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
import { Schema } from "effect";
|
|
2
|
+
/** The blob does not exist (`not_found`). */
|
|
3
|
+
export class BlobNotFound extends Schema.TaggedError()("BlobNotFound", {
|
|
4
|
+
/** The pathname or URL that was requested. */
|
|
5
|
+
locator: Schema.String,
|
|
6
|
+
}) {
|
|
7
|
+
}
|
|
8
|
+
/** The store addressed by the credentials does not exist (`store_not_found`). */
|
|
9
|
+
export class BlobStoreNotFound extends Schema.TaggedError()("BlobStoreNotFound", {}) {
|
|
10
|
+
}
|
|
11
|
+
/** The store has been suspended, for example for exceeding the Hobby quota (`store_suspended`). */
|
|
12
|
+
export class BlobStoreSuspended extends Schema.TaggedError()("BlobStoreSuspended", {}) {
|
|
13
|
+
}
|
|
14
|
+
/** The store cannot serve any request. */
|
|
15
|
+
export class BlobStoreUnavailable extends Schema.TaggedError()("BlobStoreUnavailable", {
|
|
16
|
+
reason: Schema.Union([BlobStoreNotFound, BlobStoreSuspended]),
|
|
17
|
+
}) {
|
|
18
|
+
}
|
|
19
|
+
/** A conditional write or delete found a different ETag than `ifMatch` (`precondition_failed`). */
|
|
20
|
+
export class BlobPreconditionFailed extends Schema.TaggedError()("BlobPreconditionFailed", {}) {
|
|
21
|
+
}
|
|
22
|
+
/** The upload's media type is not among the token's `allowedContentTypes`. */
|
|
23
|
+
export class ContentTypeNotAllowed extends Schema.TaggedError()("ContentTypeNotAllowed", {
|
|
24
|
+
message: Schema.String,
|
|
25
|
+
}) {
|
|
26
|
+
}
|
|
27
|
+
/** The upload is larger than `maximumSizeInBytes`, checked locally or by the store. */
|
|
28
|
+
export class FileTooLarge extends Schema.TaggedError()("FileTooLarge", {
|
|
29
|
+
message: Schema.String,
|
|
30
|
+
}) {
|
|
31
|
+
}
|
|
32
|
+
/** The upload's pathname differs from the one the client token was issued for. */
|
|
33
|
+
export class PathnameMismatch extends Schema.TaggedError()("PathnameMismatch", {
|
|
34
|
+
message: Schema.String,
|
|
35
|
+
}) {
|
|
36
|
+
}
|
|
37
|
+
/** The client token's `validUntil` has passed. */
|
|
38
|
+
export class ClientTokenExpired extends Schema.TaggedError()("ClientTokenExpired", {}) {
|
|
39
|
+
}
|
|
40
|
+
/** The store refused an upload because it breaks a constraint of its token. */
|
|
41
|
+
export class BlobUploadRejected extends Schema.TaggedError()("BlobUploadRejected", {
|
|
42
|
+
reason: Schema.Union([
|
|
43
|
+
ContentTypeNotAllowed,
|
|
44
|
+
FileTooLarge,
|
|
45
|
+
PathnameMismatch,
|
|
46
|
+
ClientTokenExpired,
|
|
47
|
+
]),
|
|
48
|
+
}) {
|
|
49
|
+
}
|
|
50
|
+
/**
|
|
51
|
+
* The operation needs a read-write or OIDC token and was called with a client token
|
|
52
|
+
* (`client_token_not_allowed`), such as `rename`.
|
|
53
|
+
*/
|
|
54
|
+
export class BlobClientTokenNotAllowed extends Schema.TaggedError()("BlobClientTokenNotAllowed", {
|
|
55
|
+
message: Schema.String,
|
|
56
|
+
}) {
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* The project enables OIDC for Blob but not for the environment the token was issued in
|
|
60
|
+
* (`oidc_environment_not_allowed`). Enable it in the store's settings or use a read-write token.
|
|
61
|
+
*/
|
|
62
|
+
export class BlobOidcEnvironmentNotAllowed extends Schema.TaggedError()("BlobOidcEnvironmentNotAllowed", {
|
|
63
|
+
message: Schema.String,
|
|
64
|
+
}) {
|
|
65
|
+
}
|
|
66
|
+
/**
|
|
67
|
+
* The operation signs with the store's read-write token, and none is configured. OIDC is not
|
|
68
|
+
* enough for client tokens and their callbacks; set `BLOB_READ_WRITE_TOKEN`.
|
|
69
|
+
*/
|
|
70
|
+
export class BlobReadWriteTokenRequired extends Schema.TaggedError()("BlobReadWriteTokenRequired", {
|
|
71
|
+
operation: Schema.String,
|
|
72
|
+
}) {
|
|
73
|
+
}
|
|
74
|
+
/** A presigned URL could not be signed: the token's scope or the options do not allow it. */
|
|
75
|
+
export class BlobPresignFailed extends Schema.TaggedError()("BlobPresignFailed", {
|
|
76
|
+
message: Schema.String,
|
|
77
|
+
}) {
|
|
78
|
+
}
|
|
79
|
+
/** The `x-vercel-signature` header is absent. */
|
|
80
|
+
export class SignatureMissing extends Schema.TaggedError()("SignatureMissing", {}) {
|
|
81
|
+
}
|
|
82
|
+
/** The `x-vercel-signature` header does not match the body. */
|
|
83
|
+
export class SignatureInvalid extends Schema.TaggedError()("SignatureInvalid", {}) {
|
|
84
|
+
}
|
|
85
|
+
/** The request body is not a known upload event, or not JSON. */
|
|
86
|
+
export class EventMalformed extends Schema.TaggedError()("EventMalformed", {
|
|
87
|
+
message: Schema.String,
|
|
88
|
+
}) {
|
|
89
|
+
}
|
|
90
|
+
/** The presigned flow has no webhook public key: set `BLOB_WEBHOOK_PUBLIC_KEY`. */
|
|
91
|
+
export class WebhookPublicKeyMissing extends Schema.TaggedError()("WebhookPublicKeyMissing", {}) {
|
|
92
|
+
}
|
|
93
|
+
/**
|
|
94
|
+
* An upload route received a request it must refuse. Respond with a 4xx: the blob store retries an
|
|
95
|
+
* upload-completed callback that does not get a 200.
|
|
96
|
+
*/
|
|
97
|
+
export class BlobUploadEventRejected extends Schema.TaggedError()("BlobUploadEventRejected", {
|
|
98
|
+
reason: Schema.Union([
|
|
99
|
+
SignatureMissing,
|
|
100
|
+
SignatureInvalid,
|
|
101
|
+
EventMalformed,
|
|
102
|
+
WebhookPublicKeyMissing,
|
|
103
|
+
]),
|
|
104
|
+
}) {
|
|
105
|
+
}
|
|
106
|
+
/** The browser could not get a client token or presigned URL from the upload route. */
|
|
107
|
+
export class BlobUploadAuthorizationFailed extends Schema.TaggedError()("BlobUploadAuthorizationFailed", {
|
|
108
|
+
/** The route's status code; none when the request failed before a response. */
|
|
109
|
+
status: Schema.Option(Schema.Int),
|
|
110
|
+
message: Schema.String,
|
|
111
|
+
cause: Schema.optional(Schema.Defect()),
|
|
112
|
+
}) {
|
|
113
|
+
}
|
|
114
|
+
//# sourceMappingURL=blob-errors.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"blob-errors.js","sourceRoot":"","sources":["../../src/contracts/blob-errors.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
import type { Array, DateTime, Effect } from "effect";
|
|
2
|
+
import { Context } from "effect";
|
|
3
|
+
import type { BlobAccess, DelegationOperation, ETag, PresignedUrlPayload, SignedToken } from "./blob-domain.ts";
|
|
4
|
+
import type { BlobPresignFailed } from "./blob-errors.ts";
|
|
5
|
+
import type { BlobRequestError } from "./blob-store.ts";
|
|
6
|
+
/** Scope of a signed token. Every field narrows what presigned URLs signed from it may do. */
|
|
7
|
+
export interface IssueSignedTokenOptions {
|
|
8
|
+
/** Pathname the token covers; `*` or omitted covers the whole store. */
|
|
9
|
+
readonly pathname?: string | undefined;
|
|
10
|
+
/** Operations the token delegates; the store defaults to `get`. Duplicates are removed. */
|
|
11
|
+
readonly operations?: Array.NonEmptyReadonlyArray<DelegationOperation> | undefined;
|
|
12
|
+
/** Expiry, in the future and at most 7 days away; the store defaults to one hour. */
|
|
13
|
+
readonly validUntil?: DateTime.Utc | undefined;
|
|
14
|
+
/** Largest upload a presigned `put` may send. */
|
|
15
|
+
readonly maximumSizeInBytes?: number | undefined;
|
|
16
|
+
/** Media types a presigned `put` may upload; wildcards such as `image/*` are allowed. */
|
|
17
|
+
readonly allowedContentTypes?: ReadonlyArray<string> | undefined;
|
|
18
|
+
}
|
|
19
|
+
/** Callback the store calls after a presigned upload completes. */
|
|
20
|
+
export interface PresignUploadCompleted {
|
|
21
|
+
/** Absolute URL of the route that handles `blob.upload-completed`. */
|
|
22
|
+
readonly callbackUrl: string;
|
|
23
|
+
/** Data passed back to the callback, such as the uploading user's id. */
|
|
24
|
+
readonly tokenPayload?: string | undefined;
|
|
25
|
+
}
|
|
26
|
+
/** What one presigned URL authorizes. Constraints may only narrow the signed token's. */
|
|
27
|
+
export type PresignOptions = {
|
|
28
|
+
readonly operation: "get";
|
|
29
|
+
readonly pathname: string;
|
|
30
|
+
/** Earlier expiry than the token's. */
|
|
31
|
+
readonly validUntil?: DateTime.Utc | undefined;
|
|
32
|
+
/** Add `cache=0` to read a private blob from origin storage; not signed. */
|
|
33
|
+
readonly useCache?: boolean | undefined;
|
|
34
|
+
} | {
|
|
35
|
+
readonly operation: "head";
|
|
36
|
+
readonly pathname: string;
|
|
37
|
+
readonly validUntil?: DateTime.Utc | undefined;
|
|
38
|
+
} | {
|
|
39
|
+
readonly operation: "put";
|
|
40
|
+
readonly pathname: string;
|
|
41
|
+
readonly validUntil?: DateTime.Utc | undefined;
|
|
42
|
+
readonly allowedContentTypes?: ReadonlyArray<string> | undefined;
|
|
43
|
+
readonly maximumSizeInBytes?: number | undefined;
|
|
44
|
+
readonly onUploadCompleted?: PresignUploadCompleted | undefined;
|
|
45
|
+
readonly allowOverwrite?: boolean | undefined;
|
|
46
|
+
readonly addRandomSuffix?: boolean | undefined;
|
|
47
|
+
/** In seconds, at most one year. */
|
|
48
|
+
readonly cacheControlMaxAge?: number | undefined;
|
|
49
|
+
readonly ifMatch?: ETag | undefined;
|
|
50
|
+
} | {
|
|
51
|
+
readonly operation: "delete";
|
|
52
|
+
readonly pathname: string;
|
|
53
|
+
readonly validUntil?: DateTime.Utc | undefined;
|
|
54
|
+
readonly ifMatch?: ETag | undefined;
|
|
55
|
+
};
|
|
56
|
+
/** The secret and public halves of a signed token, as needed to presign. */
|
|
57
|
+
export type SigningToken = Pick<SignedToken, "delegationToken" | "clientSigningToken">;
|
|
58
|
+
declare const BlobSignedUrls_base: Context.ServiceClass<BlobSignedUrls, "@effect-vercel/blob/BlobSignedUrls", {
|
|
59
|
+
/** Ask the store for a signed token (`POST /signed-token`). */
|
|
60
|
+
readonly issueSignedToken: (options?: IssueSignedTokenOptions) => Effect.Effect<SignedToken, BlobRequestError>;
|
|
61
|
+
/**
|
|
62
|
+
* Sign one request. Fails with `BlobPresignFailed` when the token has expired, does not delegate
|
|
63
|
+
* the operation, covers another pathname, or allows less than the options ask for.
|
|
64
|
+
*/
|
|
65
|
+
readonly presign: (token: SigningToken, options: PresignOptions) => Effect.Effect<PresignedUrlPayload, BlobPresignFailed>;
|
|
66
|
+
/**
|
|
67
|
+
* Sign one request and build its URL: the blob URL for `get` and `head`, the Blob API URL for
|
|
68
|
+
* `put` and `delete`.
|
|
69
|
+
*/
|
|
70
|
+
readonly presignUrl: (token: SigningToken, options: PresignOptions & {
|
|
71
|
+
readonly access: BlobAccess;
|
|
72
|
+
}) => Effect.Effect<URL, BlobPresignFailed>;
|
|
73
|
+
}>;
|
|
74
|
+
/**
|
|
75
|
+
* Signed URLs: delegate one operation on one pathname to a holder of a URL, without credentials.
|
|
76
|
+
*
|
|
77
|
+
* Issue a {@link SignedToken} once (one API call) and cache it until shortly before it expires;
|
|
78
|
+
* presigning is local HMAC-SHA256 signing.
|
|
79
|
+
*/
|
|
80
|
+
export declare class BlobSignedUrls extends BlobSignedUrls_base {
|
|
81
|
+
}
|
|
82
|
+
export {};
|
|
83
|
+
//# sourceMappingURL=blob-signed-urls.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"blob-signed-urls.d.ts","sourceRoot":"","sources":["../../src/contracts/blob-signed-urls.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { Context } from "effect";
|
|
2
|
+
/**
|
|
3
|
+
* Signed URLs: delegate one operation on one pathname to a holder of a URL, without credentials.
|
|
4
|
+
*
|
|
5
|
+
* Issue a {@link SignedToken} once (one API call) and cache it until shortly before it expires;
|
|
6
|
+
* presigning is local HMAC-SHA256 signing.
|
|
7
|
+
*/
|
|
8
|
+
export class BlobSignedUrls extends Context.Service()("@effect-vercel/blob/BlobSignedUrls") {
|
|
9
|
+
}
|
|
10
|
+
//# sourceMappingURL=blob-signed-urls.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"blob-signed-urls.js","sourceRoot":"","sources":["../../src/contracts/blob-signed-urls.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,OAAO,EAAE,MAAM,QAAQ,CAAC;AA6EjC;;;;;GAKG;AACH,MAAM,OAAO,cAAe,SAAQ,OAAO,CAAC,OAAO,EA0BhD,CAAC,oCAAoC,CAAC;CAAG"}
|