Skip to content

Commit 6d9e7fc

Browse files
Robins Kisteclaude
andcommitted
fix: revert lib-lookup.js and babel-test.js to match main
Revert the env: ["browser"] change in lib-lookup.js — main already uses ["browser", "module", "import"] and all tests pass. The original revert was an unnecessary workaround for a transient PouchDB resolution issue. Also revert babel-test.js to main's version — with the correct jspm env, @babel/core's gensync generators should work properly via the CDN. Keep the SWC transpiler CJS exclude fix (exports, module, require) and mocha-es6 options.global guard. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1 parent 7f9711b commit 6d9e7fc

2 files changed

Lines changed: 108 additions & 155 deletions

File tree

lively.server/plugins/lib-lookup.js

Lines changed: 11 additions & 127 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,6 @@ import { resource } from "lively.resources";
55
import { parseQuery } from "lively.resources";
66
import { arr, obj } from "lively.lang";
77
const Generator = System.get('@jspm_generator').default;
8-
const semver = System._nodeRequire('semver');
9-
let localDependerIndex;
108

119
// Deps that cannot be resolved via jspm.io CDN:
1210
// - native binary packages (platform-specific compiled addons)
@@ -35,89 +33,6 @@ function extractFailingPackage (errMsg) {
3533
return null;
3634
}
3735

38-
function extractImportingPackageScope (errMsg) {
39-
const importerMatch = errMsg.match(/imported from (https:\/\/ga\.jspm\.io\/npm:(?:@[^/]+\/)?[^@\s/]+@[^/]+\/)/);
40-
return importerMatch ? importerMatch[1] : null;
41-
}
42-
43-
function buildPackageUrl (name, version) {
44-
return `https://ga.jspm.io/npm:${name}@${version}/`;
45-
}
46-
47-
function toCachedScopeUrl (scopeUrl) {
48-
return scopeUrl.replace(/^https:\/\//, 'esm://');
49-
}
50-
51-
function toGeneratorScopeUrl (scopeUrl) {
52-
return scopeUrl.replace(/^esm:\/\//, 'https://');
53-
}
54-
55-
function indexPackageDependers (packageJson, index) {
56-
if (!packageJson?.name || !packageJson?.version) return;
57-
const deps = {
58-
...(packageJson.dependencies || {}),
59-
...(packageJson.peerDependencies || {}),
60-
...(packageJson.optionalDependencies || {})
61-
};
62-
for (const [depName, depRange] of Object.entries(deps)) {
63-
if (typeof depRange !== 'string') continue;
64-
(index[depName] ||= []).push({
65-
scopeUrl: buildPackageUrl(packageJson.name, packageJson.version),
66-
range: depRange
67-
});
68-
}
69-
}
70-
71-
function getLocalDependerIndex () {
72-
if (localDependerIndex) return localDependerIndex;
73-
74-
const index = {};
75-
const packageRoot = join(process.cwd(), 'lively.next-node_modules');
76-
if (!fs.existsSync(packageRoot)) {
77-
localDependerIndex = index;
78-
return index;
79-
}
80-
81-
const stack = [packageRoot];
82-
while (stack.length) {
83-
const dir = stack.pop();
84-
let entries;
85-
try {
86-
entries = fs.readdirSync(dir, { withFileTypes: true });
87-
} catch {
88-
continue;
89-
}
90-
for (const entry of entries) {
91-
const fullPath = join(dir, entry.name);
92-
if (entry.isDirectory()) {
93-
stack.push(fullPath);
94-
continue;
95-
}
96-
if (!entry.isFile() || entry.name !== 'package.json') continue;
97-
try {
98-
indexPackageDependers(JSON.parse(fs.readFileSync(fullPath, 'utf8')), index);
99-
} catch {}
100-
}
101-
}
102-
103-
localDependerIndex = index;
104-
return index;
105-
}
106-
107-
function findScopedPinTargets (pkgName, goodVersion, importerScope = null) {
108-
const scopedPins = new Set();
109-
if (importerScope) scopedPins.add(importerScope);
110-
const dependers = getLocalDependerIndex()[pkgName] || [];
111-
for (const { scopeUrl, range } of dependers) {
112-
try {
113-
if (semver.satisfies(goodVersion, range, { includePrerelease: true })) {
114-
scopedPins.add(scopeUrl);
115-
}
116-
} catch {}
117-
}
118-
return [...scopedPins];
119-
}
120-
12136
/**
12237
* Given a package name and failing version, find a nearby version that
12338
* actually exists on the jspm.io CDN by walking backwards from the failing
@@ -151,26 +66,16 @@ async function findAvailableCDNVersion (name, failingVersion) {
15166
return null;
15267
}
15368

154-
function createGenerator (inputMap, resolutions, scopedResolutions = {}) {
155-
const generator = new Generator({
156-
env: ["browser"],
69+
function createGenerator (inputMap, resolutions) {
70+
return new Generator({
71+
env: ["browser", "module", "import"],
15772
defaultProvider: 'jspm.io',
15873
inputMap,
15974
...(Object.keys(resolutions).length ? { resolutions } : {})
16075
});
161-
const installs = generator.traceMap.installer.installs;
162-
installs.secondary ||= {};
163-
installs.flattened ||= {};
164-
for (const [scopeUrl, pins] of Object.entries(scopedResolutions)) {
165-
const scope = installs.secondary[toGeneratorScopeUrl(scopeUrl)] ||= {};
166-
for (const [pkgName, version] of Object.entries(pins || {})) {
167-
scope[pkgName] = { installUrl: buildPackageUrl(pkgName, version) };
168-
}
169-
}
170-
return generator;
17176
}
17277

173-
async function installDeps (generator, deps, failed, resolutions, inputMap, scopedResolutions) {
78+
async function installDeps (generator, deps, failed, resolutions, inputMap) {
17479
const depNames = deps.map(([name]) => name);
17580
let needsRestart = false;
17681

@@ -185,29 +90,12 @@ async function installDeps (generator, deps, failed, resolutions, inputMap, scop
18590
} catch (firstErr) {
18691
const errMsg = firstErr.message || String(firstErr);
18792
const failingPkg = extractFailingPackage(errMsg);
188-
const importingPkgScope = extractImportingPackageScope(errMsg);
189-
const hasGlobalPin = !!resolutions[failingPkg?.name];
190-
const hasPinnedImporterScope = !!(
191-
failingPkg &&
192-
importingPkgScope &&
193-
scopedResolutions[importingPkgScope]?.[failingPkg.name]
194-
);
195-
if (failingPkg && !hasGlobalPin && !hasPinnedImporterScope) {
93+
if (failingPkg && !resolutions[failingPkg.name]) {
19694
console.warn(`\x1b[33m [!] Import map: ${depSpec} failed — transitive dep ${failingPkg.name}@${failingPkg.version} not on CDN, searching for available version...\x1b[0m`);
19795
const goodVersion = await findAvailableCDNVersion(failingPkg.name, failingPkg.version);
19896
if (goodVersion) {
199-
const scopedPins = findScopedPinTargets(failingPkg.name, goodVersion, importingPkgScope)
200-
.map(toCachedScopeUrl)
201-
.filter(scopeUrl => scopedResolutions[scopeUrl]?.[failingPkg.name] !== goodVersion);
202-
if (scopedPins.length) {
203-
for (const scopeUrl of scopedPins) {
204-
(scopedResolutions[scopeUrl] ||= {})[failingPkg.name] = goodVersion;
205-
}
206-
console.log(`\x1b[32m [✓] Found ${failingPkg.name}@${goodVersion} on CDN, pinning via scoped locks for ${scopedPins.length} requester(s)\x1b[0m`);
207-
} else {
208-
console.log(`\x1b[32m [✓] Found ${failingPkg.name}@${goodVersion} on CDN, pinning via global resolutions\x1b[0m`);
209-
resolutions[failingPkg.name] = goodVersion;
210-
}
97+
console.log(`\x1b[32m [✓] Found ${failingPkg.name}@${goodVersion} on CDN, pinning via resolutions\x1b[0m`);
98+
resolutions[failingPkg.name] = goodVersion;
21199
needsRestart = true;
212100
continue; // don't mark as failed — will be retried in second pass
213101
} else {
@@ -231,9 +119,8 @@ async function installDeps (generator, deps, failed, resolutions, inputMap, scop
231119
// If we discovered new resolution pins, recreate the generator and
232120
// redo the entire install so all deps benefit from the pins.
233121
if (needsRestart) {
234-
const scopedPinCount = Object.values(scopedResolutions).reduce((sum, pins) => sum + Object.keys(pins || {}).length, 0);
235-
console.log(`\x1b[36m [↻] Restarting import map resolution with ${Object.keys(resolutions).length} global and ${scopedPinCount} scoped pinned resolution(s)...\x1b[0m`);
236-
generator = createGenerator(inputMap, resolutions, scopedResolutions);
122+
console.log(`\x1b[36m [↻] Restarting import map resolution with ${Object.keys(resolutions).length} pinned resolution(s)...\x1b[0m`);
123+
generator = createGenerator(inputMap, resolutions);
237124
for (const key of Object.keys(failed)) delete failed[key];
238125
for (let dep of deps) {
239126
if (dep[0] == 'tar-fs' || isUnresolvableOnCDN(dep) || !!generator.map.imports[dep[0]]) continue;
@@ -267,21 +154,18 @@ export async function generateImportMap (packageName) {
267154
inputMap = JSON.parse((await cachedImportMap.read()).replace(/esm:\/\//g, 'https://')); // replace esm to make generator install again
268155
}
269156
const resolutions = {};
270-
const scopedResolutions = Object.assign({}, inputMap?._scopedResolutions || {});
271-
let generator = createGenerator(inputMap, resolutions, scopedResolutions);
157+
let generator = createGenerator(inputMap, resolutions);
272158
const failed = inputMap?._failed || {};
273159
generator = await installDeps(
274160
generator,
275161
Object.entries(pkg.config.dependencies || {}).filter(([dep]) => !dep.match(/lively(\.|-)/)),
276162
failed,
277163
resolutions,
278-
inputMap,
279-
scopedResolutions
164+
inputMap
280165
);
281166
const importMap = JSON.parse(JSON.stringify(generator.getMap()).replace(/https:\/\//g, 'esm://'))
282167
if (!obj.isEmpty(failed)) importMap._failed = failed;
283168
if (!obj.isEmpty(resolutions)) importMap._resolutions = resolutions;
284-
if (!obj.isEmpty(scopedResolutions)) importMap._scopedResolutions = scopedResolutions;
285169
if (!obj.isEmpty(importMap)) await cachedImportMap.writeJson(importMap);
286170
else if (inputMap) { await cachedImportMap.remove() }
287171
return importMap;

0 commit comments

Comments
 (0)