@lark-apaas/dataloom 0.1.1-alpha.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.
Files changed (98) hide show
  1. package/README.md +3 -0
  2. package/lib/DataloomClient.d.ts +31 -0
  3. package/lib/DataloomClient.d.ts.map +1 -0
  4. package/lib/DataloomClient.js +39 -0
  5. package/lib/RateLimiter.d.ts +15 -0
  6. package/lib/RateLimiter.d.ts.map +1 -0
  7. package/lib/RateLimiter.js +31 -0
  8. package/lib/index.d.ts +9 -0
  9. package/lib/index.d.ts.map +1 -0
  10. package/lib/index.js +3 -0
  11. package/lib/service/index.d.ts +9 -0
  12. package/lib/service/index.d.ts.map +1 -0
  13. package/lib/service/index.js +11 -0
  14. package/lib/service/services/DataloomServiceBase.d.ts +17 -0
  15. package/lib/service/services/DataloomServiceBase.d.ts.map +1 -0
  16. package/lib/service/services/DataloomServiceBase.js +126 -0
  17. package/lib/service/services/session-service/index.d.ts +45 -0
  18. package/lib/service/services/session-service/index.d.ts.map +1 -0
  19. package/lib/service/services/session-service/index.js +111 -0
  20. package/lib/service/services/session-service/types.d.ts +34 -0
  21. package/lib/service/services/session-service/types.d.ts.map +1 -0
  22. package/lib/service/services/session-service/types.js +0 -0
  23. package/lib/service/services/types.d.ts +12 -0
  24. package/lib/service/services/types.d.ts.map +1 -0
  25. package/lib/service/services/types.js +14 -0
  26. package/lib/service/services/user-service/index.d.ts +9 -0
  27. package/lib/service/services/user-service/index.d.ts.map +1 -0
  28. package/lib/service/services/user-service/index.js +60 -0
  29. package/lib/service/services/user-service/types.d.ts +51 -0
  30. package/lib/service/services/user-service/types.d.ts.map +1 -0
  31. package/lib/service/services/user-service/types.js +0 -0
  32. package/lib/service/utils/helpers.d.ts +8 -0
  33. package/lib/service/utils/helpers.d.ts.map +1 -0
  34. package/lib/service/utils/helpers.js +18 -0
  35. package/lib/service/utils/logger.d.ts +15 -0
  36. package/lib/service/utils/logger.d.ts.map +1 -0
  37. package/lib/service/utils/logger.js +18 -0
  38. package/lib/service/utils/trace-id.d.ts +45 -0
  39. package/lib/service/utils/trace-id.d.ts.map +1 -0
  40. package/lib/service/utils/trace-id.js +20 -0
  41. package/lib/service/utils/types.d.ts +49 -0
  42. package/lib/service/utils/types.d.ts.map +1 -0
  43. package/lib/service/utils/types.js +7 -0
  44. package/lib/storage/StorageClient.d.ts +22 -0
  45. package/lib/storage/StorageClient.d.ts.map +1 -0
  46. package/lib/storage/StorageClient.js +11 -0
  47. package/lib/storage/index.d.ts +4 -0
  48. package/lib/storage/index.d.ts.map +1 -0
  49. package/lib/storage/index.js +4 -0
  50. package/lib/storage/libs/constants.d.ts +4 -0
  51. package/lib/storage/libs/constants.d.ts.map +1 -0
  52. package/lib/storage/libs/constants.js +5 -0
  53. package/lib/storage/libs/errors.d.ts +24 -0
  54. package/lib/storage/libs/errors.d.ts.map +1 -0
  55. package/lib/storage/libs/errors.js +39 -0
  56. package/lib/storage/libs/fetch.d.ts +24 -0
  57. package/lib/storage/libs/fetch.d.ts.map +1 -0
  58. package/lib/storage/libs/fetch.js +139 -0
  59. package/lib/storage/libs/helpers.d.ts +18 -0
  60. package/lib/storage/libs/helpers.d.ts.map +1 -0
  61. package/lib/storage/libs/helpers.js +57 -0
  62. package/lib/storage/libs/index.d.ts +5 -0
  63. package/lib/storage/libs/index.d.ts.map +1 -0
  64. package/lib/storage/libs/index.js +4 -0
  65. package/lib/storage/libs/types.d.ts +205 -0
  66. package/lib/storage/libs/types.d.ts.map +1 -0
  67. package/lib/storage/libs/types.js +0 -0
  68. package/lib/storage/libs/version.d.ts +2 -0
  69. package/lib/storage/libs/version.d.ts.map +1 -0
  70. package/lib/storage/libs/version.js +2 -0
  71. package/lib/storage/packages/StorageBucketApi.d.ts +121 -0
  72. package/lib/storage/packages/StorageBucketApi.d.ts.map +1 -0
  73. package/lib/storage/packages/StorageBucketApi.js +135 -0
  74. package/lib/storage/packages/StorageFileApi.d.ts +190 -0
  75. package/lib/storage/packages/StorageFileApi.d.ts.map +1 -0
  76. package/lib/storage/packages/StorageFileApi.js +378 -0
  77. package/lib/storage/utils/logger.d.ts +15 -0
  78. package/lib/storage/utils/logger.d.ts.map +1 -0
  79. package/lib/storage/utils/logger.js +18 -0
  80. package/lib/storage/utils/trace-id.d.ts +45 -0
  81. package/lib/storage/utils/trace-id.d.ts.map +1 -0
  82. package/lib/storage/utils/trace-id.js +20 -0
  83. package/lib/utils/constants.d.ts +7 -0
  84. package/lib/utils/constants.d.ts.map +1 -0
  85. package/lib/utils/constants.js +33 -0
  86. package/lib/utils/fetch.d.ts +6 -0
  87. package/lib/utils/fetch.d.ts.map +1 -0
  88. package/lib/utils/fetch.js +22 -0
  89. package/lib/utils/helpers.d.ts +5 -0
  90. package/lib/utils/helpers.d.ts.map +1 -0
  91. package/lib/utils/helpers.js +17 -0
  92. package/lib/utils/types.d.ts +34 -0
  93. package/lib/utils/types.d.ts.map +1 -0
  94. package/lib/utils/types.js +0 -0
  95. package/lib/utils/version.d.ts +2 -0
  96. package/lib/utils/version.d.ts.map +1 -0
  97. package/lib/utils/version.js +2 -0
  98. package/package.json +34 -0
@@ -0,0 +1,190 @@
1
+ import { StorageError } from '../libs/errors';
2
+ import { type Fetch } from '../libs/fetch';
3
+ import type { FetchParameters, FileBody, FileObject, FileOptions, FileOptionsV2, OnRequestErrorType, SearchOptions, TransformOptions, UploadFileData } from '../libs/types';
4
+ export default class StorageFileApi {
5
+ protected url: string;
6
+ protected headers: {
7
+ [key: string]: string;
8
+ };
9
+ protected bucketId?: string;
10
+ protected appId?: string;
11
+ protected fetch: Fetch;
12
+ protected loggerEnabled?: boolean;
13
+ protected onRequestError?: (error: OnRequestErrorType) => void;
14
+ constructor(url: string, headers?: {
15
+ [key: string]: string;
16
+ }, bucketId?: string, appId?: string, fetch?: Fetch, loggerEnabled?: boolean, onRequestError?: (error: OnRequestErrorType) => void);
17
+ /**
18
+ * Uploads a file to an existing bucket or replaces an existing file at the specified path with a new one.
19
+ *
20
+ * @param method HTTP method.
21
+ * @param path The relative file path. Should be of the format `folder/subfolder/filename.png`. The bucket must already exist before attempting to upload.
22
+ * @param fileBody The body of the file to be stored in the bucket.
23
+ */
24
+ private uploadOrUpdate;
25
+ /**
26
+ * Uploads a file to an existing bucket.
27
+ *
28
+ * @param path The file path, including the file name. Should be of the format `folder/subfolder/filename.png`. The bucket must already exist before attempting to upload.
29
+ * @param fileBody The body of the file to be stored in the bucket.
30
+ * @param fileOptions Upload options.
31
+ */
32
+ upload(path: string, fileBody: FileBody, fileOptions?: FileOptions): Promise<{
33
+ data: UploadFileData;
34
+ error: null;
35
+ } | {
36
+ data: null;
37
+ error: StorageError;
38
+ }>;
39
+ /**
40
+ * Uploads a file to an existing bucket.
41
+ *
42
+ * @param fileBody The body of the file to be stored in the bucket.
43
+ * @param fileOptions Upload options including filePath.
44
+ */
45
+ upload(fileBody: FileBody, fileOptions?: FileOptionsV2): Promise<{
46
+ data: UploadFileData;
47
+ error: null;
48
+ } | {
49
+ data: null;
50
+ error: StorageError;
51
+ }>;
52
+ /**
53
+ * Uploads a file to an existing bucket.
54
+ *
55
+ * @param path The file path, including the file name. Should be of the format `folder/subfolder/filename.png`. The bucket must already exist before attempting to upload.
56
+ * @param fileBody The body of the file to be stored in the bucket.
57
+ */
58
+ uploadFile(fileBody: FileBody, fileOptions?: FileOptionsV2): Promise<{
59
+ data: UploadFileData;
60
+ error: null;
61
+ } | {
62
+ data: null;
63
+ error: StorageError;
64
+ }>;
65
+ /**
66
+ * Replaces an existing file at the specified path with a new one.
67
+ *
68
+ * @param path The relative file path. Should be of the format `folder/subfolder/filename.png`. The bucket must already exist before attempting to update.
69
+ * @param fileBody The body of the file to be stored in the bucket.
70
+ */
71
+ update(path: string, fileBody: ArrayBuffer | ArrayBufferView | Blob | File | FormData | ReadableStream<Uint8Array> | URLSearchParams | string, fileOptions?: FileOptions): Promise<{
72
+ data: UploadFileData;
73
+ error: null;
74
+ } | {
75
+ data: null;
76
+ error: StorageError;
77
+ }>;
78
+ /**
79
+ * Creates a signed URL. Use a signed URL to share a file for a fixed amount of time.
80
+ *
81
+ * @param path The file path, including the current file name. For example `folder/image.png`.
82
+ * @param expiresIn The number of seconds until the signed URL expires. For example, `60` for a URL which is valid for one minute.
83
+ * @param options.download triggers the file as a download if set to true. Set this parameter as the name of the file if you want to trigger the download with a different filename.
84
+ * @param options.transform Transform the asset before serving it to the client.
85
+ */
86
+ createSignedUrl(path: string, expiresIn: number, _options?: {
87
+ download?: string | boolean;
88
+ transform?: TransformOptions;
89
+ }): Promise<{
90
+ data: {
91
+ signedUrl: string;
92
+ };
93
+ error: null;
94
+ } | {
95
+ data: null;
96
+ error: StorageError;
97
+ }>;
98
+ /**
99
+ * Creates multiple signed URLs. Use a signed URL to share a file for a fixed amount of time.
100
+ *
101
+ * @param paths The file paths to be downloaded, including the current file names. For example `['folder/image.png', 'folder2/image2.png']`.
102
+ * @param expiresIn The number of seconds until the signed URLs expire. For example, `60` for URLs which are valid for one minute.
103
+ * @param options.download triggers the file as a download if set to true. Set this parameter as the name of the file if you want to trigger the download with a different filename.
104
+ *
105
+ *
106
+ * success: { error: "", path: "xxxx/xxxx.xx", signedURL: "https://xxxx"}
107
+ * failed: { error: "xxxx", path: "xxxx/xxxx.xx", signedURL: "" }
108
+ */
109
+ createSignedUrls(paths: string[], expiresIn: number, _options?: {
110
+ download: string | boolean;
111
+ }): Promise<{
112
+ data: {
113
+ error: string | null;
114
+ path: string | null;
115
+ signedUrl: string;
116
+ }[];
117
+ error: null;
118
+ } | {
119
+ data: null;
120
+ error: StorageError;
121
+ }>;
122
+ /**
123
+ * Downloads a file from a private bucket. For public buckets, make a request to the URL returned from `getPublicUrl` instead.
124
+ *
125
+ * @param path The full path and file name of the file to be downloaded. For example `folder/image.png`.
126
+ * @param options.transform Transform the asset before serving it to the client.
127
+ */
128
+ download(path: string, _options?: {
129
+ transform?: TransformOptions;
130
+ }): Promise<{
131
+ data: Blob;
132
+ error: null;
133
+ } | {
134
+ data: null;
135
+ error: StorageError;
136
+ }>;
137
+ /**
138
+ * Deletes files within the same bucket
139
+ *
140
+ * @param paths An array of files to delete, including the path and file name. For example [`'folder/image.png'`].
141
+ */
142
+ remove(paths: string[]): Promise<{
143
+ data: FileObject[];
144
+ error: null;
145
+ } | {
146
+ data: null;
147
+ error: StorageError;
148
+ }>;
149
+ /**
150
+ * Upload a file from a public URL to the bucket.
151
+ *
152
+ * @param url The public URL of the file to download (e.g., CDN link).
153
+ */
154
+ uploadFromUrl(url: string): Promise<{
155
+ data: UploadFileData;
156
+ error: null;
157
+ } | {
158
+ data: null;
159
+ error: StorageError;
160
+ }>;
161
+ /**
162
+ * Lists all the files within a bucket.
163
+ * @param path The folder path.
164
+ * @param options Search options including limit (defaults to 100), offset, sortBy, and search
165
+ */
166
+ list(path?: string, options?: SearchOptions, parameters?: FetchParameters): Promise<{
167
+ data: FileObject[];
168
+ error: null;
169
+ } | {
170
+ data: null;
171
+ error: StorageError;
172
+ }>;
173
+ generateDownloadUrlFromFilePath(filePath: string): string;
174
+ protected encodeMetadata(metadata: Record<string, any>): string;
175
+ toBase64(data: string): string;
176
+ private _getFinalPath;
177
+ private _removeEmptyFolders;
178
+ private _isValidDownloadUrl;
179
+ /**
180
+ * Get the filePath from download url with format like
181
+ * /spark/app/app_xxxx/runtime/api/v1/storage/object/bucket_xxx/123%2Fimage.png
182
+ * or /app/app_xxxx/runtime/api/v1/storage/object/bucket_xxx/123%2Fimage.png
183
+ */
184
+ private _retrieveFilePathFromDownloadUrl;
185
+ /**
186
+ * Directly copy files using VolcEngine API if url is from VolcEngine Beijing Region.
187
+ */
188
+ private _copyWithinVolcEngine;
189
+ }
190
+ //# sourceMappingURL=StorageFileApi.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"StorageFileApi.d.ts","sourceRoot":"","sources":["../../../src/storage/packages/StorageFileApi.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,378 @@
1
+ import { StorageError, StorageUnknownError, isCustomError, isStorageError } from "../libs/errors.js";
2
+ import { get, post, put, remove } from "../libs/fetch.js";
3
+ import { checkIsVolcEngineUrl, getUpdateFileSize, resolveFetch, sanitizeFileName, toValidExpiresIn, transformFilePayload } from "../libs/helpers.js";
4
+ const DEFAULT_SEARCH_OPTIONS = {
5
+ limit: 100,
6
+ offset: 0,
7
+ sortBy: {
8
+ column: 'name',
9
+ order: 'asc'
10
+ }
11
+ };
12
+ const DEFAULT_FILE_OPTIONS = {
13
+ upsert: false
14
+ };
15
+ class StorageFileApi {
16
+ constructor(url, headers = {}, bucketId, appId, fetch, loggerEnabled, onRequestError){
17
+ this.url = url;
18
+ this.headers = headers;
19
+ this.bucketId = bucketId;
20
+ this.appId = appId;
21
+ this.fetch = resolveFetch(fetch);
22
+ this.loggerEnabled = loggerEnabled;
23
+ this.onRequestError = onRequestError;
24
+ }
25
+ async uploadOrUpdate(path, fileBody, fileOptions) {
26
+ try {
27
+ const options = {
28
+ ...DEFAULT_FILE_OPTIONS,
29
+ ...fileOptions
30
+ };
31
+ const cleanPath = this._removeEmptyFolders(path);
32
+ let contentDisposition = null;
33
+ if (options?.contentDisposition) contentDisposition = options?.contentDisposition;
34
+ else if (fileBody instanceof File) contentDisposition = fileBody?.name;
35
+ const preUploadBody = {
36
+ bucket_id: this.bucketId ?? '',
37
+ file_size: getUpdateFileSize(fileBody),
38
+ upsert: options.upsert ?? false,
39
+ file_path: cleanPath,
40
+ file_name: fileBody instanceof File ? fileBody?.name : ''
41
+ };
42
+ const res = await post(this.fetch, `${this.url}/object/${this.bucketId}/pre_upload`, preUploadBody, {
43
+ headers: this.headers,
44
+ logFetch: this.loggerEnabled,
45
+ onRequestError: this.onRequestError
46
+ }, void 0, {
47
+ psmName: 'Storage.Upload.PreUpload'
48
+ });
49
+ const { upload_id, upload_url } = res?.data ?? {};
50
+ if (!upload_url || !upload_id) return {
51
+ data: null,
52
+ error: new StorageError('upload_url or upload_id is empty')
53
+ };
54
+ {
55
+ const tosHeaders = {};
56
+ if (contentDisposition) tosHeaders['content-disposition'] = `attachment; filename="${sanitizeFileName(contentDisposition)}"`;
57
+ if (options.cacheControl || 0 === options.cacheControl) tosHeaders['cache-control'] = `max-age=${options.cacheControl}`;
58
+ if (options.contentType) tosHeaders['content-type'] = options.contentType;
59
+ const tosRes = await put(this.fetch, upload_url, fileBody, {
60
+ noResolveJson: true,
61
+ headers: tosHeaders,
62
+ logFetch: this.loggerEnabled,
63
+ onRequestError: this.onRequestError
64
+ }, void 0, {
65
+ psmName: 'Storage.Upload.TosUpload'
66
+ });
67
+ const etag = tosRes?.headers?.get('Etag') ?? '';
68
+ const callbackRes = await post(this.fetch, `${this.url}/object/callback`, {
69
+ upload_id,
70
+ etag,
71
+ app_id: this.appId
72
+ }, {
73
+ headers: this.headers,
74
+ logFetch: this.loggerEnabled,
75
+ onRequestError: this.onRequestError
76
+ }, void 0, {
77
+ psmName: 'Storage.Upload.Callback'
78
+ });
79
+ return {
80
+ data: callbackRes?.data ?? {},
81
+ error: null
82
+ };
83
+ }
84
+ } catch (error) {
85
+ if (isCustomError(error) || isStorageError(error)) return {
86
+ data: null,
87
+ error: error
88
+ };
89
+ return {
90
+ data: null,
91
+ error: new StorageUnknownError('upload file error', error)
92
+ };
93
+ }
94
+ }
95
+ async upload(pathOrFileBody, fileBodyOrOptions, fileOptions) {
96
+ const isSecondArgFileBody = fileBodyOrOptions instanceof Blob || fileBodyOrOptions instanceof ArrayBuffer || 'undefined' != typeof File && fileBodyOrOptions instanceof File || fileBodyOrOptions instanceof FormData || fileBodyOrOptions instanceof URLSearchParams || 'undefined' != typeof ReadableStream && fileBodyOrOptions instanceof ReadableStream || ArrayBuffer.isView(fileBodyOrOptions) || 'string' == typeof fileBodyOrOptions;
97
+ if ('string' == typeof pathOrFileBody && isSecondArgFileBody) return this.uploadOrUpdate(pathOrFileBody, fileBodyOrOptions, fileOptions);
98
+ const options = fileBodyOrOptions;
99
+ return this.uploadOrUpdate(options?.filePath ?? '', pathOrFileBody, options);
100
+ }
101
+ async uploadFile(fileBody, fileOptions) {
102
+ return this.uploadOrUpdate(fileOptions?.filePath ?? '', fileBody, fileOptions);
103
+ }
104
+ async update(path, fileBody, fileOptions) {
105
+ return this.uploadOrUpdate(path, fileBody, fileOptions);
106
+ }
107
+ async createSignedUrl(path, expiresIn, _options) {
108
+ try {
109
+ const _path = this._getFinalPath(path);
110
+ const res = await post(this.fetch, `${this.url}/object/sign/${_path}`, {
111
+ expires_in: toValidExpiresIn(expiresIn)
112
+ }, {
113
+ headers: this.headers,
114
+ logFetch: this.loggerEnabled,
115
+ onRequestError: this.onRequestError
116
+ }, void 0, {
117
+ psmName: 'Storage.CreateSignedUrl'
118
+ });
119
+ return {
120
+ data: res.data,
121
+ error: null
122
+ };
123
+ } catch (error) {
124
+ if (isCustomError(error) || isStorageError(error)) return {
125
+ data: null,
126
+ error: error
127
+ };
128
+ return {
129
+ data: null,
130
+ error: new StorageUnknownError('create signed url error', error)
131
+ };
132
+ }
133
+ }
134
+ async createSignedUrls(paths, expiresIn, _options) {
135
+ try {
136
+ const _paths = paths.map((path)=>this._retrieveFilePathFromDownloadUrl(path));
137
+ const res = await post(this.fetch, `${this.url}/object/sign/${this.bucketId}`, {
138
+ expires_in: toValidExpiresIn(expiresIn),
139
+ paths: _paths
140
+ }, {
141
+ headers: this.headers,
142
+ logFetch: this.loggerEnabled,
143
+ onRequestError: this.onRequestError
144
+ }, void 0, {
145
+ psmName: 'Storage.CreateSignedUrls'
146
+ });
147
+ return {
148
+ data: res.data,
149
+ error: null
150
+ };
151
+ } catch (error) {
152
+ if (isCustomError(error) || isStorageError(error)) return {
153
+ data: null,
154
+ error: error
155
+ };
156
+ return {
157
+ data: null,
158
+ error: new StorageUnknownError('create signed urls error', error)
159
+ };
160
+ }
161
+ }
162
+ async download(path, _options) {
163
+ try {
164
+ const _path = this._retrieveFilePathFromDownloadUrl(path);
165
+ const res = await get(this.fetch, `${this.url}/object/${this.bucketId}/${_path}`, {
166
+ headers: this.headers,
167
+ noResolveJson: true,
168
+ logFetch: this.loggerEnabled,
169
+ onRequestError: this.onRequestError
170
+ }, void 0, {
171
+ psmName: 'Storage.Download'
172
+ });
173
+ if (res.redirected) {
174
+ const resBody = await res.blob();
175
+ return {
176
+ data: resBody,
177
+ error: null
178
+ };
179
+ }
180
+ const resBody = await res.json();
181
+ return {
182
+ data: null,
183
+ error: resBody
184
+ };
185
+ } catch (error) {
186
+ if (error && 'object' == typeof error && 'originalError' in error) {
187
+ const originalError = error.originalError;
188
+ if (originalError instanceof Response && originalError.redirected) try {
189
+ return {
190
+ data: null,
191
+ error: new StorageError(await originalError.text())
192
+ };
193
+ } catch (_e) {
194
+ return {
195
+ data: null,
196
+ error: new StorageUnknownError('download file error', error)
197
+ };
198
+ }
199
+ }
200
+ if (isCustomError(error) || isStorageError(error)) return {
201
+ data: null,
202
+ error: error
203
+ };
204
+ return {
205
+ data: null,
206
+ error: new StorageUnknownError('download file error', error)
207
+ };
208
+ }
209
+ }
210
+ async remove(paths) {
211
+ try {
212
+ const _paths = paths.map((path)=>this._retrieveFilePathFromDownloadUrl(path));
213
+ const res = await remove(this.fetch, `${this.url}/object/${this.bucketId}`, {
214
+ prefixes: _paths
215
+ }, {
216
+ headers: this.headers,
217
+ logFetch: this.loggerEnabled,
218
+ onRequestError: this.onRequestError
219
+ }, void 0, {
220
+ psmName: 'Storage.Remove'
221
+ });
222
+ return {
223
+ data: res.data.map((file)=>transformFilePayload(file)),
224
+ error: null
225
+ };
226
+ } catch (error) {
227
+ if (isCustomError(error) || isStorageError(error)) return {
228
+ data: null,
229
+ error: error
230
+ };
231
+ return {
232
+ data: null,
233
+ error: new StorageUnknownError('remove file error', error)
234
+ };
235
+ }
236
+ }
237
+ async uploadFromUrl(url) {
238
+ try {
239
+ let parsedUrl;
240
+ try {
241
+ parsedUrl = new URL(url);
242
+ } catch {
243
+ return {
244
+ data: null,
245
+ error: new StorageError('Invalid URL provided')
246
+ };
247
+ }
248
+ if ('http:' !== parsedUrl.protocol && 'https:' !== parsedUrl.protocol) return {
249
+ data: null,
250
+ error: new StorageError('Only http and https protocols are supported')
251
+ };
252
+ if (checkIsVolcEngineUrl(url)) {
253
+ const res = await this._copyWithinVolcEngine(url);
254
+ return {
255
+ data: res,
256
+ error: null
257
+ };
258
+ }
259
+ const response = await this.fetch(url);
260
+ if (!response.ok) return {
261
+ data: null,
262
+ error: new StorageError(`Failed to download file from URL: ${response.status} ${response.statusText}`)
263
+ };
264
+ const responseContentType = response.headers.get('content-type') || '';
265
+ const mimeType = responseContentType.split(';')[0].trim().toLowerCase();
266
+ const contentDisposition = response.headers.get('content-disposition');
267
+ const cacheControl = response.headers.get('cache-control');
268
+ const blob = await response.blob();
269
+ if (0 === blob.size) return {
270
+ data: null,
271
+ error: new StorageError('Downloaded file is empty')
272
+ };
273
+ const options = {};
274
+ if (mimeType) options.contentType = mimeType;
275
+ if (contentDisposition) options.contentDisposition = contentDisposition;
276
+ if (cacheControl) {
277
+ const maxAgeMatch = cacheControl.match(/max-age=(\d+)/i);
278
+ if (maxAgeMatch) options.cacheControl = Number.parseInt(maxAgeMatch[1], 10);
279
+ }
280
+ return this.uploadOrUpdate('', blob, options);
281
+ } catch (error) {
282
+ if (isCustomError(error) || isStorageError(error)) return {
283
+ data: null,
284
+ error: error
285
+ };
286
+ return {
287
+ data: null,
288
+ error: new StorageUnknownError('copy from url error', error)
289
+ };
290
+ }
291
+ }
292
+ async list(path, options, parameters) {
293
+ try {
294
+ const body = {
295
+ ...DEFAULT_SEARCH_OPTIONS,
296
+ ...options,
297
+ prefix: path || ''
298
+ };
299
+ const res = await post(this.fetch, `${this.url}/object/list/${this.bucketId}`, body, {
300
+ headers: this.headers,
301
+ logFetch: this.loggerEnabled,
302
+ onRequestError: this.onRequestError
303
+ }, parameters, {
304
+ psmName: 'Storage.List'
305
+ });
306
+ const transformedData = res.data.map((file)=>transformFilePayload(file));
307
+ return {
308
+ data: transformedData,
309
+ error: null
310
+ };
311
+ } catch (error) {
312
+ if (isCustomError(error) || isStorageError(error)) return {
313
+ data: null,
314
+ error: error
315
+ };
316
+ return {
317
+ data: null,
318
+ error: new StorageUnknownError('list file error', error)
319
+ };
320
+ }
321
+ }
322
+ generateDownloadUrlFromFilePath(filePath) {
323
+ return `/app/${this.appId}/runtime/api/v1/storage/object/${this.bucketId}/${encodeURIComponent(this._removeEmptyFolders(filePath))}`;
324
+ }
325
+ encodeMetadata(metadata) {
326
+ return JSON.stringify(metadata);
327
+ }
328
+ toBase64(data) {
329
+ if ('undefined' != typeof Buffer) return Buffer.from(data).toString('base64');
330
+ return btoa(data);
331
+ }
332
+ _getFinalPath(path) {
333
+ const _path = this._retrieveFilePathFromDownloadUrl(path);
334
+ return `${this.bucketId}/${_path.replace(/^\/+/, '')}`;
335
+ }
336
+ _removeEmptyFolders(path) {
337
+ if (!path) return path;
338
+ return path.replace(/^\/|\/$/g, '').replace(/\/+/g, '/');
339
+ }
340
+ _isValidDownloadUrl(url) {
341
+ return /^(\/spark)?\/app\/app_[\w]+\/runtime\/api\/v1\/storage\/object\//.test(url);
342
+ }
343
+ _retrieveFilePathFromDownloadUrl(url) {
344
+ if (!this._isValidDownloadUrl(url)) return url;
345
+ const objectPath = '/object/';
346
+ const objectIndex = url.indexOf(objectPath);
347
+ if (-1 === objectIndex) return '';
348
+ const afterObject = url.slice(objectIndex + objectPath.length);
349
+ const bucketEndIndex = afterObject.indexOf('/');
350
+ if (-1 !== bucketEndIndex) {
351
+ const result = afterObject.slice(bucketEndIndex + 1);
352
+ return decodeURIComponent(result);
353
+ }
354
+ return '';
355
+ }
356
+ async _copyWithinVolcEngine(url) {
357
+ const res = await post(this.fetch, `${this.url}/runtime/app/${this.appId}/object/${this.bucketId}/copy`, {
358
+ source: {
359
+ type: 'externalTOS',
360
+ externalURL: url
361
+ }
362
+ }, {
363
+ headers: this.headers,
364
+ logFetch: this.loggerEnabled,
365
+ onRequestError: this.onRequestError
366
+ }, void 0, {
367
+ psmName: 'Storage.Copy'
368
+ });
369
+ const { metadata } = res?.data ?? {};
370
+ return {
371
+ id: metadata?.id ?? '',
372
+ file_path: metadata?.filePath ?? '',
373
+ bucket_id: metadata?.bucketID ?? '',
374
+ download_url: metadata?.downloadURL ?? ''
375
+ };
376
+ }
377
+ }
378
+ export { StorageFileApi as default };
@@ -0,0 +1,15 @@
1
+ type FetchMethod = 'GET' | 'POST' | 'PUT' | 'DELETE' | 'HEAD';
2
+ type LogParams = {
3
+ traceId: number;
4
+ url: string;
5
+ method: FetchMethod;
6
+ body?: unknown;
7
+ };
8
+ export declare const logRequest: (params: LogParams, psmName?: string) => void;
9
+ export declare const logResponse: (traceId: number, response: {
10
+ data: any;
11
+ error: any;
12
+ status: number;
13
+ }, psmName?: string) => void;
14
+ export {};
15
+ //# sourceMappingURL=logger.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.d.ts","sourceRoot":"","sources":["../../../src/storage/utils/logger.ts"],"names":[],"mappings":"AAAA,KAAK,WAAW,GAAG,KAAK,GAAG,MAAM,GAAG,KAAK,GAAG,QAAQ,GAAG,MAAM,CAAC;AAE9D,KAAK,SAAS,GAAG;IACf,OAAO,EAAE,MAAM,CAAC;IAChB,GAAG,EAAE,MAAM,CAAC;IACZ,MAAM,EAAE,WAAW,CAAC;IACpB,IAAI,CAAC,EAAE,OAAO,CAAC;CAChB,CAAC;AAEF,eAAO,MAAM,UAAU,GAAI,QAAQ,SAAS,EAAE,gBAAmB,SAoBhE,CAAC;AAEF,eAAO,MAAM,WAAW,GACtB,SAAS,MAAM,EACf,UAAU;IAAE,IAAI,EAAE,GAAG,CAAC;IAAC,KAAK,EAAE,GAAG,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,EACnD,gBAAmB,SA0BpB,CAAC"}
@@ -0,0 +1,18 @@
1
+ const logRequest = (params, psmName = 'Storage')=>{
2
+ const { traceId, url, method, body } = params;
3
+ const decodedParams = Array.from(new URL(url).searchParams.entries()).filter(([key])=>![
4
+ 'count',
5
+ 'tx',
6
+ 'missing',
7
+ 'resolution',
8
+ 'column'
9
+ ].includes(key)).map(([key, value])=>`${key}=${value}`);
10
+ console.log(`[Dataloom][${psmName}][Request]`, 'trace id:', traceId, 'method:', method, 'params:', decodedParams.join(','), 'body:', body);
11
+ };
12
+ const logResponse = (traceId, response, psmName = 'Storage')=>{
13
+ const { data, error, status } = response;
14
+ const hasError = !!error;
15
+ if (hasError) console.error(`[Dataloom][${psmName}][Response Failed]`, 'trace id:', traceId, 'statusCode:', status, 'error:', error);
16
+ else console.log(`[Dataloom][${psmName}][Response Success]`, 'trace id:', traceId, 'statusCode:', status, 'data:', data);
17
+ };
18
+ export { logRequest, logResponse };
@@ -0,0 +1,45 @@
1
+ /**
2
+ * TraceIdGenerator
3
+ *
4
+ * A singleton class for generating auto-incrementing trace IDs within a process.
5
+ * Each call to next() returns a unique, incremented number.
6
+ *
7
+ * @example
8
+ * const traceId = traceIdGenerator.next();
9
+ */
10
+ declare class TraceIdGenerator {
11
+ /**
12
+ * The singleton instance of TraceIdGenerator.
13
+ */
14
+ private static instance;
15
+ /**
16
+ * The current trace id value.
17
+ */
18
+ private counter;
19
+ private constructor();
20
+ /**
21
+ * Get the singleton instance of TraceIdGenerator.
22
+ * @returns {TraceIdGenerator}
23
+ */
24
+ static getInstance(): TraceIdGenerator;
25
+ /**
26
+ * Get the next trace id (auto-increment).
27
+ * @returns {number} The next trace id.
28
+ */
29
+ next(): number;
30
+ /**
31
+ * Get the current trace id (without increment).
32
+ * @returns {number} The current trace id.
33
+ */
34
+ getCurrent(): number;
35
+ /**
36
+ * Reset the trace id counter to 1. (For testing or special use only)
37
+ */
38
+ reset(): void;
39
+ }
40
+ /**
41
+ * The singleton instance for trace id generation.
42
+ */
43
+ declare const traceIdGenerator: TraceIdGenerator;
44
+ export { TraceIdGenerator, traceIdGenerator };
45
+ //# sourceMappingURL=trace-id.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"trace-id.d.ts","sourceRoot":"","sources":["../../../src/storage/utils/trace-id.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AACH,cAAM,gBAAgB;IACpB;;OAEG;IACH,OAAO,CAAC,MAAM,CAAC,QAAQ,CAAmB;IAE1C;;OAEG;IACH,OAAO,CAAC,OAAO,CAAa;IAE5B,OAAO;IAEP;;;OAGG;WACW,WAAW,IAAI,gBAAgB;IAO7C;;;OAGG;IACI,IAAI,IAAI,MAAM;IAIrB;;;OAGG;IACI,UAAU,IAAI,MAAM;IAI3B;;OAEG;IACI,KAAK,IAAI,IAAI;CAGrB;AAED;;GAEG;AACH,QAAA,MAAM,gBAAgB,kBAAiC,CAAC;AAExD,OAAO,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,CAAC"}
@@ -0,0 +1,20 @@
1
+ class TraceIdGenerator {
2
+ constructor(){
3
+ this.counter = 1;
4
+ }
5
+ static getInstance() {
6
+ if (!TraceIdGenerator.instance) TraceIdGenerator.instance = new TraceIdGenerator();
7
+ return TraceIdGenerator.instance;
8
+ }
9
+ next() {
10
+ return this.counter++;
11
+ }
12
+ getCurrent() {
13
+ return this.counter;
14
+ }
15
+ reset() {
16
+ this.counter = 1;
17
+ }
18
+ }
19
+ const traceIdGenerator = TraceIdGenerator.getInstance();
20
+ export { TraceIdGenerator, traceIdGenerator };