forked from syndicate-lang/preserves
Rename DefaultPointer -> GenericPointer
This commit is contained in:
parent
8c783dbc7d
commit
e5965fde83
|
@ -4,7 +4,7 @@ import { AsPreserve, PreserveOn } from "./symbols";
|
||||||
import { Value } from "./values";
|
import { Value } from "./values";
|
||||||
import { is, isAnnotated, IsPreservesAnnotated } from "./is";
|
import { is, isAnnotated, IsPreservesAnnotated } from "./is";
|
||||||
import { stringify } from "./text";
|
import { stringify } from "./text";
|
||||||
import { DefaultPointer } from "./pointer";
|
import { GenericPointer } from "./pointer";
|
||||||
|
|
||||||
export interface Position {
|
export interface Position {
|
||||||
line?: number;
|
line?: number;
|
||||||
|
@ -53,7 +53,7 @@ export function formatPosition(p: Position | null | string): string {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Annotated<T = DefaultPointer> {
|
export class Annotated<T = GenericPointer> {
|
||||||
readonly annotations: Array<Value<T>>;
|
readonly annotations: Array<Value<T>>;
|
||||||
readonly pos: Position | null;
|
readonly pos: Position | null;
|
||||||
readonly item: Value<T>;
|
readonly item: Value<T>;
|
||||||
|
@ -99,17 +99,17 @@ export class Annotated<T = DefaultPointer> {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
static isAnnotated<T = DefaultPointer>(x: any): x is Annotated<T> {
|
static isAnnotated<T = GenericPointer>(x: any): x is Annotated<T> {
|
||||||
return isAnnotated(x);
|
return isAnnotated(x);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export function annotate<T = DefaultPointer>(v0: Value<T>, ...anns: Value<T>[]): Annotated<T> {
|
export function annotate<T = GenericPointer>(v0: Value<T>, ...anns: Value<T>[]): Annotated<T> {
|
||||||
const v = Annotated.isAnnotated<T>(v0) ? v0 : new Annotated(v0);
|
const v = Annotated.isAnnotated<T>(v0) ? v0 : new Annotated(v0);
|
||||||
anns.forEach((a) => v.annotations.push(a));
|
anns.forEach((a) => v.annotations.push(a));
|
||||||
return v;
|
return v;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function position<T = DefaultPointer>(v: Value<T>): Position | null {
|
export function position<T = GenericPointer>(v: Value<T>): Position | null {
|
||||||
return Annotated.isAnnotated<T>(v) ? v.pos : null;
|
return Annotated.isAnnotated<T>(v) ? v.pos : null;
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,7 +2,7 @@ import { Tag } from './constants';
|
||||||
import { AsPreserve, PreserveOn } from './symbols';
|
import { AsPreserve, PreserveOn } from './symbols';
|
||||||
import { Encoder, Preservable } from './encoder';
|
import { Encoder, Preservable } from './encoder';
|
||||||
import { Value } from './values';
|
import { Value } from './values';
|
||||||
import { DefaultPointer } from './pointer';
|
import { GenericPointer } from './pointer';
|
||||||
|
|
||||||
const textEncoder = new TextEncoder();
|
const textEncoder = new TextEncoder();
|
||||||
const textDecoder = new TextDecoder();
|
const textDecoder = new TextDecoder();
|
||||||
|
@ -127,7 +127,7 @@ export class Bytes implements Preservable<never> {
|
||||||
return this.asPreservesText();
|
return this.asPreservesText();
|
||||||
}
|
}
|
||||||
|
|
||||||
[AsPreserve]<T = DefaultPointer>(): Value<T> {
|
[AsPreserve]<T = GenericPointer>(): Value<T> {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
import type { Compound, Value } from "./values";
|
import type { Compound, Value } from "./values";
|
||||||
import type { DefaultPointer } from "./pointer";
|
import type { GenericPointer } from "./pointer";
|
||||||
import { Dictionary, Set } from "./dictionary";
|
import { Dictionary, Set } from "./dictionary";
|
||||||
|
|
||||||
export function isCompound<T = DefaultPointer>(x: Value<T>): x is Compound<T>
|
export function isCompound<T = GenericPointer>(x: Value<T>): x is Compound<T>
|
||||||
{
|
{
|
||||||
return (Array.isArray(x) || Set.isSet(x) || Dictionary.isDictionary(x));
|
return (Array.isArray(x) || Set.isSet(x) || Dictionary.isDictionary(x));
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,17 +6,17 @@ import { stringify } from "./text";
|
||||||
import { Value } from "./values";
|
import { Value } from "./values";
|
||||||
import { Bytes } from './bytes';
|
import { Bytes } from './bytes';
|
||||||
import { fromJS } from "./fromjs";
|
import { fromJS } from "./fromjs";
|
||||||
import { DefaultPointer } from "./pointer";
|
import { GenericPointer } from "./pointer";
|
||||||
|
|
||||||
export type DictionaryType = 'Dictionary' | 'Set';
|
export type DictionaryType = 'Dictionary' | 'Set';
|
||||||
export const DictionaryType = Symbol.for('DictionaryType');
|
export const DictionaryType = Symbol.for('DictionaryType');
|
||||||
|
|
||||||
export class KeyedDictionary<K extends Value<T>, V, T = DefaultPointer> extends FlexMap<K, V> {
|
export class KeyedDictionary<K extends Value<T>, V, T = GenericPointer> extends FlexMap<K, V> {
|
||||||
get [DictionaryType](): DictionaryType {
|
get [DictionaryType](): DictionaryType {
|
||||||
return 'Dictionary';
|
return 'Dictionary';
|
||||||
}
|
}
|
||||||
|
|
||||||
static isKeyedDictionary<K extends Value<T>, V, T = DefaultPointer>(x: any): x is KeyedDictionary<K, V, T> {
|
static isKeyedDictionary<K extends Value<T>, V, T = GenericPointer>(x: any): x is KeyedDictionary<K, V, T> {
|
||||||
return x?.[DictionaryType] === 'Dictionary';
|
return x?.[DictionaryType] === 'Dictionary';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -26,7 +26,7 @@ export class KeyedDictionary<K extends Value<T>, V, T = DefaultPointer> extends
|
||||||
super(canonicalString, items);
|
super(canonicalString, items);
|
||||||
}
|
}
|
||||||
|
|
||||||
mapEntries<W, S extends Value<R>, R = DefaultPointer>(f: (entry: [K, V]) => [S, W]): KeyedDictionary<S, W, R> {
|
mapEntries<W, S extends Value<R>, R = GenericPointer>(f: (entry: [K, V]) => [S, W]): KeyedDictionary<S, W, R> {
|
||||||
const result = new KeyedDictionary<S, W, R>();
|
const result = new KeyedDictionary<S, W, R>();
|
||||||
for (let oldEntry of this.entries()) {
|
for (let oldEntry of this.entries()) {
|
||||||
const newEntry = f(oldEntry);
|
const newEntry = f(oldEntry);
|
||||||
|
@ -75,12 +75,12 @@ export class KeyedDictionary<K extends Value<T>, V, T = DefaultPointer> extends
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Dictionary<T = DefaultPointer, V = Value<T>> extends KeyedDictionary<Value<T>, V, T> {
|
export class Dictionary<T = GenericPointer, V = Value<T>> extends KeyedDictionary<Value<T>, V, T> {
|
||||||
static isDictionary<T = DefaultPointer, V = Value<T>>(x: any): x is Dictionary<T, V> {
|
static isDictionary<T = GenericPointer, V = Value<T>>(x: any): x is Dictionary<T, V> {
|
||||||
return x?.[DictionaryType] === 'Dictionary';
|
return x?.[DictionaryType] === 'Dictionary';
|
||||||
}
|
}
|
||||||
|
|
||||||
static fromJS<T = DefaultPointer, V = DefaultPointer>(x: object): Dictionary<T, Value<V>> {
|
static fromJS<T = GenericPointer, V = GenericPointer>(x: object): Dictionary<T, Value<V>> {
|
||||||
if (Dictionary.isDictionary<T, Value<V>>(x)) return x;
|
if (Dictionary.isDictionary<T, Value<V>>(x)) return x;
|
||||||
const d = new Dictionary<T, Value<V>>();
|
const d = new Dictionary<T, Value<V>>();
|
||||||
Object.entries(x).forEach(([key, value]) => d.set(key, fromJS(value)));
|
Object.entries(x).forEach(([key, value]) => d.set(key, fromJS(value)));
|
||||||
|
@ -88,12 +88,12 @@ export class Dictionary<T = DefaultPointer, V = Value<T>> extends KeyedDictionar
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class KeyedSet<K extends Value<T>, T = DefaultPointer> extends FlexSet<K> {
|
export class KeyedSet<K extends Value<T>, T = GenericPointer> extends FlexSet<K> {
|
||||||
get [DictionaryType](): DictionaryType {
|
get [DictionaryType](): DictionaryType {
|
||||||
return 'Set';
|
return 'Set';
|
||||||
}
|
}
|
||||||
|
|
||||||
static isKeyedSet<K extends Value<T>, T = DefaultPointer>(x: any): x is KeyedSet<K, T> {
|
static isKeyedSet<K extends Value<T>, T = GenericPointer>(x: any): x is KeyedSet<K, T> {
|
||||||
return x?.[DictionaryType] === 'Set';
|
return x?.[DictionaryType] === 'Set';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -101,7 +101,7 @@ export class KeyedSet<K extends Value<T>, T = DefaultPointer> extends FlexSet<K>
|
||||||
super(canonicalString, items);
|
super(canonicalString, items);
|
||||||
}
|
}
|
||||||
|
|
||||||
map<S extends Value<R>, R = DefaultPointer>(f: (value: K) => S): KeyedSet<S, R> {
|
map<S extends Value<R>, R = GenericPointer>(f: (value: K) => S): KeyedSet<S, R> {
|
||||||
return new KeyedSet(_iterMap(this[Symbol.iterator](), f));
|
return new KeyedSet(_iterMap(this[Symbol.iterator](), f));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -138,8 +138,8 @@ export class KeyedSet<K extends Value<T>, T = DefaultPointer> extends FlexSet<K>
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Set<T = DefaultPointer> extends KeyedSet<Value<T>, T> {
|
export class Set<T = GenericPointer> extends KeyedSet<Value<T>, T> {
|
||||||
static isSet<T = DefaultPointer>(x: any): x is Set<T> {
|
static isSet<T = GenericPointer>(x: any): x is Set<T> {
|
||||||
return x?.[DictionaryType] === 'Set';
|
return x?.[DictionaryType] === 'Set';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,7 +2,7 @@ import { Encoder, Preservable } from "./encoder";
|
||||||
import { Tag } from "./constants";
|
import { Tag } from "./constants";
|
||||||
import { AsPreserve, PreserveOn } from "./symbols";
|
import { AsPreserve, PreserveOn } from "./symbols";
|
||||||
import { Value } from "./values";
|
import { Value } from "./values";
|
||||||
import { DefaultPointer } from "./pointer";
|
import { GenericPointer } from "./pointer";
|
||||||
|
|
||||||
export type FloatType = 'Single' | 'Double';
|
export type FloatType = 'Single' | 'Double';
|
||||||
export const FloatType = Symbol.for('FloatType');
|
export const FloatType = Symbol.for('FloatType');
|
||||||
|
@ -45,7 +45,7 @@ export function floatValue(f: any): number {
|
||||||
}
|
}
|
||||||
|
|
||||||
export class SingleFloat extends Float implements Preservable<never> {
|
export class SingleFloat extends Float implements Preservable<never> {
|
||||||
[AsPreserve]<T = DefaultPointer>(): Value<T> {
|
[AsPreserve]<T = GenericPointer>(): Value<T> {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -70,7 +70,7 @@ export function Single(value: number | Float): SingleFloat {
|
||||||
}
|
}
|
||||||
|
|
||||||
export class DoubleFloat extends Float implements Preservable<never> {
|
export class DoubleFloat extends Float implements Preservable<never> {
|
||||||
[AsPreserve]<T = DefaultPointer>(): Value<T> {
|
[AsPreserve]<T = GenericPointer>(): Value<T> {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,11 +1,11 @@
|
||||||
import { embed, DefaultPointer } from "./pointer";
|
import { embed, GenericPointer } from "./pointer";
|
||||||
import { Bytes } from "./bytes";
|
import { Bytes } from "./bytes";
|
||||||
import { Record, Tuple } from "./record";
|
import { Record, Tuple } from "./record";
|
||||||
import { AsPreserve } from "./symbols";
|
import { AsPreserve } from "./symbols";
|
||||||
import { Value } from "./values";
|
import { Value } from "./values";
|
||||||
import { Dictionary, Set } from "./dictionary";
|
import { Dictionary, Set } from "./dictionary";
|
||||||
|
|
||||||
export function fromJS<T = DefaultPointer>(x: any): Value<T> {
|
export function fromJS<T = GenericPointer>(x: any): Value<T> {
|
||||||
switch (typeof x) {
|
switch (typeof x) {
|
||||||
case 'number':
|
case 'number':
|
||||||
if (!Number.isInteger(x)) {
|
if (!Number.isInteger(x)) {
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
import type { DefaultPointer } from "./pointer";
|
import type { GenericPointer } from "./pointer";
|
||||||
import type { Annotated } from "./annotated";
|
import type { Annotated } from "./annotated";
|
||||||
|
|
||||||
export const IsPreservesAnnotated = Symbol.for('IsPreservesAnnotated');
|
export const IsPreservesAnnotated = Symbol.for('IsPreservesAnnotated');
|
||||||
|
|
||||||
export function isAnnotated<T = DefaultPointer>(x: any): x is Annotated<T>
|
export function isAnnotated<T = GenericPointer>(x: any): x is Annotated<T>
|
||||||
{
|
{
|
||||||
return !!x?.[IsPreservesAnnotated];
|
return !!x?.[IsPreservesAnnotated];
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,8 +7,8 @@ export type PointerType<T> = {
|
||||||
decode(s: DecoderState): T;
|
decode(s: DecoderState): T;
|
||||||
encode(s: EncoderState, v: T): void;
|
encode(s: EncoderState, v: T): void;
|
||||||
|
|
||||||
fromValue(v: Value<DefaultPointer>): T;
|
fromValue(v: Value<GenericPointer>): T;
|
||||||
toValue(v: T): Value<DefaultPointer>;
|
toValue(v: T): Value<GenericPointer>;
|
||||||
}
|
}
|
||||||
|
|
||||||
export class Pointer<T> {
|
export class Pointer<T> {
|
||||||
|
@ -35,7 +35,7 @@ export function isPointer<T>(v: Value<T>): v is Pointer<T> {
|
||||||
return typeof v === 'object' && 'embeddedValue' in v;
|
return typeof v === 'object' && 'embeddedValue' in v;
|
||||||
}
|
}
|
||||||
|
|
||||||
export class DefaultPointer {
|
export class GenericPointer {
|
||||||
generic: Value;
|
generic: Value;
|
||||||
|
|
||||||
constructor(generic: Value) {
|
constructor(generic: Value) {
|
||||||
|
@ -51,20 +51,20 @@ export class DefaultPointer {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export const genericPointerType: PointerType<DefaultPointer> = {
|
export const genericPointerType: PointerType<GenericPointer> = {
|
||||||
decode(s: DecoderState): DefaultPointer {
|
decode(s: DecoderState): GenericPointer {
|
||||||
return new DefaultPointer(new Decoder(s, this).next());
|
return new GenericPointer(new Decoder(s, this).next());
|
||||||
},
|
},
|
||||||
|
|
||||||
encode(s: EncoderState, v: DefaultPointer): void {
|
encode(s: EncoderState, v: GenericPointer): void {
|
||||||
new Encoder(s, this).push(v.generic);
|
new Encoder(s, this).push(v.generic);
|
||||||
},
|
},
|
||||||
|
|
||||||
fromValue(v: Value<DefaultPointer>): DefaultPointer {
|
fromValue(v: Value<GenericPointer>): GenericPointer {
|
||||||
return new DefaultPointer(strip(v));
|
return new GenericPointer(strip(v));
|
||||||
},
|
},
|
||||||
|
|
||||||
toValue(v: DefaultPointer): Value<DefaultPointer> {
|
toValue(v: GenericPointer): Value<GenericPointer> {
|
||||||
return v.generic;
|
return v.generic;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
@ -78,11 +78,11 @@ export const neverPointerType: PointerType<never> = {
|
||||||
throw new Error("Pointers not permitted encoding Preserves document");
|
throw new Error("Pointers not permitted encoding Preserves document");
|
||||||
},
|
},
|
||||||
|
|
||||||
fromValue(_v: Value<DefaultPointer>): never {
|
fromValue(_v: Value<GenericPointer>): never {
|
||||||
throw new Error("Pointers not permitted at this point in Preserves document");
|
throw new Error("Pointers not permitted at this point in Preserves document");
|
||||||
},
|
},
|
||||||
|
|
||||||
toValue(_v: never): Value<DefaultPointer> {
|
toValue(_v: never): Value<GenericPointer> {
|
||||||
throw new Error("Pointers not permitted encoding Preserves document");
|
throw new Error("Pointers not permitted encoding Preserves document");
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
@ -107,11 +107,11 @@ export const identityPointerType: PointerType<any> = {
|
||||||
new Encoder(s, this).push(pointerId(v));
|
new Encoder(s, this).push(pointerId(v));
|
||||||
},
|
},
|
||||||
|
|
||||||
fromValue(_v: Value<DefaultPointer>): any {
|
fromValue(_v: Value<GenericPointer>): any {
|
||||||
throw new Error("Cannot decode identityPointerType");
|
throw new Error("Cannot decode identityPointerType");
|
||||||
},
|
},
|
||||||
|
|
||||||
toValue(v: any): Value<DefaultPointer> {
|
toValue(v: any): Value<GenericPointer> {
|
||||||
return pointerId(v);
|
return pointerId(v);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -10,7 +10,7 @@ import { Record } from './record';
|
||||||
import { Annotated, newPosition, Position, updatePosition } from './annotated';
|
import { Annotated, newPosition, Position, updatePosition } from './annotated';
|
||||||
import { Double, DoubleFloat, Single, SingleFloat } from './float';
|
import { Double, DoubleFloat, Single, SingleFloat } from './float';
|
||||||
import { stringify } from './text';
|
import { stringify } from './text';
|
||||||
import { embed, DefaultPointer, genericPointerType, neverPointerType, PointerType } from './pointer';
|
import { embed, GenericPointer, genericPointerType, neverPointerType, PointerType } from './pointer';
|
||||||
|
|
||||||
export interface ReaderStateOptions {
|
export interface ReaderStateOptions {
|
||||||
includeAnnotations?: boolean;
|
includeAnnotations?: boolean;
|
||||||
|
@ -383,7 +383,7 @@ export class Reader<T> {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
case '!': return embed(this.pointerType.fromValue(
|
case '!': return embed(this.pointerType.fromValue(
|
||||||
new Reader<DefaultPointer>(this.state, genericPointerType).next()));
|
new Reader<GenericPointer>(this.state, genericPointerType).next()));
|
||||||
default:
|
default:
|
||||||
this.state.error(`Invalid # syntax: ${c}`, startPos);
|
this.state.error(`Invalid # syntax: ${c}`, startPos);
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,10 +1,10 @@
|
||||||
import { DefaultPointer } from "./pointer";
|
import { GenericPointer } from "./pointer";
|
||||||
import { is } from "./is";
|
import { is } from "./is";
|
||||||
import { Value } from "./values";
|
import { Value } from "./values";
|
||||||
|
|
||||||
export type Tuple<T> = Array<T> | [T];
|
export type Tuple<T> = Array<T> | [T];
|
||||||
|
|
||||||
export type Record<LabelType extends Value<T>, FieldsType extends Tuple<Value<T>>, T = DefaultPointer>
|
export type Record<LabelType extends Value<T>, FieldsType extends Tuple<Value<T>>, T = GenericPointer>
|
||||||
= FieldsType & { label: LabelType };
|
= FieldsType & { label: LabelType };
|
||||||
|
|
||||||
export type RecordGetters<Fs, R> = {
|
export type RecordGetters<Fs, R> = {
|
||||||
|
@ -14,14 +14,14 @@ export type RecordGetters<Fs, R> = {
|
||||||
export type CtorTypes<Fs, Names extends Tuple<keyof Fs>> =
|
export type CtorTypes<Fs, Names extends Tuple<keyof Fs>> =
|
||||||
{ [K in keyof Names]: Fs[keyof Fs & Names[K]] } & any[];
|
{ [K in keyof Names]: Fs[keyof Fs & Names[K]] } & any[];
|
||||||
|
|
||||||
export interface RecordConstructor<L extends Value<T>, Fs, Names extends Tuple<keyof Fs>, T = DefaultPointer> {
|
export interface RecordConstructor<L extends Value<T>, Fs, Names extends Tuple<keyof Fs>, T = GenericPointer> {
|
||||||
(...fields: CtorTypes<Fs, Names>): Record<L, CtorTypes<Fs, Names>, T>;
|
(...fields: CtorTypes<Fs, Names>): Record<L, CtorTypes<Fs, Names>, T>;
|
||||||
constructorInfo: RecordConstructorInfo<L, T>;
|
constructorInfo: RecordConstructorInfo<L, T>;
|
||||||
isClassOf(v: any): v is Record<L, CtorTypes<Fs, Names>, T>;
|
isClassOf(v: any): v is Record<L, CtorTypes<Fs, Names>, T>;
|
||||||
_: RecordGetters<Fs, Record<L, CtorTypes<Fs, Names>, T>>;
|
_: RecordGetters<Fs, Record<L, CtorTypes<Fs, Names>, T>>;
|
||||||
};
|
};
|
||||||
|
|
||||||
export interface RecordConstructorInfo<L extends Value<T>, T = DefaultPointer> {
|
export interface RecordConstructorInfo<L extends Value<T>, T = GenericPointer> {
|
||||||
label: L;
|
label: L;
|
||||||
arity: number;
|
arity: number;
|
||||||
}
|
}
|
||||||
|
@ -46,7 +46,7 @@ export function Record<L, FieldsType extends Tuple<any>>(
|
||||||
}
|
}
|
||||||
|
|
||||||
export namespace Record {
|
export namespace Record {
|
||||||
export function isRecord<L extends Value<T>, FieldsType extends Tuple<Value<T>>, T = DefaultPointer>(x: any): x is Record<L, FieldsType, T> {
|
export function isRecord<L extends Value<T>, FieldsType extends Tuple<Value<T>>, T = GenericPointer>(x: any): x is Record<L, FieldsType, T> {
|
||||||
return Array.isArray(x) && 'label' in x;
|
return Array.isArray(x) && 'label' in x;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -54,19 +54,19 @@ export namespace Record {
|
||||||
return '<unprintable_preserves_field_value>';
|
return '<unprintable_preserves_field_value>';
|
||||||
}
|
}
|
||||||
|
|
||||||
export function constructorInfo<L extends Value<T>, FieldsType extends Tuple<Value<T>>, T = DefaultPointer>(
|
export function constructorInfo<L extends Value<T>, FieldsType extends Tuple<Value<T>>, T = GenericPointer>(
|
||||||
r: Record<L, FieldsType, T>): RecordConstructorInfo<L, T>
|
r: Record<L, FieldsType, T>): RecordConstructorInfo<L, T>
|
||||||
{
|
{
|
||||||
return { label: r.label, arity: r.length };
|
return { label: r.label, arity: r.length };
|
||||||
}
|
}
|
||||||
|
|
||||||
export function isClassOf<L extends Value<T>, FieldsType extends Tuple<Value<T>>, T = DefaultPointer>(
|
export function isClassOf<L extends Value<T>, FieldsType extends Tuple<Value<T>>, T = GenericPointer>(
|
||||||
ci: RecordConstructorInfo<L, T>, v: any): v is Record<L, FieldsType, T>
|
ci: RecordConstructorInfo<L, T>, v: any): v is Record<L, FieldsType, T>
|
||||||
{
|
{
|
||||||
return (Record.isRecord(v)) && is(ci.label, v.label) && (ci.arity === v.length);
|
return (Record.isRecord(v)) && is(ci.label, v.label) && (ci.arity === v.length);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function makeConstructor<Fs, T = DefaultPointer>()
|
export function makeConstructor<Fs, T = GenericPointer>()
|
||||||
: (<L extends Value<T>, Names extends Tuple<keyof Fs>>(label: L, fieldNames: Names) =>
|
: (<L extends Value<T>, Names extends Tuple<keyof Fs>>(label: L, fieldNames: Names) =>
|
||||||
RecordConstructor<L, Fs, Names, T>)
|
RecordConstructor<L, Fs, Names, T>)
|
||||||
{
|
{
|
||||||
|
@ -86,7 +86,7 @@ export namespace Record {
|
||||||
|
|
||||||
Array.prototype.asPreservesText = function (): string {
|
Array.prototype.asPreservesText = function (): string {
|
||||||
if ('label' in (this as any)) {
|
if ('label' in (this as any)) {
|
||||||
const r = this as Record<Value, Tuple<Value>, DefaultPointer>;
|
const r = this as Record<Value, Tuple<Value>, GenericPointer>;
|
||||||
return '<' + r.label.asPreservesText() + (r.length > 0 ? ' ': '') +
|
return '<' + r.label.asPreservesText() + (r.length > 0 ? ' ': '') +
|
||||||
r.map(f => {
|
r.map(f => {
|
||||||
try {
|
try {
|
||||||
|
|
|
@ -2,17 +2,17 @@ import { Value } from "./values";
|
||||||
import { Annotated } from "./annotated";
|
import { Annotated } from "./annotated";
|
||||||
import { Record, Tuple } from "./record";
|
import { Record, Tuple } from "./record";
|
||||||
import { Set, Dictionary } from "./dictionary";
|
import { Set, Dictionary } from "./dictionary";
|
||||||
import type { DefaultPointer } from "./pointer";
|
import type { GenericPointer } from "./pointer";
|
||||||
|
|
||||||
export function unannotate<T = DefaultPointer>(v: Value<T>): Value<T> {
|
export function unannotate<T = GenericPointer>(v: Value<T>): Value<T> {
|
||||||
return Annotated.isAnnotated<T>(v) ? v.item : v;
|
return Annotated.isAnnotated<T>(v) ? v.item : v;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function peel<T = DefaultPointer>(v: Value<T>): Value<T> {
|
export function peel<T = GenericPointer>(v: Value<T>): Value<T> {
|
||||||
return strip(v, 1);
|
return strip(v, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function strip<T = DefaultPointer>(
|
export function strip<T = GenericPointer>(
|
||||||
v: Value<T>,
|
v: Value<T>,
|
||||||
depth: number = Infinity): Value<T>
|
depth: number = Infinity): Value<T>
|
||||||
{
|
{
|
||||||
|
|
|
@ -4,9 +4,9 @@ import type { Bytes } from './bytes';
|
||||||
import type { DoubleFloat, SingleFloat } from './float';
|
import type { DoubleFloat, SingleFloat } from './float';
|
||||||
import type { Annotated } from './annotated';
|
import type { Annotated } from './annotated';
|
||||||
import type { Set, Dictionary } from './dictionary';
|
import type { Set, Dictionary } from './dictionary';
|
||||||
import type { Pointer, DefaultPointer } from './pointer';
|
import type { Pointer, GenericPointer } from './pointer';
|
||||||
|
|
||||||
export type Value<T = DefaultPointer> =
|
export type Value<T = GenericPointer> =
|
||||||
| Atom
|
| Atom
|
||||||
| Compound<T>
|
| Compound<T>
|
||||||
| Pointer<T>
|
| Pointer<T>
|
||||||
|
@ -19,7 +19,7 @@ export type Atom =
|
||||||
| string
|
| string
|
||||||
| Bytes
|
| Bytes
|
||||||
| symbol;
|
| symbol;
|
||||||
export type Compound<T = DefaultPointer> =
|
export type Compound<T = GenericPointer> =
|
||||||
| (Array<Value<T>> | [Value<T>]) & { label: Value<T> }
|
| (Array<Value<T>> | [Value<T>]) & { label: Value<T> }
|
||||||
// ^ expanded from definition of Record<> in record.ts,
|
// ^ expanded from definition of Record<> in record.ts,
|
||||||
// because if we use Record<Value<T>, Tuple<Value<T>>, T>,
|
// because if we use Record<Value<T>, Tuple<Value<T>>, T>,
|
||||||
|
|
|
@ -10,7 +10,7 @@ import {
|
||||||
fromJS,
|
fromJS,
|
||||||
Constants,
|
Constants,
|
||||||
Encoder,
|
Encoder,
|
||||||
DefaultPointer,
|
GenericPointer,
|
||||||
EncoderState,
|
EncoderState,
|
||||||
PointerType,
|
PointerType,
|
||||||
DecoderState,
|
DecoderState,
|
||||||
|
@ -27,9 +27,9 @@ import * as fs from 'fs';
|
||||||
const _discard = Symbol.for('discard');
|
const _discard = Symbol.for('discard');
|
||||||
const _capture = Symbol.for('capture');
|
const _capture = Symbol.for('capture');
|
||||||
const _observe = Symbol.for('observe');
|
const _observe = Symbol.for('observe');
|
||||||
const Discard = Record.makeConstructor<{}, DefaultPointer>()(_discard, []);
|
const Discard = Record.makeConstructor<{}, GenericPointer>()(_discard, []);
|
||||||
const Capture = Record.makeConstructor<{pattern: Value<DefaultPointer>}, DefaultPointer>()(_capture, ['pattern']);
|
const Capture = Record.makeConstructor<{pattern: Value<GenericPointer>}, GenericPointer>()(_capture, ['pattern']);
|
||||||
const Observe = Record.makeConstructor<{pattern: Value<DefaultPointer>}, DefaultPointer>()(_observe, ['pattern']);
|
const Observe = Record.makeConstructor<{pattern: Value<GenericPointer>}, GenericPointer>()(_observe, ['pattern']);
|
||||||
|
|
||||||
describe('record constructors', () => {
|
describe('record constructors', () => {
|
||||||
it('should have constructorInfo', () => {
|
it('should have constructorInfo', () => {
|
||||||
|
@ -95,7 +95,7 @@ describe('encoding and decoding pointers', () => {
|
||||||
}
|
}
|
||||||
|
|
||||||
decode(d: DecoderState): object {
|
decode(d: DecoderState): object {
|
||||||
return this.fromValue(new Decoder<DefaultPointer>(d).next());
|
return this.fromValue(new Decoder<GenericPointer>(d).next());
|
||||||
}
|
}
|
||||||
|
|
||||||
encode(e: EncoderState, v: object): void {
|
encode(e: EncoderState, v: object): void {
|
||||||
|
@ -106,7 +106,7 @@ describe('encoding and decoding pointers', () => {
|
||||||
return Object.is(a, b);
|
return Object.is(a, b);
|
||||||
}
|
}
|
||||||
|
|
||||||
fromValue(v: Value<DefaultPointer>): object {
|
fromValue(v: Value<GenericPointer>): object {
|
||||||
if (typeof v !== 'number' || v < 0 || v >= this.objects.length) {
|
if (typeof v !== 'number' || v < 0 || v >= this.objects.length) {
|
||||||
throw new Error("Unknown pointer target");
|
throw new Error("Unknown pointer target");
|
||||||
}
|
}
|
||||||
|
@ -186,7 +186,7 @@ describe('common test suite', () => {
|
||||||
const samples = decodeWithAnnotations(samples_bin, { pointerType: genericPointerType });
|
const samples = decodeWithAnnotations(samples_bin, { pointerType: genericPointerType });
|
||||||
|
|
||||||
const TestCases = Record.makeConstructor<{
|
const TestCases = Record.makeConstructor<{
|
||||||
cases: Dictionary<DefaultPointer>
|
cases: Dictionary<GenericPointer>
|
||||||
}>()(Symbol.for('TestCases'), ['cases']);
|
}>()(Symbol.for('TestCases'), ['cases']);
|
||||||
type TestCases = ReturnType<typeof TestCases>;
|
type TestCases = ReturnType<typeof TestCases>;
|
||||||
|
|
||||||
|
@ -196,48 +196,48 @@ describe('common test suite', () => {
|
||||||
function D(bs: Bytes) {
|
function D(bs: Bytes) {
|
||||||
return decodeWithAnnotations(bs, { pointerType: genericPointerType });
|
return decodeWithAnnotations(bs, { pointerType: genericPointerType });
|
||||||
}
|
}
|
||||||
function E(v: Value<DefaultPointer>) {
|
function E(v: Value<GenericPointer>) {
|
||||||
return encodeWithAnnotations(v, { pointerType: genericPointerType });
|
return encodeWithAnnotations(v, { pointerType: genericPointerType });
|
||||||
}
|
}
|
||||||
|
|
||||||
interface ExpectedValues {
|
interface ExpectedValues {
|
||||||
[testName: string]: ({
|
[testName: string]: ({
|
||||||
value: Value<DefaultPointer>;
|
value: Value<GenericPointer>;
|
||||||
} | {
|
} | {
|
||||||
forward: Value<DefaultPointer>;
|
forward: Value<GenericPointer>;
|
||||||
back: Value<DefaultPointer>;
|
back: Value<GenericPointer>;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
const expectedValues: ExpectedValues = {
|
const expectedValues: ExpectedValues = {
|
||||||
annotation1: { forward: annotate<DefaultPointer>(9, "abc"),
|
annotation1: { forward: annotate<GenericPointer>(9, "abc"),
|
||||||
back: 9 },
|
back: 9 },
|
||||||
annotation2: { forward: annotate<DefaultPointer>([[], annotate<DefaultPointer>([], "x")],
|
annotation2: { forward: annotate<GenericPointer>([[], annotate<GenericPointer>([], "x")],
|
||||||
"abc",
|
"abc",
|
||||||
"def"),
|
"def"),
|
||||||
back: [[], []] },
|
back: [[], []] },
|
||||||
annotation3: { forward: annotate<DefaultPointer>(5,
|
annotation3: { forward: annotate<GenericPointer>(5,
|
||||||
annotate<DefaultPointer>(2, 1),
|
annotate<GenericPointer>(2, 1),
|
||||||
annotate<DefaultPointer>(4, 3)),
|
annotate<GenericPointer>(4, 3)),
|
||||||
back: 5 },
|
back: 5 },
|
||||||
annotation5: {
|
annotation5: {
|
||||||
forward: annotate<DefaultPointer>(
|
forward: annotate<GenericPointer>(
|
||||||
Record<symbol, any>(Symbol.for('R'),
|
Record<symbol, any>(Symbol.for('R'),
|
||||||
[annotate<DefaultPointer>(Symbol.for('f'),
|
[annotate<GenericPointer>(Symbol.for('f'),
|
||||||
Symbol.for('af'))]),
|
Symbol.for('af'))]),
|
||||||
Symbol.for('ar')),
|
Symbol.for('ar')),
|
||||||
back: Record<Value<DefaultPointer>, any>(Symbol.for('R'), [Symbol.for('f')])
|
back: Record<Value<GenericPointer>, any>(Symbol.for('R'), [Symbol.for('f')])
|
||||||
},
|
},
|
||||||
annotation6: {
|
annotation6: {
|
||||||
forward: Record<Value<DefaultPointer>, any>(
|
forward: Record<Value<GenericPointer>, any>(
|
||||||
annotate<DefaultPointer>(Symbol.for('R'),
|
annotate<GenericPointer>(Symbol.for('R'),
|
||||||
Symbol.for('ar')),
|
Symbol.for('ar')),
|
||||||
[annotate<DefaultPointer>(Symbol.for('f'),
|
[annotate<GenericPointer>(Symbol.for('f'),
|
||||||
Symbol.for('af'))]),
|
Symbol.for('af'))]),
|
||||||
back: Record<symbol, any>(Symbol.for('R'), [Symbol.for('f')])
|
back: Record<symbol, any>(Symbol.for('R'), [Symbol.for('f')])
|
||||||
},
|
},
|
||||||
annotation7: {
|
annotation7: {
|
||||||
forward: annotate<DefaultPointer>([], Symbol.for('a'), Symbol.for('b'), Symbol.for('c')),
|
forward: annotate<GenericPointer>([], Symbol.for('a'), Symbol.for('b'), Symbol.for('c')),
|
||||||
back: []
|
back: []
|
||||||
},
|
},
|
||||||
list1: {
|
list1: {
|
||||||
|
@ -257,7 +257,7 @@ describe('common test suite', () => {
|
||||||
function runTestCase(variety: Variety,
|
function runTestCase(variety: Variety,
|
||||||
tName: string,
|
tName: string,
|
||||||
binaryForm: Bytes,
|
binaryForm: Bytes,
|
||||||
annotatedTextForm: Value<DefaultPointer>)
|
annotatedTextForm: Value<GenericPointer>)
|
||||||
{
|
{
|
||||||
describe(tName, () => {
|
describe(tName, () => {
|
||||||
const textForm = strip(annotatedTextForm);
|
const textForm = strip(annotatedTextForm);
|
||||||
|
@ -286,10 +286,10 @@ describe('common test suite', () => {
|
||||||
}
|
}
|
||||||
|
|
||||||
const tests = (peel(TestCases._.cases(peel(samples) as TestCases)) as
|
const tests = (peel(TestCases._.cases(peel(samples) as TestCases)) as
|
||||||
Dictionary<DefaultPointer>);
|
Dictionary<GenericPointer>);
|
||||||
tests.forEach((t0: Value<DefaultPointer>, tName0: Value<DefaultPointer>) => {
|
tests.forEach((t0: Value<GenericPointer>, tName0: Value<GenericPointer>) => {
|
||||||
const tName = Symbol.keyFor(strip(tName0) as symbol)!;
|
const tName = Symbol.keyFor(strip(tName0) as symbol)!;
|
||||||
const t = peel(t0) as Record<symbol, any, DefaultPointer>;
|
const t = peel(t0) as Record<symbol, any, GenericPointer>;
|
||||||
switch (t.label) {
|
switch (t.label) {
|
||||||
case Symbol.for('Test'):
|
case Symbol.for('Test'):
|
||||||
runTestCase('normal', tName, strip(t[0]) as Bytes, t[1]);
|
runTestCase('normal', tName, strip(t[0]) as Bytes, t[1]);
|
||||||
|
|
Loading…
Reference in New Issue