@openrewrite/recipes-nodejs 0.35.0-20251120-132843 → 0.35.0-20251120-142354

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.
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAEA,OAAO,EAAC,cAAc,EAAC,MAAM,sBAAsB,CAAC;AAQpD,wBAAgB,QAAQ,CAAC,QAAQ,EAAE,cAAc,QAQhD"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAEA,OAAO,EAAC,cAAc,EAAC,MAAM,sBAAsB,CAAC;AAUpD,wBAAgB,QAAQ,CAAC,QAAQ,EAAE,cAAc,QAUhD"}
package/dist/index.js CHANGED
@@ -8,6 +8,8 @@ const crypto_constructors_1 = require("./migrate/crypto-constructors");
8
8
  const util_log_1 = require("./migrate/util-log");
9
9
  const util_extend_1 = require("./migrate/util-extend");
10
10
  const crypto_fips_1 = require("./migrate/crypto-fips");
11
+ const slow_buffer_1 = require("./migrate/slow-buffer");
12
+ const fs_access_constants_1 = require("./migrate/fs-access-constants");
11
13
  function activate(registry) {
12
14
  registry.register(util_type_checking_1.UseNativeTypeCheckingMethods);
13
15
  registry.register(buffer_slice_1.ReplaceDeprecatedBufferSlice);
@@ -16,5 +18,7 @@ function activate(registry) {
16
18
  registry.register(util_log_1.ReplaceUtilLog);
17
19
  registry.register(util_extend_1.ReplaceUtilExtend);
18
20
  registry.register(crypto_fips_1.ReplaceCryptoFips);
21
+ registry.register(slow_buffer_1.ReplaceSlowBuffer);
22
+ registry.register(fs_access_constants_1.ReplaceFsAccessConstants);
19
23
  }
20
24
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;AAUA,4BAQC;AAlBD,qEAA0E;AAC1E,yDAAoE;AAEpE,yEAAwF;AACxF,uEAAwE;AACxE,iDAAkD;AAClD,uDAAwD;AACxD,uDAAwD;AAGxD,SAAgB,QAAQ,CAAC,QAAwB;IAC7C,QAAQ,CAAC,QAAQ,CAAC,iDAA4B,CAAC,CAAC;IAChD,QAAQ,CAAC,QAAQ,CAAC,2CAA4B,CAAC,CAAC;IAChD,QAAQ,CAAC,QAAQ,CAAC,+DAAwC,CAAC,CAAC;IAC5D,QAAQ,CAAC,QAAQ,CAAC,+CAAyB,CAAC,CAAC;IAC7C,QAAQ,CAAC,QAAQ,CAAC,yBAAc,CAAC,CAAC;IAClC,QAAQ,CAAC,QAAQ,CAAC,+BAAiB,CAAC,CAAC;IACrC,QAAQ,CAAC,QAAQ,CAAC,+BAAiB,CAAC,CAAC;AACzC,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;AAYA,4BAUC;AAtBD,qEAA0E;AAC1E,yDAAoE;AAEpE,yEAAwF;AACxF,uEAAwE;AACxE,iDAAkD;AAClD,uDAAwD;AACxD,uDAAwD;AACxD,uDAAwD;AACxD,uEAAuE;AAGvE,SAAgB,QAAQ,CAAC,QAAwB;IAC7C,QAAQ,CAAC,QAAQ,CAAC,iDAA4B,CAAC,CAAC;IAChD,QAAQ,CAAC,QAAQ,CAAC,2CAA4B,CAAC,CAAC;IAChD,QAAQ,CAAC,QAAQ,CAAC,+DAAwC,CAAC,CAAC;IAC5D,QAAQ,CAAC,QAAQ,CAAC,+CAAyB,CAAC,CAAC;IAC7C,QAAQ,CAAC,QAAQ,CAAC,yBAAc,CAAC,CAAC;IAClC,QAAQ,CAAC,QAAQ,CAAC,+BAAiB,CAAC,CAAC;IACrC,QAAQ,CAAC,QAAQ,CAAC,+BAAiB,CAAC,CAAC;IACrC,QAAQ,CAAC,QAAQ,CAAC,+BAAiB,CAAC,CAAC;IACrC,QAAQ,CAAC,QAAQ,CAAC,8CAAwB,CAAC,CAAC;AAChD,CAAC"}
@@ -0,0 +1,9 @@
1
+ import { ExecutionContext, Recipe, TreeVisitor } from "@openrewrite/rewrite";
2
+ export declare class ReplaceFsAccessConstants extends Recipe {
3
+ readonly name = "org.openrewrite.node.migrate.fs.replace-fs-access-constants";
4
+ readonly displayName: string;
5
+ readonly description: string;
6
+ readonly tags: string[];
7
+ editor(): Promise<TreeVisitor<any, ExecutionContext>>;
8
+ }
9
+ //# sourceMappingURL=fs-access-constants.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"fs-access-constants.d.ts","sourceRoot":"","sources":["../../src/migrate/fs-access-constants.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,gBAAgB,EAAE,MAAM,EAAE,WAAW,EAAC,MAAM,sBAAsB,CAAC;AAO3E,qBAAa,wBAAyB,SAAQ,MAAM;IAChD,QAAQ,CAAC,IAAI,iEAAgE;IAC7E,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAyF;IACrH,QAAQ,CAAC,WAAW,EAAE,MAAM,CAA4O;IACxQ,QAAQ,CAAC,IAAI,EAAE,MAAM,EAAE,CAAe;IAEhC,MAAM,IAAI,OAAO,CAAC,WAAW,CAAC,GAAG,EAAE,gBAAgB,CAAC,CAAC;CAoD9D"}
@@ -0,0 +1,73 @@
1
+ "use strict";
2
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
+ return new (P || (P = Promise))(function (resolve, reject) {
5
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
6
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
7
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
8
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
9
+ });
10
+ };
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ exports.ReplaceFsAccessConstants = void 0;
13
+ const rewrite_1 = require("@openrewrite/rewrite");
14
+ const javascript_1 = require("@openrewrite/rewrite/javascript");
15
+ const java_1 = require("@openrewrite/rewrite/java");
16
+ class ReplaceFsAccessConstants extends rewrite_1.Recipe {
17
+ constructor() {
18
+ super(...arguments);
19
+ this.name = "org.openrewrite.node.migrate.fs.replace-fs-access-constants";
20
+ this.displayName = "Replace deprecated `fs.F_OK`, `fs.R_OK`, `fs.W_OK`, `fs.X_OK` with `fs.constants.*`";
21
+ this.description = "Replace deprecated file access constants (`fs.F_OK`, `fs.R_OK`, `fs.W_OK`, `fs.X_OK`) with their equivalents from `fs.constants`. These constants were removed in Node.js v24+ and should be accessed through the constants namespace.";
22
+ this.tags = ["DEP0176"];
23
+ }
24
+ editor() {
25
+ return __awaiter(this, void 0, void 0, function* () {
26
+ return new class extends javascript_1.JavaScriptVisitor {
27
+ isFsAccessConstant(fieldAccess) {
28
+ const constantName = fieldAccess.name.element.simpleName;
29
+ if (!["F_OK", "R_OK", "W_OK", "X_OK"].includes(constantName)) {
30
+ return false;
31
+ }
32
+ if (fieldAccess.target.kind === java_1.J.Kind.Identifier) {
33
+ const identifier = fieldAccess.target;
34
+ const idType = identifier.type;
35
+ if ((idType === null || idType === void 0 ? void 0 : idType.kind) === java_1.Type.Kind.Class) {
36
+ const classType = idType;
37
+ return classType.fullyQualifiedName === "fs" ||
38
+ classType.fullyQualifiedName === "node:fs";
39
+ }
40
+ }
41
+ return false;
42
+ }
43
+ visitFieldAccess(fieldAccess, p) {
44
+ const _super = Object.create(null, {
45
+ visitFieldAccess: { get: () => super.visitFieldAccess }
46
+ });
47
+ return __awaiter(this, void 0, void 0, function* () {
48
+ const field = yield _super.visitFieldAccess.call(this, fieldAccess, p);
49
+ if (this.isFsAccessConstant(field)) {
50
+ const fsIdentifier = field.target;
51
+ const constantName = field.name.element.simpleName;
52
+ if (constantName === "F_OK") {
53
+ return yield (0, javascript_1.template) `${fsIdentifier}.constants.F_OK`.apply(field, this.cursor);
54
+ }
55
+ else if (constantName === "R_OK") {
56
+ return yield (0, javascript_1.template) `${fsIdentifier}.constants.R_OK`.apply(field, this.cursor);
57
+ }
58
+ else if (constantName === "W_OK") {
59
+ return yield (0, javascript_1.template) `${fsIdentifier}.constants.W_OK`.apply(field, this.cursor);
60
+ }
61
+ else if (constantName === "X_OK") {
62
+ return yield (0, javascript_1.template) `${fsIdentifier}.constants.X_OK`.apply(field, this.cursor);
63
+ }
64
+ }
65
+ return field;
66
+ });
67
+ }
68
+ };
69
+ });
70
+ }
71
+ }
72
+ exports.ReplaceFsAccessConstants = ReplaceFsAccessConstants;
73
+ //# sourceMappingURL=fs-access-constants.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"fs-access-constants.js","sourceRoot":"","sources":["../../src/migrate/fs-access-constants.ts"],"names":[],"mappings":";;;;;;;;;;;;AAAA,kDAA2E;AAC3E,gEAA4E;AAC5E,oDAAkD;AAKlD,MAAa,wBAAyB,SAAQ,gBAAM;IAApD;;QACa,SAAI,GAAG,6DAA6D,CAAA;QACpE,gBAAW,GAAW,qFAAqF,CAAC;QAC5G,gBAAW,GAAW,wOAAwO,CAAC;QAC/P,SAAI,GAAa,CAAC,SAAS,CAAC,CAAC;IAsD1C,CAAC;IApDS,MAAM;;YACR,OAAO,IAAI,KAAM,SAAQ,8BAAmC;gBAGhD,kBAAkB,CAAC,WAA0B;oBACjD,MAAM,YAAY,GAAG,WAAW,CAAC,IAAI,CAAC,OAAO,CAAC,UAAU,CAAC;oBAGzD,IAAI,CAAC,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,CAAC,CAAC,QAAQ,CAAC,YAAY,CAAC,EAAE,CAAC;wBAC3D,OAAO,KAAK,CAAC;oBACjB,CAAC;oBAGD,IAAI,WAAW,CAAC,MAAM,CAAC,IAAI,KAAK,QAAC,CAAC,IAAI,CAAC,UAAU,EAAE,CAAC;wBAChD,MAAM,UAAU,GAAG,WAAW,CAAC,MAAsB,CAAC;wBACtD,MAAM,MAAM,GAAG,UAAU,CAAC,IAAI,CAAC;wBAG/B,IAAI,CAAA,MAAM,aAAN,MAAM,uBAAN,MAAM,CAAE,IAAI,MAAK,WAAI,CAAC,IAAI,CAAC,KAAK,EAAE,CAAC;4BACnC,MAAM,SAAS,GAAG,MAAoB,CAAC;4BACvC,OAAO,SAAS,CAAC,kBAAkB,KAAK,IAAI;gCACrC,SAAS,CAAC,kBAAkB,KAAK,SAAS,CAAC;wBACtD,CAAC;oBACL,CAAC;oBAED,OAAO,KAAK,CAAC;gBACjB,CAAC;gBAEe,gBAAgB,CAAC,WAA0B,EAAE,CAAmB;;;;;wBAC5E,MAAM,KAAK,GAAG,MAAM,OAAM,gBAAgB,YAAC,WAAW,EAAE,CAAC,CAAkB,CAAC;wBAE5E,IAAI,IAAI,CAAC,kBAAkB,CAAC,KAAK,CAAC,EAAE,CAAC;4BACjC,MAAM,YAAY,GAAG,KAAK,CAAC,MAAM,CAAC;4BAClC,MAAM,YAAY,GAAG,KAAK,CAAC,IAAI,CAAC,OAAO,CAAC,UAAU,CAAC;4BAInD,IAAI,YAAY,KAAK,MAAM,EAAE,CAAC;gCAC1B,OAAO,MAAM,IAAA,qBAAQ,EAAA,GAAG,YAAY,iBAAiB,CAAC,KAAK,CAAC,KAAK,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;4BACpF,CAAC;iCAAM,IAAI,YAAY,KAAK,MAAM,EAAE,CAAC;gCACjC,OAAO,MAAM,IAAA,qBAAQ,EAAA,GAAG,YAAY,iBAAiB,CAAC,KAAK,CAAC,KAAK,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;4BACpF,CAAC;iCAAM,IAAI,YAAY,KAAK,MAAM,EAAE,CAAC;gCACjC,OAAO,MAAM,IAAA,qBAAQ,EAAA,GAAG,YAAY,iBAAiB,CAAC,KAAK,CAAC,KAAK,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;4BACpF,CAAC;iCAAM,IAAI,YAAY,KAAK,MAAM,EAAE,CAAC;gCACjC,OAAO,MAAM,IAAA,qBAAQ,EAAA,GAAG,YAAY,iBAAiB,CAAC,KAAK,CAAC,KAAK,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;4BACpF,CAAC;wBACL,CAAC;wBAED,OAAO,KAAK,CAAC;oBACjB,CAAC;iBAAA;aACJ,CAAC;QACN,CAAC;KAAA;CACJ;AA1DD,4DA0DC"}
@@ -0,0 +1,9 @@
1
+ import { ExecutionContext, Recipe, TreeVisitor } from "@openrewrite/rewrite";
2
+ export declare class ReplaceSlowBuffer extends Recipe {
3
+ readonly name = "org.openrewrite.node.migrate.buffer.replace-slow-buffer";
4
+ readonly displayName: string;
5
+ readonly description: string;
6
+ readonly tags: string[];
7
+ editor(): Promise<TreeVisitor<any, ExecutionContext>>;
8
+ }
9
+ //# sourceMappingURL=slow-buffer.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"slow-buffer.d.ts","sourceRoot":"","sources":["../../src/migrate/slow-buffer.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,gBAAgB,EAAE,MAAM,EAAE,WAAW,EAAC,MAAM,sBAAsB,CAAC;AAO3E,qBAAa,iBAAkB,SAAQ,MAAM;IACzC,QAAQ,CAAC,IAAI,6DAA4D;IACzE,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAqE;IACjG,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAmO;IAC/P,QAAQ,CAAC,IAAI,EAAE,MAAM,EAAE,CAAe;IAEhC,MAAM,IAAI,OAAO,CAAC,WAAW,CAAC,GAAG,EAAE,gBAAgB,CAAC,CAAC;CAiC9D"}
@@ -0,0 +1,60 @@
1
+ "use strict";
2
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
3
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
4
+ return new (P || (P = Promise))(function (resolve, reject) {
5
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
6
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
7
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
8
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
9
+ });
10
+ };
11
+ Object.defineProperty(exports, "__esModule", { value: true });
12
+ exports.ReplaceSlowBuffer = void 0;
13
+ const rewrite_1 = require("@openrewrite/rewrite");
14
+ const javascript_1 = require("@openrewrite/rewrite/javascript");
15
+ const java_1 = require("@openrewrite/rewrite/java");
16
+ class ReplaceSlowBuffer extends rewrite_1.Recipe {
17
+ constructor() {
18
+ super(...arguments);
19
+ this.name = "org.openrewrite.node.migrate.buffer.replace-slow-buffer";
20
+ this.displayName = "Replace deprecated `SlowBuffer` with `Buffer.allocUnsafeSlow()`";
21
+ this.description = "Replace deprecated `new SlowBuffer(size)` calls with `Buffer.allocUnsafeSlow(size)`. SlowBuffer was used to create un-pooled Buffer instances, but has been removed in favor of the explicit Buffer.allocUnsafeSlow() method.";
22
+ this.tags = ["DEP0030"];
23
+ }
24
+ editor() {
25
+ return __awaiter(this, void 0, void 0, function* () {
26
+ return new class extends javascript_1.JavaScriptVisitor {
27
+ visitNewClass(nc, p) {
28
+ const _super = Object.create(null, {
29
+ visitNewClass: { get: () => super.visitNewClass }
30
+ });
31
+ return __awaiter(this, void 0, void 0, function* () {
32
+ var _a;
33
+ const newClass = yield _super.visitNewClass.call(this, nc, p);
34
+ const clazz = newClass.class;
35
+ const args = (_a = newClass.arguments) === null || _a === void 0 ? void 0 : _a.elements;
36
+ if (!args || args.length !== 1) {
37
+ return newClass;
38
+ }
39
+ const sizeArg = args[0].element;
40
+ if (clazz && clazz.kind === java_1.J.Kind.Identifier) {
41
+ const constructorType = newClass.constructorType;
42
+ if ((constructorType === null || constructorType === void 0 ? void 0 : constructorType.declaringType.kind) === java_1.Type.Kind.Class &&
43
+ constructorType.name === "SlowBuffer") {
44
+ const declaringClass = constructorType.declaringType;
45
+ if (declaringClass.fullyQualifiedName === "buffer") {
46
+ (0, javascript_1.maybeRemoveImport)(this, "buffer", "SlowBuffer");
47
+ (0, javascript_1.maybeRemoveImport)(this, "node:buffer", "SlowBuffer");
48
+ return yield (0, javascript_1.template) `Buffer.allocUnsafeSlow(${sizeArg})`.apply(newClass, this.cursor);
49
+ }
50
+ }
51
+ }
52
+ return _super.visitNewClass.call(this, newClass, p);
53
+ });
54
+ }
55
+ };
56
+ });
57
+ }
58
+ }
59
+ exports.ReplaceSlowBuffer = ReplaceSlowBuffer;
60
+ //# sourceMappingURL=slow-buffer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"slow-buffer.js","sourceRoot":"","sources":["../../src/migrate/slow-buffer.ts"],"names":[],"mappings":";;;;;;;;;;;;AAAA,kDAA2E;AAC3E,gEAA+F;AAC/F,oDAAkD;AAKlD,MAAa,iBAAkB,SAAQ,gBAAM;IAA7C;;QACa,SAAI,GAAG,yDAAyD,CAAA;QAChE,gBAAW,GAAW,iEAAiE,CAAC;QACxF,gBAAW,GAAW,+NAA+N,CAAC;QACtP,SAAI,GAAa,CAAC,SAAS,CAAC,CAAC;IAmC1C,CAAC;IAjCS,MAAM;;YACR,OAAO,IAAI,KAAM,SAAQ,8BAAmC;gBAExC,aAAa,CAAC,EAAc,EAAE,CAAmB;;;;;;wBAC7D,MAAM,QAAQ,GAAG,MAAM,OAAM,aAAa,YAAC,EAAE,EAAE,CAAC,CAAe,CAAC;wBAEhE,MAAM,KAAK,GAAG,QAAQ,CAAC,KAAK,CAAC;wBAC7B,MAAM,IAAI,GAAG,MAAA,QAAQ,CAAC,SAAS,0CAAE,QAAQ,CAAC;wBAE1C,IAAI,CAAC,IAAI,IAAI,IAAI,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;4BAC7B,OAAO,QAAQ,CAAC;wBACpB,CAAC;wBAED,MAAM,OAAO,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC;wBAEhC,IAAI,KAAK,IAAI,KAAK,CAAC,IAAI,KAAK,QAAC,CAAC,IAAI,CAAC,UAAU,EAAE,CAAC;4BAC5C,MAAM,eAAe,GAAG,QAAQ,CAAC,eAAe,CAAC;4BACjD,IAAI,CAAA,eAAe,aAAf,eAAe,uBAAf,eAAe,CAAE,aAAa,CAAC,IAAI,MAAK,WAAI,CAAC,IAAI,CAAC,KAAK;gCACvD,eAAe,CAAC,IAAI,KAAK,YAAY,EAAE,CAAC;gCACxC,MAAM,cAAc,GAAG,eAAe,CAAC,aAA2B,CAAC;gCAEnE,IAAI,cAAc,CAAC,kBAAkB,KAAK,QAAQ,EAAE,CAAC;oCACjD,IAAA,8BAAiB,EAAC,IAAI,EAAE,QAAQ,EAAE,YAAY,CAAC,CAAC;oCAChD,IAAA,8BAAiB,EAAC,IAAI,EAAE,aAAa,EAAE,YAAY,CAAC,CAAC;oCACrD,OAAO,MAAM,IAAA,qBAAQ,EAAA,0BAA0B,OAAO,GAAG,CAAC,KAAK,CAAC,QAAQ,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;gCAC3F,CAAC;4BACL,CAAC;wBACL,CAAC;wBAED,OAAO,OAAM,aAAa,YAAC,QAAQ,EAAE,CAAC,EAAE;oBAC5C,CAAC;iBAAA;aACJ,CAAC;QACN,CAAC;KAAA;CACJ;AAvCD,8CAuCC"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@openrewrite/recipes-nodejs",
3
- "version": "0.35.0-20251120-132843",
3
+ "version": "0.35.0-20251120-142354",
4
4
  "license": "Moderne Source Available License",
5
5
  "description": "OpenRewrite recipes for Node.js library migrations.",
6
6
  "homepage": "https://github.com/moderneinc/rewrite-node",
package/src/index.ts CHANGED
@@ -6,6 +6,8 @@ import {ReplaceCryptoConstructors} from "./migrate/crypto-constructors";
6
6
  import {ReplaceUtilLog} from "./migrate/util-log";
7
7
  import {ReplaceUtilExtend} from "./migrate/util-extend";
8
8
  import {ReplaceCryptoFips} from "./migrate/crypto-fips";
9
+ import {ReplaceSlowBuffer} from "./migrate/slow-buffer";
10
+ import {ReplaceFsAccessConstants} from "./migrate/fs-access-constants";
9
11
 
10
12
 
11
13
  export function activate(registry: RecipeRegistry) {
@@ -16,4 +18,6 @@ export function activate(registry: RecipeRegistry) {
16
18
  registry.register(ReplaceUtilLog);
17
19
  registry.register(ReplaceUtilExtend);
18
20
  registry.register(ReplaceCryptoFips);
21
+ registry.register(ReplaceSlowBuffer);
22
+ registry.register(ReplaceFsAccessConstants);
19
23
  }
@@ -0,0 +1,66 @@
1
+ import {ExecutionContext, Recipe, TreeVisitor} from "@openrewrite/rewrite";
2
+ import {JavaScriptVisitor, template} from "@openrewrite/rewrite/javascript";
3
+ import {J, Type} from "@openrewrite/rewrite/java";
4
+
5
+ /**
6
+ * Replace deprecated fs.F_OK, fs.R_OK, fs.W_OK, fs.X_OK with fs.constants.*
7
+ */
8
+ export class ReplaceFsAccessConstants extends Recipe {
9
+ readonly name = "org.openrewrite.node.migrate.fs.replace-fs-access-constants"
10
+ readonly displayName: string = "Replace deprecated `fs.F_OK`, `fs.R_OK`, `fs.W_OK`, `fs.X_OK` with `fs.constants.*`";
11
+ readonly description: string = "Replace deprecated file access constants (`fs.F_OK`, `fs.R_OK`, `fs.W_OK`, `fs.X_OK`) with their equivalents from `fs.constants`. These constants were removed in Node.js v24+ and should be accessed through the constants namespace.";
12
+ readonly tags: string[] = ["DEP0176"];
13
+
14
+ async editor(): Promise<TreeVisitor<any, ExecutionContext>> {
15
+ return new class extends JavaScriptVisitor<ExecutionContext> {
16
+
17
+ // Check if a field access is accessing one of the deprecated fs constants
18
+ private isFsAccessConstant(fieldAccess: J.FieldAccess): boolean {
19
+ const constantName = fieldAccess.name.element.simpleName;
20
+
21
+ // Check if accessing F_OK, R_OK, W_OK, or X_OK
22
+ if (!["F_OK", "R_OK", "W_OK", "X_OK"].includes(constantName)) {
23
+ return false;
24
+ }
25
+
26
+ // Check if the target is an identifier with type fs
27
+ if (fieldAccess.target.kind === J.Kind.Identifier) {
28
+ const identifier = fieldAccess.target as J.Identifier;
29
+ const idType = identifier.type;
30
+
31
+ // Check if the identifier type is the fs module
32
+ if (idType?.kind === Type.Kind.Class) {
33
+ const classType = idType as Type.Class;
34
+ return classType.fullyQualifiedName === "fs" ||
35
+ classType.fullyQualifiedName === "node:fs";
36
+ }
37
+ }
38
+
39
+ return false;
40
+ }
41
+
42
+ protected async visitFieldAccess(fieldAccess: J.FieldAccess, p: ExecutionContext): Promise<J | undefined> {
43
+ const field = await super.visitFieldAccess(fieldAccess, p) as J.FieldAccess;
44
+
45
+ if (this.isFsAccessConstant(field)) {
46
+ const fsIdentifier = field.target;
47
+ const constantName = field.name.element.simpleName;
48
+
49
+ // Replace fs.F_OK with fs.constants.F_OK
50
+ // Build the template string dynamically based on the constant name
51
+ if (constantName === "F_OK") {
52
+ return await template`${fsIdentifier}.constants.F_OK`.apply(field, this.cursor);
53
+ } else if (constantName === "R_OK") {
54
+ return await template`${fsIdentifier}.constants.R_OK`.apply(field, this.cursor);
55
+ } else if (constantName === "W_OK") {
56
+ return await template`${fsIdentifier}.constants.W_OK`.apply(field, this.cursor);
57
+ } else if (constantName === "X_OK") {
58
+ return await template`${fsIdentifier}.constants.X_OK`.apply(field, this.cursor);
59
+ }
60
+ }
61
+
62
+ return field;
63
+ }
64
+ };
65
+ }
66
+ }
@@ -0,0 +1,47 @@
1
+ import {ExecutionContext, Recipe, TreeVisitor} from "@openrewrite/rewrite";
2
+ import {JavaScriptVisitor, maybeRemoveImport, template} from "@openrewrite/rewrite/javascript";
3
+ import {J, Type} from "@openrewrite/rewrite/java";
4
+
5
+ /**
6
+ * Replace deprecated SlowBuffer with Buffer.allocUnsafeSlow()
7
+ */
8
+ export class ReplaceSlowBuffer extends Recipe {
9
+ readonly name = "org.openrewrite.node.migrate.buffer.replace-slow-buffer"
10
+ readonly displayName: string = "Replace deprecated `SlowBuffer` with `Buffer.allocUnsafeSlow()`";
11
+ readonly description: string = "Replace deprecated `new SlowBuffer(size)` calls with `Buffer.allocUnsafeSlow(size)`. SlowBuffer was used to create un-pooled Buffer instances, but has been removed in favor of the explicit Buffer.allocUnsafeSlow() method.";
12
+ readonly tags: string[] = ["DEP0030"];
13
+
14
+ async editor(): Promise<TreeVisitor<any, ExecutionContext>> {
15
+ return new class extends JavaScriptVisitor<ExecutionContext> {
16
+
17
+ protected async visitNewClass(nc: J.NewClass, p: ExecutionContext): Promise<J | undefined> {
18
+ const newClass = await super.visitNewClass(nc, p) as J.NewClass;
19
+
20
+ const clazz = newClass.class;
21
+ const args = newClass.arguments?.elements;
22
+
23
+ if (!args || args.length !== 1) {
24
+ return newClass;
25
+ }
26
+
27
+ const sizeArg = args[0].element;
28
+
29
+ if (clazz && clazz.kind === J.Kind.Identifier) {
30
+ const constructorType = newClass.constructorType;
31
+ if (constructorType?.declaringType.kind === Type.Kind.Class &&
32
+ constructorType.name === "SlowBuffer") {
33
+ const declaringClass = constructorType.declaringType as Type.Class;
34
+
35
+ if (declaringClass.fullyQualifiedName === "buffer") {
36
+ maybeRemoveImport(this, "buffer", "SlowBuffer");
37
+ maybeRemoveImport(this, "node:buffer", "SlowBuffer");
38
+ return await template`Buffer.allocUnsafeSlow(${sizeArg})`.apply(newClass, this.cursor);
39
+ }
40
+ }
41
+ }
42
+
43
+ return super.visitNewClass(newClass, p);
44
+ }
45
+ };
46
+ }
47
+ }