cobolx-2 1.2.3 → 1.2.4
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/examples/math-calculations.cbx +128 -0
- package/examples/string-processing.cbx +105 -0
- package/package.json +1 -1
- package/runtime/src/date_utils.ts +400 -0
- package/runtime/src/file_utils.ts +414 -0
- package/runtime/src/index.ts +19 -0
- package/runtime/src/math_utils.ts +316 -0
- package/runtime/src/string_utils.ts +307 -0
|
@@ -0,0 +1,414 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* COBOL-X Standard Library — File I/O Utilities
|
|
3
|
+
*
|
|
4
|
+
* Provides COBOL-style file operations that mirror traditional COBOL
|
|
5
|
+
* file handling (OPEN, READ, WRITE, CLOSE) with a modern async/await API.
|
|
6
|
+
* In COBOL, files are traditionally sequential, indexed, or relative;
|
|
7
|
+
* this module focuses on sequential text file operations.
|
|
8
|
+
*
|
|
9
|
+
* All operations use Node.js fs/promises for non-blocking I/O.
|
|
10
|
+
* Error handling follows COBOL FILE STATUS conventions.
|
|
11
|
+
*
|
|
12
|
+
* @module file_utils
|
|
13
|
+
*/
|
|
14
|
+
|
|
15
|
+
import * as fs from "node:fs/promises";
|
|
16
|
+
import * as fsSync from "node:fs";
|
|
17
|
+
import * as path from "node:path";
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* File status codes matching COBOL FILE STATUS conventions.
|
|
21
|
+
*
|
|
22
|
+
* "00" = Success
|
|
23
|
+
* "10" = End of file
|
|
24
|
+
* "35" = File not found (OPEN)
|
|
25
|
+
* "93" = File locked / conflict
|
|
26
|
+
* "99" = I/O error (unknown)
|
|
27
|
+
*/
|
|
28
|
+
export type FileStatus = "00" | "10" | "35" | "93" | "99";
|
|
29
|
+
|
|
30
|
+
/** Result type for file operations with COBOL-style status. */
|
|
31
|
+
export interface FileResult<T = string> {
|
|
32
|
+
status: FileStatus;
|
|
33
|
+
data?: T;
|
|
34
|
+
error?: string;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
/**
|
|
38
|
+
* FILE-READ — Reads the entire contents of a text file.
|
|
39
|
+
*
|
|
40
|
+
* COBOL equivalent: OPEN INPUT file, READ file INTO ws-record, CLOSE file.
|
|
41
|
+
*
|
|
42
|
+
* @param filePath - The path to the file to read.
|
|
43
|
+
* @param encoding - The character encoding (default: "utf8").
|
|
44
|
+
* @returns A FileResult with the file contents on success.
|
|
45
|
+
*
|
|
46
|
+
* @example
|
|
47
|
+
* const result = await FILE_READ("/data/records.txt");
|
|
48
|
+
* IF result.status = "00"
|
|
49
|
+
* DISPLAY result.data
|
|
50
|
+
* END-IF
|
|
51
|
+
*/
|
|
52
|
+
export async function FILE_READ(
|
|
53
|
+
filePath: string,
|
|
54
|
+
encoding: BufferEncoding = "utf8"
|
|
55
|
+
): Promise<FileResult> {
|
|
56
|
+
if (typeof filePath !== "string") {
|
|
57
|
+
return { status: "99", error: `FILE-READ: filePath must be PIC X, received ${typeof filePath}` };
|
|
58
|
+
}
|
|
59
|
+
try {
|
|
60
|
+
const resolvedPath = path.resolve(filePath);
|
|
61
|
+
const data = await fs.readFile(resolvedPath, encoding);
|
|
62
|
+
return { status: "00", data };
|
|
63
|
+
} catch (err: unknown) {
|
|
64
|
+
const nodeErr = err as NodeJS.ErrnoException;
|
|
65
|
+
if (nodeErr.code === "ENOENT") {
|
|
66
|
+
return { status: "35", error: `FILE-READ: file not found '${filePath}'` };
|
|
67
|
+
}
|
|
68
|
+
if (nodeErr.code === "EACCES") {
|
|
69
|
+
return { status: "93", error: `FILE-READ: permission denied '${filePath}'` };
|
|
70
|
+
}
|
|
71
|
+
return { status: "99", error: `FILE-READ: ${nodeErr.message}` };
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
/**
|
|
76
|
+
* FILE-WRITE — Writes content to a text file, creating or overwriting it.
|
|
77
|
+
*
|
|
78
|
+
* COBOL equivalent: OPEN OUTPUT file, WRITE ws-record FROM ws-data, CLOSE file.
|
|
79
|
+
*
|
|
80
|
+
* @param filePath - The path to the file to write.
|
|
81
|
+
* @param content - The content to write to the file.
|
|
82
|
+
* @param encoding - The character encoding (default: "utf8").
|
|
83
|
+
* @returns A FileResult indicating success or failure.
|
|
84
|
+
*
|
|
85
|
+
* @example
|
|
86
|
+
* const result = await FILE_WRITE("/data/output.txt", "Hello COBOL-X");
|
|
87
|
+
*/
|
|
88
|
+
export async function FILE_WRITE(
|
|
89
|
+
filePath: string,
|
|
90
|
+
content: string,
|
|
91
|
+
encoding: BufferEncoding = "utf8"
|
|
92
|
+
): Promise<FileResult> {
|
|
93
|
+
if (typeof filePath !== "string") {
|
|
94
|
+
return { status: "99", error: `FILE-WRITE: filePath must be PIC X, received ${typeof filePath}` };
|
|
95
|
+
}
|
|
96
|
+
if (typeof content !== "string") {
|
|
97
|
+
return { status: "99", error: `FILE-WRITE: content must be PIC X, received ${typeof content}` };
|
|
98
|
+
}
|
|
99
|
+
try {
|
|
100
|
+
const resolvedPath = path.resolve(filePath);
|
|
101
|
+
// Ensure parent directory exists (COBOL doesn't need this, but it's helpful)
|
|
102
|
+
const dir = path.dirname(resolvedPath);
|
|
103
|
+
await fs.mkdir(dir, { recursive: true });
|
|
104
|
+
await fs.writeFile(resolvedPath, content, encoding);
|
|
105
|
+
return { status: "00" };
|
|
106
|
+
} catch (err: unknown) {
|
|
107
|
+
const nodeErr = err as NodeJS.ErrnoException;
|
|
108
|
+
if (nodeErr.code === "EACCES") {
|
|
109
|
+
return { status: "93", error: `FILE-WRITE: permission denied '${filePath}'` };
|
|
110
|
+
}
|
|
111
|
+
return { status: "99", error: `FILE-WRITE: ${nodeErr.message}` };
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
/**
|
|
116
|
+
* FILE-APPEND — Appends content to an existing text file.
|
|
117
|
+
*
|
|
118
|
+
* COBOL equivalent: OPEN EXTEND file, WRITE ws-record, CLOSE file.
|
|
119
|
+
*
|
|
120
|
+
* @param filePath - The path to the file.
|
|
121
|
+
* @param content - The content to append.
|
|
122
|
+
* @param encoding - The character encoding (default: "utf8").
|
|
123
|
+
* @returns A FileResult indicating success or failure.
|
|
124
|
+
*
|
|
125
|
+
* @example
|
|
126
|
+
* const result = await FILE_APPEND("/data/log.txt", "New log entry\n");
|
|
127
|
+
*/
|
|
128
|
+
export async function FILE_APPEND(
|
|
129
|
+
filePath: string,
|
|
130
|
+
content: string,
|
|
131
|
+
encoding: BufferEncoding = "utf8"
|
|
132
|
+
): Promise<FileResult> {
|
|
133
|
+
if (typeof filePath !== "string") {
|
|
134
|
+
return { status: "99", error: `FILE-APPEND: filePath must be PIC X, received ${typeof filePath}` };
|
|
135
|
+
}
|
|
136
|
+
if (typeof content !== "string") {
|
|
137
|
+
return { status: "99", error: `FILE-APPEND: content must be PIC X, received ${typeof content}` };
|
|
138
|
+
}
|
|
139
|
+
try {
|
|
140
|
+
const resolvedPath = path.resolve(filePath);
|
|
141
|
+
await fs.appendFile(resolvedPath, content, encoding);
|
|
142
|
+
return { status: "00" };
|
|
143
|
+
} catch (err: unknown) {
|
|
144
|
+
const nodeErr = err as NodeJS.ErrnoException;
|
|
145
|
+
if (nodeErr.code === "ENOENT") {
|
|
146
|
+
return { status: "35", error: `FILE-APPEND: file not found '${filePath}'` };
|
|
147
|
+
}
|
|
148
|
+
if (nodeErr.code === "EACCES") {
|
|
149
|
+
return { status: "93", error: `FILE-APPEND: permission denied '${filePath}'` };
|
|
150
|
+
}
|
|
151
|
+
return { status: "99", error: `FILE-APPEND: ${nodeErr.message}` };
|
|
152
|
+
}
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
/**
|
|
156
|
+
* FILE-EXISTS — Checks whether a file or directory exists at the given path.
|
|
157
|
+
*
|
|
158
|
+
* COBOL equivalent: OPEN INPUT file with FILE STATUS check for "35".
|
|
159
|
+
*
|
|
160
|
+
* @param filePath - The path to check.
|
|
161
|
+
* @returns 1 if the file/directory exists, 0 otherwise.
|
|
162
|
+
*
|
|
163
|
+
* @example
|
|
164
|
+
* IF FILE_EXISTS("/data/records.txt") = 1
|
|
165
|
+
* DISPLAY "File exists"
|
|
166
|
+
* END-IF
|
|
167
|
+
*/
|
|
168
|
+
export function FILE_EXISTS(filePath: string): 0 | 1 {
|
|
169
|
+
if (typeof filePath !== "string") {
|
|
170
|
+
throw new Error(`FILE-EXISTS: filePath must be PIC X, received ${typeof filePath}`);
|
|
171
|
+
}
|
|
172
|
+
try {
|
|
173
|
+
const resolvedPath = path.resolve(filePath);
|
|
174
|
+
fsSync.accessSync(resolvedPath, fsSync.constants.F_OK);
|
|
175
|
+
return 1;
|
|
176
|
+
} catch {
|
|
177
|
+
return 0;
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
/**
|
|
182
|
+
* FILE-DELETE — Deletes a file at the given path.
|
|
183
|
+
*
|
|
184
|
+
* COBOL equivalent: OPEN I-O file, DELETE file, CLOSE file.
|
|
185
|
+
*
|
|
186
|
+
* @param filePath - The path to the file to delete.
|
|
187
|
+
* @returns A FileResult indicating success or failure.
|
|
188
|
+
*
|
|
189
|
+
* @example
|
|
190
|
+
* const result = await FILE_DELETE("/data/temp.txt");
|
|
191
|
+
*/
|
|
192
|
+
export async function FILE_DELETE(filePath: string): Promise<FileResult> {
|
|
193
|
+
if (typeof filePath !== "string") {
|
|
194
|
+
return { status: "99", error: `FILE-DELETE: filePath must be PIC X, received ${typeof filePath}` };
|
|
195
|
+
}
|
|
196
|
+
try {
|
|
197
|
+
const resolvedPath = path.resolve(filePath);
|
|
198
|
+
await fs.unlink(resolvedPath);
|
|
199
|
+
return { status: "00" };
|
|
200
|
+
} catch (err: unknown) {
|
|
201
|
+
const nodeErr = err as NodeJS.ErrnoException;
|
|
202
|
+
if (nodeErr.code === "ENOENT") {
|
|
203
|
+
return { status: "35", error: `FILE-DELETE: file not found '${filePath}'` };
|
|
204
|
+
}
|
|
205
|
+
if (nodeErr.code === "EACCES" || nodeErr.code === "EPERM") {
|
|
206
|
+
return { status: "93", error: `FILE-DELETE: permission denied '${filePath}'` };
|
|
207
|
+
}
|
|
208
|
+
return { status: "99", error: `FILE-DELETE: ${nodeErr.message}` };
|
|
209
|
+
}
|
|
210
|
+
}
|
|
211
|
+
|
|
212
|
+
/**
|
|
213
|
+
* LIST-DIRECTORY — Lists the files and subdirectories in a directory.
|
|
214
|
+
*
|
|
215
|
+
* COBOL equivalent: No direct equivalent; traditionally done via OS CALL.
|
|
216
|
+
*
|
|
217
|
+
* @param dirPath - The path to the directory to list.
|
|
218
|
+
* @param options - Options: recursive (default: false), pattern (glob, default: all).
|
|
219
|
+
* @returns A FileResult with an array of entry names on success.
|
|
220
|
+
*
|
|
221
|
+
* @example
|
|
222
|
+
* const result = await LIST_DIRECTORY("/data");
|
|
223
|
+
* IF result.status = "00"
|
|
224
|
+
* DISPLAY result.data // ["file1.txt", "file2.txt", "subdir/"]
|
|
225
|
+
* END-IF
|
|
226
|
+
*/
|
|
227
|
+
export async function LIST_DIRECTORY(
|
|
228
|
+
dirPath: string,
|
|
229
|
+
options: { recursive?: boolean; pattern?: string } = {}
|
|
230
|
+
): Promise<FileResult<string[]>> {
|
|
231
|
+
if (typeof dirPath !== "string") {
|
|
232
|
+
return { status: "99", error: `LIST-DIRECTORY: dirPath must be PIC X, received ${typeof dirPath}` };
|
|
233
|
+
}
|
|
234
|
+
const { recursive = false, pattern } = options;
|
|
235
|
+
|
|
236
|
+
try {
|
|
237
|
+
const resolvedPath = path.resolve(dirPath);
|
|
238
|
+
const stat = await fs.stat(resolvedPath);
|
|
239
|
+
if (!stat.isDirectory()) {
|
|
240
|
+
return { status: "99", error: `LIST-DIRECTORY: '${dirPath}' is not a directory` };
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
let entries: string[];
|
|
244
|
+
if (recursive) {
|
|
245
|
+
entries = await listRecursive(resolvedPath, resolvedPath);
|
|
246
|
+
} else {
|
|
247
|
+
const rawEntries = await fs.readdir(resolvedPath, { withFileTypes: true });
|
|
248
|
+
entries = rawEntries.map((entry) =>
|
|
249
|
+
entry.isDirectory() ? `${entry.name}/` : entry.name
|
|
250
|
+
);
|
|
251
|
+
}
|
|
252
|
+
|
|
253
|
+
// Apply pattern filter if provided
|
|
254
|
+
if (pattern) {
|
|
255
|
+
const regex = new RegExp(pattern, "i");
|
|
256
|
+
entries = entries.filter((e) => regex.test(e));
|
|
257
|
+
}
|
|
258
|
+
|
|
259
|
+
return { status: "00", data: entries };
|
|
260
|
+
} catch (err: unknown) {
|
|
261
|
+
const nodeErr = err as NodeJS.ErrnoException;
|
|
262
|
+
if (nodeErr.code === "ENOENT") {
|
|
263
|
+
return { status: "35", error: `LIST-DIRECTORY: directory not found '${dirPath}'` };
|
|
264
|
+
}
|
|
265
|
+
if (nodeErr.code === "EACCES") {
|
|
266
|
+
return { status: "93", error: `LIST-DIRECTORY: permission denied '${dirPath}'` };
|
|
267
|
+
}
|
|
268
|
+
return { status: "99", error: `LIST-DIRECTORY: ${nodeErr.message}` };
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
|
|
272
|
+
/**
|
|
273
|
+
* Internal helper: recursively list all files under a directory.
|
|
274
|
+
*/
|
|
275
|
+
async function listRecursive(basePath: string, currentPath: string): Promise<string[]> {
|
|
276
|
+
const results: string[] = [];
|
|
277
|
+
const entries = await fs.readdir(currentPath, { withFileTypes: true });
|
|
278
|
+
|
|
279
|
+
for (const entry of entries) {
|
|
280
|
+
const fullPath = path.join(currentPath, entry.name);
|
|
281
|
+
const relativePath = path.relative(basePath, fullPath);
|
|
282
|
+
if (entry.isDirectory()) {
|
|
283
|
+
results.push(`${relativePath}/`);
|
|
284
|
+
const subEntries = await listRecursive(basePath, fullPath);
|
|
285
|
+
results.push(...subEntries);
|
|
286
|
+
} else {
|
|
287
|
+
results.push(relativePath);
|
|
288
|
+
}
|
|
289
|
+
}
|
|
290
|
+
|
|
291
|
+
return results;
|
|
292
|
+
}
|
|
293
|
+
|
|
294
|
+
/**
|
|
295
|
+
* FILE-COPY — Copies a file from source to destination.
|
|
296
|
+
*
|
|
297
|
+
* COBOL equivalent: READ source, WRITE destination (manual loop).
|
|
298
|
+
*
|
|
299
|
+
* @param sourcePath - The source file path.
|
|
300
|
+
* @param destPath - The destination file path.
|
|
301
|
+
* @returns A FileResult indicating success or failure.
|
|
302
|
+
*
|
|
303
|
+
* @example
|
|
304
|
+
* const result = await FILE_COPY("/data/input.txt", "/data/backup/input.txt");
|
|
305
|
+
*/
|
|
306
|
+
export async function FILE_COPY(sourcePath: string, destPath: string): Promise<FileResult> {
|
|
307
|
+
if (typeof sourcePath !== "string") {
|
|
308
|
+
return { status: "99", error: `FILE-COPY: sourcePath must be PIC X, received ${typeof sourcePath}` };
|
|
309
|
+
}
|
|
310
|
+
if (typeof destPath !== "string") {
|
|
311
|
+
return { status: "99", error: `FILE-COPY: destPath must be PIC X, received ${typeof destPath}` };
|
|
312
|
+
}
|
|
313
|
+
try {
|
|
314
|
+
const resolvedSource = path.resolve(sourcePath);
|
|
315
|
+
const resolvedDest = path.resolve(destPath);
|
|
316
|
+
|
|
317
|
+
// Ensure destination directory exists
|
|
318
|
+
const destDir = path.dirname(resolvedDest);
|
|
319
|
+
await fs.mkdir(destDir, { recursive: true });
|
|
320
|
+
|
|
321
|
+
await fs.copyFile(resolvedSource, resolvedDest);
|
|
322
|
+
return { status: "00" };
|
|
323
|
+
} catch (err: unknown) {
|
|
324
|
+
const nodeErr = err as NodeJS.ErrnoException;
|
|
325
|
+
if (nodeErr.code === "ENOENT") {
|
|
326
|
+
return { status: "35", error: `FILE-COPY: file not found '${sourcePath}'` };
|
|
327
|
+
}
|
|
328
|
+
if (nodeErr.code === "EACCES") {
|
|
329
|
+
return { status: "93", error: `FILE-COPY: permission denied` };
|
|
330
|
+
}
|
|
331
|
+
return { status: "99", error: `FILE-COPY: ${nodeErr.message}` };
|
|
332
|
+
}
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
/**
|
|
336
|
+
* FILE-MOVE — Moves (renames) a file from source to destination.
|
|
337
|
+
*
|
|
338
|
+
* COBOL equivalent: No direct equivalent; uses OS-level rename.
|
|
339
|
+
*
|
|
340
|
+
* @param sourcePath - The source file path.
|
|
341
|
+
* @param destPath - The destination file path.
|
|
342
|
+
* @returns A FileResult indicating success or failure.
|
|
343
|
+
*
|
|
344
|
+
* @example
|
|
345
|
+
* const result = await FILE_MOVE("/data/temp.txt", "/data/archive/old.txt");
|
|
346
|
+
*/
|
|
347
|
+
export async function FILE_MOVE(sourcePath: string, destPath: string): Promise<FileResult> {
|
|
348
|
+
if (typeof sourcePath !== "string") {
|
|
349
|
+
return { status: "99", error: `FILE-MOVE: sourcePath must be PIC X, received ${typeof sourcePath}` };
|
|
350
|
+
}
|
|
351
|
+
if (typeof destPath !== "string") {
|
|
352
|
+
return { status: "99", error: `FILE-MOVE: destPath must be PIC X, received ${typeof destPath}` };
|
|
353
|
+
}
|
|
354
|
+
try {
|
|
355
|
+
const resolvedSource = path.resolve(sourcePath);
|
|
356
|
+
const resolvedDest = path.resolve(destPath);
|
|
357
|
+
|
|
358
|
+
// Ensure destination directory exists
|
|
359
|
+
const destDir = path.dirname(resolvedDest);
|
|
360
|
+
await fs.mkdir(destDir, { recursive: true });
|
|
361
|
+
|
|
362
|
+
await fs.rename(resolvedSource, resolvedDest);
|
|
363
|
+
return { status: "00" };
|
|
364
|
+
} catch (err: unknown) {
|
|
365
|
+
const nodeErr = err as NodeJS.ErrnoException;
|
|
366
|
+
if (nodeErr.code === "ENOENT") {
|
|
367
|
+
return { status: "35", error: `FILE-MOVE: file not found '${sourcePath}'` };
|
|
368
|
+
}
|
|
369
|
+
if (nodeErr.code === "EACCES") {
|
|
370
|
+
return { status: "93", error: `FILE-MOVE: permission denied` };
|
|
371
|
+
}
|
|
372
|
+
if (nodeErr.code === "EXDEV") {
|
|
373
|
+
// Cross-device move: copy + delete
|
|
374
|
+
const copyResult = await FILE_COPY(sourcePath, destPath);
|
|
375
|
+
if (copyResult.status !== "00") {
|
|
376
|
+
return copyResult;
|
|
377
|
+
}
|
|
378
|
+
return FILE_DELETE(sourcePath);
|
|
379
|
+
}
|
|
380
|
+
return { status: "99", error: `FILE-MOVE: ${nodeErr.message}` };
|
|
381
|
+
}
|
|
382
|
+
}
|
|
383
|
+
|
|
384
|
+
/**
|
|
385
|
+
* FILE-SIZE — Returns the size of a file in bytes.
|
|
386
|
+
*
|
|
387
|
+
* COBOL equivalent: No direct equivalent; uses OS CALL.
|
|
388
|
+
*
|
|
389
|
+
* @param filePath - The path to the file.
|
|
390
|
+
* @returns A FileResult with the file size in bytes, or error status.
|
|
391
|
+
*
|
|
392
|
+
* @example
|
|
393
|
+
* const result = await FILE_SIZE("/data/records.txt");
|
|
394
|
+
* DISPLAY result.data // e.g., 1024
|
|
395
|
+
*/
|
|
396
|
+
export async function FILE_SIZE(filePath: string): Promise<FileResult<number>> {
|
|
397
|
+
if (typeof filePath !== "string") {
|
|
398
|
+
return { status: "99", error: `FILE-SIZE: filePath must be PIC X, received ${typeof filePath}` };
|
|
399
|
+
}
|
|
400
|
+
try {
|
|
401
|
+
const resolvedPath = path.resolve(filePath);
|
|
402
|
+
const stat = await fs.stat(resolvedPath);
|
|
403
|
+
return { status: "00", data: stat.size };
|
|
404
|
+
} catch (err: unknown) {
|
|
405
|
+
const nodeErr = err as NodeJS.ErrnoException;
|
|
406
|
+
if (nodeErr.code === "ENOENT") {
|
|
407
|
+
return { status: "35", error: `FILE-SIZE: file not found '${filePath}'` };
|
|
408
|
+
}
|
|
409
|
+
if (nodeErr.code === "EACCES") {
|
|
410
|
+
return { status: "93", error: `FILE-SIZE: permission denied '${filePath}'` };
|
|
411
|
+
}
|
|
412
|
+
return { status: "99", error: `FILE-SIZE: ${nodeErr.message}` };
|
|
413
|
+
}
|
|
414
|
+
}
|
package/runtime/src/index.ts
CHANGED
|
@@ -18,3 +18,22 @@ export { Supervisor, healthCheck } from "./healing/index.js";
|
|
|
18
18
|
export { VersionedState } from "./state/versioned.js";
|
|
19
19
|
export { normalizeIntent } from "./intents/index.js";
|
|
20
20
|
export { inspectProgram } from "./code_as_data/index.js";
|
|
21
|
+
export {
|
|
22
|
+
STRING_REVERSE, STRING_UPPER, STRING_LOWER, STRING_TRIM,
|
|
23
|
+
STRING_SPLIT, STRING_JOIN, STRING_REPLACE, STRING_CONTAINS,
|
|
24
|
+
STRING_LENGTH, STRING_SUBSTRING, STRING_PAD,
|
|
25
|
+
} from "./string_utils.js";
|
|
26
|
+
export {
|
|
27
|
+
COMPUTE_POWER, COMPUTE_SQRT, COMPUTE_ABS, COMPUTE_MOD,
|
|
28
|
+
COMPUTE_MIN, COMPUTE_MAX, COMPUTE_ROUND, COMPUTE_FLOOR,
|
|
29
|
+
COMPUTE_CEIL, COMPUTE_SIGN, COMPUTE_CLAMP, COMPUTE_PERCENTAGE,
|
|
30
|
+
} from "./math_utils.js";
|
|
31
|
+
export {
|
|
32
|
+
CURRENT_DATE, CURRENT_DATE_ISO, DATE_ADD, DATE_DIFF,
|
|
33
|
+
FORMAT_DATE, PARSE_DATE, DAY_OF_WEEK, IS_LEAP_YEAR,
|
|
34
|
+
} from "./date_utils.js";
|
|
35
|
+
export {
|
|
36
|
+
FILE_READ, FILE_WRITE, FILE_APPEND, FILE_EXISTS, FILE_DELETE,
|
|
37
|
+
LIST_DIRECTORY, FILE_COPY, FILE_MOVE, FILE_SIZE,
|
|
38
|
+
} from "./file_utils.js";
|
|
39
|
+
export type { FileStatus, FileResult } from "./file_utils.js";
|