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
124 changes: 85 additions & 39 deletions src/djv.ts
Original file line number Diff line number Diff line change
Expand Up @@ -33,18 +33,58 @@ import { add, use } from './utils/environment.js';
* const env = new djv({ errorHandler: () => ';' });
* ```
*/

export interface IOptions {
version: string;
versionConfigure?: Function;
formats?: IFormats;
inner: boolean;
errorHandler?: Function;
}

interface IFormats {
[key: string]: Function;
}

export interface ISchema {
id: string;
toString:(a: string) => string
}

interface IResolve {
name: string;
schema: any;
fn: any;
}

type INoNameResolve = Omit<IResolve, 'name'>

class Environment {
static expression = expression

state: State
options: IOptions;
private defaultOptions: IOptions = {
version: 'draft-06',
inner: false,
}
resolved: {
[key: string]: IResolve
};

constructur(this: Environment, options = {}) {
this.options = options;
constructor(options: Partial<IOptions> = {}) {
const enrichedOptions: IOptions = {
...this.defaultOptions,
...options
}
const {version, versionConfigure} = enrichedOptions;
this.options = enrichedOptions;
this.resolved = {};
this.state = new State(null, this);

this.useVersion(options.version, options.versionConfigure);
this.addFormat(options.formats);

this.useVersion(version, versionConfigure);
formats.setFormatters(enrichedOptions.formats || {})

}
/**
* check if object correspond to schema
Expand Down Expand Up @@ -76,21 +116,20 @@ class Environment {
*
* @param {string?} name
* @param {object} schema
* @param {object} schema
* @returns {resolved}
*/
addSchema(name: string, schema: object) {
addSchema(name: string, schema: ISchema): INoNameResolve {
const realSchema = typeof name === 'object' ? name : schema;
const resolved = {
schema: realSchema,
fn: generate(this, realSchema, undefined, this.options),
};

[name, schema.id]
.filter(id => typeof id === 'string')
.forEach((id) => {
this.resolved[id] = Object.assign({ name: id }, resolved);
});
// .filter(id => typeof id === 'string')
.forEach((id) => {
this.resolved[id] = Object.assign({ name: id }, resolved);
});

return resolved;
}
Expand Down Expand Up @@ -125,11 +164,11 @@ class Environment {
* @param {string} name
* @returns {resolved}
*/
resolve(name: string) {
resolve(name: string): INoNameResolve {
if (typeof name === 'object' || !this.resolved[name]) {
return this.addSchema(
name,
this.state.resolve(name)
name,
this.state.resolve(name)
);
}

Expand All @@ -149,13 +188,13 @@ class Environment {
* @returns {serializedInternalState}
*/
export(name: string) {
let resolved;
let resolved: any;
if (name) {
resolved = this.resolve(name);
const resolvedNoName = this.resolve(name);
resolved = {
name,
schema: resolved.schema,
fn: resolved.fn.toString()
schema: resolvedNoName.schema,
fn: resolvedNoName.fn.toString()
};
} else {
resolved = {};
Expand Down Expand Up @@ -217,16 +256,23 @@ class Environment {
* @param {string/object?} name
* @param {string/function} formatter
*/
addFormat(name: string, formatter: Function) {
if (typeof name === 'string') {
formats[name] = formatter;
return;
}

if (typeof name === 'object') {
Object.assign(formats, name);
}
}

//
// addFormat(name: string | IFormats, formatter?: Function) {
// if (typeof name === 'string' && formatter) {
// formats.setFormatter(name, formatter)
// return;
// }
//
// if (typeof name === 'object') {
// formats.setFormatters()
// Object.assign<IFormats, IFormats>(formats, name);
// }
// }



/**
* @name setErrorHandler
* @type function
Expand Down Expand Up @@ -265,19 +311,19 @@ class Environment {
*/
setErrorHandler(errorHandler: Function) {
Object.assign(this.options, { errorHandler });
}
}
/**
* @name useVersion
* @type {function}
* @description
* Add a specification version for environment
* A configure function is called with exposed environments, like keys, formats, etc.
* Updates internals utilities and configurations to fix versions implementation conflicts
* @param {string} version of json-schema specification to use
* @param {function} configure
* @returns void
*/
useVersion(version: string, configure: Function) {
* @name useVersion
* @type {function}
* @description
* Add a specification version for environment
* A configure function is called with exposed environments, like keys, formats, etc.
* Updates internals utilities and configurations to fix versions implementation conflicts
* @param {string} version of json-schema specification to use
* @param {function} configure
* @returns void
*/
useVersion(version: string, configure?: Function) {
if (typeof configure !== 'function' && version === 'draft-04') {
/* eslint-disable no-param-reassign, global-require, import/no-extraneous-dependencies */
configure = require('@korzio/djv-draft-04');
Expand Down
10 changes: 7 additions & 3 deletions src/utils/environment.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,13 +11,17 @@ import formats from './formats';
import { keys } from './uri';
import { transformation } from './schema';

const environmentConfig = {};
type envConf = {
[key: string]: Function | undefined;
}

const environmentConfig: envConf = {};

function add(version, config) {
function add(version: string, config: Function) {
environmentConfig[version] = config;
}

function use(version) {
function use(version?: string) {
if (!version || !environmentConfig[version]) {
return;
}
Expand Down
21 changes: 20 additions & 1 deletion src/utils/formats.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,24 @@

import { expression } from './template';

export default {
interface IFormatsFuncs {
[key: string]: Function | undefined;
}

interface IFormatsSetters {
setFormatter: (name: string, func: Function) => void;
setFormatters: (formatters: IFormatsFuncs) => void;
}

type IFormats = IFormatsFuncs & IFormatsSetters

const formats: IFormats = {
setFormatter(name: string, func) {
this[name] = func
},
setFormatters(obj: IFormatsFuncs){
Object.assign<IFormats, IFormatsFuncs>(this, obj)
},
alpha: expression`!/^[a-zA-Z]+$/.test(${'data'})`,
alphanumeric: expression`!/^[a-zA-Z0-9]+$/.test(${'data'})`,
identifier: expression`!/^[-_a-zA-Z0-9]+$/.test(${'data'})`,
Expand All @@ -27,3 +44,5 @@ export default {
'uri-reference': expression`!/^(?:[A-Za-z][A-Za-z0-9+\\-.]*:(?:\\/\\/(?:(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:]|%[0-9A-Fa-f]{2})*@)?(?:\\[(?:(?:(?:(?:[0-9A-Fa-f]{1,4}:){6}|::(?:[0-9A-Fa-f]{1,4}:){5}|(?:[0-9A-Fa-f]{1,4})?::(?:[0-9A-Fa-f]{1,4}:){4}|(?:(?:[0-9A-Fa-f]{1,4}:){0,1}[0-9A-Fa-f]{1,4})?::(?:[0-9A-Fa-f]{1,4}:){3}|(?:(?:[0-9A-Fa-f]{1,4}:){0,2}[0-9A-Fa-f]{1,4})?::(?:[0-9A-Fa-f]{1,4}:){2}|(?:(?:[0-9A-Fa-f]{1,4}:){0,3}[0-9A-Fa-f]{1,4})?::[0-9A-Fa-f]{1,4}:|(?:(?:[0-9A-Fa-f]{1,4}:){0,4}[0-9A-Fa-f]{1,4})?::)(?:[0-9A-Fa-f]{1,4}:[0-9A-Fa-f]{1,4}|(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?))|(?:(?:[0-9A-Fa-f]{1,4}:){0,5}[0-9A-Fa-f]{1,4})?::[0-9A-Fa-f]{1,4}|(?:(?:[0-9A-Fa-f]{1,4}:){0,6}[0-9A-Fa-f]{1,4})?::)|[Vv][0-9A-Fa-f]+\\.[A-Za-z0-9\\-._~!$&\'()*+,;=:]+)\\]|(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)|(?:[A-Za-z0-9\\-._~!$&\'()*+,;=]|%[0-9A-Fa-f]{2})*)(?::[0-9]*)?(?:\\/(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@]|%[0-9A-Fa-f]{2})*)*|\\/(?:(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@]|%[0-9A-Fa-f]{2})+(?:\\/(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@]|%[0-9A-Fa-f]{2})*)*)?|(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@]|%[0-9A-Fa-f]{2})+(?:\\/(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@]|%[0-9A-Fa-f]{2})*)*|)(?:\\?(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@\\/?]|%[0-9A-Fa-f]{2})*)?(?:\\#(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@\\/?]|%[0-9A-Fa-f]{2})*)?|(?:\\/\\/(?:(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:]|%[0-9A-Fa-f]{2})*@)?(?:\\[(?:(?:(?:(?:[0-9A-Fa-f]{1,4}:){6}|::(?:[0-9A-Fa-f]{1,4}:){5}|(?:[0-9A-Fa-f]{1,4})?::(?:[0-9A-Fa-f]{1,4}:){4}|(?:(?:[0-9A-Fa-f]{1,4}:){0,1}[0-9A-Fa-f]{1,4})?::(?:[0-9A-Fa-f]{1,4}:){3}|(?:(?:[0-9A-Fa-f]{1,4}:){0,2}[0-9A-Fa-f]{1,4})?::(?:[0-9A-Fa-f]{1,4}:){2}|(?:(?:[0-9A-Fa-f]{1,4}:){0,3}[0-9A-Fa-f]{1,4})?::[0-9A-Fa-f]{1,4}:|(?:(?:[0-9A-Fa-f]{1,4}:){0,4}[0-9A-Fa-f]{1,4})?::)(?:[0-9A-Fa-f]{1,4}:[0-9A-Fa-f]{1,4}|(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?))|(?:(?:[0-9A-Fa-f]{1,4}:){0,5}[0-9A-Fa-f]{1,4})?::[0-9A-Fa-f]{1,4}|(?:(?:[0-9A-Fa-f]{1,4}:){0,6}[0-9A-Fa-f]{1,4})?::)|[Vv][0-9A-Fa-f]+\\.[A-Za-z0-9\\-._~!$&\'()*+,;=:]+)\\]|(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)|(?:[A-Za-z0-9\\-._~!$&\'()*+,;=]|%[0-9A-Fa-f]{2})*)(?::[0-9]*)?(?:\\/(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@]|%[0-9A-Fa-f]{2})*)*|\\/(?:(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@]|%[0-9A-Fa-f]{2})+(?:\\/(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@]|%[0-9A-Fa-f]{2})*)*)?|(?:[A-Za-z0-9\\-._~!$&\'()*+,;=@]|%[0-9A-Fa-f]{2})+(?:\\/(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@]|%[0-9A-Fa-f]{2})*)*|)(?:\\?(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@\\/?]|%[0-9A-Fa-f]{2})*)?(?:\\#(?:[A-Za-z0-9\\-._~!$&\'()*+,;=:@\\/?]|%[0-9A-Fa-f]{2})*)?)$/i.test(${'data'})`,
'uri-template': expression`!/^(?:(?:[^\\x00-\\x20"\'<>%\\\\^\`{|}]|%[0-9a-f]{2})|\\{[+#.\\/;?&=,!@|]?(?:[a-z0-9_]|%[0-9a-f]{2})+(?:\\:[1-9][0-9]{0,3}|\\*)?(?:,(?:[a-z0-9_]|%[0-9a-f]{2})+(?:\\:[1-9][0-9]{0,3}|\\*)?)*\\})*$/i.test(${'data'})`,
};

export default formats
4 changes: 3 additions & 1 deletion src/utils/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@
* Basic utilities for djv project
*/

import {ISchema} from "../djv";

/**
* @name asExpression
* @type {function}
Expand All @@ -15,7 +17,7 @@
* @param {object} tpl templater instance
* @returns {string} expression
*/
function asExpression(fn, schema, tpl) {
function asExpression(fn: Function, schema: ISchema, tpl) {
if (typeof fn !== 'function') {
return fn;
}
Expand Down
Loading