@effect/language-service 0.75.0 → 0.75.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/cli.js +250 -168
- package/cli.js.map +1 -1
- package/effect-lsp-patch-utils.js +249 -168
- package/effect-lsp-patch-utils.js.map +1 -1
- package/index.js +347 -206
- package/index.js.map +1 -1
- package/package.json +1 -1
- package/transform.js +249 -167
- package/transform.js.map +1 -1
package/package.json
CHANGED
package/transform.js
CHANGED
|
@@ -849,6 +849,7 @@ var dedupe = (self) => dedupeWith(self, equivalence());
|
|
|
849
849
|
var join = /* @__PURE__ */ dual(2, (self, sep) => fromIterable(self).join(sep));
|
|
850
850
|
|
|
851
851
|
// src/core/Nano.ts
|
|
852
|
+
var debugPerformance = false;
|
|
852
853
|
var NanoTag = class {
|
|
853
854
|
constructor(key) {
|
|
854
855
|
this.key = key;
|
|
@@ -946,7 +947,6 @@ var NanoFiber = class {
|
|
|
946
947
|
_yielded = void 0;
|
|
947
948
|
_services = {};
|
|
948
949
|
_cache = {};
|
|
949
|
-
_perf = false;
|
|
950
950
|
_lastSpan = "";
|
|
951
951
|
runLoop(nano) {
|
|
952
952
|
let current = nano;
|
|
@@ -977,7 +977,7 @@ var WithSpanProto = {
|
|
|
977
977
|
...PrimitiveProto,
|
|
978
978
|
[evaluate](fiber) {
|
|
979
979
|
const [fa, name] = this[args];
|
|
980
|
-
if (!
|
|
980
|
+
if (!debugPerformance) return fa;
|
|
981
981
|
const previousSpan = fiber._lastSpan;
|
|
982
982
|
fiber._lastSpan = name;
|
|
983
983
|
const start = performance.now();
|
|
@@ -1920,6 +1920,26 @@ var getApplicableRefactors = fn("LSP.getApplicableRefactors")(function* (refacto
|
|
|
1920
1920
|
}
|
|
1921
1921
|
return effectRefactors;
|
|
1922
1922
|
});
|
|
1923
|
+
function codeFixNameToFullyQualifiedName(name) {
|
|
1924
|
+
return `@effect/language-service/codefixes/${name}`;
|
|
1925
|
+
}
|
|
1926
|
+
var codeFixesToApplicableRefactor = fn("LSP.codeFixesToApplicableRefactor")(function* (codeFixes, sourceFile, positionOrRange) {
|
|
1927
|
+
const effectRefactors = [];
|
|
1928
|
+
const range = typeof positionOrRange === "number" ? { pos: positionOrRange, end: positionOrRange } : positionOrRange;
|
|
1929
|
+
const inRangeCodeFixes = codeFixes.filter((_) => _.start <= range.pos && _.end >= range.end);
|
|
1930
|
+
for (const codeFix of inRangeCodeFixes) {
|
|
1931
|
+
effectRefactors.push({
|
|
1932
|
+
name: codeFixNameToFullyQualifiedName(codeFix.fixName),
|
|
1933
|
+
description: "Quick Fix: " + codeFix.description,
|
|
1934
|
+
actions: [{
|
|
1935
|
+
name: codeFixNameToFullyQualifiedName(codeFix.fixName),
|
|
1936
|
+
description: "Quick Fix: " + codeFix.description,
|
|
1937
|
+
kind: "refactor.rewrite.codeFixEffect." + codeFix.fixName
|
|
1938
|
+
}]
|
|
1939
|
+
});
|
|
1940
|
+
}
|
|
1941
|
+
return effectRefactors;
|
|
1942
|
+
});
|
|
1923
1943
|
var getEditsForRefactor = fn("LSP.getEditsForRefactor")(function* (refactors, sourceFile, positionOrRange, refactorName) {
|
|
1924
1944
|
const refactor = refactors.find((refactor2) => refactorNameToFullyQualifiedName(refactor2.name) === refactorName);
|
|
1925
1945
|
if (!refactor) {
|
|
@@ -1928,6 +1948,16 @@ var getEditsForRefactor = fn("LSP.getEditsForRefactor")(function* (refactors, so
|
|
|
1928
1948
|
const textRange = typeof positionOrRange === "number" ? { pos: positionOrRange, end: positionOrRange } : positionOrRange;
|
|
1929
1949
|
return yield* refactor.apply(sourceFile, textRange);
|
|
1930
1950
|
});
|
|
1951
|
+
var getEditsForCodeFixes = fn("LSP.getEditsForCodeFixes")(function* (codeFixes, positionOrRange, refactorName) {
|
|
1952
|
+
const textRange = typeof positionOrRange === "number" ? { pos: positionOrRange, end: positionOrRange } : positionOrRange;
|
|
1953
|
+
const fixToRun = codeFixes.find(
|
|
1954
|
+
(_) => codeFixNameToFullyQualifiedName(_.fixName) === refactorName && _.start <= textRange.pos && _.end >= textRange.end
|
|
1955
|
+
);
|
|
1956
|
+
if (!fixToRun) {
|
|
1957
|
+
return yield* fail(new RefactorNotApplicableError());
|
|
1958
|
+
}
|
|
1959
|
+
return fixToRun;
|
|
1960
|
+
});
|
|
1931
1961
|
var getCompletionsAtPosition = fn("LSP.getCompletionsAtPosition")(function* (completions, sourceFile, position, options, formatCodeSettings) {
|
|
1932
1962
|
let effectCompletions = [];
|
|
1933
1963
|
for (const completion of completions) {
|
|
@@ -2011,7 +2041,7 @@ var createDiagnosticExecutor = fn("LSP.createCommentDirectivesProcessor")(
|
|
|
2011
2041
|
message: ts.DiagnosticCategory.Message,
|
|
2012
2042
|
suggestion: ts.DiagnosticCategory.Suggestion
|
|
2013
2043
|
};
|
|
2014
|
-
const execute = (
|
|
2044
|
+
const execute = fn("LSP.execute")(function* (rule) {
|
|
2015
2045
|
const diagnostics2 = [];
|
|
2016
2046
|
const codeFixes = [];
|
|
2017
2047
|
const ruleNameLowered = rule.name.toLowerCase();
|
|
@@ -2792,6 +2822,9 @@ function make2(ts, tsUtils, typeChecker, typeCheckerUtils, program) {
|
|
|
2792
2822
|
if (signatures.length !== 1) {
|
|
2793
2823
|
return typeParserIssue("Covariant type has no call signature", type);
|
|
2794
2824
|
}
|
|
2825
|
+
if (signatures[0].typeParameters && signatures[0].typeParameters.length > 0) {
|
|
2826
|
+
return typeParserIssue("Invariant type should not have type parameters", type);
|
|
2827
|
+
}
|
|
2795
2828
|
return succeed(typeChecker.getReturnTypeOfSignature(signatures[0]));
|
|
2796
2829
|
}
|
|
2797
2830
|
function contravariantTypeArgument(type) {
|
|
@@ -2799,6 +2832,9 @@ function make2(ts, tsUtils, typeChecker, typeCheckerUtils, program) {
|
|
|
2799
2832
|
if (signatures.length !== 1) {
|
|
2800
2833
|
return typeParserIssue("Contravariant type has no call signature", type);
|
|
2801
2834
|
}
|
|
2835
|
+
if (signatures[0].typeParameters && signatures[0].typeParameters.length > 0) {
|
|
2836
|
+
return typeParserIssue("Invariant type should not have type parameters", type);
|
|
2837
|
+
}
|
|
2802
2838
|
return succeed(typeCheckerUtils.getTypeParameterAtPosition(signatures[0], 0));
|
|
2803
2839
|
}
|
|
2804
2840
|
function invariantTypeArgument(type) {
|
|
@@ -2806,6 +2842,9 @@ function make2(ts, tsUtils, typeChecker, typeCheckerUtils, program) {
|
|
|
2806
2842
|
if (signatures.length !== 1) {
|
|
2807
2843
|
return typeParserIssue("Invariant type has no call signature", type);
|
|
2808
2844
|
}
|
|
2845
|
+
if (signatures[0].typeParameters && signatures[0].typeParameters.length > 0) {
|
|
2846
|
+
return typeParserIssue("Invariant type should not have type parameters", type);
|
|
2847
|
+
}
|
|
2809
2848
|
return succeed(typeChecker.getReturnTypeOfSignature(signatures[0]));
|
|
2810
2849
|
}
|
|
2811
2850
|
const pipeableType = cachedBy(
|
|
@@ -4693,32 +4732,38 @@ var catchAllToMapError = createDiagnostic({
|
|
|
4693
4732
|
return void 0;
|
|
4694
4733
|
};
|
|
4695
4734
|
const getEffectFailCallInfo = (body) => {
|
|
4696
|
-
|
|
4697
|
-
|
|
4698
|
-
|
|
4699
|
-
|
|
4700
|
-
|
|
4701
|
-
|
|
4702
|
-
|
|
4703
|
-
return { failCall: body, failArg: body.arguments[0] };
|
|
4704
|
-
}
|
|
4705
|
-
}
|
|
4706
|
-
if (ts.isBlock(body)) {
|
|
4707
|
-
const statements = body.statements;
|
|
4708
|
-
if (statements.length === 1) {
|
|
4709
|
-
const stmt = statements[0];
|
|
4710
|
-
if (ts.isReturnStatement(stmt) && stmt.expression && ts.isCallExpression(stmt.expression)) {
|
|
4711
|
-
const isFailCall = yield* pipe(
|
|
4712
|
-
typeParser.isNodeReferenceToEffectModuleApi("fail")(stmt.expression.expression),
|
|
4713
|
-
orUndefined
|
|
4714
|
-
);
|
|
4715
|
-
if (isFailCall && stmt.expression.arguments.length >= 1) {
|
|
4716
|
-
return { failCall: stmt.expression, failArg: stmt.expression.arguments[0] };
|
|
4717
|
-
}
|
|
4735
|
+
if (ts.isCallExpression(body)) {
|
|
4736
|
+
return pipe(
|
|
4737
|
+
typeParser.isNodeReferenceToEffectModuleApi("fail")(body.expression),
|
|
4738
|
+
orUndefined,
|
|
4739
|
+
map4((isFailCall) => {
|
|
4740
|
+
if (isFailCall && body.arguments.length >= 1) {
|
|
4741
|
+
return { failCall: body, failArg: body.arguments[0] };
|
|
4718
4742
|
}
|
|
4743
|
+
return void 0;
|
|
4744
|
+
})
|
|
4745
|
+
);
|
|
4746
|
+
}
|
|
4747
|
+
if (ts.isBlock(body)) {
|
|
4748
|
+
const statements = body.statements;
|
|
4749
|
+
if (statements.length === 1) {
|
|
4750
|
+
const stmt = statements[0];
|
|
4751
|
+
if (ts.isReturnStatement(stmt) && stmt.expression && ts.isCallExpression(stmt.expression)) {
|
|
4752
|
+
const callExpr = stmt.expression;
|
|
4753
|
+
return pipe(
|
|
4754
|
+
typeParser.isNodeReferenceToEffectModuleApi("fail")(callExpr.expression),
|
|
4755
|
+
orUndefined,
|
|
4756
|
+
map4((isFailCall) => {
|
|
4757
|
+
if (isFailCall && callExpr.arguments.length >= 1) {
|
|
4758
|
+
return { failCall: callExpr, failArg: callExpr.arguments[0] };
|
|
4759
|
+
}
|
|
4760
|
+
return void 0;
|
|
4761
|
+
})
|
|
4762
|
+
);
|
|
4719
4763
|
}
|
|
4720
4764
|
}
|
|
4721
|
-
}
|
|
4765
|
+
}
|
|
4766
|
+
return void_;
|
|
4722
4767
|
};
|
|
4723
4768
|
const flows = yield* typeParser.pipingFlows(true)(sourceFile);
|
|
4724
4769
|
for (const flow2 of flows) {
|
|
@@ -4963,20 +5008,21 @@ var deterministicKeys = createDiagnostic({
|
|
|
4963
5008
|
const typeScriptUtils = yield* service(TypeScriptUtils);
|
|
4964
5009
|
const options = yield* service(LanguageServicePluginOptions);
|
|
4965
5010
|
const parseExtendsCustom = cachedBy(
|
|
4966
|
-
|
|
5011
|
+
(classDeclaration) => {
|
|
4967
5012
|
if (!options.extendedKeyDetection) {
|
|
4968
|
-
return
|
|
5013
|
+
return TypeParserIssue.issue;
|
|
4969
5014
|
}
|
|
4970
5015
|
if (!classDeclaration.name) {
|
|
4971
|
-
return
|
|
5016
|
+
return TypeParserIssue.issue;
|
|
4972
5017
|
}
|
|
4973
5018
|
if (!ts.isIdentifier(classDeclaration.name)) {
|
|
4974
|
-
return
|
|
5019
|
+
return TypeParserIssue.issue;
|
|
4975
5020
|
}
|
|
4976
5021
|
const heritageClauses = classDeclaration.heritageClauses;
|
|
4977
5022
|
if (!heritageClauses) {
|
|
4978
|
-
return
|
|
5023
|
+
return TypeParserIssue.issue;
|
|
4979
5024
|
}
|
|
5025
|
+
const className = classDeclaration.name;
|
|
4980
5026
|
const nodeToVisit2 = [...classDeclaration.heritageClauses];
|
|
4981
5027
|
const appendNodeToVisit2 = (node) => {
|
|
4982
5028
|
nodeToVisit2.push(node);
|
|
@@ -4997,7 +5043,7 @@ var deterministicKeys = createDiagnostic({
|
|
|
4997
5043
|
const parameterSourceFile = typeScriptUtils.getSourceFileOfNode(declaration);
|
|
4998
5044
|
const paramText = parameterSourceFile.text.substring(declaration.pos, declaration.end);
|
|
4999
5045
|
if (paramText.toLowerCase().includes("@effect-identifier")) {
|
|
5000
|
-
return { className
|
|
5046
|
+
return succeed({ className, keyStringLiteral: arg, target: "custom" });
|
|
5001
5047
|
}
|
|
5002
5048
|
}
|
|
5003
5049
|
}
|
|
@@ -5006,12 +5052,8 @@ var deterministicKeys = createDiagnostic({
|
|
|
5006
5052
|
}
|
|
5007
5053
|
ts.forEachChild(node, appendNodeToVisit2);
|
|
5008
5054
|
}
|
|
5009
|
-
return
|
|
5010
|
-
|
|
5011
|
-
void 0,
|
|
5012
|
-
classDeclaration
|
|
5013
|
-
);
|
|
5014
|
-
}),
|
|
5055
|
+
return TypeParserIssue.issue;
|
|
5056
|
+
},
|
|
5015
5057
|
"deterministicKeys.parseExtendsCustom",
|
|
5016
5058
|
(classDeclaration) => classDeclaration
|
|
5017
5059
|
);
|
|
@@ -5290,7 +5332,7 @@ var effectFnOpportunity = createDiagnostic({
|
|
|
5290
5332
|
}
|
|
5291
5333
|
return false;
|
|
5292
5334
|
};
|
|
5293
|
-
const tryExtractWithSpanExpression = (
|
|
5335
|
+
const tryExtractWithSpanExpression = fn("effectFnOpportunity.tryExtractWithSpanExpression")(function* (expr) {
|
|
5294
5336
|
if (!ts.isCallExpression(expr)) return void 0;
|
|
5295
5337
|
const callee = expr.expression;
|
|
5296
5338
|
const isWithSpan = yield* pipe(
|
|
@@ -5302,7 +5344,9 @@ var effectFnOpportunity = createDiagnostic({
|
|
|
5302
5344
|
if (expr.arguments.length === 0) return void 0;
|
|
5303
5345
|
return expr.arguments[0];
|
|
5304
5346
|
});
|
|
5305
|
-
const tryParseGenOpportunity = (
|
|
5347
|
+
const tryParseGenOpportunity = fn(
|
|
5348
|
+
"effectFnOpportunity.tryParseGenOpportunity"
|
|
5349
|
+
)(function* (fnNode) {
|
|
5306
5350
|
const bodyExpression = getBodyExpression(fnNode);
|
|
5307
5351
|
if (!bodyExpression) return yield* TypeParserIssue.issue;
|
|
5308
5352
|
const { pipeArguments: pipeArguments2, subject } = yield* pipe(
|
|
@@ -5338,62 +5382,67 @@ var effectFnOpportunity = createDiagnostic({
|
|
|
5338
5382
|
orElse2(() => succeed(false))
|
|
5339
5383
|
);
|
|
5340
5384
|
};
|
|
5341
|
-
const
|
|
5385
|
+
const parseEffectFnOpportunityTargetGen = fn("effectFnOpportunity.parseEffectFnOpportunityTarget")(
|
|
5386
|
+
function* (node, returnType, traceName, nameIdentifier) {
|
|
5387
|
+
if (yield* isInsideEffectFn(node)) {
|
|
5388
|
+
return yield* TypeParserIssue.issue;
|
|
5389
|
+
}
|
|
5390
|
+
const unionMembers = typeCheckerUtils.unrollUnionMembers(returnType);
|
|
5391
|
+
yield* all(...unionMembers.map((member) => typeParser.strictEffectType(member, node)));
|
|
5392
|
+
const opportunity = yield* pipe(
|
|
5393
|
+
tryParseGenOpportunity(node),
|
|
5394
|
+
orElse2(() => {
|
|
5395
|
+
if (ts.isArrowFunction(node) && !ts.isBlock(node.body)) {
|
|
5396
|
+
return TypeParserIssue.issue;
|
|
5397
|
+
}
|
|
5398
|
+
const body = ts.isArrowFunction(node) ? node.body : node.body;
|
|
5399
|
+
if (!body || !ts.isBlock(body) || body.statements.length <= 5) {
|
|
5400
|
+
return TypeParserIssue.issue;
|
|
5401
|
+
}
|
|
5402
|
+
return succeed({
|
|
5403
|
+
effectModuleName: sourceEffectModuleName,
|
|
5404
|
+
pipeArguments: [],
|
|
5405
|
+
generatorFunction: void 0,
|
|
5406
|
+
explicitTraceExpression: void 0
|
|
5407
|
+
});
|
|
5408
|
+
})
|
|
5409
|
+
);
|
|
5410
|
+
return {
|
|
5411
|
+
node,
|
|
5412
|
+
nameIdentifier,
|
|
5413
|
+
effectModuleName: opportunity.effectModuleName,
|
|
5414
|
+
inferredTraceName: traceName,
|
|
5415
|
+
explicitTraceExpression: opportunity.explicitTraceExpression,
|
|
5416
|
+
pipeArguments: opportunity.pipeArguments,
|
|
5417
|
+
generatorFunction: opportunity.generatorFunction,
|
|
5418
|
+
hasParamsInPipeArgs: areParametersReferencedIn(node, opportunity.pipeArguments)
|
|
5419
|
+
};
|
|
5420
|
+
}
|
|
5421
|
+
);
|
|
5422
|
+
const parseEffectFnOpportunityTarget = (node) => {
|
|
5342
5423
|
if (!ts.isFunctionExpression(node) && !ts.isArrowFunction(node) && !ts.isFunctionDeclaration(node)) {
|
|
5343
|
-
return
|
|
5424
|
+
return TypeParserIssue.issue;
|
|
5344
5425
|
}
|
|
5345
5426
|
if ((ts.isFunctionExpression(node) || ts.isFunctionDeclaration(node)) && node.asteriskToken) {
|
|
5346
|
-
return
|
|
5427
|
+
return TypeParserIssue.issue;
|
|
5347
5428
|
}
|
|
5348
5429
|
if (ts.isFunctionExpression(node) && node.name) {
|
|
5349
|
-
return
|
|
5430
|
+
return TypeParserIssue.issue;
|
|
5350
5431
|
}
|
|
5351
5432
|
if (node.type) {
|
|
5352
|
-
return
|
|
5353
|
-
}
|
|
5354
|
-
if (yield* isInsideEffectFn(node)) {
|
|
5355
|
-
return yield* TypeParserIssue.issue;
|
|
5433
|
+
return TypeParserIssue.issue;
|
|
5356
5434
|
}
|
|
5357
5435
|
const functionType = typeChecker.getTypeAtLocation(node);
|
|
5358
|
-
if (!functionType) return
|
|
5436
|
+
if (!functionType) return TypeParserIssue.issue;
|
|
5359
5437
|
const callSignatures = typeChecker.getSignaturesOfType(functionType, ts.SignatureKind.Call);
|
|
5360
|
-
if (callSignatures.length !== 1) return
|
|
5438
|
+
if (callSignatures.length !== 1) return TypeParserIssue.issue;
|
|
5361
5439
|
const signature = callSignatures[0];
|
|
5362
5440
|
const returnType = typeChecker.getReturnTypeOfSignature(signature);
|
|
5363
|
-
const unionMembers = typeCheckerUtils.unrollUnionMembers(returnType);
|
|
5364
|
-
yield* all(...unionMembers.map((member) => typeParser.strictEffectType(member, node)));
|
|
5365
5441
|
const nameIdentifier = getNameIdentifier(node);
|
|
5366
5442
|
const traceName = nameIdentifier ? ts.isIdentifier(nameIdentifier) ? ts.idText(nameIdentifier) : nameIdentifier.text : void 0;
|
|
5367
|
-
if (!traceName) return
|
|
5368
|
-
|
|
5369
|
-
|
|
5370
|
-
orElse2(() => {
|
|
5371
|
-
if (ts.isArrowFunction(node) && !ts.isBlock(node.body)) {
|
|
5372
|
-
return TypeParserIssue.issue;
|
|
5373
|
-
}
|
|
5374
|
-
const body = ts.isArrowFunction(node) ? node.body : node.body;
|
|
5375
|
-
if (!body || !ts.isBlock(body) || body.statements.length <= 5) {
|
|
5376
|
-
return TypeParserIssue.issue;
|
|
5377
|
-
}
|
|
5378
|
-
return succeed({
|
|
5379
|
-
effectModuleName: sourceEffectModuleName,
|
|
5380
|
-
pipeArguments: [],
|
|
5381
|
-
generatorFunction: void 0,
|
|
5382
|
-
explicitTraceExpression: void 0
|
|
5383
|
-
});
|
|
5384
|
-
})
|
|
5385
|
-
);
|
|
5386
|
-
return {
|
|
5387
|
-
node,
|
|
5388
|
-
nameIdentifier,
|
|
5389
|
-
effectModuleName: opportunity.effectModuleName,
|
|
5390
|
-
inferredTraceName: traceName,
|
|
5391
|
-
explicitTraceExpression: opportunity.explicitTraceExpression,
|
|
5392
|
-
pipeArguments: opportunity.pipeArguments,
|
|
5393
|
-
generatorFunction: opportunity.generatorFunction,
|
|
5394
|
-
hasParamsInPipeArgs: areParametersReferencedIn(node, opportunity.pipeArguments)
|
|
5395
|
-
};
|
|
5396
|
-
});
|
|
5443
|
+
if (!traceName) return TypeParserIssue.issue;
|
|
5444
|
+
return parseEffectFnOpportunityTargetGen(node, returnType, traceName, nameIdentifier);
|
|
5445
|
+
};
|
|
5397
5446
|
const getFunctionBodyBlock = (node) => {
|
|
5398
5447
|
if (ts.isArrowFunction(node)) {
|
|
5399
5448
|
if (ts.isBlock(node.body)) {
|
|
@@ -5634,7 +5683,7 @@ var effectInVoidSuccess = createDiagnostic({
|
|
|
5634
5683
|
);
|
|
5635
5684
|
return { voidedEffect };
|
|
5636
5685
|
}
|
|
5637
|
-
return yield*
|
|
5686
|
+
return yield* TypeParserIssue.issue;
|
|
5638
5687
|
});
|
|
5639
5688
|
const entries = typeCheckerUtils.expectedAndRealType(sourceFile);
|
|
5640
5689
|
for (const [node, expectedType, valueNode, realType] of entries) {
|
|
@@ -7446,25 +7495,27 @@ var generate = fn("writeTagClassAccessors.generate")(function* (sourceFile, serv
|
|
|
7446
7495
|
return succeed(typeNode);
|
|
7447
7496
|
})
|
|
7448
7497
|
);
|
|
7449
|
-
const proxySignature = (
|
|
7450
|
-
|
|
7451
|
-
|
|
7452
|
-
|
|
7453
|
-
|
|
7454
|
-
|
|
7455
|
-
|
|
7456
|
-
|
|
7457
|
-
|
|
7458
|
-
|
|
7459
|
-
|
|
7460
|
-
|
|
7461
|
-
|
|
7462
|
-
|
|
7463
|
-
|
|
7464
|
-
|
|
7465
|
-
|
|
7466
|
-
|
|
7467
|
-
|
|
7498
|
+
const proxySignature = fn("writeTagClassAccessors.proxySignature")(
|
|
7499
|
+
function* (signature, atLocation2, className2) {
|
|
7500
|
+
const signatureDeclaration = typeChecker.signatureToSignatureDeclaration(
|
|
7501
|
+
signature,
|
|
7502
|
+
ts.SyntaxKind.FunctionType,
|
|
7503
|
+
atLocation2,
|
|
7504
|
+
ts.NodeBuilderFlags.NoTruncation
|
|
7505
|
+
);
|
|
7506
|
+
if (!signatureDeclaration) return yield* fail("error generating signature");
|
|
7507
|
+
const returnType = yield* generateReturnType(
|
|
7508
|
+
typeChecker.getReturnTypeOfSignature(signature),
|
|
7509
|
+
atLocation2,
|
|
7510
|
+
className2
|
|
7511
|
+
);
|
|
7512
|
+
return ts.factory.createFunctionTypeNode(
|
|
7513
|
+
signatureDeclaration.typeParameters,
|
|
7514
|
+
signatureDeclaration.parameters,
|
|
7515
|
+
returnType
|
|
7516
|
+
);
|
|
7517
|
+
}
|
|
7518
|
+
);
|
|
7468
7519
|
for (const { property, propertyType } of involvedMembers) {
|
|
7469
7520
|
const callSignatures = [];
|
|
7470
7521
|
let propertyDeclaration = void 0;
|
|
@@ -7601,7 +7652,7 @@ var annotate = createCodegen({
|
|
|
7601
7652
|
const tsUtils = yield* service(TypeScriptUtils);
|
|
7602
7653
|
const typeChecker = yield* service(TypeCheckerApi);
|
|
7603
7654
|
const typeCheckerUtils = yield* service(TypeCheckerUtils);
|
|
7604
|
-
const parse3 = (
|
|
7655
|
+
const parse3 = fn("annotate.parse")(function* (node) {
|
|
7605
7656
|
let variableDeclarations = [];
|
|
7606
7657
|
const result = [];
|
|
7607
7658
|
if (ts.isVariableStatement(node)) {
|
|
@@ -8281,7 +8332,7 @@ var typeToSchema = createCodegen({
|
|
|
8281
8332
|
new CodegenNotApplicableError("the typeToSchema codegen can be used only once per file")
|
|
8282
8333
|
);
|
|
8283
8334
|
}
|
|
8284
|
-
const parse3 = (
|
|
8335
|
+
const parse3 = fn("typeToSchema.parse")(function* (node) {
|
|
8285
8336
|
if (!ts.isTypeAliasDeclaration(node)) {
|
|
8286
8337
|
return yield* fail(
|
|
8287
8338
|
new CodegenNotApplicableError(
|
|
@@ -8558,73 +8609,99 @@ var preferSchemaOverJson = createDiagnostic({
|
|
|
8558
8609
|
apply: fn("preferSchemaOverJson.apply")(function* (sourceFile, report) {
|
|
8559
8610
|
const ts = yield* service(TypeScriptApi);
|
|
8560
8611
|
const typeParser = yield* service(TypeParser);
|
|
8561
|
-
const
|
|
8562
|
-
|
|
8563
|
-
const
|
|
8564
|
-
|
|
8565
|
-
|
|
8566
|
-
|
|
8567
|
-
|
|
8568
|
-
|
|
8612
|
+
const isJsonCall = (node) => ts.isCallExpression(node) && ts.isPropertyAccessExpression(node.expression) && ts.isIdentifier(node.expression.expression) && ts.idText(node.expression.expression) === "JSON" && (ts.idText(node.expression.name) === "parse" || ts.idText(node.expression.name) === "stringify");
|
|
8613
|
+
const findEnclosingEffectTry = (jsonCall) => {
|
|
8614
|
+
const parent = jsonCall.parent;
|
|
8615
|
+
let lazy;
|
|
8616
|
+
if (ts.isArrowFunction(parent) && parent.body === jsonCall && parent.parameters.length === 0 && (!parent.typeParameters || parent.typeParameters.length === 0)) {
|
|
8617
|
+
lazy = parent;
|
|
8618
|
+
}
|
|
8619
|
+
if (!lazy && ts.isReturnStatement(parent) && parent.expression === jsonCall) {
|
|
8620
|
+
const block = parent.parent;
|
|
8621
|
+
if (ts.isBlock(block) && block.statements.length === 1) {
|
|
8622
|
+
const fn2 = block.parent;
|
|
8623
|
+
if ((ts.isArrowFunction(fn2) || ts.isFunctionExpression(fn2)) && fn2.parameters.length === 0 && (!fn2.typeParameters || fn2.typeParameters.length === 0)) {
|
|
8624
|
+
lazy = fn2;
|
|
8625
|
+
}
|
|
8626
|
+
}
|
|
8569
8627
|
}
|
|
8570
|
-
if (
|
|
8571
|
-
|
|
8628
|
+
if (!lazy) return void 0;
|
|
8629
|
+
const lazyParent = lazy.parent;
|
|
8630
|
+
if (ts.isCallExpression(lazyParent) && lazyParent.arguments.length > 0 && lazyParent.arguments[0] === lazy) {
|
|
8631
|
+
return lazyParent;
|
|
8572
8632
|
}
|
|
8573
|
-
|
|
8574
|
-
|
|
8575
|
-
|
|
8576
|
-
|
|
8633
|
+
if (ts.isPropertyAssignment(lazyParent) && ts.isIdentifier(lazyParent.name) && ts.idText(lazyParent.name) === "try") {
|
|
8634
|
+
const objLiteral = lazyParent.parent;
|
|
8635
|
+
if (ts.isObjectLiteralExpression(objLiteral)) {
|
|
8636
|
+
const callExpr = objLiteral.parent;
|
|
8637
|
+
if (ts.isCallExpression(callExpr) && callExpr.arguments.length > 0 && callExpr.arguments[0] === objLiteral) {
|
|
8638
|
+
return callExpr;
|
|
8639
|
+
}
|
|
8640
|
+
}
|
|
8641
|
+
}
|
|
8642
|
+
return void 0;
|
|
8643
|
+
};
|
|
8644
|
+
const jsonCalls = [];
|
|
8645
|
+
const collectJsonCalls = (node) => {
|
|
8646
|
+
if (isJsonCall(node)) {
|
|
8647
|
+
jsonCalls.push(node);
|
|
8648
|
+
}
|
|
8649
|
+
ts.forEachChild(node, collectJsonCalls);
|
|
8650
|
+
};
|
|
8651
|
+
ts.forEachChild(sourceFile, collectJsonCalls);
|
|
8652
|
+
if (jsonCalls.length === 0) return;
|
|
8653
|
+
const effectTrySimple = fn("preferSchemaOverJson.effectTrySimple")(function* (node) {
|
|
8577
8654
|
yield* typeParser.isNodeReferenceToEffectModuleApi("try")(node.expression);
|
|
8578
|
-
if (node.arguments.length === 0) return yield*
|
|
8655
|
+
if (node.arguments.length === 0) return yield* TypeParserIssue.issue;
|
|
8579
8656
|
const lazyFn = yield* typeParser.lazyExpression(node.arguments[0]);
|
|
8580
|
-
|
|
8581
|
-
return
|
|
8657
|
+
if (!isJsonCall(lazyFn.expression)) return yield* TypeParserIssue.issue;
|
|
8658
|
+
return lazyFn.expression;
|
|
8582
8659
|
});
|
|
8583
|
-
const effectTryObject = (
|
|
8584
|
-
if (!ts.isCallExpression(node)) return yield* fail("node is not a call expression");
|
|
8660
|
+
const effectTryObject = fn("preferSchemaOverJson.effectTryObject")(function* (node) {
|
|
8585
8661
|
yield* typeParser.isNodeReferenceToEffectModuleApi("try")(node.expression);
|
|
8586
|
-
if (node.arguments.length === 0) return yield*
|
|
8662
|
+
if (node.arguments.length === 0) return yield* TypeParserIssue.issue;
|
|
8587
8663
|
const arg = node.arguments[0];
|
|
8588
|
-
if (!ts.isObjectLiteralExpression(arg)) return yield*
|
|
8664
|
+
if (!ts.isObjectLiteralExpression(arg)) return yield* TypeParserIssue.issue;
|
|
8589
8665
|
const tryProp = arg.properties.find(
|
|
8590
8666
|
(p) => ts.isPropertyAssignment(p) && ts.isIdentifier(p.name) && ts.idText(p.name) === "try"
|
|
8591
8667
|
);
|
|
8592
|
-
if (!tryProp) return yield*
|
|
8668
|
+
if (!tryProp) return yield* TypeParserIssue.issue;
|
|
8593
8669
|
const lazyFn = yield* typeParser.lazyExpression(tryProp.initializer);
|
|
8594
|
-
|
|
8595
|
-
return
|
|
8670
|
+
if (!isJsonCall(lazyFn.expression)) return yield* TypeParserIssue.issue;
|
|
8671
|
+
return lazyFn.expression;
|
|
8596
8672
|
});
|
|
8597
|
-
const jsonMethodInEffectGen = (
|
|
8598
|
-
|
|
8599
|
-
|
|
8600
|
-
|
|
8601
|
-
|
|
8673
|
+
const jsonMethodInEffectGen = fn("preferSchemaOverJson.jsonMethodInEffectGen")(
|
|
8674
|
+
function* (jsonCall) {
|
|
8675
|
+
const { effectGen, scopeNode } = yield* typeParser.findEnclosingScopes(jsonCall);
|
|
8676
|
+
if (!effectGen || effectGen.body.statements.length === 0) {
|
|
8677
|
+
return yield* TypeParserIssue.issue;
|
|
8678
|
+
}
|
|
8679
|
+
if (scopeNode && scopeNode !== effectGen.generatorFunction) {
|
|
8680
|
+
return yield* TypeParserIssue.issue;
|
|
8681
|
+
}
|
|
8682
|
+
return jsonCall;
|
|
8602
8683
|
}
|
|
8603
|
-
|
|
8604
|
-
|
|
8684
|
+
);
|
|
8685
|
+
for (const jsonCall of jsonCalls) {
|
|
8686
|
+
const effectTryCall = findEnclosingEffectTry(jsonCall);
|
|
8687
|
+
let match2;
|
|
8688
|
+
if (effectTryCall) {
|
|
8689
|
+
match2 = yield* pipe(
|
|
8690
|
+
firstSuccessOf([
|
|
8691
|
+
effectTrySimple(effectTryCall),
|
|
8692
|
+
effectTryObject(effectTryCall)
|
|
8693
|
+
]),
|
|
8694
|
+
option
|
|
8695
|
+
);
|
|
8696
|
+
} else {
|
|
8697
|
+
match2 = yield* pipe(
|
|
8698
|
+
jsonMethodInEffectGen(jsonCall),
|
|
8699
|
+
option
|
|
8700
|
+
);
|
|
8605
8701
|
}
|
|
8606
|
-
return { node: jsonMethod.node, methodName: jsonMethod.methodName };
|
|
8607
|
-
});
|
|
8608
|
-
const nodeToVisit = [];
|
|
8609
|
-
const appendNodeToVisit = (node) => {
|
|
8610
|
-
nodeToVisit.push(node);
|
|
8611
|
-
return void 0;
|
|
8612
|
-
};
|
|
8613
|
-
ts.forEachChild(sourceFile, appendNodeToVisit);
|
|
8614
|
-
while (nodeToVisit.length > 0) {
|
|
8615
|
-
const node = nodeToVisit.shift();
|
|
8616
|
-
ts.forEachChild(node, appendNodeToVisit);
|
|
8617
|
-
const match2 = yield* pipe(
|
|
8618
|
-
firstSuccessOf([
|
|
8619
|
-
effectTrySimple(node),
|
|
8620
|
-
effectTryObject(node),
|
|
8621
|
-
jsonMethodInEffectGen(node)
|
|
8622
|
-
]),
|
|
8623
|
-
option
|
|
8624
|
-
);
|
|
8625
8702
|
if (isSome2(match2)) {
|
|
8626
8703
|
report({
|
|
8627
|
-
location: match2.value
|
|
8704
|
+
location: match2.value,
|
|
8628
8705
|
messageText: "Consider using Effect Schema for JSON operations instead of JSON.parse/JSON.stringify",
|
|
8629
8706
|
fixes: []
|
|
8630
8707
|
});
|
|
@@ -9268,19 +9345,24 @@ var strictEffectProvide = createDiagnostic({
|
|
|
9268
9345
|
const ts = yield* service(TypeScriptApi);
|
|
9269
9346
|
const typeCheckerUtils = yield* service(TypeCheckerUtils);
|
|
9270
9347
|
const typeParser = yield* service(TypeParser);
|
|
9271
|
-
const
|
|
9348
|
+
const parseEffectProvideWithLayerGen = fn("strictEffectProvide.parseEffectProvideWithLayer")(
|
|
9349
|
+
function* (node) {
|
|
9350
|
+
yield* typeParser.isNodeReferenceToEffectModuleApi("provide")(node.expression);
|
|
9351
|
+
return yield* firstSuccessOf(
|
|
9352
|
+
node.arguments.map((arg) => {
|
|
9353
|
+
const argType = typeCheckerUtils.getTypeAtLocation(arg);
|
|
9354
|
+
if (!argType) return typeParserIssue("Could not get argument type");
|
|
9355
|
+
return typeParser.layerType(argType, arg);
|
|
9356
|
+
})
|
|
9357
|
+
);
|
|
9358
|
+
}
|
|
9359
|
+
);
|
|
9360
|
+
const parseEffectProvideWithLayer = (node) => {
|
|
9272
9361
|
if (!ts.isCallExpression(node) || node.arguments.length === 0) {
|
|
9273
|
-
return
|
|
9274
|
-
}
|
|
9275
|
-
|
|
9276
|
-
|
|
9277
|
-
node.arguments.map((arg) => {
|
|
9278
|
-
const argType = typeCheckerUtils.getTypeAtLocation(arg);
|
|
9279
|
-
if (!argType) return typeParserIssue("Could not get argument type");
|
|
9280
|
-
return typeParser.layerType(argType, arg);
|
|
9281
|
-
})
|
|
9282
|
-
);
|
|
9283
|
-
});
|
|
9362
|
+
return TypeParserIssue.issue;
|
|
9363
|
+
}
|
|
9364
|
+
return parseEffectProvideWithLayerGen(node);
|
|
9365
|
+
};
|
|
9284
9366
|
const nodeToVisit = [];
|
|
9285
9367
|
const appendNodeToVisit = (node) => {
|
|
9286
9368
|
nodeToVisit.push(node);
|