diff --git a/lib/config/builder/config.ts b/lib/config/builder/config.ts
index d76d10d..c2eda1f 100644
--- a/lib/config/builder/config.ts
+++ b/lib/config/builder/config.ts
@@ -19,7 +19,7 @@ import { Value } from "./value";
The idea of a config is that now the form is going to ask for
Test: [ ] and the value is going to be checked as a boolean.
- There are more complex values like enums, lists, and objects. See {@link Value}
+ There are more complex values like selects, lists, and objects. See {@link Value}
Also, there is the ability to get a validator/parser from this config spec.
```ts
@@ -81,7 +81,7 @@ import { Value } from "./value";
"warning": null,
});
export const auth = Value.list(authorizationList);
- export const serialversion = Value.enum({
+ export const serialversion = Value.select({
"name": "Serialization Version",
"description":
"Return raw transaction or block hex with Segwit or non-SegWit serialization.",
diff --git a/lib/config/builder/list.ts b/lib/config/builder/list.ts
index 84c47ea..b52ad98 100644
--- a/lib/config/builder/list.ts
+++ b/lib/config/builder/list.ts
@@ -59,24 +59,6 @@ export class List extends IBuilder {
...a,
});
}
- static enum<
- A extends Description &
- Default & {
- range: string;
- spec: {
- values: string[];
- "value-names": {
- [key: string]: string;
- };
- };
- }
- >(a: A) {
- return new List({
- type: "list" as const,
- subtype: "enum" as const,
- ...a,
- });
- }
static obj<
A extends Description &
Default[]> & {
diff --git a/lib/config/builder/value.ts b/lib/config/builder/value.ts
index cde5804..aeed549 100644
--- a/lib/config/builder/value.ts
+++ b/lib/config/builder/value.ts
@@ -95,7 +95,7 @@ export class Value extends IBuilder {
...a,
} as ValueSpecNumber);
}
- static enum<
+ static select<
A extends Description &
Default & {
values: readonly string[] | string[];
@@ -103,7 +103,7 @@ export class Value extends IBuilder {
}
>(a: A) {
return new Value({
- type: "enum" as const,
+ type: "select" as const,
...a,
});
}
diff --git a/lib/config/builder/variants.ts b/lib/config/builder/variants.ts
index c689b2e..9e01bb7 100644
--- a/lib/config/builder/variants.ts
+++ b/lib/config/builder/variants.ts
@@ -3,9 +3,9 @@ import { BuilderExtract, IBuilder } from "./builder";
import { Config } from ".";
/**
- * Used in the the Value.enum { @link './value.ts' }
- * to indicate the type of enums variants that are available. The key for the record passed in will be the
- * key to the tag.id in the Value.enum
+ * Used in the the Value.select { @link './value.ts' }
+ * to indicate the type of select variants that are available. The key for the record passed in will be the
+ * key to the tag.id in the Value.select
```ts
export const pruningSettingsVariants = Variants.of({
"disabled": disabled,
diff --git a/lib/scripts/oldSpecToBuilder.ts b/lib/scripts/oldSpecToBuilder.ts
index 75e31f0..a5e0992 100644
--- a/lib/scripts/oldSpecToBuilder.ts
+++ b/lib/scripts/oldSpecToBuilder.ts
@@ -97,7 +97,7 @@ export default async function makeFileContent(
)})`;
}
case "enum": {
- return `Value.enum(${JSON.stringify(
+ return `Value.select(${JSON.stringify(
{
name: value.name || null,
description: value.description || null,
@@ -205,14 +205,12 @@ export default async function makeFileContent(
)})`;
}
case "enum": {
- return `List.enum(${JSON.stringify(
+ return `Value.multiselect(${JSON.stringify(
{
name: value.name || null,
range: value.range || null,
- spec: {
- values: value?.spec?.["values"] || null,
- "value-names": value?.spec?.["value-names"] || {},
- },
+ values: value?.spec?.["values"] || null,
+ "value-names": value?.spec?.["value-names"] || {},
default: value.default || null,
description: value.description || null,
warning: value.warning || null,
diff --git a/lib/types/config-types.ts b/lib/types/config-types.ts
index 8b69d3c..c75d8ed 100644
--- a/lib/types/config-types.ts
+++ b/lib/types/config-types.ts
@@ -4,22 +4,25 @@ export type ValueType =
| "string"
| "number"
| "boolean"
- | "enum"
+ | "select"
+ | "multiselect"
| "list"
| "object"
| "file"
| "union";
export type ValueSpec = ValueSpecOf;
-// core spec types. These types provide the metadata for performing validations
+/** core spec types. These types provide the metadata for performing validations */
export type ValueSpecOf = T extends "string"
? ValueSpecString
: T extends "number"
? ValueSpecNumber
: T extends "boolean"
? ValueSpecBoolean
- : T extends "enum"
- ? ValueSpecEnum
+ : T extends "select"
+ ? ValueSpecSelect
+ : T extends "multiselect"
+ ? ValueSpecMultiselect
: T extends "list"
? ValueSpecList
: T extends "object"
@@ -43,11 +46,18 @@ export interface ValueSpecNumber extends ListValueSpecNumber, WithStandalone {
default: null | number;
}
-export interface ValueSpecEnum extends ListValueSpecEnum, WithStandalone {
- type: "enum";
+export interface ValueSpecSelect extends SelectBase, WithStandalone {
+ type: "select";
default: string;
}
+export interface ValueSpecMultiselect extends SelectBase, WithStandalone {
+ type: "multiselect";
+ /**'[0,1]' (inclusive) OR '[0,*)' (right unbounded), normal math rules */
+ range: string;
+ default: string[];
+}
+
export interface ValueSpecBoolean extends WithStandalone {
type: "boolean";
default: boolean;
@@ -61,7 +71,7 @@ export interface ValueSpecUnion {
}
export interface ValueSpecFile extends WithStandalone {
- type: 'file';
+ type: "file";
placeholder: null | string;
nullable: boolean;
extensions: string[];
@@ -78,31 +88,28 @@ export interface WithStandalone {
warning: null | string;
}
-// no lists of booleans, lists
-export type ListValueSpecType =
- | "string"
- | "number"
- | "enum"
- | "object"
- | "union";
+export interface SelectBase {
+ values: string[] | readonly string[];
+ "value-names": { [value: string]: string };
+}
-// represents a spec for the values of a list
+/** no lists of booleans, lists*/
+export type ListValueSpecType = "string" | "number" | "object" | "union";
+
+/** represents a spec for the values of a list */
export type ListValueSpecOf = T extends "string"
? ListValueSpecString
: T extends "number"
? ListValueSpecNumber
- : T extends "enum"
- ? ListValueSpecEnum
: T extends "object"
? ListValueSpecObject
: T extends "union"
? ListValueSpecUnion
: never;
-// represents a spec for a list
+/** represents a spec for a list */
export type ValueSpecList = ValueSpecListOf;
-export interface ValueSpecListOf
- extends WithStandalone {
+export interface ValueSpecListOf extends WithStandalone {
type: "list";
subtype: T;
spec: ListValueSpecOf;
@@ -119,10 +126,7 @@ export interface ValueSpecListOf
}
// sometimes the type checker needs just a little bit of help
-export function isValueSpecListOf(
- t: ValueSpecList,
- s: S
-): t is ValueSpecListOf {
+export function isValueSpecListOf(t: ValueSpecList, s: S): t is ValueSpecListOf {
return t.subtype === s;
}
@@ -134,21 +138,20 @@ export interface ListValueSpecString {
}
export interface ListValueSpecNumber {
+ /** '[0,1]' (inclusive) OR '[0,*)' (right unbounded), normal math rules */
range: string;
integral: boolean;
units: null | string;
placeholder: null | string;
}
-export interface ListValueSpecEnum {
- values: string[] | readonly string[];
- "value-names": { [value: string]: string };
-}
-
export interface ListValueSpecObject {
- spec: InputSpec; // this is a mapped type of the config object at this level, replacing the object's values with specs on those values
- "unique-by": UniqueBy; // indicates whether duplicates can be permitted in the list
- "display-as": null | string; // this should be a handlebars template which can make use of the entire config which corresponds to 'spec'
+ /** this is a mapped type of the config object at this level, replacing the object's values with specs on those values */
+ spec: InputSpec;
+ /** indicates whether duplicates can be permitted in the list */
+ "unique-by": UniqueBy;
+ /** this should be a handlebars template which can make use of the entire config which corresponds to 'spec' */
+ "display-as": null | string;
}
export type UniqueBy =
@@ -161,15 +164,18 @@ export type UniqueBy =
export interface ListValueSpecUnion {
tag: UnionTagSpec;
variants: { [key: string]: InputSpec };
- "display-as": null | string; // this may be a handlebars template which can conditionally (on tag.id) make use of each union's entries, or if left blank will display as tag.id
+ /** this may be a handlebars template which can conditionally (on tag.id) make use of each union's entries, or if left blank will display as tag.id*/
+ "display-as": null | string;
"unique-by": UniqueBy;
- default: string; // this should be the variantName which one prefers a user to start with by default when creating a new union instance in a list
+ /** this should be the variantName which one prefers a user to start with by default when creating a new union instance in a list*/
+ default: string;
}
export interface UnionTagSpec {
- id: string; // The name of the field containing one of the union variants
+ /** The name of the field containing one of the union variants*/
+ id: string;
"variant-names": {
- // the name of each variant
+ /** the name of each variant*/
[variant: string]: string;
};
name: string;
diff --git a/lib/util/artifacts/makeOutput.ts b/lib/util/artifacts/makeOutput.ts
index 8fa33a0..9bf8cc8 100644
--- a/lib/util/artifacts/makeOutput.ts
+++ b/lib/util/artifacts/makeOutput.ts
@@ -1,5 +1,4 @@
import { writeConvertedFile } from "../../scripts/oldSpecToBuilder";
-import { writeFileSync, readFileSync } from "fs";
writeConvertedFile(
"./lib/util/artifacts/output.ts",
@@ -66,7 +65,7 @@ writeConvertedFile(
name: "Serialization Version",
description:
"Return raw transaction or block hex with Segwit or non-SegWit serialization.",
- type: "enum",
+ type: "select",
values: ["non-segwit", "segwit"],
"value-names": {},
default: "segwit",
diff --git a/lib/util/artifacts/output.ts b/lib/util/artifacts/output.ts
index de40e99..427ac4b 100644
--- a/lib/util/artifacts/output.ts
+++ b/lib/util/artifacts/output.ts
@@ -51,7 +51,7 @@ export const authorizationList = List.string({
warning: null,
});
export const auth = Value.list(authorizationList);
-export const serialversion = Value.enum({
+export const serialversion = Value.select({
name: "Serialization Version",
description:
"Return raw transaction or block hex with Segwit or non-SegWit serialization.",
diff --git a/lib/util/propertiesMatcher.ts b/lib/util/propertiesMatcher.ts
index 40e9cdf..6dd7ee8 100644
--- a/lib/util/propertiesMatcher.ts
+++ b/lib/util/propertiesMatcher.ts
@@ -6,7 +6,8 @@ type TypeString = "string";
type TypeNumber = "number";
type TypeObject = "object";
type TypeList = "list";
-type TypeEnum = "enum";
+type TypeSelect = "select";
+type TypeMultiselect = "multiselect";
type TypePointer = "pointer";
type TypeUnion = "union";
@@ -49,8 +50,12 @@ type GuardPointer =
A extends {readonly type:TypePointer} ? (string | null) :
unknown
// prettier-ignore
-type GuardEnum =
- A extends {readonly type:TypeEnum, readonly values: ArrayLike} ? GuardDefaultNullable :
+type GuardSelect =
+ A extends {readonly type:TypeSelect, readonly values: ArrayLike} ? GuardDefaultNullable :
+ unknown
+// prettier-ignore
+type GuardMultiselect =
+ A extends {readonly type:TypeMultiselect, readonly values: ArrayLike} ? GuardDefaultNullable :
unknown
// prettier-ignore
type GuardUnion =
@@ -65,7 +70,8 @@ export type GuardAll = GuardNumber &
GuardList &
GuardPointer &
GuardUnion &
- GuardEnum;
+ GuardSelect &
+ GuardMultiselect;
// prettier-ignore
export type TypeFromProps =
A extends Record ? {readonly [K in keyof A & string]: _>} :
@@ -247,7 +253,7 @@ export function guardAll(
value
) as any;
}
- case "enum":
+ case "select":
if (matchValues.test(value)) {
return defaultNullable(
matches.literals(value.values[0], ...value.values),
@@ -255,6 +261,20 @@ export function guardAll(
) as any;
}
return matches.unknown as any;
+ case "multiselect":
+ if (matchValues.test(value)) {
+ const rangeValidate =
+ (matchRange.test(value) && matchNumberWithRange(value.range).test) ||
+ (() => true);
+
+ return defaultNullable(
+ matches
+ .literals(value.values[0], ...value.values)
+ .validate((x) => rangeValidate(x.length), "valid length"),
+ value
+ ) as any;
+ }
+ return matches.unknown as any;
case "union":
if (matchUnion.test(value)) {
return matches.some(