@fedify/vocab-tools 2.4.0-dev.2054 → 2.4.0-dev.2063

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/src/class.ts CHANGED
@@ -19,8 +19,15 @@ const INTERNAL_RUNTIME_IMPORTS = [
19
19
  "normalizeJsonLdIris",
20
20
  ].join(",\n ");
21
21
  const PORTABLE_DEREFERENCE_IMPORTS = [
22
+ "copyPortableProvenance",
22
23
  "dereferencePortableIri",
24
+ "isCompatibleEf61Iri",
25
+ "isInPortableChain",
23
26
  "isPortableIri",
27
+ "isUnsecuredPortableObject",
28
+ "recordPortableReferrer",
29
+ "rejectPortableChainReference",
30
+ "warnUnverifiableEmbeddedObject",
24
31
  ].join(",\n ");
25
32
  const SIGNED_REPRESENTATION_IMPORTS = [
26
33
  "enterSignedValueScope",
@@ -246,6 +246,7 @@ export async function* generateCloner(
246
246
  { id: values.id ?? this.id },
247
247
  options
248
248
  );
249
+ copyPortableProvenance(this, clone);
249
250
  `;
250
251
  } else {
251
252
  yield `const clone = super.clone(values, options) as unknown as ${type.name};`;
package/src/property.ts CHANGED
@@ -97,6 +97,10 @@ async function* generateProperty(
97
97
  tracerProvider,
98
98
  gateways: options.gateways,
99
99
  verifyPortableObject: options.verifyPortableObject,
100
+ referrer: {
101
+ object: this,
102
+ property: ${JSON.stringify(property.uri)},
103
+ },
100
104
  suppressError: options.suppressError,
101
105
  crossOrigin: options.crossOrigin,
102
106
  span,
@@ -128,6 +132,11 @@ async function* generateProperty(
128
132
  }
129
133
  }
130
134
  const lookupUrl = formatIri(url);
135
+ const inPortableChain = isInPortableChain(this);
136
+ if (inPortableChain && isCompatibleEf61Iri(url)) {
137
+ span.end();
138
+ return rejectPortableChainReference(lookupUrl, options.crossOrigin);
139
+ }
131
140
  let fetchResult: RemoteDocument;
132
141
  try {
133
142
  fetchResult = await documentLoader(lookupUrl);
@@ -153,6 +162,17 @@ async function* generateProperty(
153
162
  document,
154
163
  { documentLoader, contextLoader, tracerProvider, baseUrl }
155
164
  );
165
+ if (
166
+ inPortableChain &&
167
+ (isCompatibleEf61Iri(documentUrl) ||
168
+ (obj.id != null &&
169
+ (isPortableIri(obj.id) || isCompatibleEf61Iri(obj.id))))
170
+ ) {
171
+ return rejectPortableChainReference(
172
+ documentUrl,
173
+ options.crossOrigin,
174
+ );
175
+ }
156
176
  if (obj?.id != null && !isTrustedIriOrigin(options, obj.id, baseUrl)) {
157
177
  if (options.crossOrigin === "throw") {
158
178
  throw new Error(
@@ -319,10 +339,21 @@ async function* generateProperty(
319
339
  if (this.${await getFieldName(property.uri)}.length < 1) return null;
320
340
  let v = this.${await getFieldName(property.uri)}[0];
321
341
  if (!(v instanceof URL) &&
322
- v.id != null &&
323
- !isTrustedIriOrigin(options, v.id, ${trustOwner}) &&
324
342
  !this.${await getFieldName(property.uri, "#_trust")}.has(0)) {
325
- v = v.id;
343
+ if (v.id == null) {
344
+ if (isUnsecuredPortableObject(this)) {
345
+ warnUnverifiableEmbeddedObject(this, ${
346
+ JSON.stringify(property.uri)
347
+ });
348
+ return null;
349
+ }
350
+ } else if (
351
+ !isTrustedIriOrigin(options, v.id, ${trustOwner}) ||
352
+ isUnsecuredPortableObject(this) ||
353
+ (isInPortableChain(this) && isCompatibleEf61Iri(v.id))
354
+ ) {
355
+ v = v.id;
356
+ }
326
357
  }
327
358
  if (v instanceof URL) {
328
359
  const fetched =
@@ -331,6 +362,9 @@ async function* generateProperty(
331
362
  this.${await getFieldName(property.uri)}[0] = fetched;
332
363
  this.${await getFieldName(property.uri, "#_trust")}.add(0);
333
364
  this._cachedJsonLd = undefined;
365
+ recordPortableReferrer(this, fetched, ${
366
+ JSON.stringify(property.uri)
367
+ });
334
368
  return fetched;
335
369
  }
336
370
  `;
@@ -360,9 +394,11 @@ async function* generateProperty(
360
394
  }
361
395
  yield `
362
396
  if (v?.id != null &&
363
- ${
397
+ ((${
364
398
  type.trustEmbeddedObjects === false ? "" : "this.id != null && "
365
- }!isTrustedIriOrigin(options, v.id, ${trustOwner}) &&
399
+ }!isTrustedIriOrigin(options, v.id, ${trustOwner})) ||
400
+ isUnsecuredPortableObject(this) ||
401
+ (isInPortableChain(this) && isCompatibleEf61Iri(v.id))) &&
366
402
  !this.${await getFieldName(property.uri, "#_trust")}.has(0)) {
367
403
  if (options.crossOrigin === "throw") {
368
404
  throw new Error(
@@ -370,7 +406,7 @@ async function* generateProperty(
370
406
  "origin than the property owner's @id (" + ${
371
407
  type.trustEmbeddedObjects === false
372
408
  ? '"untrusted metadata"'
373
- : "this.id.href"
409
+ : "(this.id?.href ?? null)"
374
410
  } + "); " +
375
411
  "refusing to return the object. If you want to bypass this " +
376
412
  "check and are aware of the security implications, set the " +
@@ -386,11 +422,12 @@ async function* generateProperty(
386
422
  { objectId: v.id.href, parentObjectId: ${
387
423
  type.trustEmbeddedObjects === false
388
424
  ? '"untrusted metadata"'
389
- : "this.id.href"
425
+ : "(this.id?.href ?? null)"
390
426
  } },
391
427
  );
392
428
  return null;
393
429
  }
430
+ recordPortableReferrer(this, v, ${JSON.stringify(property.uri)});
394
431
  return v;
395
432
  }
396
433
  `;
@@ -437,10 +474,21 @@ async function* generateProperty(
437
474
  for (let i = 0; i < vs.length; i++) {
438
475
  let v = vs[i];
439
476
  if (!(v instanceof URL) &&
440
- v.id != null &&
441
- !isTrustedIriOrigin(options, v.id, ${trustOwner}) &&
442
477
  !this.${await getFieldName(property.uri, "#_trust")}.has(i)) {
443
- v = v.id;
478
+ if (v.id == null) {
479
+ if (isUnsecuredPortableObject(this)) {
480
+ warnUnverifiableEmbeddedObject(this, ${
481
+ JSON.stringify(property.uri)
482
+ });
483
+ continue;
484
+ }
485
+ } else if (
486
+ !isTrustedIriOrigin(options, v.id, ${trustOwner}) ||
487
+ isUnsecuredPortableObject(this) ||
488
+ (isInPortableChain(this) && isCompatibleEf61Iri(v.id))
489
+ ) {
490
+ v = v.id;
491
+ }
444
492
  }
445
493
  if (v instanceof URL) {
446
494
  const fetched =
@@ -449,6 +497,9 @@ async function* generateProperty(
449
497
  vs[i] = fetched;
450
498
  this.${await getFieldName(property.uri, "#_trust")}.add(i);
451
499
  this._cachedJsonLd = undefined;
500
+ recordPortableReferrer(this, fetched, ${
501
+ JSON.stringify(property.uri)
502
+ });
452
503
  yield fetched;
453
504
  continue;
454
505
  }
@@ -479,9 +530,11 @@ async function* generateProperty(
479
530
  }
480
531
  yield `
481
532
  if (v?.id != null &&
482
- ${
533
+ ((${
483
534
  type.trustEmbeddedObjects === false ? "" : "this.id != null && "
484
- }!isTrustedIriOrigin(options, v.id, ${trustOwner}) &&
535
+ }!isTrustedIriOrigin(options, v.id, ${trustOwner})) ||
536
+ isUnsecuredPortableObject(this) ||
537
+ (isInPortableChain(this) && isCompatibleEf61Iri(v.id))) &&
485
538
  !this.${await getFieldName(property.uri, "#_trust")}.has(i)) {
486
539
  if (options.crossOrigin === "throw") {
487
540
  throw new Error(
@@ -489,7 +542,7 @@ async function* generateProperty(
489
542
  "origin than the property owner's @id (" + ${
490
543
  type.trustEmbeddedObjects === false
491
544
  ? '"untrusted metadata"'
492
- : "this.id.href"
545
+ : "(this.id?.href ?? null)"
493
546
  } + "); " +
494
547
  "refusing to return the object. If you want to bypass this " +
495
548
  "check and are aware of the security implications, set the " +
@@ -505,11 +558,12 @@ async function* generateProperty(
505
558
  { objectId: v.id.href, parentObjectId: ${
506
559
  type.trustEmbeddedObjects === false
507
560
  ? '"untrusted metadata"'
508
- : "this.id.href"
561
+ : "(this.id?.href ?? null)"
509
562
  } },
510
563
  );
511
564
  continue;
512
565
  }
566
+ recordPortableReferrer(this, v, ${JSON.stringify(property.uri)});
513
567
  yield v;
514
568
  }
515
569
  }