Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

refactor: Prepare for better guard typing from endo #8220

Merged
merged 1 commit into from
Aug 30, 2023
Merged
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
8 changes: 4 additions & 4 deletions packages/ERTP/src/issuerKit.js
Original file line number Diff line number Diff line change
Expand Up @@ -123,8 +123,8 @@ export const hasIssuer = baggage => baggage.has(INSTANCE_KEY);
* `displayInfo` gives information to the UI on how to display the amount.
* @param {Baggage} issuerBaggage
* @param {string} name
* @param {K} [assetKind=AssetKind.NAT]
* @param {AdditionalDisplayInfo} [displayInfo={}]
* @param {K} [assetKind]
* @param {AdditionalDisplayInfo} [displayInfo]
* @param {ShutdownWithFailure} [optShutdownWithFailure] If this issuer fails in
* the middle of an atomic action (which btw should never happen), it
* potentially leaves its ledger in a corrupted state. If this function was
Expand Down Expand Up @@ -164,8 +164,8 @@ harden(makeDurableIssuerKit);
*
* `displayInfo` gives information to the UI on how to display the amount.
* @param {string} name
* @param {K} [assetKind='nat']
* @param {AdditionalDisplayInfo} [displayInfo={}]
* @param {K} [assetKind]
* @param {AdditionalDisplayInfo} [displayInfo]
* @param {ShutdownWithFailure} [optShutdownWithFailure] If this issuer fails in
* the middle of an atomic action (which btw should never happen), it
* potentially leaves its ledger in a corrupted state. If this function was
Expand Down
5 changes: 5 additions & 0 deletions packages/ERTP/src/payment.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,11 @@
import { initEmpty } from '@agoric/store';
import { prepareExoClass } from '@agoric/vat-data';

/** @typedef {import('@endo/patterns').MethodGuard} MethodGuard */
/**
* @template {Record<string | symbol, MethodGuard>} [T=Record<string | symbol, MethodGuard>]
* @typedef {import('@endo/patterns').InterfaceGuard<T>} InterfaceGuard
*/
/** @typedef {import('@agoric/vat-data').Baggage} Baggage */

/**
Expand Down
5 changes: 5 additions & 0 deletions packages/ERTP/src/types-ambient.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,11 @@

/// <reference types="ses"/>

/**
* @template {Key} [K=Key]
* @typedef {import('@endo/patterns').CopyBag<K>} CopyBag
*/

/**
* @template {AssetKind} [K=AssetKind]
* @typedef {object} Amount Amounts are descriptions of digital assets,
Expand Down
2 changes: 2 additions & 0 deletions packages/store/src/stores/store-utils.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
import { Far } from '@endo/marshal';
import { M, matches } from '@endo/patterns';

/** @typedef {import('@endo/marshal').RankCompare} RankCompare */

const { Fail, quote: q } = assert;

// TODO: Undate `@endo/patterns` to export the original, and delete the
Expand Down
110 changes: 18 additions & 92 deletions packages/store/src/types.js
Original file line number Diff line number Diff line change
@@ -1,118 +1,44 @@
/// <reference types="ses"/>

/** @typedef {import('@endo/marshal').Passable} Passable */
/** @typedef {import('@endo/marshal').PassStyle} PassStyle */
/** @typedef {import('@endo/marshal').CopyTagged} CopyTagged */
/** @template T @typedef {import('@endo/marshal').CopyRecord<T>} CopyRecord */
/** @template T @typedef {import('@endo/marshal').CopyArray<T>} CopyArray */
/** @typedef {import('@endo/marshal').Checker} Checker */
/** @typedef {import('@endo/marshal/src/rankOrder').RankCompare} RankCompare */
/** @typedef {import('@endo/marshal/src/rankOrder').RankComparison} RankComparison */

// /////////////////////////////////////////////////////////////////////////////
// Placeholder redundant types, to be imported from `@endo/patterns` instead.

// TODO placeholder. Figure out how to import from `@endo/patterns` instead
/** @typedef {Passable} Key */

// TODO placeholder. Figure out how to import from `@endo/patterns` instead
/** @typedef {Passable} Pattern */

// TODO placeholder. Figure out how to import from `@endo/patterns` instead
/**
* @template {Key} [K=Key]
* @typedef {CopyTagged & {
* [Symbol.toStringTag]: 'copySet';
* payload: K[];
* }} CopySet
* Note TODO https://github.com/endojs/endo/issues/1488
*
* @typedef {import('@endo/pass-style').Passable} Passable
*/

// TODO placeholder. Figure out how to import from `@endo/patterns` instead
/** @typedef {import('@endo/pass-style').CopyTagged} CopyTagged */
/** @typedef {import('@endo/patterns').Pattern} Pattern */
/** @typedef {import('@endo/patterns').Key} Key */
/**
* @template {Key} [K=Key]
* @typedef {CopyTagged & {
* [Symbol.toStringTag]: 'copyBag';
* payload: [K, bigint][];
* }} CopyBag
* @typedef {import('@endo/patterns').CopySet<K>} CopySet
*/

// TODO placeholder. Figure out how to import from `@endo/patterns` instead
/**
* @template {Key} [K=Key]
* @template {Passable} [V=Passable]
* @typedef {CopyTagged & {
* [Symbol.toStringTag]: 'copyMap';
* payload: { keys: K[]; values: V[] };
* }} CopyMap
*/

// TODO placeholder. Figure out how to import from `@endo/patterns` instead
/**
* @typedef {object} GuardMakers
* @property {<M extends Record<any, any>>(
* interfaceName: string,
* methodGuards: M,
* options?: { sloppy?: boolean },
* ) => InterfaceGuard} interface
* @property {(...argGuards: ArgGuard[]) => MethodGuardMaker} call Guard a
* synchronous call
* @property {(...argGuards: ArgGuard[]) => MethodGuardMaker} callWhen Guard an
* async call
* @property {(argGuard: ArgGuard) => ArgGuard} await Guard an await
* @typedef {import('@endo/patterns').CopyMap<K, V>} CopyMap
*/

// TODO placeholder. Figure out how to import from `@endo/patterns` instead
/** @typedef {(...args: any[]) => any} Method */

// TODO placeholder. Figure out how to import from `@endo/patterns` instead
/**
* @typedef {{
* klass: 'Interface';
* interfaceName: string;
* methodGuards: Record<string | symbol, MethodGuard>;
* sloppy?: boolean;
* }} InterfaceGuard
*/

// TODO placeholder. Figure out how to import from `@endo/patterns` instead
/** @typedef {any} MethodGuardMaker */

// TODO placeholder. Figure out how to import from `@endo/patterns` instead
/**
* @typedef {{
* klass: 'methodGuard';
* callKind: 'sync' | 'async';
* returnGuard: unknown;
* }} MethodGuard
*/

// TODO placeholder. Figure out how to import from `@endo/patterns` instead
/** @typedef {any} ArgGuard */

// /////////////////////////////////////////////////////////////////////////////

/**
* @typedef {object} StoreOptions Of the dimensions on which KeyedStores can
* differ, we only represent a few of them as standard options. A given store
* maker should document which options it supports, as well as its positions
* on dimensions for which it does not support options.
* @property {boolean} [longLived=true] Which way to optimize a weak store. True
* @property {boolean} [longLived] Which way to optimize a weak store. True
erights marked this conversation as resolved.
Show resolved Hide resolved
* means that we expect this weak store to outlive most of its keys, in which
* case we internally may use a JavaScript `WeakMap`. Otherwise we internally
* may use a JavaScript `Map`. Defaults to true, so please mark short lived
* stores explicitly.
* @property {boolean} [durable=false] The contents of this store survive
* termination of its containing process, allowing for restart or upgrade but
* at the cost of forbidding storage of references to ephemeral data. Defaults
* to false.
* @property {boolean} [fakeDurable=false] This store pretends to be a durable
* store but does not enforce that the things stored in it actually be
* themselves durable (whereas an actual durable store would forbid storage of
* such items). This is in service of allowing incremental transition to use
* of durable stores, to enable normal operation and testing when some stuff
* @property {boolean} [durable] The contents of this store survive termination
* of its containing process, allowing for restart or upgrade but at the cost
* of forbidding storage of references to ephemeral data. Defaults to false.
* @property {boolean} [fakeDurable] This store pretends to be a durable store
* but does not enforce that the things stored in it actually be themselves
* durable (whereas an actual durable store would forbid storage of such
* items). This is in service of allowing incremental transition to use of
* durable stores, to enable normal operation and testing when some stuff
* intended to eventually be durable has not yet been made durable. A store
* marked as fakeDurable will appear to operate normally but any attempt to
* upgrade its containing vat will fail with an error.
* upgrade its containing vat will fail with an error. Defaults to false.
* @property {Pattern} [keyShape]
* @property {Pattern} [valueShape]
*/
Expand Down
34 changes: 29 additions & 5 deletions packages/swingset-liveslots/src/vatDataTypes.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,16 +5,19 @@
* Behavior is a description when defining a kind of what facets it will have.
* For the non-multi defineKind, there is just one facet so it doesn't have a key.
*/
import type { InterfaceGuard, Pattern } from '@endo/patterns';
import type {
InterfaceGuard,
MapStore,
Pattern,
SetStore,
StoreOptions,
WeakMapStore,
WeakSetStore,
} from '@agoric/store';

// TODO should be moved into @endo/patterns and eventually imported here
// instead of this local definition.
export type InterfaceGuardKit = Record<string, InterfaceGuard>;

export type { MapStore, Pattern };

// This needs `any` values. If they were `unknown`, code that uses Baggage
Expand Down Expand Up @@ -97,15 +100,36 @@ export type DefineKindOptions<C> = {

/**
* Intended for internal use only.
* Only applicable if this is a class kind. A class kit kind should use
* `interfaceGuardKit` instead.
*
* If an `interfaceGuard` is provided, then the raw methods passed alongside
* it are wrapped by a function that first checks that this method's guard
* pattern is satisfied before calling the raw method.
*
* In `defineDurableKind` and its siblings, this defaults to off.
* `prepareExoClass` use this internally to protect their raw class methods
* In `defineDurableKind` and its siblings, this defaults to `undefined`.
* Exo classes use this internally to protect their raw class methods
erights marked this conversation as resolved.
Show resolved Hide resolved
* using the provided interface.
* In absence, an exo is protected anyway, while a bare kind is
* not (detected by `!thisfulMethods`),
*/
interfaceGuard?: InterfaceGuard;

/**
* Intended for internal use only.
* Only applicable if this is a class kit kind. A class kind should use
* `interfaceGuard` instead.
*
* If an `interfaceGuardKit` is provided, then each member of the
* interfaceGuardKit is used to guard the corresponding facet of the
* class kit.
*
* In `defineDurableKindMulti` and its siblings, this defaults to `undefined`.
* Exo class kits use this internally to protect their facets.
* In absence, an exo is protected anyway, while a bare kind is
* not (detected by `!thisfulMethods`),
*/
interfaceGuard?: InterfaceGuard<unknown>;
interfaceGuardKit?: InterfaceGuardKit;
};

export type VatData = {
Expand Down
11 changes: 10 additions & 1 deletion packages/swingset-liveslots/src/virtualObjectManager.js
Original file line number Diff line number Diff line change
Expand Up @@ -719,6 +719,7 @@ export const makeVirtualObjectManager = (
stateShape = undefined,
thisfulMethods = false,
interfaceGuard = undefined,
interfaceGuardKit = undefined,
} = options;

const statePrototype = {}; // Not frozen yet
Expand All @@ -739,11 +740,19 @@ export const makeVirtualObjectManager = (
switch (assessFacetiousness(behavior)) {
case 'one': {
assert(!multifaceted);
interfaceGuardKit === undefined ||
Fail`Use an interfaceGuard, not interfaceGuardKit, to protect class ${q(
tag,
)}`;
proposedFacetNames = undefined;
break;
}
case 'many': {
assert(multifaceted);
interfaceGuard === undefined ||
Fail`Use an interfaceGuardKit, not an interfaceGuard, to protect class kit ${q(
tag,
)}`;
proposedFacetNames = ownKeys(behavior).sort();
break;
}
Expand Down Expand Up @@ -954,7 +963,7 @@ export const makeVirtualObjectManager = (
makeContextProviderKit(contextCache, getSlotForVal, facetNames),
behavior,
thisfulMethods,
interfaceGuard,
interfaceGuardKit,
);
} else {
proto = defendPrototype(
Expand Down
3 changes: 2 additions & 1 deletion packages/time/src/timeMath.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,14 @@ import { RelativeTimeRecordShape, TimestampRecordShape } from './typeGuards.js';

const { Fail, quote: q } = assert;
/**
* @typedef {import('@endo/marshal').RankComparison} RankComparison
*
* @typedef {import('./types').TimerBrand} TimerBrand
* @typedef {import('./types').Timestamp} Timestamp
* @typedef {import('./types').RelativeTime} RelativeTime
* @typedef {import('./types').RelativeTimeValue} RelativeTimeValue
* @typedef {import('./types').TimestampValue} TimestampValue
* @typedef {import('./types').TimeMathType} TimeMathType
*
*/

/**
Expand Down
2 changes: 1 addition & 1 deletion packages/time/src/types.d.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
/* eslint-disable no-use-before-define, no-undef */
import type { ERef } from '@endo/eventual-send';

import type { RankComparison } from '@agoric/store';
import type { RankComparison } from '@endo/marshal';

/// <reference types="@agoric/notifier/src/types.js"/>

Expand Down
Loading
Loading