@effect/language-service 0.31.1 → 0.32.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/index.js CHANGED
@@ -1528,7 +1528,8 @@ function parse(config) {
1528
1528
  goto: isObject(config) && hasProperty(config, "goto") && isBoolean(config.goto) ? config.goto : true,
1529
1529
  allowedDuplicatedPackages: isObject(config) && hasProperty(config, "allowedDuplicatedPackages") && isArray(config.allowedDuplicatedPackages) && config.allowedDuplicatedPackages.every(isString) ? config.allowedDuplicatedPackages.map((_) => _.toLowerCase()) : [],
1530
1530
  namespaceImportPackages: isObject(config) && hasProperty(config, "namespaceImportPackages") && isArray(config.namespaceImportPackages) && config.namespaceImportPackages.every(isString) ? config.namespaceImportPackages.map((_) => _.toLowerCase()) : [],
1531
- barrelImportPackages: isObject(config) && hasProperty(config, "barrelImportPackages") && isArray(config.barrelImportPackages) && config.barrelImportPackages.every(isString) ? config.barrelImportPackages.map((_) => _.toLowerCase()) : []
1531
+ barrelImportPackages: isObject(config) && hasProperty(config, "barrelImportPackages") && isArray(config.barrelImportPackages) && config.barrelImportPackages.every(isString) ? config.barrelImportPackages.map((_) => _.toLowerCase()) : [],
1532
+ topLevelNamedReexports: isObject(config) && hasProperty(config, "topLevelNamedReexports") && isString(config.topLevelNamedReexports) && (config.topLevelNamedReexports.toLowerCase() === "ignore" || config.topLevelNamedReexports.toLowerCase() === "follow") ? config.topLevelNamedReexports.toLowerCase() : "ignore"
1532
1533
  };
1533
1534
  }
1534
1535
 
@@ -2993,6 +2994,7 @@ function make3(ts, tsUtils, typeChecker) {
2993
2994
  className: atLocation.name,
2994
2995
  selfTypeNode,
2995
2996
  args: wholeCall.arguments,
2997
+ options: wholeCall.arguments[1],
2996
2998
  accessors: accessors2,
2997
2999
  dependencies
2998
3000
  };
@@ -3598,9 +3600,11 @@ var floatingEffect = createDiagnostic({
3598
3600
  option
3599
3601
  );
3600
3602
  if (isNone2(allowedFloatingEffects)) {
3603
+ const isStrictEffect = yield* option(typeParser.strictEffectType(type, node.expression));
3604
+ const name = isSome2(isStrictEffect) ? "Effect" : "Effect-able " + typeChecker.typeToString(type);
3601
3605
  report({
3602
3606
  location: node,
3603
- messageText: `Effect must be yielded or assigned to a variable.`,
3607
+ messageText: `${name} must be yielded or assigned to a variable.`,
3604
3608
  fixes: []
3605
3609
  });
3606
3610
  }
@@ -4109,7 +4113,7 @@ var missingEffectServiceDependency = createDiagnostic({
4109
4113
  orElse2(() => void_)
4110
4114
  );
4111
4115
  if (serviceResult) {
4112
- const { className, dependencies } = serviceResult;
4116
+ const { className, options } = serviceResult;
4113
4117
  const classSymbol = typeChecker.getSymbolAtLocation(className);
4114
4118
  if (classSymbol) {
4115
4119
  const classType = typeChecker.getTypeOfSymbol(classSymbol);
@@ -4130,11 +4134,17 @@ var missingEffectServiceDependency = createDiagnostic({
4130
4134
  excludeNever
4131
4135
  );
4132
4136
  const providedIndexes = /* @__PURE__ */ new Set();
4133
- const dependenciesToProcess = dependencies || [];
4134
- for (const depExpression of dependenciesToProcess) {
4135
- const depType = typeChecker.getTypeAtLocation(depExpression);
4137
+ const optionsType = typeChecker.getTypeAtLocation(options);
4138
+ const dependenciesProperty = typeChecker.getPropertyOfType(optionsType, "dependencies");
4139
+ let types = [];
4140
+ if (dependenciesProperty) {
4141
+ const dependenciesTypes = typeChecker.getTypeOfSymbolAtLocation(dependenciesProperty, options);
4142
+ const numberIndexType = dependenciesTypes.getNumberIndexType();
4143
+ types = numberIndexType ? unrollUnionMembers(numberIndexType) : [];
4144
+ }
4145
+ for (const depType of types) {
4136
4146
  const depLayerResult = yield* pipe(
4137
- typeParser.layerType(depType, depExpression),
4147
+ typeParser.layerType(depType, options),
4138
4148
  orElse2(() => void_)
4139
4149
  );
4140
4150
  if (depLayerResult) {
@@ -4221,7 +4231,7 @@ var missingReturnYieldStar = createDiagnostic({
4221
4231
  }] : [];
4222
4232
  report({
4223
4233
  location: node,
4224
- messageText: `Yielded Effect never succeeds, so it is best to use a 'return yield*' instead.`,
4234
+ messageText: `It is recommended to use return yield* for Effects that never succeed to signal a definitive exit point for type narrowing and tooling support.`,
4225
4235
  fixes: fix
4226
4236
  });
4227
4237
  }
@@ -5300,6 +5310,7 @@ var makeAutoImportProvider = fn("TypeScriptApi")(function* (fromSourceFile) {
5300
5310
  }
5301
5311
  }
5302
5312
  const mapFromBarrelToNamespace = /* @__PURE__ */ new Map();
5313
+ const mapFromBarrelToBarrel = /* @__PURE__ */ new Map();
5303
5314
  const mapFromNamespaceToBarrel = /* @__PURE__ */ new Map();
5304
5315
  const mapFilenameToModuleAlias = /* @__PURE__ */ new Map();
5305
5316
  const mapFilenameToExportExcludes = /* @__PURE__ */ new Map();
@@ -5320,7 +5331,7 @@ var makeAutoImportProvider = fn("TypeScriptApi")(function* (fromSourceFile) {
5320
5331
  mapFilenameToModuleName.set(realPath, absoluteName);
5321
5332
  };
5322
5333
  const collectImportCache = fn("TypeScriptApi")(
5323
- function* (packagePatterns, kind) {
5334
+ function* (packagePatterns, kind, topLevelNamedReexports) {
5324
5335
  for (const packagePattern of packagePatterns) {
5325
5336
  const packageNames = tsUtils.resolveModulePattern(fromSourceFile, packagePattern);
5326
5337
  for (const packageName of packageNames) {
@@ -5370,11 +5381,28 @@ var makeAutoImportProvider = fn("TypeScriptApi")(function* (fromSourceFile) {
5370
5381
  }
5371
5382
  if (isPackageRoot) {
5372
5383
  for (const namedExport of reExports.namedExports) {
5373
- mapFilenameToExportExcludes.set(barrelSourceFile.fileName, [
5374
- ...mapFilenameToExportExcludes.get(barrelSourceFile.fileName) || [],
5375
- namedExport.name
5376
- ]);
5377
- break;
5384
+ if (topLevelNamedReexports === "ignore") {
5385
+ mapFilenameToExportExcludes.set(barrelSourceFile.fileName, [
5386
+ ...mapFilenameToExportExcludes.get(barrelSourceFile.fileName) || [],
5387
+ namedExport.name
5388
+ ]);
5389
+ } else if (topLevelNamedReexports === "follow") {
5390
+ const reexportedFile = ts.resolveModuleName(
5391
+ namedExport.moduleSpecifier.text,
5392
+ barrelSourceFile.fileName,
5393
+ program.getCompilerOptions(),
5394
+ host
5395
+ );
5396
+ if (!reexportedFile) continue;
5397
+ if (!reexportedFile.resolvedModule) continue;
5398
+ mapFromBarrelToBarrel.set(barrelSourceFile.fileName, {
5399
+ ...mapFromBarrelToBarrel.get(barrelSourceFile.fileName) || {},
5400
+ [namedExport.name]: {
5401
+ fileName: reexportedFile.resolvedModule.resolvedFileName,
5402
+ exportName: namedExport.name
5403
+ }
5404
+ });
5405
+ }
5378
5406
  }
5379
5407
  }
5380
5408
  }
@@ -5382,8 +5410,12 @@ var makeAutoImportProvider = fn("TypeScriptApi")(function* (fromSourceFile) {
5382
5410
  }
5383
5411
  }
5384
5412
  );
5385
- yield* collectImportCache(languageServicePluginOptions.namespaceImportPackages, "namespace");
5386
- yield* collectImportCache(languageServicePluginOptions.barrelImportPackages, "barrel");
5413
+ yield* collectImportCache(
5414
+ languageServicePluginOptions.namespaceImportPackages,
5415
+ "namespace",
5416
+ languageServicePluginOptions.topLevelNamedReexports
5417
+ );
5418
+ yield* collectImportCache(languageServicePluginOptions.barrelImportPackages, "barrel", "ignore");
5387
5419
  const resolveModuleName = (fileName) => {
5388
5420
  const fixedModuleName = mapFilenameToModuleName.get(fileName);
5389
5421
  if (fixedModuleName) return fixedModuleName;
@@ -5401,6 +5433,18 @@ var makeAutoImportProvider = fn("TypeScriptApi")(function* (fromSourceFile) {
5401
5433
  const resolve = (exportFileName, exportName) => {
5402
5434
  const excludedExports = mapFilenameToExportExcludes.get(exportFileName);
5403
5435
  if (excludedExports && excludedExports.includes(exportName)) return;
5436
+ const mapToBarrelRewritten = mapFromBarrelToBarrel.get(exportFileName);
5437
+ if (mapToBarrelRewritten && exportName in mapToBarrelRewritten) {
5438
+ const reexportedFile = mapToBarrelRewritten[exportName];
5439
+ if (reexportedFile) {
5440
+ return {
5441
+ _tag: "NamedImport",
5442
+ fileName: reexportedFile.fileName,
5443
+ moduleName: resolveModuleName(reexportedFile.fileName),
5444
+ name: exportName
5445
+ };
5446
+ }
5447
+ }
5404
5448
  const mapToNamespace = mapFromBarrelToNamespace.get(exportFileName);
5405
5449
  if (mapToNamespace && exportName in mapToNamespace) {
5406
5450
  const namespacedFileName = mapToNamespace[exportName];