@fable-org/fable-library-js 2.4.2 → 2.5.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/Array.js +3 -2
- package/CHANGELOG.md +18 -1
- package/Directory.js +11 -0
- package/List.js +2 -1
- package/Map.js +8 -4
- package/MutableMap.js +2 -2
- package/MutableSet.js +1 -1
- package/Option.js +1 -18
- package/Seq.js +2 -2
- package/package.json +1 -1
- package/quotation.js +25 -8
package/Array.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { disposeSafe, getEnumerator, copyToArray, defaultOf, Exception } from "./Util.js";
|
|
2
2
|
import { Helpers_allocateArrayFromCons } from "./Native.js";
|
|
3
3
|
import { setItem as setItem_1, item as item_2 } from "./Array.js";
|
|
4
|
-
import { value as value_2,
|
|
4
|
+
import { value as value_2, defaultArg, some } from "./Option.js";
|
|
5
5
|
import { min as min_1, max as max_1 } from "./Double.js";
|
|
6
6
|
import { SR_notEnoughElements, SR_inputMustBeNonNegative, SR_inputSequenceEmpty, SR_Arg_ArgumentOutOfRangeException, SR_indexOutOfBounds } from "./Global.js";
|
|
7
7
|
import { Operators_IsNull } from "./FSharp.Core.js";
|
|
@@ -183,8 +183,9 @@ export function where(predicate, array) {
|
|
|
183
183
|
return array.filter(predicate);
|
|
184
184
|
}
|
|
185
185
|
export function indexOf(array, item_1, start, count, eq) {
|
|
186
|
+
let option_1 = undefined;
|
|
186
187
|
const start_1 = defaultArg(start, 0) | 0;
|
|
187
|
-
const end$0027 = defaultArg(
|
|
188
|
+
const end$0027 = defaultArg((option_1 = count, (option_1 != null) ? (start_1 + value_2(option_1)) : undefined), array.length) | 0;
|
|
188
189
|
const loop = (i_mut) => {
|
|
189
190
|
loop: while (true) {
|
|
190
191
|
const i = i_mut;
|
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
---
|
|
2
|
-
last_commit_released:
|
|
2
|
+
last_commit_released: 619d7afddbaf25108e819abaaa9d8a6503c457d6
|
|
3
3
|
updaters:
|
|
4
4
|
- package.json:
|
|
5
5
|
file: package.json
|
|
@@ -15,6 +15,23 @@ All notable changes to this project will be documented in this file.
|
|
|
15
15
|
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
16
16
|
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
17
17
|
|
|
18
|
+
## 2.5.1 - 2026-07-24
|
|
19
|
+
|
|
20
|
+
### 🐞 Bug Fixes
|
|
21
|
+
|
|
22
|
+
* *(js/ts,python)* Inline Option/ValueOption combinators to avoid closures and allocations (#4836) ([61cac646](https://github.com/fable-compiler/Fable/commit/61cac646e6385d82247082dbb90a98b1646560de))
|
|
23
|
+
|
|
24
|
+
<strong><small>[View changes on Github](https://github.com/fable-compiler/Fable/compare/6568f35ece227fc30ce84111c8d2e975b09bac00..619d7afddbaf25108e819abaaa9d8a6503c457d6)</small></strong>
|
|
25
|
+
|
|
26
|
+
## 2.5.0 - 2026-07-15
|
|
27
|
+
|
|
28
|
+
### 🚀 Features
|
|
29
|
+
|
|
30
|
+
* *(js/ts)* Add `System.IO.Directory` support (Exists, CreateDirectory) (#4798) ([6568f35e](https://github.com/fable-compiler/Fable/commit/6568f35ece227fc30ce84111c8d2e975b09bac00))
|
|
31
|
+
* *(js/ts/python/beam)* Preserve member calls and pattern matches in quotations (#4780) ([55482e6b](https://github.com/fable-compiler/Fable/commit/55482e6b5e6306fd4dbaba5759024313cb26682a))
|
|
32
|
+
|
|
33
|
+
<strong><small>[View changes on Github](https://github.com/fable-compiler/Fable/compare/a8d9bf5f0b7cc4560bb107963348e765695c22b6..6568f35ece227fc30ce84111c8d2e975b09bac00)</small></strong>
|
|
34
|
+
|
|
18
35
|
## 2.4.2 - 2026-07-11
|
|
19
36
|
|
|
20
37
|
### 🐞 Bug Fixes
|
package/Directory.js
ADDED
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
// This library doesn't depend on @types/node (to stay browser-compatible),
|
|
2
|
+
// so this Node.js built-in import can't be type-checked; the exported
|
|
3
|
+
// functions below still declare their own types for callers to rely on.
|
|
4
|
+
// @ts-ignore
|
|
5
|
+
import { existsSync, mkdirSync, statSync } from "node:fs";
|
|
6
|
+
export function exists(path) {
|
|
7
|
+
return existsSync(path) && statSync(path).isDirectory();
|
|
8
|
+
}
|
|
9
|
+
export function createDirectory(path) {
|
|
10
|
+
mkdirSync(path, { recursive: true });
|
|
11
|
+
}
|
package/List.js
CHANGED
|
@@ -253,12 +253,13 @@ export function FSharpList__get_Item_Z524259A4(xs, index) {
|
|
|
253
253
|
const i = i_mut, xs_1 = xs_1_mut;
|
|
254
254
|
const matchValue = xs_1.tail;
|
|
255
255
|
if (matchValue != null) {
|
|
256
|
+
const t = value_1(matchValue);
|
|
256
257
|
if (i === index) {
|
|
257
258
|
return xs_1.head;
|
|
258
259
|
}
|
|
259
260
|
else {
|
|
260
261
|
i_mut = (i + 1);
|
|
261
|
-
xs_1_mut =
|
|
262
|
+
xs_1_mut = t;
|
|
262
263
|
continue loop;
|
|
263
264
|
}
|
|
264
265
|
}
|
package/Map.js
CHANGED
|
@@ -702,11 +702,15 @@ export function MapTreeModule_foldSectionOpt(comparer, lo, hi, f, m, x) {
|
|
|
702
702
|
return x_3;
|
|
703
703
|
}
|
|
704
704
|
}
|
|
705
|
-
else if ((comparer.Compare(lo, MapTreeLeaf$2__get_Key(m2)) <= 0) && (comparer.Compare(MapTreeLeaf$2__get_Key(m2), hi) <= 0)) {
|
|
706
|
-
return f_1(MapTreeLeaf$2__get_Key(m2), MapTreeLeaf$2__get_Value(m2), x_1);
|
|
707
|
-
}
|
|
708
705
|
else {
|
|
709
|
-
|
|
706
|
+
const cLoKey_1 = comparer.Compare(lo, MapTreeLeaf$2__get_Key(m2)) | 0;
|
|
707
|
+
const cKeyHi_1 = comparer.Compare(MapTreeLeaf$2__get_Key(m2), hi) | 0;
|
|
708
|
+
if ((cLoKey_1 <= 0) && (cKeyHi_1 <= 0)) {
|
|
709
|
+
return f_1(MapTreeLeaf$2__get_Key(m2), MapTreeLeaf$2__get_Value(m2), x_1);
|
|
710
|
+
}
|
|
711
|
+
else {
|
|
712
|
+
return x_1;
|
|
713
|
+
}
|
|
710
714
|
}
|
|
711
715
|
}
|
|
712
716
|
else {
|
package/MutableMap.js
CHANGED
|
@@ -272,7 +272,7 @@ export function Dictionary__set_Item_5BDDA1(this$, k, v) {
|
|
|
272
272
|
setItem(getItemFromDict(this$.hashMap, matchValue[1]), matchValue[2], [k, v]);
|
|
273
273
|
}
|
|
274
274
|
else {
|
|
275
|
-
|
|
275
|
+
void (getItemFromDict(this$.hashMap, matchValue[1]).push([k, v]));
|
|
276
276
|
}
|
|
277
277
|
}
|
|
278
278
|
else {
|
|
@@ -286,7 +286,7 @@ export function Dictionary__Add_5BDDA1(this$, k, v) {
|
|
|
286
286
|
throw ArgumentException_$ctor_Z721C83C5(format("An item with the same key has already been added. Key: {0}", k));
|
|
287
287
|
}
|
|
288
288
|
else {
|
|
289
|
-
|
|
289
|
+
void (getItemFromDict(this$.hashMap, matchValue[1]).push([k, v]));
|
|
290
290
|
}
|
|
291
291
|
}
|
|
292
292
|
else {
|
package/MutableSet.js
CHANGED
|
@@ -178,7 +178,7 @@ export function HashSet__Add_2B595(this$, k) {
|
|
|
178
178
|
return false;
|
|
179
179
|
}
|
|
180
180
|
else {
|
|
181
|
-
|
|
181
|
+
void (getItemFromDict(this$.hashMap, matchValue[1]).push(k));
|
|
182
182
|
return true;
|
|
183
183
|
}
|
|
184
184
|
}
|
package/Option.js
CHANGED
|
@@ -70,30 +70,13 @@ export function toArray(opt) {
|
|
|
70
70
|
export function defaultArg(opt, defaultValue) {
|
|
71
71
|
return (opt != null) ? value(opt) : defaultValue;
|
|
72
72
|
}
|
|
73
|
-
export function defaultArgWith(opt, defThunk) {
|
|
74
|
-
return (opt != null) ? value(opt) : defThunk();
|
|
75
|
-
}
|
|
76
73
|
export function orElse(opt, ifNone) {
|
|
77
74
|
return opt == null ? ifNone : opt;
|
|
78
75
|
}
|
|
79
|
-
|
|
80
|
-
return opt == null ? ifNoneThunk() : opt;
|
|
81
|
-
}
|
|
82
|
-
export function filter(predicate, opt) {
|
|
83
|
-
return (opt != null) ? (predicate(value(opt)) ? opt : undefined) : opt;
|
|
84
|
-
}
|
|
76
|
+
// Only used by Replacements.Util.fs's curry/uncurry helpers, not by `Option.map` itself.
|
|
85
77
|
export function map(mapping, opt) {
|
|
86
78
|
return (opt != null) ? some(mapping(value(opt))) : undefined;
|
|
87
79
|
}
|
|
88
|
-
export function map2(mapping, opt1, opt2) {
|
|
89
|
-
return (opt1 != null && opt2 != null) ? mapping(value(opt1), value(opt2)) : undefined;
|
|
90
|
-
}
|
|
91
|
-
export function map3(mapping, opt1, opt2, opt3) {
|
|
92
|
-
return (opt1 != null && opt2 != null && opt3 != null) ? mapping(value(opt1), value(opt2), value(opt3)) : undefined;
|
|
93
|
-
}
|
|
94
|
-
export function bind(binder, opt) {
|
|
95
|
-
return opt != null ? binder(value(opt)) : undefined;
|
|
96
|
-
}
|
|
97
80
|
export function tryOp(op, arg) {
|
|
98
81
|
try {
|
|
99
82
|
return some(op(arg));
|
package/Seq.js
CHANGED
|
@@ -277,7 +277,7 @@ export function Enumerator_unfold(f, state) {
|
|
|
277
277
|
return Enumerator_FromFunctions$1_$ctor_58C54629(() => {
|
|
278
278
|
if (curr != null) {
|
|
279
279
|
const x = value_1(curr)[0];
|
|
280
|
-
|
|
280
|
+
value_1(curr)[1];
|
|
281
281
|
return x;
|
|
282
282
|
}
|
|
283
283
|
else {
|
|
@@ -286,7 +286,7 @@ export function Enumerator_unfold(f, state) {
|
|
|
286
286
|
}, () => {
|
|
287
287
|
curr = f(acc);
|
|
288
288
|
if (curr != null) {
|
|
289
|
-
|
|
289
|
+
value_1(curr)[0];
|
|
290
290
|
const st_1 = value_1(curr)[1];
|
|
291
291
|
acc = st_1;
|
|
292
292
|
return true;
|
package/package.json
CHANGED
package/quotation.js
CHANGED
|
@@ -5,6 +5,7 @@
|
|
|
5
5
|
* and pattern matching helpers compatible with Fable's option convention
|
|
6
6
|
* (undefined = no match, value/tuple = match).
|
|
7
7
|
*/
|
|
8
|
+
import { ofArray } from "./List.js";
|
|
8
9
|
// ===================================================================
|
|
9
10
|
// Var: represents an F# quotation variable
|
|
10
11
|
// ===================================================================
|
|
@@ -74,11 +75,12 @@ export class ExprIfThenElse {
|
|
|
74
75
|
toJSON() { return ["IfThenElse", this.guard, this.thenExpr, this.elseExpr]; }
|
|
75
76
|
}
|
|
76
77
|
export class ExprCall {
|
|
77
|
-
constructor(instance, method, args) {
|
|
78
|
+
constructor(instance, method, args, declaringType = "") {
|
|
78
79
|
this.tag = "Call";
|
|
79
80
|
this.instance = instance;
|
|
80
81
|
this.method = method;
|
|
81
82
|
this.args = args;
|
|
83
|
+
this.declaringType = declaringType;
|
|
82
84
|
}
|
|
83
85
|
toJSON() { return ["Call", this.instance, this.method, this.args]; }
|
|
84
86
|
}
|
|
@@ -176,6 +178,10 @@ export class ExprVarSet {
|
|
|
176
178
|
export function mkValue(value, type) {
|
|
177
179
|
return new ExprValue(value, type);
|
|
178
180
|
}
|
|
181
|
+
export function mkNull(type) {
|
|
182
|
+
// A null-value node (no instance / null literal / empty option or list).
|
|
183
|
+
return new ExprValue(null, type);
|
|
184
|
+
}
|
|
179
185
|
export function mkVar(v) {
|
|
180
186
|
return new ExprVarExpr(v);
|
|
181
187
|
}
|
|
@@ -191,8 +197,8 @@ export function mkLet(v, value, body) {
|
|
|
191
197
|
export function mkIfThenElse(guard, thenExpr, elseExpr) {
|
|
192
198
|
return new ExprIfThenElse(guard, thenExpr, elseExpr);
|
|
193
199
|
}
|
|
194
|
-
export function mkCall(instance, method, args) {
|
|
195
|
-
return new ExprCall(instance, method, args);
|
|
200
|
+
export function mkCall(instance, method, args, declaringType = "") {
|
|
201
|
+
return new ExprCall(instance, method, args, declaringType);
|
|
196
202
|
}
|
|
197
203
|
export function mkSequential(first, second) {
|
|
198
204
|
return new ExprSequential(first, second);
|
|
@@ -273,10 +279,17 @@ export function isIfThenElse(expr) {
|
|
|
273
279
|
return undefined;
|
|
274
280
|
}
|
|
275
281
|
export function isCall(expr) {
|
|
276
|
-
if (expr instanceof ExprCall)
|
|
277
|
-
|
|
282
|
+
if (expr instanceof ExprCall) {
|
|
283
|
+
// "novalue" is the "no instance" sentinel, distinct from a genuine quoted null ("null").
|
|
284
|
+
const instance = (expr.instance instanceof ExprValue && expr.instance.type === "novalue") ? null : expr.instance;
|
|
285
|
+
// Must be a real FSharpList (not the raw array), same reasoning as isFieldGet below.
|
|
286
|
+
return [instance, expr.method, ofArray(expr.args)];
|
|
287
|
+
}
|
|
278
288
|
return undefined;
|
|
279
289
|
}
|
|
290
|
+
export function callDeclaringType(expr) {
|
|
291
|
+
return expr instanceof ExprCall ? expr.declaringType : "";
|
|
292
|
+
}
|
|
280
293
|
export function isSequential(expr) {
|
|
281
294
|
if (expr instanceof ExprSequential)
|
|
282
295
|
return [expr.first, expr.second];
|
|
@@ -303,8 +316,12 @@ export function isTupleGet(expr) {
|
|
|
303
316
|
return undefined;
|
|
304
317
|
}
|
|
305
318
|
export function isFieldGet(expr) {
|
|
306
|
-
|
|
307
|
-
|
|
319
|
+
// Third element mirrors PropertyGet's indexer-args slot, always empty here (never indexed).
|
|
320
|
+
// "novalue" is the "no instance" sentinel, distinct from a genuine quoted null ("null").
|
|
321
|
+
if (expr instanceof ExprFieldGet) {
|
|
322
|
+
const instance = (expr.expr instanceof ExprValue && expr.expr.type === "novalue") ? null : expr.expr;
|
|
323
|
+
return [instance, expr.fieldName, []];
|
|
324
|
+
}
|
|
308
325
|
return undefined;
|
|
309
326
|
}
|
|
310
327
|
// ===================================================================
|
|
@@ -555,7 +572,7 @@ export function substitute(expr, fn) {
|
|
|
555
572
|
return new ExprIfThenElse(sub(e.guard), sub(e.thenExpr), sub(e.elseExpr));
|
|
556
573
|
if (e instanceof ExprCall) {
|
|
557
574
|
const newInst = e.instance != null ? sub(e.instance) : e.instance;
|
|
558
|
-
return new ExprCall(newInst, e.method, e.args.map(sub));
|
|
575
|
+
return new ExprCall(newInst, e.method, e.args.map(sub), e.declaringType);
|
|
559
576
|
}
|
|
560
577
|
if (e instanceof ExprSequential)
|
|
561
578
|
return new ExprSequential(sub(e.first), sub(e.second));
|