Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 14 additions & 1 deletion CHANGES.md
Original file line number Diff line number Diff line change
Expand Up @@ -423,7 +423,21 @@ To be released.
identifiers (`_:b0`) against `options.baseUrl`; blank nodes are left
as `null` in the resulting instance's `id` field. [[#792]]

- Added the second-stage vocabulary types for [FEP-0837], economic
resource coordination in federated networks.
[[#775], [#817] by Samuel Brinkmann]

- Added `Agreement` class, representing the agreement reached between
parties responding to a `Proposal`, wrapped in an `Offer` and
finalized as the `result` of an `Accept`.
- Added `Commitment` class, representing a promised economic
transaction that references an `Intent` via `satisfies` and carries
the committed quantity via `resourceQuantity`.

[FEP-0837]: https://w3id.org/fep/0837
[#775]: https://github.com/fedify-dev/fedify/issues/775
[#790]: https://github.com/fedify-dev/fedify/issues/790
[#817]: https://github.com/fedify-dev/fedify/pull/817

### @fedify/vocab-tools

Expand Down Expand Up @@ -718,7 +732,6 @@ Released on April 28, 2026.
measure, with `unit` and `numericalValue` properties.

[FEP-044f]: https://w3id.org/fep/044f
[FEP-0837]: https://w3id.org/fep/0837
[#452]: https://github.com/fedify-dev/fedify/issues/452
[#578]: https://github.com/fedify-dev/fedify/issues/578
[#645]: https://github.com/fedify-dev/fedify/issues/645
Expand Down
1,230 changes: 1,219 additions & 11 deletions packages/vocab-tools/src/__snapshots__/class.test.ts.deno.snap

Large diffs are not rendered by default.

1,230 changes: 1,219 additions & 11 deletions packages/vocab-tools/src/__snapshots__/class.test.ts.node.snap

Large diffs are not rendered by default.

1,230 changes: 1,219 additions & 11 deletions packages/vocab-tools/src/__snapshots__/class.test.ts.snap

Large diffs are not rendered by default.

159 changes: 159 additions & 0 deletions packages/vocab/src/__snapshots__/vocab.test.ts.snap
Original file line number Diff line number Diff line change
Expand Up @@ -1794,6 +1794,165 @@ snapshot[`Deno.inspect(Multikey) [auto] 3`] = `
}'
`;

snapshot[`Deno.inspect(Agreement) [auto] 1`] = `
'Agreement {
id: URL "https://example.com/",
attachments: [ Object {}, Link {}, PropertyValue {} ],
attributions: [ Application {}, Group {}, Organization {}, Person {}, Service {} ],
audience: Object {},
contents: [ "hello", <en> "hello" ],
contexts: [ Object {}, Link {} ],
names: [ "hello", <en> "hello" ],
endTime: 2024-03-03T08:30:06.796196096Z,
generators: [ Object {}, Link {} ],
icon: Image {},
image: Image {},
replyTargets: [ Object {}, Link {} ],
locations: [ Object {}, Link {} ],
previews: [ Link {}, Object {} ],
published: 2024-03-03T08:30:06.796196096Z,
replies: Collection {},
shares: Collection {},
likes: Collection {},
emojiReactions: Collection {},
startTime: 2024-03-03T08:30:06.796196096Z,
summaries: [ "hello", <en> "hello" ],
tags: [ Object {}, Link {} ],
updated: 2024-03-03T08:30:06.796196096Z,
urls: [ URL "https://example.com/", Link {} ],
to: Object {},
bto: Object {},
cc: Object {},
bcc: Object {},
mediaType: "hello",
duration: PT1H,
sensitive: true,
source: Source {},
proof: DataIntegrityProof {},
interactionPolicy: InteractionPolicy {},
approvedBy: URL "https://example.com/",
likeAuthorization: LikeAuthorization {},
replyAuthorization: ReplyAuthorization {},
announceAuthorization: AnnounceAuthorization {},
stipulates: Commitment {},
stipulatesReciprocal: Commitment {}
}'
`;

snapshot[`Deno.inspect(Agreement) [auto] 2`] = `
'Agreement {
id: URL "https://example.com/",
attachments: [ URL "https://example.com/" ],
attribution: URL "https://example.com/",
audience: URL "https://example.com/",
contents: [ "hello", <en> "hello" ],
contexts: [ URL "https://example.com/" ],
names: [ "hello", <en> "hello" ],
endTime: 2024-03-03T08:30:06.796196096Z,
generators: [ URL "https://example.com/" ],
icon: URL "https://example.com/",
image: URL "https://example.com/",
replyTarget: URL "https://example.com/",
location: URL "https://example.com/",
preview: URL "https://example.com/",
published: 2024-03-03T08:30:06.796196096Z,
replies: URL "https://example.com/",
shares: URL "https://example.com/",
likes: URL "https://example.com/",
emojiReactions: URL "https://example.com/",
startTime: 2024-03-03T08:30:06.796196096Z,
summaries: [ "hello", <en> "hello" ],
tags: [ URL "https://example.com/" ],
updated: 2024-03-03T08:30:06.796196096Z,
urls: [ URL "https://example.com/", Link {} ],
to: URL "https://example.com/",
bto: URL "https://example.com/",
cc: URL "https://example.com/",
bcc: URL "https://example.com/",
mediaType: "hello",
duration: PT1H,
sensitive: true,
source: Source {},
proof: URL "https://example.com/",
interactionPolicy: InteractionPolicy {},
approvedBy: URL "https://example.com/",
likeAuthorization: URL "https://example.com/",
replyAuthorization: URL "https://example.com/",
announceAuthorization: URL "https://example.com/",
stipulates: Commitment {},
stipulatesReciprocal: Commitment {}
}'
`;

snapshot[`Deno.inspect(Agreement) [auto] 3`] = `
'Agreement {
id: URL "https://example.com/",
attachments: [ Object {}, Object {} ],
attributions: [ Application {}, Application {} ],
audiences: [ Object {}, Object {} ],
contents: [ "hello", "hello" ],
contexts: [ Object {}, Object {} ],
names: [ "hello", "hello" ],
endTime: 2024-03-03T08:30:06.796196096Z,
generators: [ Object {}, Object {} ],
icons: [ Image {}, Image {} ],
images: [ Image {}, Image {} ],
replyTargets: [ Object {}, Object {} ],
locations: [ Object {}, Object {} ],
previews: [ Link {}, Link {} ],
published: 2024-03-03T08:30:06.796196096Z,
replies: Collection {},
shares: Collection {},
likes: Collection {},
emojiReactions: Collection {},
startTime: 2024-03-03T08:30:06.796196096Z,
summaries: [ "hello", "hello" ],
tags: [ Object {}, Object {} ],
updated: 2024-03-03T08:30:06.796196096Z,
urls: [ URL "https://example.com/", URL "https://example.com/" ],
tos: [ Object {}, Object {} ],
btos: [ Object {}, Object {} ],
ccs: [ Object {}, Object {} ],
bccs: [ Object {}, Object {} ],
mediaType: "hello",
duration: PT1H,
sensitive: true,
source: Source {},
proofs: [ DataIntegrityProof {}, DataIntegrityProof {} ],
interactionPolicy: InteractionPolicy {},
approvedBy: URL "https://example.com/",
likeAuthorization: LikeAuthorization {},
replyAuthorization: ReplyAuthorization {},
announceAuthorization: AnnounceAuthorization {},
stipulates: Commitment {},
stipulatesReciprocal: Commitment {}
}'
`;

snapshot[`Deno.inspect(Commitment) [auto] 1`] = `
'Commitment {
id: URL "https://example.com/",
satisfies: URL "https://example.com/",
resourceQuantity: Measure {}
}'
`;

snapshot[`Deno.inspect(Commitment) [auto] 2`] = `
'Commitment {
id: URL "https://example.com/",
satisfies: URL "https://example.com/",
resourceQuantity: Measure {}
}'
`;

snapshot[`Deno.inspect(Commitment) [auto] 3`] = `
'Commitment {
id: URL "https://example.com/",
satisfies: URL "https://example.com/",
resourceQuantity: Measure {}
}'
`;

snapshot[`Deno.inspect(Intent) [auto] 1`] = `
'Intent {
id: URL "https://example.com/",
Expand Down
68 changes: 68 additions & 0 deletions packages/vocab/src/agreement.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
$schema: ../../vocab-tools/schema.yaml
name: Agreement
compactName: Agreement
uri: "https://w3id.org/valueflows/ont/vf#Agreement"
extends: "https://www.w3.org/ns/activitystreams#Object"
entity: true
description: |
The agreement reached between parties responding to a {@link Proposal}.

An interested party sends an `Agreement` wrapped in an {@link Offer}
activity. The proposing party then either finalizes the agreement by
sending an {@link Accept} activity with the finalized `Agreement` as
its `result`, or sends a {@link Reject} activity.

Note: This type extends ActivityStreams `Object` for practical
interoperability within ActivityPub federation, even though FEP-0837
defines `Agreement` as a pure ValueFlows type. Extending `Object`
provides useful inherited properties such as `id`, `attributedTo`,
`url`, `to`, and `published` without needing to redefine them.
# NOTE: The context includes mappings for Commitment and Measure properties
# (satisfies, resourceQuantity, hasUnit, hasNumericalValue) because the
# code generator does not automatically merge contexts from referenced
# types. Agreement must declare all mappings needed for correct JSON-LD
# serialization of its embedded Commitment and Measure objects.
defaultContext:
- "https://www.w3.org/ns/activitystreams"
- "https://w3id.org/security/data-integrity/v1"
- "https://gotosocial.org/ns"
- vf: "https://w3id.org/valueflows/ont/vf#"
om2: "http://www.ontology-of-units-of-measure.org/resource/om-2/"
fedibird: "http://fedibird.com/ns#"
sensitive: "as:sensitive"
emojiReactions:
"@id": "fedibird:emojiReactions"
"@type": "@id"
Agreement: "vf:Agreement"
Commitment: "vf:Commitment"
stipulates: "vf:stipulates"
stipulatesReciprocal: "vf:stipulatesReciprocal"
satisfies:
"@id": "vf:satisfies"
"@type": "@id"
resourceQuantity: "vf:resourceQuantity"
hasUnit: "om2:hasUnit"
hasNumericalValue: "om2:hasNumericalValue"

properties:
- singularName: stipulates
functional: true
compactName: stipulates
uri: "https://w3id.org/valueflows/ont/vf#stipulates"
description: |
The primary {@link Commitment} associated with the agreement. This
commitment satisfies the primary {@link Intent} of the corresponding
{@link Proposal}.
range:
- "https://w3id.org/valueflows/ont/vf#Commitment"

- singularName: stipulatesReciprocal
functional: true
compactName: stipulatesReciprocal
uri: "https://w3id.org/valueflows/ont/vf#stipulatesReciprocal"
description: |
The reciprocal {@link Commitment} associated with the agreement.
Required if the corresponding {@link Proposal} has a reciprocal
{@link Intent}.
range:
- "https://w3id.org/valueflows/ont/vf#Commitment"
47 changes: 47 additions & 0 deletions packages/vocab/src/commitment.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
$schema: ../../vocab-tools/schema.yaml
name: Commitment
compactName: Commitment
uri: "https://w3id.org/valueflows/ont/vf#Commitment"
entity: false
description: |
A promised economic transaction, referenced by an {@link Agreement}.

A commitment satisfies an {@link Intent} of a {@link Proposal} and
specifies the actual amount of the economic resource being committed.
defaultContext:
- "https://www.w3.org/ns/activitystreams"
- vf: "https://w3id.org/valueflows/ont/vf#"
om2: "http://www.ontology-of-units-of-measure.org/resource/om-2/"
Commitment: "vf:Commitment"
satisfies:
"@id": "vf:satisfies"
"@type": "@id"
resourceQuantity: "vf:resourceQuantity"
hasUnit: "om2:hasUnit"
hasNumericalValue: "om2:hasNumericalValue"

properties:
- singularName: satisfies
functional: true
compactName: satisfies
uri: "https://w3id.org/valueflows/ont/vf#satisfies"
description: |
The {@link Intent} of a {@link Proposal} that this commitment
satisfies. The value is the proposal's URI with a
[fragment](https://developer.mozilla.org/en-US/docs/Web/URI/Reference/Fragment)
appended to identify the intent. Recommended fragments are
`primary` and `reciprocal`.
range:
- "http://www.w3.org/2001/XMLSchema#anyURI"

- singularName: resourceQuantity
functional: true
compactName: resourceQuantity
uri: "https://w3id.org/valueflows/ont/vf#resourceQuantity"
untyped: true
description: |
The amount and unit of the economic resource being committed. The
unit must match the unit specified in the corresponding {@link Intent}
of the proposal.
range:
- "http://www.ontology-of-units-of-measure.org/resource/om-2/Measure"
Loading