functionalscript 0.33.0 → 0.34.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 (70) hide show
  1. package/README.md +1 -1
  2. package/fs/asserts/module.f.d.ts +1 -1
  3. package/fs/asserts/module.f.js +4 -1
  4. package/fs/bnf/data/module.f.d.ts +0 -103
  5. package/fs/bnf/data/module.f.js +10 -246
  6. package/fs/bnf/data/proof.f.d.ts +0 -10
  7. package/fs/bnf/data/proof.f.js +2 -642
  8. package/fs/bnf/descent/module.f.d.ts +56 -0
  9. package/fs/bnf/descent/module.f.js +119 -0
  10. package/fs/bnf/descent/proof.f.d.ts +5 -0
  11. package/fs/bnf/descent/proof.f.js +296 -0
  12. package/fs/bnf/ll1/module.f.d.ts +72 -0
  13. package/fs/bnf/ll1/module.f.js +153 -0
  14. package/fs/bnf/ll1/proof.f.d.ts +9 -0
  15. package/fs/bnf/ll1/proof.f.js +358 -0
  16. package/fs/cas/cli/module.f.d.ts +6 -0
  17. package/fs/cas/cli/module.f.js +56 -0
  18. package/fs/cas/cli/proof.f.d.ts +14 -0
  19. package/fs/cas/cli/proof.f.js +149 -0
  20. package/fs/cas/mcp/module.f.d.ts +9 -17
  21. package/fs/cas/mcp/module.f.js +116 -84
  22. package/fs/cas/mcp/proof.f.d.ts +5 -1
  23. package/fs/cas/mcp/proof.f.js +74 -32
  24. package/fs/cas/module.f.d.ts +35 -15
  25. package/fs/cas/module.f.js +168 -131
  26. package/fs/cas/proof.f.d.ts +16 -13
  27. package/fs/cas/proof.f.js +255 -121
  28. package/fs/ci/config/module.f.d.ts +14 -14
  29. package/fs/ci/config/module.f.js +14 -14
  30. package/fs/djs/tokenizer-new/module.f.js +1 -1
  31. package/fs/djs/tokenizer-new/proof.f.d.ts +2 -0
  32. package/fs/djs/tokenizer-new/proof.f.js +357 -229
  33. package/fs/effects/list/module.f.d.ts +31 -0
  34. package/fs/effects/list/module.f.js +16 -0
  35. package/fs/effects/module.f.d.ts +11 -5
  36. package/fs/effects/module.f.js +16 -6
  37. package/fs/effects/node/module.f.d.ts +29 -3
  38. package/fs/effects/node/module.f.js +35 -1
  39. package/fs/effects/node/module.js +32 -18
  40. package/fs/effects/node/virtual/module.f.js +57 -0
  41. package/fs/effects/proof.f.d.ts +4 -0
  42. package/fs/effects/proof.f.js +18 -1
  43. package/fs/fjs/module.f.js +2 -8
  44. package/fs/html/module.f.js +6 -8
  45. package/fs/mcp/module.f.d.ts +1 -1
  46. package/fs/mime/module.f.d.ts +101 -5
  47. package/fs/mime/module.f.js +159 -6
  48. package/fs/mime/proof.f.d.ts +25 -0
  49. package/fs/mime/proof.f.js +193 -3
  50. package/fs/text/code_point/module.f.d.ts +39 -2
  51. package/fs/text/code_point/module.f.js +74 -2
  52. package/fs/text/code_point/proof.f.d.ts +8 -0
  53. package/fs/text/code_point/proof.f.js +72 -0
  54. package/fs/text/utf16/module.f.js +4 -26
  55. package/fs/text/utf8/module.f.d.ts +27 -0
  56. package/fs/text/utf8/module.f.js +8 -14
  57. package/fs/types/function/operator/module.f.d.ts +26 -0
  58. package/fs/types/list/module.f.d.ts +3 -0
  59. package/fs/types/result/module.d.ts +2 -4
  60. package/fs/types/result/module.js +9 -3
  61. package/package.json +3 -3
  62. package/issues/demo/data/data.f.js +0 -12
  63. package/issues/demo/data/shared.f.js +0 -3
  64. package/issues/demo/fs/app.js +0 -4
  65. package/issues/demo/fs/math.f.js +0 -4
  66. package/issues/demo/sample/proof.f.js +0 -13
  67. /package/{issues → todo}/031-json.f.d.ts +0 -0
  68. /package/{issues → todo}/031-json.f.js +0 -0
  69. /package/{issues → todo}/proof.f.d.ts +0 -0
  70. /package/{issues → todo}/proof.f.js +0 -0
@@ -9,33 +9,11 @@ import { map, reduce, flatMap, empty, } from "../../types/list/module.f.js";
9
9
  import { concat } from "../../types/function/operator/module.f.js";
10
10
  import { contains } from "../../types/range/module.f.js";
11
11
  import { fn } from "../../types/function/module.f.js";
12
- import { decoder, errorMask } from "../code_point/module.f.js";
13
- /**
14
- * Ranges of code points for the lower (Low) and higher (High) parts of the BMP (Basic Multilingual Plane) plane.
15
- */
16
- const lowBmp = contains([0x0000, 0xd7ff]);
17
- const highBmp = contains([0xe000, 0xffff]);
18
- /**
19
- * Checks whether the code point is in the BMP range.
20
- * BMP is the main multi-plane Unicode plane that covers code points 0x0000 - 0xFFFF, except for the range of surrogates.
21
- */
22
- const isBmpCodePoint = (codePoint) => lowBmp(codePoint) || highBmp(codePoint);
23
- /**
24
- * Checks whether the 16-bit word (U16) is a surrogate of the high part.
25
- * Range: 0xD800 - 0xDBFF.
26
- */
27
- const isHighSurrogate = contains([0xd800, 0xdbff]);
28
- /**
29
- * Checks whether the 16-bit word (U16) is a substitute for the low part.
30
- * Range: 0xDC00 – 0xDFFF.
31
- */
32
- const isLowSurrogate = contains([0xdc00, 0xdfff]);
33
- /**
34
- * Checks whether the code point belongs to the additional (Supplementary) plane of Unicode.
35
- * Additional planes include code points from 0x010000 to 0x10FFFF.
36
- */
37
- const isSupplementaryPlane = contains([0x01_0000, 0x10_ffff]);
12
+ import { decoder, errorMask, isBmpCodePoint, isHighSurrogate, isLowSurrogate, isSupplementaryPlane, } from "../code_point/module.f.js";
38
13
  /**
14
+ * The BMP / surrogate / supplementary-plane predicates used below live in
15
+ * `code_point`, the shared Unicode contract; see that module for their ranges.
16
+ *
39
17
  * Converts a Unicode code point to its corresponding UTF-16 representation.
40
18
  *
41
19
  * This function handles:
@@ -4,6 +4,7 @@
4
4
  * @module
5
5
  */
6
6
  import { type List, type Thunk } from '../../types/list/module.f.ts';
7
+ import type { StateScan } from '../../types/function/operator/module.f.ts';
7
8
  import type { Array1, Array2, Array3 } from '../../types/array/module.f.ts';
8
9
  import { type Vec } from '../../types/bit_vec/module.f.ts';
9
10
  /**
@@ -35,6 +36,32 @@ export type Utf8State = null | Utf8NonEmptyState;
35
36
  * @returns A thunk that lazily produces a sequence of UTF-8 bytes.
36
37
  */
37
38
  export declare const fromCodePointList: (input: List<number>) => Thunk<U8>;
39
+ /**
40
+ * Converts a non-empty UTF-8 decoding state to an error code.
41
+ *
42
+ * @param state - A non-empty UTF-8 decoding state.
43
+ * @returns An I32 error code derived from the invalid UTF-8 state.
44
+ */
45
+ export declare const utf8StateToError: (state: Utf8NonEmptyState) => I32;
46
+ /**
47
+ * Decodes a byte into a Unicode code point, using a given UTF-8 state.
48
+ *
49
+ * @param state - The current UTF-8 decoding state.
50
+ * @param byte - A single byte to decode.
51
+ * @returns A tuple containing:
52
+ * - A list of decoded Unicode code points or error codes.
53
+ * - The updated UTF-8 state.
54
+ */
55
+ export declare const utf8ByteToCodePointOp: StateScan<number, Utf8State, readonly I32[]>;
56
+ /**
57
+ * Handles the end-of-file (EOF) case for UTF-8 decoding.
58
+ *
59
+ * @param state - The current UTF-8 decoding state.
60
+ * @returns A tuple containing:
61
+ * - A list of decoded Unicode code points or error codes.
62
+ * - The reset UTF-8 state (`null`).
63
+ */
64
+ export declare const utf8EofToCodePointOp: (state: Utf8State) => readonly [List<I32>, Utf8State];
38
65
  /**
39
66
  * Converts a list of UTF-8 bytes into a list of Unicode code points.
40
67
  *
@@ -4,7 +4,7 @@
4
4
  * @module
5
5
  */
6
6
  import { flatMap, toArray } from "../../types/list/module.f.js";
7
- import { decoder, errorMask } from "../code_point/module.f.js";
7
+ import { decoder, errorMask, isValidCodePoint } from "../code_point/module.f.js";
8
8
  import { msb, u8List, length } from "../../types/bit_vec/module.f.js";
9
9
  import { codePointListToString } from "../utf16/module.f.js";
10
10
  /**
@@ -106,7 +106,7 @@ export const fromCodePointList = flatMap(codePointToUtf8);
106
106
  * @param state - A non-empty UTF-8 decoding state.
107
107
  * @returns An I32 error code derived from the invalid UTF-8 state.
108
108
  */
109
- const utf8StateToError = (state) => {
109
+ export const utf8StateToError = (state) => {
110
110
  let x;
111
111
  switch (state.length) {
112
112
  case 1: {
@@ -127,8 +127,8 @@ const utf8StateToError = (state) => {
127
127
  contPayload(s2) + 0b1000_0000_0000_0000;
128
128
  break;
129
129
  }
130
- default:
131
- throw 'invalid state';
130
+ //default:
131
+ // throw 'invalid state'
132
132
  }
133
133
  return x | errorMask;
134
134
  };
@@ -141,7 +141,7 @@ const utf8StateToError = (state) => {
141
141
  * - A list of decoded Unicode code points or error codes.
142
142
  * - The updated UTF-8 state.
143
143
  */
144
- const utf8ByteToCodePointOp = (byte, state) => {
144
+ export const utf8ByteToCodePointOp = (byte, state) => {
145
145
  if (byte < 0x00 || byte > 0xff) {
146
146
  return [[errorMask], state];
147
147
  }
@@ -199,7 +199,7 @@ const utf8ByteToCodePointOp = (byte, state) => {
199
199
  * - A list of decoded Unicode code points or error codes.
200
200
  * - The reset UTF-8 state (`null`).
201
201
  */
202
- const utf8EofToCodePointOp = (state) => [
202
+ export const utf8EofToCodePointOp = (state) => [
203
203
  state === null ? null : [utf8StateToError(state)],
204
204
  null,
205
205
  ];
@@ -216,18 +216,12 @@ export const toCodePointList = decoder(utf8ByteToCodePointOp, utf8EofToCodePoint
216
216
  * code points.
217
217
  */
218
218
  export const fromVec = (v) => {
219
- if (length(v) % 8n !== 0n) {
219
+ if ((length(v) & 7n) !== 0n) {
220
220
  return null;
221
221
  }
222
222
  const arr = toArray(toCodePointList(u8List(msb)(v)));
223
223
  for (const cp of arr) {
224
- if (cp < 0) {
225
- return null;
226
- }
227
- if (cp > 0x10FFFF) {
228
- return null;
229
- }
230
- if (cp >= 0xD800 && cp <= 0xDFFF) {
224
+ if (!isValidCodePoint(cp)) {
231
225
  return null;
232
226
  }
233
227
  }
@@ -12,6 +12,32 @@ export declare const logicalNot: Unary<boolean, boolean>;
12
12
  export type Equal<T> = Binary<T, T, boolean>;
13
13
  export declare const strictEqual: <T>(a: T) => (b: T) => boolean;
14
14
  export type Scan<I, O> = (input: I) => readonly [O, Scan<I, O>];
15
+ /**
16
+ * One step of a stream transducer: given an `input` symbol and the `prior`
17
+ * state, produce an `output` and the next state. It both maps an input stream
18
+ * to an output stream and threads state, so it models tokenizers, decoders, and
19
+ * other stream-to-stream stages.
20
+ *
21
+ * This is the *shape* of a [Mealy machine](https://en.wikipedia.org/wiki/Mealy_machine)
22
+ * — a [finite-state transducer](https://en.wikipedia.org/wiki/Finite-state_transducer)
23
+ * — but only its signature. The state `S` (and `I`, `O`) is an arbitrary type,
24
+ * not a finite set, so a `StateScan` is strictly more expressive than a Mealy
25
+ * machine — its power is the power of `S`:
26
+ * - a finite `S`/`I`/`O` recovers the classical finite-state machine (e.g. the
27
+ * DFA states in `../../../fsm/module.f.ts`);
28
+ * - an `S` that is a stack makes it a
29
+ * [pushdown / stack machine](https://en.wikipedia.org/wiki/Pushdown_automaton)
30
+ * (context-free power — balanced brackets, nested structure, the AST tier);
31
+ * - an unbounded `S` like `bigint` can count, which no finite automaton can.
32
+ *
33
+ * And `O` may be a list (0+ symbols per input), not the single symbol strict
34
+ * Mealy emits. (Functional/coalgebraic usage still calls this `(input, state)
35
+ * => [output, state]` shape a "Mealy machine", finiteness aside.)
36
+ *
37
+ * A {@link Fold} is the output-less special case (state only); driving a
38
+ * `StateScan` over a `List` is `stateScan` in `../../list/module.f.ts`, and
39
+ * {@link stateScanToScan} hides the state to recover a {@link Scan}.
40
+ */
15
41
  export type StateScan<I, S, O> = (input: I, prior: S) => readonly [O, S];
16
42
  export declare const stateScanToScan: <I, S, O>(op: StateScan<I, S, O>) => (prior: S) => Scan<I, O>;
17
43
  export declare const foldToScan: <I, O>(fold: Fold<I, O>) => (prior: O) => Scan<I, O>;
@@ -4,6 +4,9 @@ type NotLazy<T> = Result<T> | Concat<T> | readonly T[];
4
4
  type Empty = null;
5
5
  export type Result<T> = Empty | NonEmpty<T>;
6
6
  export type Thunk<T> = () => List<T>;
7
+ /**
8
+ * See also https://en.wikipedia.org/wiki/Cons#Lists
9
+ */
7
10
  export type NonEmpty<T> = {
8
11
  readonly first: T;
9
12
  readonly tail: List<T>;
@@ -1,5 +1,3 @@
1
1
  import { type Result } from './module.f.ts';
2
- declare const _default: {
3
- readonly tryCatch: <T>(f: () => T) => Result<T, unknown>;
4
- };
5
- export default _default;
2
+ export declare const tryCatch: <T>(f: () => T) => Result<T, unknown>;
3
+ export declare const asyncTryCatch: <T>(f: () => Promise<T>) => Promise<Result<T, unknown>>;
@@ -1,5 +1,5 @@
1
1
  import { ok, error } from "./module.f.js";
2
- const tryCatch = f => {
2
+ export const tryCatch = f => {
3
3
  // Side effect: `try catch` is not allowed in FunctionalScript.
4
4
  try {
5
5
  return ok(f());
@@ -8,6 +8,12 @@ const tryCatch = f => {
8
8
  return error(e);
9
9
  }
10
10
  };
11
- export default {
12
- tryCatch,
11
+ export const asyncTryCatch = async (f) => {
12
+ // Side effect: `try catch` is not allowed in FunctionalScript.
13
+ try {
14
+ return ok(await f());
15
+ }
16
+ catch (e) {
17
+ return error(e);
18
+ }
13
19
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "functionalscript",
3
- "version": "0.33.0",
3
+ "version": "0.34.0",
4
4
  "type": "module",
5
5
  "files": [
6
6
  "**/*.js",
@@ -43,8 +43,8 @@
43
43
  },
44
44
  "homepage": "https://github.com/functionalscript/functionalscript#readme",
45
45
  "devDependencies": {
46
- "@playwright/test": "1.61.0",
47
- "@types/node": "26.0.0",
46
+ "@playwright/test": "1.61.1",
47
+ "@types/node": "26.0.1",
48
48
  "typescript": "6.0.3"
49
49
  }
50
50
  }
@@ -1,12 +0,0 @@
1
- import shared from "./shared.f.js"
2
-
3
- // comment
4
- const s = "Hello, world!"
5
-
6
- export default {
7
- "a": shared,
8
- "b": shared,
9
- "s": s,
10
- d: -24n,
11
- x: undefined,
12
- }
@@ -1,3 +0,0 @@
1
- export default {
2
- "name": "shared object"
3
- }
@@ -1,4 +0,0 @@
1
- import math from "./math.f.js"
2
-
3
- const add2 = math.add(2)
4
- console.log("5 ===", add2(3))
@@ -1,4 +0,0 @@
1
- export default {
2
- add: a => b => a + b,
3
- mul: a => b => a * b,
4
- }
@@ -1,13 +0,0 @@
1
- const arrayOfTests = [
2
- () => {
3
- if (2 + 2 !== 4) throw "It's the end of the world as we know it!"
4
- },
5
- () => {
6
- if (2n + 2n !== 4n) throw "It's the end of the world as we know it!"
7
- }
8
- ]
9
-
10
- export const proof = {
11
- arrayOfTests,
12
- generatingTests: () => arrayOfTests,
13
- }
File without changes
File without changes
File without changes
File without changes