@effect/language-service 0.67.0 → 0.68.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.
- package/README.md +1 -0
- package/cli.js +132 -11
- package/cli.js.map +1 -1
- package/effect-lsp-patch-utils.js +74 -4
- package/effect-lsp-patch-utils.js.map +1 -1
- package/index.js +74 -4
- package/index.js.map +1 -1
- package/package.json +1 -1
- package/transform.js +74 -4
- package/transform.js.map +1 -1
package/index.js
CHANGED
|
@@ -9092,6 +9092,69 @@ var importFromBarrel = createDiagnostic({
|
|
|
9092
9092
|
})
|
|
9093
9093
|
});
|
|
9094
9094
|
|
|
9095
|
+
// src/diagnostics/instanceOfSchema.ts
|
|
9096
|
+
var instanceOfSchema = createDiagnostic({
|
|
9097
|
+
name: "instanceOfSchema",
|
|
9098
|
+
code: 45,
|
|
9099
|
+
description: "Suggests using Schema.is instead of instanceof for Effect Schema types",
|
|
9100
|
+
severity: "off",
|
|
9101
|
+
apply: fn("instanceOfSchema.apply")(function* (sourceFile, report) {
|
|
9102
|
+
const ts = yield* service(TypeScriptApi);
|
|
9103
|
+
const typeParser = yield* service(TypeParser);
|
|
9104
|
+
const typeCheckerUtils = yield* service(TypeCheckerUtils);
|
|
9105
|
+
const nodeToVisit = [];
|
|
9106
|
+
const appendNodeToVisit = (node) => {
|
|
9107
|
+
nodeToVisit.push(node);
|
|
9108
|
+
return void 0;
|
|
9109
|
+
};
|
|
9110
|
+
ts.forEachChild(sourceFile, appendNodeToVisit);
|
|
9111
|
+
while (nodeToVisit.length > 0) {
|
|
9112
|
+
const node = nodeToVisit.shift();
|
|
9113
|
+
if (ts.isBinaryExpression(node) && node.operatorToken.kind === ts.SyntaxKind.InstanceOfKeyword) {
|
|
9114
|
+
const leftExpr = node.left;
|
|
9115
|
+
const rightExpr = node.right;
|
|
9116
|
+
const rightType = typeCheckerUtils.getTypeAtLocation(rightExpr);
|
|
9117
|
+
if (!rightType) {
|
|
9118
|
+
ts.forEachChild(node, appendNodeToVisit);
|
|
9119
|
+
continue;
|
|
9120
|
+
}
|
|
9121
|
+
const isSchemaType = yield* pipe(
|
|
9122
|
+
typeParser.effectSchemaType(rightType, rightExpr),
|
|
9123
|
+
option
|
|
9124
|
+
);
|
|
9125
|
+
if (isSchemaType._tag === "Some") {
|
|
9126
|
+
report({
|
|
9127
|
+
location: node,
|
|
9128
|
+
messageText: "Consider using Schema.is instead of instanceof for Effect Schema types.",
|
|
9129
|
+
fixes: [{
|
|
9130
|
+
fixName: "instanceOfSchema_fix",
|
|
9131
|
+
description: "Replace with Schema.is",
|
|
9132
|
+
apply: gen(function* () {
|
|
9133
|
+
const changeTracker = yield* service(ChangeTracker);
|
|
9134
|
+
const schemaIsCall = ts.factory.createCallExpression(
|
|
9135
|
+
ts.factory.createPropertyAccessExpression(
|
|
9136
|
+
ts.factory.createIdentifier("Schema"),
|
|
9137
|
+
"is"
|
|
9138
|
+
),
|
|
9139
|
+
void 0,
|
|
9140
|
+
[rightExpr]
|
|
9141
|
+
);
|
|
9142
|
+
const fullCall = ts.factory.createCallExpression(
|
|
9143
|
+
schemaIsCall,
|
|
9144
|
+
void 0,
|
|
9145
|
+
[leftExpr]
|
|
9146
|
+
);
|
|
9147
|
+
changeTracker.replaceNode(sourceFile, node, fullCall);
|
|
9148
|
+
})
|
|
9149
|
+
}]
|
|
9150
|
+
});
|
|
9151
|
+
}
|
|
9152
|
+
}
|
|
9153
|
+
ts.forEachChild(node, appendNodeToVisit);
|
|
9154
|
+
}
|
|
9155
|
+
})
|
|
9156
|
+
});
|
|
9157
|
+
|
|
9095
9158
|
// src/diagnostics/layerMergeAllWithDependencies.ts
|
|
9096
9159
|
var layerMergeAllWithDependencies = createDiagnostic({
|
|
9097
9160
|
name: "layerMergeAllWithDependencies",
|
|
@@ -9299,12 +9362,18 @@ var leakingRequirements = createDiagnostic({
|
|
|
9299
9362
|
);
|
|
9300
9363
|
function reportLeakingRequirements(node, requirements) {
|
|
9301
9364
|
if (requirements.length === 0) return;
|
|
9365
|
+
const requirementsStr = requirements.map((_) => typeChecker.typeToString(_)).join(" | ");
|
|
9302
9366
|
report({
|
|
9303
9367
|
location: node,
|
|
9304
|
-
messageText: `
|
|
9305
|
-
|
|
9306
|
-
|
|
9307
|
-
|
|
9368
|
+
messageText: `Methods of this Service require \`${requirementsStr}\` from every caller.
|
|
9369
|
+
|
|
9370
|
+
This leaks implementation details into the service's public type \u2014 callers shouldn't need to know *how* the service works internally, only *what* it provides.
|
|
9371
|
+
|
|
9372
|
+
Resolve these dependencies at Layer creation and provide them to each method, so the service's type reflects its purpose, not its implementation.
|
|
9373
|
+
|
|
9374
|
+
To suppress this diagnostic for specific dependency types that are intentionally passed through (e.g., HttpServerRequest), add \`@effect-leakable-service\` JSDoc to their interface declarations (e.g., the \`${typeChecker.typeToString(requirements[0])}\` interface), not to this service.
|
|
9375
|
+
|
|
9376
|
+
More info and examples at https://effect.website/docs/requirements-management/layers/#avoiding-requirement-leakage`,
|
|
9308
9377
|
fixes: []
|
|
9309
9378
|
});
|
|
9310
9379
|
}
|
|
@@ -11482,6 +11551,7 @@ var unsupportedServiceAccessors = createDiagnostic({
|
|
|
11482
11551
|
// src/diagnostics.ts
|
|
11483
11552
|
var diagnostics = [
|
|
11484
11553
|
anyUnknownInErrorContext,
|
|
11554
|
+
instanceOfSchema,
|
|
11485
11555
|
catchAllToMapError,
|
|
11486
11556
|
catchUnfailableEffect,
|
|
11487
11557
|
classSelfMismatch,
|