@thoughtbot/superglue 2.0.0-alpha.4 → 2.0.0-alpha.7

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.
@@ -6060,9 +6060,214 @@ var prependToFragment = (0, import_toolkit.createAction)(
6060
6060
  }
6061
6061
  );
6062
6062
 
6063
+ // lib/utils/proxy.ts
6064
+ var ORIGINAL_TARGET = Symbol("@@originalTarget");
6065
+ var ARRAY_GETTER_METHODS = /* @__PURE__ */ new Set([
6066
+ Symbol.iterator,
6067
+ "at",
6068
+ "concat",
6069
+ "entries",
6070
+ "every",
6071
+ "filter",
6072
+ "find",
6073
+ "findIndex",
6074
+ "flat",
6075
+ "flatMap",
6076
+ "forEach",
6077
+ "includes",
6078
+ "indexOf",
6079
+ "join",
6080
+ "keys",
6081
+ "lastIndexOf",
6082
+ "map",
6083
+ "reduce",
6084
+ "reduceRight",
6085
+ "slice",
6086
+ "some",
6087
+ "toString",
6088
+ "values"
6089
+ ]);
6090
+ var ARRAY_SETTER_METHODS = /* @__PURE__ */ new Set([
6091
+ "copyWithin",
6092
+ "fill",
6093
+ "pop",
6094
+ "push",
6095
+ "reverse",
6096
+ "shift",
6097
+ "sort",
6098
+ "splice",
6099
+ "unshift"
6100
+ ]);
6101
+ function isArraySetter(prop) {
6102
+ return ARRAY_SETTER_METHODS.has(prop);
6103
+ }
6104
+ function isArrayGetter(prop) {
6105
+ return ARRAY_GETTER_METHODS.has(prop);
6106
+ }
6107
+ function convertToInt(prop) {
6108
+ if (typeof prop === "symbol") return null;
6109
+ const num = Number(prop);
6110
+ return Number.isInteger(num) ? num : null;
6111
+ }
6112
+ function isFragmentReference(value) {
6113
+ return !!value && typeof value === "object" && "__id" in value && typeof value.__id === "string";
6114
+ }
6115
+ function createArrayProxy(arrayData, fragments, dependencies, proxyCache) {
6116
+ if (proxyCache && proxyCache.has(arrayData)) {
6117
+ return proxyCache.get(arrayData);
6118
+ }
6119
+ const proxy = new Proxy(arrayData, {
6120
+ get(target, prop) {
6121
+ if (prop === ORIGINAL_TARGET) {
6122
+ return target;
6123
+ }
6124
+ if (isArrayGetter(prop)) {
6125
+ const method = target[prop];
6126
+ if (typeof method === "function") {
6127
+ return function(...args) {
6128
+ return Reflect.apply(method, proxy, args);
6129
+ };
6130
+ }
6131
+ return method;
6132
+ }
6133
+ if (isArraySetter(prop)) {
6134
+ throw new Error(
6135
+ `Cannot mutate proxy array. Use Redux actions to update state.`
6136
+ );
6137
+ }
6138
+ const index = convertToInt(prop);
6139
+ if (index !== null && index >= 0 && index < target.length) {
6140
+ const item = target[index];
6141
+ if (isFragmentReference(item)) {
6142
+ dependencies.add(item.__id);
6143
+ const fragmentData = fragments.current[item.__id];
6144
+ if (!fragmentData) {
6145
+ throw new Error(`Fragment with id "${item.__id}" not found`);
6146
+ }
6147
+ return createProxy(fragmentData, fragments, dependencies, proxyCache);
6148
+ }
6149
+ if (typeof item === "object" && item !== null) {
6150
+ if ("$$typeof" in item) {
6151
+ return item;
6152
+ } else {
6153
+ return createProxy(
6154
+ item,
6155
+ fragments,
6156
+ dependencies,
6157
+ proxyCache
6158
+ );
6159
+ }
6160
+ }
6161
+ return item;
6162
+ }
6163
+ return Reflect.get(target, prop);
6164
+ },
6165
+ has(target, prop) {
6166
+ if (prop === ORIGINAL_TARGET) {
6167
+ return true;
6168
+ }
6169
+ return Reflect.has(target, prop);
6170
+ },
6171
+ set() {
6172
+ throw new Error(
6173
+ "Cannot mutate proxy array. Use Redux actions to update state."
6174
+ );
6175
+ },
6176
+ deleteProperty() {
6177
+ throw new Error(
6178
+ "Cannot delete properties on proxy array. Use Redux actions to update state."
6179
+ );
6180
+ },
6181
+ defineProperty() {
6182
+ throw new Error(
6183
+ "Cannot define properties on proxy array. Use Redux actions to update state."
6184
+ );
6185
+ }
6186
+ });
6187
+ if (proxyCache) {
6188
+ proxyCache.set(arrayData, proxy);
6189
+ }
6190
+ return proxy;
6191
+ }
6192
+ function createObjectProxy(objectData, fragments, dependencies, proxyCache) {
6193
+ if (proxyCache && proxyCache.has(objectData)) {
6194
+ return proxyCache.get(objectData);
6195
+ }
6196
+ const proxy = new Proxy(objectData, {
6197
+ get(target, prop) {
6198
+ if (prop === ORIGINAL_TARGET) {
6199
+ return target;
6200
+ }
6201
+ const value = target[prop];
6202
+ if (isFragmentReference(value)) {
6203
+ dependencies.add(value.__id);
6204
+ const fragmentData = fragments.current[value.__id];
6205
+ if (!fragmentData) {
6206
+ throw new Error(`Fragment with id "${value.__id}" not found`);
6207
+ }
6208
+ return createProxy(fragmentData, fragments, dependencies, proxyCache);
6209
+ }
6210
+ if (typeof value === "object" && value !== null) {
6211
+ if ("$$typeof" in value) {
6212
+ return value;
6213
+ } else if (Array.isArray(value)) {
6214
+ return createArrayProxy(value, fragments, dependencies, proxyCache);
6215
+ } else {
6216
+ return createObjectProxy(value, fragments, dependencies, proxyCache);
6217
+ }
6218
+ }
6219
+ return value;
6220
+ },
6221
+ has(target, prop) {
6222
+ if (prop === ORIGINAL_TARGET) {
6223
+ return true;
6224
+ }
6225
+ return Reflect.has(target, prop);
6226
+ },
6227
+ set() {
6228
+ throw new Error(
6229
+ "Cannot mutate proxy object. Use Redux actions to update state."
6230
+ );
6231
+ },
6232
+ deleteProperty() {
6233
+ throw new Error(
6234
+ "Cannot delete properties on proxy object. Use Redux actions to update state."
6235
+ );
6236
+ },
6237
+ defineProperty() {
6238
+ throw new Error(
6239
+ "Cannot define properties on proxy object. Use Redux actions to update state."
6240
+ );
6241
+ }
6242
+ });
6243
+ if (proxyCache) {
6244
+ proxyCache.set(objectData, proxy);
6245
+ }
6246
+ return proxy;
6247
+ }
6248
+ function createProxy(content, fragments, dependencies, proxyCache) {
6249
+ if (!content || typeof content !== "object") {
6250
+ return content;
6251
+ }
6252
+ if ("$$typeof" in content) {
6253
+ return content;
6254
+ }
6255
+ if (Array.isArray(content)) {
6256
+ return createArrayProxy(content, fragments, dependencies, proxyCache);
6257
+ }
6258
+ return createObjectProxy(content, fragments, dependencies, proxyCache);
6259
+ }
6260
+ function unproxy(proxy) {
6261
+ if (proxy && typeof proxy === "object" && ORIGINAL_TARGET in proxy) {
6262
+ return proxy[ORIGINAL_TARGET];
6263
+ }
6264
+ return proxy;
6265
+ }
6266
+
6063
6267
  // lib/action_creators/requests.ts
6064
6268
  function handleFetchErr(err, fetchArgs, dispatch) {
6065
6269
  dispatch(superglueError({ message: err.message }));
6270
+ console.error(err);
6066
6271
  throw err;
6067
6272
  }
6068
6273
  function buildMeta(pageKey, page, state, rsp, fetchArgs) {
@@ -6101,7 +6306,7 @@ var remote = (path, {
6101
6306
  dispatch(beforeRemote({ currentPageKey, fetchArgs }));
6102
6307
  dispatch(beforeFetch({ fetchArgs }));
6103
6308
  return fetch(...fetchArgs).then(parseResponse).then(({ rsp, json }) => {
6104
- const { superglue, pages = {} } = getState();
6309
+ const { superglue, pages = {}, fragments } = getState();
6105
6310
  let pageKey;
6106
6311
  if (targetPageKey === void 0) {
6107
6312
  const isGet = fetchArgs[1].method === "GET";
@@ -6134,7 +6339,15 @@ the same page. Or if you're sure you want to proceed, use force: true.
6134
6339
  }
6135
6340
  }
6136
6341
  dispatch(receiveResponse({ pageKey, response: json }));
6137
- const page = beforeSave(pages[pageKey], json);
6342
+ const existingPage = createProxy(
6343
+ pages[pageKey],
6344
+ { current: fragments },
6345
+ /* @__PURE__ */ new Set(),
6346
+ /* @__PURE__ */ new WeakMap()
6347
+ );
6348
+ const page = JSON.parse(
6349
+ JSON.stringify(beforeSave(existingPage, json))
6350
+ );
6138
6351
  return dispatch(saveAndProcessPage(pageKey, page)).then(() => meta);
6139
6352
  }).catch((e) => handleFetchErr(e, fetchArgs, dispatch));
6140
6353
  };
@@ -6300,210 +6513,6 @@ var handleStreamResponse = (response) => {
6300
6513
  };
6301
6514
  };
6302
6515
 
6303
- // lib/utils/proxy.ts
6304
- var ORIGINAL_TARGET = Symbol("@@originalTarget");
6305
- var ARRAY_GETTER_METHODS = /* @__PURE__ */ new Set([
6306
- Symbol.iterator,
6307
- "at",
6308
- "concat",
6309
- "entries",
6310
- "every",
6311
- "filter",
6312
- "find",
6313
- "findIndex",
6314
- "flat",
6315
- "flatMap",
6316
- "forEach",
6317
- "includes",
6318
- "indexOf",
6319
- "join",
6320
- "keys",
6321
- "lastIndexOf",
6322
- "map",
6323
- "reduce",
6324
- "reduceRight",
6325
- "slice",
6326
- "some",
6327
- "toString",
6328
- "values"
6329
- ]);
6330
- var ARRAY_SETTER_METHODS = /* @__PURE__ */ new Set([
6331
- "copyWithin",
6332
- "fill",
6333
- "pop",
6334
- "push",
6335
- "reverse",
6336
- "shift",
6337
- "sort",
6338
- "splice",
6339
- "unshift"
6340
- ]);
6341
- function isArraySetter(prop) {
6342
- return ARRAY_SETTER_METHODS.has(prop);
6343
- }
6344
- function isArrayGetter(prop) {
6345
- return ARRAY_GETTER_METHODS.has(prop);
6346
- }
6347
- function convertToInt(prop) {
6348
- if (typeof prop === "symbol") return null;
6349
- const num = Number(prop);
6350
- return Number.isInteger(num) ? num : null;
6351
- }
6352
- function isFragmentReference(value) {
6353
- return !!value && typeof value === "object" && "__id" in value && typeof value.__id === "string";
6354
- }
6355
- function createArrayProxy(arrayData, fragments, dependencies, proxyCache) {
6356
- if (proxyCache && proxyCache.has(arrayData)) {
6357
- return proxyCache.get(arrayData);
6358
- }
6359
- const proxy = new Proxy(arrayData, {
6360
- get(target, prop) {
6361
- if (prop === ORIGINAL_TARGET) {
6362
- return target;
6363
- }
6364
- if (isArrayGetter(prop)) {
6365
- const method = target[prop];
6366
- if (typeof method === "function") {
6367
- return function(...args) {
6368
- return Reflect.apply(method, proxy, args);
6369
- };
6370
- }
6371
- return method;
6372
- }
6373
- if (isArraySetter(prop)) {
6374
- throw new Error(
6375
- `Cannot mutate proxy array. Use Redux actions to update state.`
6376
- );
6377
- }
6378
- const index = convertToInt(prop);
6379
- if (index !== null && index >= 0 && index < target.length) {
6380
- const item = target[index];
6381
- if (isFragmentReference(item)) {
6382
- dependencies.add(item.__id);
6383
- const fragmentData = fragments.current[item.__id];
6384
- if (!fragmentData) {
6385
- throw new Error(`Fragment with id "${item.__id}" not found`);
6386
- }
6387
- return createProxy(fragmentData, fragments, dependencies, proxyCache);
6388
- }
6389
- if (typeof item === "object" && item !== null) {
6390
- if ("$$typeof" in item) {
6391
- return item;
6392
- } else {
6393
- return createProxy(
6394
- item,
6395
- fragments,
6396
- dependencies,
6397
- proxyCache
6398
- );
6399
- }
6400
- }
6401
- return item;
6402
- }
6403
- return Reflect.get(target, prop);
6404
- },
6405
- has(target, prop) {
6406
- if (prop === ORIGINAL_TARGET) {
6407
- return true;
6408
- }
6409
- return Reflect.has(target, prop);
6410
- },
6411
- set() {
6412
- throw new Error(
6413
- "Cannot mutate proxy array. Use Redux actions to update state."
6414
- );
6415
- },
6416
- deleteProperty() {
6417
- throw new Error(
6418
- "Cannot delete properties on proxy array. Use Redux actions to update state."
6419
- );
6420
- },
6421
- defineProperty() {
6422
- throw new Error(
6423
- "Cannot define properties on proxy array. Use Redux actions to update state."
6424
- );
6425
- }
6426
- });
6427
- if (proxyCache) {
6428
- proxyCache.set(arrayData, proxy);
6429
- }
6430
- return proxy;
6431
- }
6432
- function createObjectProxy(objectData, fragments, dependencies, proxyCache) {
6433
- if (proxyCache && proxyCache.has(objectData)) {
6434
- return proxyCache.get(objectData);
6435
- }
6436
- const proxy = new Proxy(objectData, {
6437
- get(target, prop) {
6438
- if (prop === ORIGINAL_TARGET) {
6439
- return target;
6440
- }
6441
- const value = target[prop];
6442
- if (isFragmentReference(value)) {
6443
- dependencies.add(value.__id);
6444
- const fragmentData = fragments.current[value.__id];
6445
- if (!fragmentData) {
6446
- throw new Error(`Fragment with id "${value.__id}" not found`);
6447
- }
6448
- return createProxy(fragmentData, fragments, dependencies, proxyCache);
6449
- }
6450
- if (typeof value === "object" && value !== null) {
6451
- if ("$$typeof" in value) {
6452
- return value;
6453
- } else if (Array.isArray(value)) {
6454
- return createArrayProxy(value, fragments, dependencies, proxyCache);
6455
- } else {
6456
- return createObjectProxy(value, fragments, dependencies, proxyCache);
6457
- }
6458
- }
6459
- return value;
6460
- },
6461
- has(target, prop) {
6462
- if (prop === ORIGINAL_TARGET) {
6463
- return true;
6464
- }
6465
- return Reflect.has(target, prop);
6466
- },
6467
- set() {
6468
- throw new Error(
6469
- "Cannot mutate proxy object. Use Redux actions to update state."
6470
- );
6471
- },
6472
- deleteProperty() {
6473
- throw new Error(
6474
- "Cannot delete properties on proxy object. Use Redux actions to update state."
6475
- );
6476
- },
6477
- defineProperty() {
6478
- throw new Error(
6479
- "Cannot define properties on proxy object. Use Redux actions to update state."
6480
- );
6481
- }
6482
- });
6483
- if (proxyCache) {
6484
- proxyCache.set(objectData, proxy);
6485
- }
6486
- return proxy;
6487
- }
6488
- function createProxy(content, fragments, dependencies, proxyCache) {
6489
- if (!content || typeof content !== "object") {
6490
- return content;
6491
- }
6492
- if ("$$typeof" in content) {
6493
- return content;
6494
- }
6495
- if (Array.isArray(content)) {
6496
- return createArrayProxy(content, fragments, dependencies, proxyCache);
6497
- }
6498
- return createObjectProxy(content, fragments, dependencies, proxyCache);
6499
- }
6500
- function unproxy(proxy) {
6501
- if (proxy && typeof proxy === "object" && ORIGINAL_TARGET in proxy) {
6502
- return proxy[ORIGINAL_TARGET];
6503
- }
6504
- return proxy;
6505
- }
6506
-
6507
6516
  // lib/action_creators/index.ts
6508
6517
  function fetchDeferments(pageKey, defers = []) {
6509
6518
  pageKey = urlToPageKey(pageKey);
@@ -6619,8 +6628,6 @@ function useContent(fragmentRef, options) {
6619
6628
  const superglueState = useSuperglue();
6620
6629
  const currentPageKey = superglueState.currentPageKey;
6621
6630
  const dependencies = (0, import_react.useRef)(/* @__PURE__ */ new Set());
6622
- const fragmentsHookRef = (0, import_react.useRef)({});
6623
- const proxyCache = (0, import_react.useRef)(/* @__PURE__ */ new WeakMap());
6624
6631
  const fragmentId = typeof fragmentRef === "string" ? fragmentRef : fragmentRef?.__id;
6625
6632
  const sourceData = (0, import_react_redux.useSelector)((state) => {
6626
6633
  if (fragmentId) {
@@ -6629,7 +6636,7 @@ function useContent(fragmentRef, options) {
6629
6636
  return state.pages[currentPageKey].data;
6630
6637
  }
6631
6638
  });
6632
- const fragments = (0, import_react_redux.useSelector)(
6639
+ const trackedFragments = (0, import_react_redux.useSelector)(
6633
6640
  (state) => state.fragments,
6634
6641
  (oldFragments, newFragments) => {
6635
6642
  if (oldFragments === newFragments) {
@@ -6642,9 +6649,10 @@ function useContent(fragmentRef, options) {
6642
6649
  });
6643
6650
  }
6644
6651
  );
6645
- fragmentsHookRef.current = fragments;
6646
6652
  const raiseOnMissing = !(options?.optional ?? false);
6653
+ const store = (0, import_react_redux.useStore)();
6647
6654
  const proxy = (0, import_react.useMemo)(() => {
6655
+ const proxyCache = /* @__PURE__ */ new WeakMap();
6648
6656
  if (fragmentId && !sourceData) {
6649
6657
  if (raiseOnMissing) {
6650
6658
  throw new Error(`Fragment with id "${fragmentId}" not found`);
@@ -6654,11 +6662,11 @@ function useContent(fragmentRef, options) {
6654
6662
  }
6655
6663
  return createProxy(
6656
6664
  sourceData,
6657
- fragmentsHookRef,
6665
+ { current: store.getState().fragments },
6658
6666
  dependencies.current,
6659
- proxyCache.current
6667
+ proxyCache
6660
6668
  );
6661
- }, [sourceData, options?.optional]);
6669
+ }, [sourceData, trackedFragments, options?.optional]);
6662
6670
  return proxy;
6663
6671
  }
6664
6672
  function unproxy2(proxy) {
@@ -7140,7 +7148,21 @@ var rootReducer = {
7140
7148
  };
7141
7149
 
7142
7150
  // lib/index.tsx
7143
- var cable = (0, import_actioncable.createConsumer)();
7151
+ function getConfig(name) {
7152
+ if (typeof document !== "undefined") {
7153
+ const element = document.head.querySelector(
7154
+ `meta[name='action-cable-${name}']`
7155
+ );
7156
+ if (element) {
7157
+ return element.getAttribute("content") || "/cable";
7158
+ } else {
7159
+ return "/cable";
7160
+ }
7161
+ } else {
7162
+ return "/cable";
7163
+ }
7164
+ }
7165
+ var cable = (0, import_actioncable.createConsumer)(getConfig("url"));
7144
7166
  var hasWindow2 = typeof window !== "undefined";
7145
7167
  var createHistory = () => {
7146
7168
  if (hasWindow2) {