@syncbridge/common 0.6.0 → 0.6.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,11 +1,16 @@
1
- export declare class SbError extends Error {
1
+ import { ErrorIssue } from '@opra/common';
2
+ export declare class SbError extends Error implements ErrorIssue {
2
3
  readonly cause?: Error;
4
+ severity: ErrorIssue['severity'];
3
5
  code?: string;
4
6
  [index: string]: any;
5
7
  constructor(message?: string | Error, options?: SbErrorOptions);
6
- toJSON(): any;
7
8
  }
8
- export interface SbErrorOptions {
9
+ export interface SbErrorOptions extends Partial<ErrorIssue> {
9
10
  cause?: Error;
10
- [key: string]: any;
11
+ }
12
+ /**
13
+ *
14
+ */
15
+ export declare class SbValidationError extends SbError {
11
16
  }
@@ -1,5 +1,6 @@
1
1
  import { isPlainObject } from '@jsopen/objects';
2
2
  export class SbError extends Error {
3
+ severity = 'error';
3
4
  code;
4
5
  constructor(message, options) {
5
6
  super(typeof message === 'object' ? message.message || '' : message);
@@ -41,14 +42,9 @@ export class SbError extends Error {
41
42
  }
42
43
  }
43
44
  }
44
- toJSON() {
45
- const out = {
46
- message: this.message,
47
- };
48
- for (const k of Object.keys(this)) {
49
- if (k !== 'stack')
50
- out[k] = this[k];
51
- }
52
- return out;
53
- }
45
+ }
46
+ /**
47
+ *
48
+ */
49
+ export class SbValidationError extends SbError {
54
50
  }
@@ -1,4 +1,5 @@
1
1
  import { ValidationError } from 'valgen';
2
+ import { SbValidationError } from './sb-error.js';
2
3
  export class StackExecutor {
3
4
  stack = [];
4
5
  issues = [];
@@ -30,20 +31,16 @@ export class StackExecutor {
30
31
  const location = this.stack.join('/');
31
32
  if (e instanceof ValidationError) {
32
33
  e.issues.forEach(x => {
33
- this.issues.push({
34
- ...x,
35
- severity: 'error',
36
- location: location + (x.location ? '/' + x.location : ''),
37
- });
34
+ const issue = new SbValidationError(x.message, x);
35
+ x.severity = x.severity ?? 'error';
36
+ x.location = location + (x.location ? '/' + x.location : '');
37
+ this.issues.push(issue);
38
38
  });
39
39
  }
40
40
  else {
41
- this.issues.push({
42
- message: e.message,
43
- ...e,
44
- severity: 'error',
45
- location,
46
- });
41
+ e.severity = e.severity ?? 'error';
42
+ e.location = location;
43
+ this.issues.push(e);
47
44
  }
48
45
  }
49
46
  }
package/constants.js CHANGED
@@ -1,4 +1,4 @@
1
- export const version = '0.6.0';
1
+ export const version = '0.6.1';
2
2
  export const OWN_ELEMENT_METADATA = Symbol.for('OWN_ELEMENT_METADATA');
3
3
  export const COMPONENT_OPTIONS = Symbol.for('COMPONENT_OPTIONS');
4
4
  export const PROCESSOR_OPTIONS = Symbol.for('PROCESSOR_OPTIONS');
package/index.d.ts CHANGED
@@ -16,5 +16,5 @@ export * from './models-document.js';
16
16
  export * from './processor-factory.js';
17
17
  export * from './registry/extension-package.js';
18
18
  export * from './registry/extension-registry.js';
19
+ export * from './utils/decode-profile.js';
19
20
  export * from './utils/materialize-metadata.js';
20
- export * from './utils/profile-utils.js';
package/index.js CHANGED
@@ -16,5 +16,5 @@ export * from './models-document.js';
16
16
  export * from './processor-factory.js';
17
17
  export * from './registry/extension-package.js';
18
18
  export * from './registry/extension-registry.js';
19
+ export * from './utils/decode-profile.js';
19
20
  export * from './utils/materialize-metadata.js';
20
- export * from './utils/profile-utils.js';
@@ -1,4 +1,5 @@
1
1
  import { ApiDocumentFactory } from '@opra/common';
2
+ import { SbError } from './classes/sb-error.js';
2
3
  import * as models from './models/index.js';
3
4
  let doc;
4
5
  export async function initializeModelsDocument() {
@@ -11,6 +12,8 @@ export async function initializeModelsDocument() {
11
12
  }
12
13
  export function getModelsDocument() {
13
14
  if (!doc)
14
- throw new Error('You must call initializeModelsDocument() first');
15
+ throw new SbError('You must call initializeModelsDocument() first', {
16
+ severity: 'fatal',
17
+ });
15
18
  return doc;
16
19
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@syncbridge/common",
3
- "version": "0.6.0",
3
+ "version": "0.6.1",
4
4
  "description": "SyncBridge Common utilities",
5
5
  "author": "Panates Inc",
6
6
  "license": "MIT",
@@ -1,4 +1,5 @@
1
1
  import equal from 'fast-deep-equal';
2
+ import { SbError } from './classes/sb-error.js';
2
3
  import { StackExecutor } from './classes/stack-executor.js';
3
4
  import { initializeModelsDocument } from './models-document.js';
4
5
  import { ExtensionRegistry } from './registry/extension-registry.js';
@@ -94,7 +95,7 @@ export var ProcessorFactory;
94
95
  if (processor.stopped &&
95
96
  oldMetadata?.className &&
96
97
  oldMetadata?.className !== newMetadata.className)
97
- throw new Error('Can not change component class while processor running. You should stop it first.');
98
+ throw new SbError('Cannot change component class while processor running. You should stop it first.');
98
99
  /** Validate sub components */
99
100
  if (childMetadata.components) {
100
101
  _validateComponents({
@@ -4,6 +4,7 @@ import path from 'node:path';
4
4
  import process from 'node:process';
5
5
  import { fileURLToPath, pathToFileURL } from 'node:url';
6
6
  import { updateErrorMessage } from '@jsopen/objects';
7
+ import { SbError } from '../classes/sb-error.js';
7
8
  import { COMPONENT_OPTIONS, PROCESSOR_OPTIONS } from '../constants.js';
8
9
  import { isComponentBase, isProcessorBase } from '../utils/type-guartds.js';
9
10
  import { normalizeComponentMetadata, normalizeProcessorMetadata, } from './helpers.js';
@@ -26,10 +27,10 @@ export class ExtensionPackage {
26
27
  static async fromDirectory(directory) {
27
28
  let filename = path.join(directory, 'package.json');
28
29
  if (!fs.existsSync(filename))
29
- throw new TypeError(`Directory "${directory}" does not contain package.json`);
30
+ throw new SbError(`Directory "${directory}" does not contain package.json`);
30
31
  const pkgJson = JSON.parse(fs.readFileSync(filename, 'utf8'));
31
32
  if (!pkgJson.syncbridge)
32
- throw new TypeError(`"${pkgJson.name}" is not a SyncBridge extension package`);
33
+ throw new SbError(`"${pkgJson.name}" is not a SyncBridge extension package`);
33
34
  const out = new ExtensionPackage();
34
35
  out.name = pkgJson.name;
35
36
  out.version = pkgJson.version;
@@ -100,7 +101,7 @@ export class ExtensionPackage {
100
101
  let entryPoint = (resolver || import.meta.resolve)(specifier);
101
102
  const pkgJson = locatePkgJson(path.dirname(entryPoint));
102
103
  if (!pkgJson) {
103
- throw new TypeError(`Can't locate package.json file for "${specifier}"`);
104
+ throw new SbError(`Can't locate package.json file for "${specifier}"`);
104
105
  }
105
106
  if (path.isAbsolute(entryPoint) && process.platform === 'win32') {
106
107
  entryPoint = pathToFileURL(entryPoint).href;
@@ -178,11 +179,11 @@ export class ComponentExtension {
178
179
  const module = await import(this.pkg.entryPoint);
179
180
  const ctor = module[this.exportName];
180
181
  if (!ctor)
181
- throw new TypeError(`Exported component "${this.exportName}" not found in package "${this.pkg.name}"`);
182
+ throw new SbError(`Exported component "${this.exportName}" not found in package "${this.pkg.name}"`);
182
183
  if (typeof ctor !== 'function')
183
- throw new TypeError(`Exported component "${this.exportName}" is not a class`);
184
+ throw new SbError(`Exported component "${this.exportName}" is not a class`);
184
185
  if (!isComponentBase(ctor.prototype))
185
- throw new TypeError(`Exported component "${this.exportName}" does not extends ComponentBase`);
186
+ throw new SbError(`Exported component "${this.exportName}" does not extends ComponentBase`);
186
187
  this._ctor = ctor;
187
188
  return this._ctor;
188
189
  }
@@ -216,11 +217,11 @@ export class ProcessorExtension {
216
217
  const module = await import(this.pkg.entryPoint);
217
218
  const ctor = module[this.exportName];
218
219
  if (!ctor)
219
- throw new TypeError(`Exported processor "${this.exportName}" not found in package "${this.pkg.name}"`);
220
+ throw new SbError(`Exported processor "${this.exportName}" not found in package "${this.pkg.name}"`);
220
221
  if (typeof ctor !== 'function')
221
- throw new TypeError(`Exported processor "${this.exportName}" is not a class`);
222
+ throw new SbError(`Exported processor "${this.exportName}" is not a class`);
222
223
  if (!isProcessorBase(ctor.prototype))
223
- throw new TypeError(`Exported processor "${this.exportName}" does not extends ProcessorBase`);
224
+ throw new SbError(`Exported processor "${this.exportName}" does not extends ProcessorBase`);
224
225
  this._ctor = ctor;
225
226
  return this._ctor;
226
227
  }
@@ -1,4 +1,5 @@
1
1
  import semver from 'semver';
2
+ import { SbError } from '../classes/sb-error.js';
2
3
  import { COMPONENT_OPTIONS, PROCESSOR_OPTIONS } from '../constants.js';
3
4
  import { ComponentExtension, ExtensionPackage, ProcessorExtension, } from './extension-package.js';
4
5
  import { normalizeComponentMetadata, normalizeProcessorMetadata, } from './helpers.js';
@@ -24,7 +25,7 @@ export var ExtensionRegistry;
24
25
  const cmp = findComponent(className, version);
25
26
  if (cmp)
26
27
  return cmp;
27
- throw new Error(`Component "${className}" version "${version}" not found in registry`);
28
+ throw new SbError(`Component "${className}" version "${version}" not found in registry`);
28
29
  }
29
30
  ExtensionRegistry.getComponent = getComponent;
30
31
  /**
@@ -42,7 +43,7 @@ export var ExtensionRegistry;
42
43
  function getProcessor(className, version = '*') {
43
44
  const cmp = findProcessor(className, version);
44
45
  if (!cmp) {
45
- throw new Error(`Processor "${className}" version "${version}" not found in registry`);
46
+ throw new SbError(`Processor "${className}" version "${version}" not found in registry`);
46
47
  }
47
48
  return cmp;
48
49
  }
@@ -75,7 +76,7 @@ export var ExtensionRegistry;
75
76
  async function registerComponent(ctor) {
76
77
  const _metadata = Reflect.getMetadata(COMPONENT_OPTIONS, ctor);
77
78
  if (!_metadata)
78
- throw new TypeError(`Class "${ctor.name}" has no component metadata.`);
79
+ throw new SbError(`Class "${ctor.name}" has no component metadata.`);
79
80
  if (_metadata.abstract)
80
81
  return;
81
82
  const metadata = await normalizeComponentMetadata(_metadata);
@@ -100,7 +101,7 @@ export var ExtensionRegistry;
100
101
  async function registerProcessor(ctor) {
101
102
  const _metadata = Reflect.getMetadata(PROCESSOR_OPTIONS, ctor);
102
103
  if (!_metadata)
103
- throw new TypeError(`Class "${ctor.name}" has no processor metadata.`);
104
+ throw new SbError(`Class "${ctor.name}" has no processor metadata.`);
104
105
  if (_metadata.abstract)
105
106
  return;
106
107
  const metadata = await normalizeProcessorMetadata(_metadata);
@@ -1,5 +1,5 @@
1
1
  import { isAny, isBase64, isBoolean, isDateString, isEmail, isHex, isNumber, isString, isTime, isURL, validator, vg, } from 'valgen';
2
- import { SbError } from '../classes/sb-error.js';
2
+ import { SbValidationError } from '../classes/sb-error.js';
3
3
  import { StackExecutor } from '../classes/stack-executor.js';
4
4
  import { Profile, VariableType, } from '../models/index.js';
5
5
  import { getModelsDocument } from '../models-document.js';
@@ -14,7 +14,7 @@ export function decodeProfile(materializedMetadata, rawProfile, options) {
14
14
  issues
15
15
  .map(issue => `- ${issue.message}. Location: /${issue.location}`)
16
16
  .join('\n ');
17
- throw new SbError(msg, {
17
+ throw new SbValidationError(msg, {
18
18
  workerId: rawProfile.id,
19
19
  issues,
20
20
  });
@@ -75,11 +75,7 @@ function _codecProcessElement(stackExecutor, codec, metadata, profile, options)
75
75
  for (const [k, defComponent] of Object.entries(metadata.components)) {
76
76
  if (!profile.components[k]) {
77
77
  if (defComponent.required) {
78
- stackExecutor.issues.push({
79
- message: `Component "${k}" is required`,
80
- severity: 'error',
81
- location: `/components/${k}`,
82
- });
78
+ stackExecutor.issues.push(new SbValidationError(`Component "${k}" is required`));
83
79
  }
84
80
  continue;
85
81
  }
@@ -1,5 +1,5 @@
1
1
  import { clone, merge, omitUndefined } from '@jsopen/objects';
2
- import { SbError } from '../classes/sb-error.js';
2
+ import { SbValidationError } from '../classes/sb-error.js';
3
3
  import { StackExecutor } from '../classes/stack-executor.js';
4
4
  import { VariableType, } from '../models/index.js';
5
5
  import { ExtensionRegistry } from '../registry/extension-registry.js';
@@ -13,7 +13,7 @@ export function materializeMetadata(profile) {
13
13
  issues
14
14
  .map(issue => `- ${issue.message}. Location: /${issue.location}`)
15
15
  .join('\n ');
16
- throw new SbError(msg, {
16
+ throw new SbValidationError(msg, {
17
17
  workerId: profile.id,
18
18
  issues,
19
19
  });
@@ -67,12 +67,12 @@ function _materializeComponents(stackExecutor, metadata, profile) {
67
67
  const profileComponent = profile?.components?.[componentName];
68
68
  if (!profileComponent) {
69
69
  if (metadataComponent.required)
70
- throw new Error(`Component "${componentName}" should be configured`);
70
+ throw new SbValidationError(`Component "${componentName}" should be configured`);
71
71
  return;
72
72
  }
73
73
  /** istanbul ignore next */
74
74
  if (!profileComponent.className)
75
- throw new Error(`"className" property required`);
75
+ throw new SbValidationError(`"className" property required`);
76
76
  const reg = ExtensionRegistry.getComponent(profileComponent.className);
77
77
  materializedComponent.className = profileComponent.className;
78
78
  materializedComponent.variables = merge({}, [reg.metadata.variables || {}, metadataComponent.variables || {}], { deep: 'full' });
@@ -80,14 +80,14 @@ function _materializeComponents(stackExecutor, metadata, profile) {
80
80
  if (metadataComponent.className) {
81
81
  if (materializedComponent.className &&
82
82
  materializedComponent.className !== metadataComponent.className)
83
- throw new Error(`Selected component class "${profileComponent.className}" do not match with definition component class (${metadataComponent.className}).`);
83
+ throw new SbValidationError(`Selected component class "${profileComponent.className}" do not match with definition component class (${metadataComponent.className}).`);
84
84
  }
85
85
  else {
86
86
  const requiredInterfaces = metadataComponent.interfaces || [];
87
87
  const implementations = reg.metadata.interfaces || [];
88
88
  const filtered = requiredInterfaces.filter(x => !implementations.includes(x));
89
89
  if (filtered.length) {
90
- throw new Error(`Selected component "${profileComponent.className}" do not implements some of required interfaces (${filtered.join(',')}).`);
90
+ throw new SbValidationError(`Selected component "${profileComponent.className}" do not implements some of required interfaces (${filtered.join(',')}).`);
91
91
  }
92
92
  }
93
93
  if (materializedComponent.variables) {