ember-vite-hmr 2.2.4 → 2.3.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/dist/lib/babel-plugin.js +71 -4
- package/dist/lib/hmr.js +25 -1
- package/package.json +5 -5
package/dist/lib/babel-plugin.js
CHANGED
|
@@ -221,17 +221,73 @@ export default function hotReplaceAst(babel) {
|
|
|
221
221
|
if (import.meta.hot) {
|
|
222
222
|
import.meta.hot.data._proxy = this;
|
|
223
223
|
}
|
|
224
|
+
// Bound methods are cached per-delegate (not per-proxy) so identity
|
|
225
|
+
// stays stable across repeated reads of the same delegate (e.g.
|
|
226
|
+
// {{on "click" this.svc.handler}} comparing args by reference), while
|
|
227
|
+
// naturally invalidating once a delegate is swapped out on HMR accept.
|
|
228
|
+
const boundMethods = new WeakMap();
|
|
224
229
|
return new Proxy(this, {
|
|
225
|
-
get(target, prop) {
|
|
230
|
+
get(target, prop, receiver) {
|
|
226
231
|
if (prop === '_delegate') {
|
|
227
232
|
return target._delegate;
|
|
228
233
|
}
|
|
229
|
-
|
|
234
|
+
// A subclass of this service (see the Reflect.get fallback
|
|
235
|
+
// below) may override a method the base delegate class also
|
|
236
|
+
// defines. Since 'prop in delegate' walks the delegate's
|
|
237
|
+
// *entire* prototype chain, it would match the base
|
|
238
|
+
// implementation before the subclass's own override ever
|
|
239
|
+
// gets a chance -- so look for an own property between
|
|
240
|
+
// target's dynamic prototype and this proxy's own prototype
|
|
241
|
+
// first, and prefer it over the delegate.
|
|
242
|
+
let proto = Object.getPrototypeOf(target);
|
|
243
|
+
while (proto && proto !== ${proxyClassName}.prototype) {
|
|
244
|
+
if (Object.prototype.hasOwnProperty.call(proto, prop)) {
|
|
245
|
+
return Reflect.get(target, prop, receiver);
|
|
246
|
+
}
|
|
247
|
+
proto = Object.getPrototypeOf(proto);
|
|
248
|
+
}
|
|
249
|
+
const delegate = target._delegate;
|
|
250
|
+
// Methods invoked via normal member-call syntax (service.method())
|
|
251
|
+
// bind 'this' to whatever object the property access happened on
|
|
252
|
+
// -- the proxy, here -- not to the delegate. That breaks native
|
|
253
|
+
// private fields, whose storage lives only on the concrete
|
|
254
|
+
// delegate instance, so delegate-owned methods are explicitly
|
|
255
|
+
// bound to the delegate.
|
|
256
|
+
if (prop in delegate) {
|
|
257
|
+
const value = delegate[prop];
|
|
258
|
+
if (typeof value === 'function') {
|
|
259
|
+
let cache = boundMethods.get(delegate);
|
|
260
|
+
if (!cache) {
|
|
261
|
+
cache = new Map();
|
|
262
|
+
boundMethods.set(delegate, cache);
|
|
263
|
+
}
|
|
264
|
+
let bound = cache.get(prop);
|
|
265
|
+
if (!bound) {
|
|
266
|
+
bound = value.bind(delegate);
|
|
267
|
+
cache.set(prop, bound);
|
|
268
|
+
}
|
|
269
|
+
return bound;
|
|
270
|
+
}
|
|
271
|
+
return value;
|
|
272
|
+
}
|
|
273
|
+
// Not on the delegate: fall through to the proxy's own real
|
|
274
|
+
// prototype chain, which covers methods declared on a subclass
|
|
275
|
+
// of this service (the subclass never went through this babel
|
|
276
|
+
// transform itself, since it doesn't extend Service directly).
|
|
277
|
+
return Reflect.get(target, prop, receiver);
|
|
230
278
|
},
|
|
231
279
|
set(target, prop, value) {
|
|
232
280
|
target._delegate[prop] = value;
|
|
233
281
|
return true;
|
|
234
282
|
},
|
|
283
|
+
defineProperty(target, prop, descriptor) {
|
|
284
|
+
// A subclass's own class fields are installed via
|
|
285
|
+
// [[DefineOwnProperty]] against whatever 'this' super() returned
|
|
286
|
+
// (this proxy), bypassing the 'set' trap entirely. Route them to
|
|
287
|
+
// the delegate too, so subclass state lives alongside the rest
|
|
288
|
+
// of the service's state instead of stranded on the proxy target.
|
|
289
|
+
return Reflect.defineProperty(target._delegate, prop, descriptor);
|
|
290
|
+
},
|
|
235
291
|
});
|
|
236
292
|
`)();
|
|
237
293
|
const willDestroyBody = babelTemplate.statements(`
|
|
@@ -309,8 +365,19 @@ export default function hotReplaceAst(babel) {
|
|
|
309
365
|
continue;
|
|
310
366
|
}
|
|
311
367
|
|
|
312
|
-
// Skip
|
|
313
|
-
|
|
368
|
+
// Skip function properties that the new implementation also
|
|
369
|
+
// declares (a fresh redefinition should win over the old
|
|
370
|
+
// one). But a function-valued property the new
|
|
371
|
+
// implementation *doesn't* declare at all isn't a stale
|
|
372
|
+
// redefinition -- it's state a subclass installed on the
|
|
373
|
+
// delegate directly (subclasses of this service never go
|
|
374
|
+
// through this transform themselves, since their
|
|
375
|
+
// superclass isn't literally named Service; their own
|
|
376
|
+
// class fields land on the delegate via the proxy's
|
|
377
|
+
// defineProperty trap instead). Dropping it here would
|
|
378
|
+
// silently break e.g. an arrow-function class field on a
|
|
379
|
+
// subclass across a base-class HMR swap.
|
|
380
|
+
if (typeof previousValue === 'function' && hasOwnDefault) {
|
|
314
381
|
continue;
|
|
315
382
|
}
|
|
316
383
|
|
package/dist/lib/hmr.js
CHANGED
|
@@ -141,6 +141,17 @@ shadowManager.create = function (owner, definition, vmArgs) {
|
|
|
141
141
|
capturedArgsStack.pop();
|
|
142
142
|
}
|
|
143
143
|
};
|
|
144
|
+
// Glimmer's debug render tree normally adds one 'component' node per
|
|
145
|
+
// invoked component instance (see VM_GET_COMPONENT_SELF_OP). Returning no
|
|
146
|
+
// nodes here suppresses that node for HotComponent itself, so only the
|
|
147
|
+
// real, curried target component (invoked in HotComponent's own template)
|
|
148
|
+
// shows up in ember-inspector's component tree - this is the same hook
|
|
149
|
+
// Ember core uses internally to keep its own {{outlet}}/{{mount}} wrapper
|
|
150
|
+
// machinery out of (or relabeled in) that tree (see OutletComponentManager
|
|
151
|
+
// and MountManager in ember-source).
|
|
152
|
+
shadowManager.getDebugCustomRenderTree = function () {
|
|
153
|
+
return [];
|
|
154
|
+
};
|
|
144
155
|
setInternalComponentManager(shadowManager, HotComponent);
|
|
145
156
|
`;
|
|
146
157
|
const cachedYields = {};
|
|
@@ -188,7 +199,8 @@ export function hmr(enableViteHmrForModes = ['development']) {
|
|
|
188
199
|
return {
|
|
189
200
|
name: 'hmr-plugin',
|
|
190
201
|
enforce: 'post',
|
|
191
|
-
config(
|
|
202
|
+
config(config, env) {
|
|
203
|
+
var _a;
|
|
192
204
|
// The per-component hot wrapper (see getHotComponent) imports the first
|
|
193
205
|
// four of these, but it is generated/served on demand, so it is never
|
|
194
206
|
// part of the static module graph Vite's dependency scanner crawls on
|
|
@@ -207,6 +219,18 @@ export function hmr(enableViteHmrForModes = ['development']) {
|
|
|
207
219
|
if (!enableViteHmrForModes.includes(env.mode)) {
|
|
208
220
|
return;
|
|
209
221
|
}
|
|
222
|
+
// With `optimizeDeps.noDiscovery: true`, Vite never scans the app's own
|
|
223
|
+
// source, so nothing else pulls these same glimmer subpaths into the
|
|
224
|
+
// optimizer. Forcing them into `include` then creates a second,
|
|
225
|
+
// separately pre-bundled copy of the glimmer VM alongside the
|
|
226
|
+
// unoptimized one the rest of the (unscanned) app actually uses,
|
|
227
|
+
// leading to "The global context for Glimmer VM was not set" (#554).
|
|
228
|
+
// There's nothing useful this hook can pre-declare in that mode, so
|
|
229
|
+
// skip it entirely rather than fight the user's own dep-optimization
|
|
230
|
+
// config.
|
|
231
|
+
if ((_a = config.optimizeDeps) === null || _a === void 0 ? void 0 : _a.noDiscovery) {
|
|
232
|
+
return;
|
|
233
|
+
}
|
|
210
234
|
return {
|
|
211
235
|
optimizeDeps: {
|
|
212
236
|
include: [
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "ember-vite-hmr",
|
|
3
|
-
"version": "2.
|
|
3
|
+
"version": "2.3.0",
|
|
4
4
|
"private": false,
|
|
5
5
|
"description": "provides hmr support for ember apps",
|
|
6
6
|
"keywords": [
|
|
@@ -14,7 +14,8 @@
|
|
|
14
14
|
"author": "Patrick Pircher",
|
|
15
15
|
"exports": {
|
|
16
16
|
".": {
|
|
17
|
-
"
|
|
17
|
+
"node": "./dist/lib/hmr.js",
|
|
18
|
+
"default": null
|
|
18
19
|
},
|
|
19
20
|
"./*": {
|
|
20
21
|
"types": "./declarations/*.d.ts",
|
|
@@ -22,7 +23,6 @@
|
|
|
22
23
|
},
|
|
23
24
|
"./addon-main.js": "./addon-main.cjs"
|
|
24
25
|
},
|
|
25
|
-
"main": "dist/lib/hmr.js",
|
|
26
26
|
"typesVersions": {
|
|
27
27
|
"*": {
|
|
28
28
|
"*": [
|
|
@@ -38,7 +38,7 @@
|
|
|
38
38
|
"@babel/core": "^7.29.0",
|
|
39
39
|
"@babel/plugin-transform-typescript": "^7.28.6",
|
|
40
40
|
"@babel/traverse": "^7.29.0",
|
|
41
|
-
"@babel/types": "^
|
|
41
|
+
"@babel/types": "^7.28.5",
|
|
42
42
|
"@embroider/addon-shim": "^1.10.3",
|
|
43
43
|
"@glimmer/syntax": "^0.95.0",
|
|
44
44
|
"@types/supports-color": "^10.0.0",
|
|
@@ -52,7 +52,7 @@
|
|
|
52
52
|
"@babel/plugin-proposal-class-properties": "^7.16.7",
|
|
53
53
|
"@babel/plugin-proposal-decorators": "^7.28.0",
|
|
54
54
|
"@babel/plugin-transform-class-static-block": "^7.28.6",
|
|
55
|
-
"@babel/runtime": "^
|
|
55
|
+
"@babel/runtime": "^7.28.4",
|
|
56
56
|
"@embroider/addon-dev": "^8.3.0",
|
|
57
57
|
"@embroider/compat": "^4.1.20",
|
|
58
58
|
"@embroider/core": "^4.6.2",
|