-
-
Notifications
You must be signed in to change notification settings - Fork 98
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
ddc0383
commit f1989d6
Showing
18 changed files
with
553 additions
and
33 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,26 +1,29 @@ | ||
import { InfoInterface } from "./info"; | ||
import { BaseModel } from "./base"; | ||
|
||
import { AsyncAPIDocumentV2 } from "./v2"; | ||
import { AsyncAPIDocumentV3 } from "./v3"; | ||
|
||
export interface AsyncAPIDocumentInterface extends BaseModel { | ||
version(): string; | ||
info(): InfoInterface | ||
import { ExternalDocsMixinInterface, SpecificationExtensionsMixinInterface, TagsMixinInterface } from "./mixins"; | ||
|
||
export interface AsyncAPIDocumentInterface extends BaseModel, ExternalDocsMixinInterface, SpecificationExtensionsMixinInterface, TagsMixinInterface { | ||
version(): string; | ||
info(): InfoInterface; | ||
} | ||
|
||
export function newAsyncAPIDocument(json: Record<string, any>): AsyncAPIDocumentInterface { | ||
const version = json['asyncapi']; // Maybe this should be an arg. | ||
if (version == undefined || version == null || version == '') { | ||
throw new Error('Missing AsyncAPI version in document'); | ||
} | ||
const version = json['asyncapi']; // Maybe this should be an arg. | ||
if (version == undefined || version == null || version == '') { | ||
throw new Error('Missing AsyncAPI version in document'); | ||
} | ||
|
||
const major = version.split(".")[0]; | ||
switch (major) { | ||
case '2': | ||
return new AsyncAPIDocumentV2(json); | ||
case '3': | ||
return new AsyncAPIDocumentV3(json); | ||
default: | ||
throw new Error(`Unsupported version: ${version}`); | ||
} | ||
} | ||
const major = version.split(".")[0]; | ||
switch (major) { | ||
case '2': | ||
return new AsyncAPIDocumentV2(json); | ||
case '3': | ||
return new AsyncAPIDocumentV3(json); | ||
default: | ||
throw new Error(`Unsupported version: ${version}`); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,33 @@ | ||
import { BaseModel } from "../base"; | ||
|
||
export interface BindingsMixinInterface { | ||
hasBindings(): boolean; | ||
hasBindings(protocol: string): boolean; | ||
bindings(): any[]; // TODO: Change type to Tag | ||
bindings(protocol: string): any; // TODO: Change type to Tag | ||
} | ||
|
||
export abstract class BindingsMixin extends BaseModel implements BindingsMixinInterface { | ||
hasBindings(): boolean; | ||
hasBindings(protocol: string): boolean; | ||
hasBindings(protocol?: string): boolean { | ||
const bindings = this.bindings(protocol!); | ||
if (typeof protocol === 'string') { | ||
return Boolean(bindings); | ||
} | ||
return Object.keys(bindings || {}).length > 0; | ||
}; | ||
|
||
|
||
bindings(): any[]; | ||
bindings(protocol: string): any; | ||
bindings(protocol?: string): any | any[] { | ||
if (typeof protocol === 'string') { | ||
if (this._json.bindings && typeof this._json.bindings === 'object') { | ||
return this._json.bindings[protocol]; | ||
} | ||
return; | ||
} | ||
return this._json.bindings || {}; | ||
}; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,16 @@ | ||
import { BaseModel } from "../base"; | ||
|
||
export interface DescriptionMixinInterface { | ||
hasDescription(): boolean; | ||
description(): string | undefined; | ||
} | ||
|
||
export abstract class DescriptionMixin extends BaseModel implements DescriptionMixinInterface { | ||
hasDescription() { | ||
return Boolean(this._json.description); | ||
}; | ||
|
||
description(): string | undefined { | ||
return this._json.description; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
import { BaseModel } from "../base"; | ||
|
||
export interface ExternalDocsMixinInterface { | ||
hasExternalDocs(): boolean; | ||
externalDocs(): any; // TODO: Change type to ExternalDocs | ||
} | ||
|
||
export abstract class ExternalDocsMixin extends BaseModel implements ExternalDocsMixinInterface { | ||
hasExternalDocs(): boolean { | ||
return !!(this._json.externalDocs && Object.keys(this._json.externalDocs).length); | ||
}; | ||
|
||
// TODO: implement it when the ExternalDocs class will be implemented | ||
externalDocs(): any { | ||
return; | ||
}; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,41 @@ | ||
import type { BaseModel } from '../base'; | ||
|
||
export * from './bindings'; | ||
export * from './description'; | ||
export * from './external-docs'; | ||
export * from './specification-extensions'; | ||
export * from './tags'; | ||
|
||
export interface Constructor<T = any> extends Function { | ||
new (...any: any[]): T; | ||
} | ||
|
||
export interface MixinType<T = any> extends Function { | ||
prototype: T; | ||
} | ||
|
||
export function Mixin(a: typeof BaseModel): typeof BaseModel; | ||
export function Mixin<A>(a: typeof BaseModel, b: MixinType<A>): typeof BaseModel & Constructor<A>; | ||
export function Mixin<A, B>(a: typeof BaseModel, b: MixinType<A>, c: MixinType<B>): typeof BaseModel & Constructor<A> & Constructor<B>; | ||
export function Mixin<A, B, C>(a: typeof BaseModel, b: MixinType<A>, c: MixinType<B>, d: MixinType<C>): typeof BaseModel & Constructor<A> & Constructor<B> & Constructor<C>; | ||
export function Mixin<A, B, C, D>(a: typeof BaseModel, b: MixinType<A>, c: MixinType<B>, d: MixinType<C>, e: MixinType<D>): typeof BaseModel & Constructor<B> & Constructor<C> & Constructor<D> & Constructor<D>; | ||
export function Mixin<A, B, C, D, E>(a: typeof BaseModel, b: MixinType<A>, c: MixinType<B>, d: MixinType<C>, e: MixinType<D>, f: MixinType<E>): typeof BaseModel & Constructor<A> & Constructor<B> & Constructor<C> & Constructor<D> & Constructor<E>; | ||
export function Mixin(baseModel: typeof BaseModel, ...constructors: any[]) { | ||
return mixin(class extends baseModel {}, constructors); | ||
} | ||
|
||
function mixin(derivedCtor: any, constructors: any[]): typeof BaseModel { | ||
constructors.forEach((baseCtor) => { | ||
Object.getOwnPropertyNames(baseCtor.prototype).forEach((name) => { | ||
if (name === 'constructor') { | ||
return; | ||
} | ||
Object.defineProperty( | ||
derivedCtor.prototype, | ||
name, | ||
Object.getOwnPropertyDescriptor(baseCtor.prototype, name) || Object.create(null), | ||
); | ||
}); | ||
}); | ||
return derivedCtor; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,39 @@ | ||
import { BaseModel } from "../base"; | ||
|
||
import { EXTENSION_REGEX } from '../../constants'; | ||
|
||
export interface SpecificationExtensionsMixinInterface { | ||
hasExtensions(): boolean; | ||
hasExtensions(name: string): boolean; | ||
extensions(): Record<string, any>; | ||
extensions(name: string): any; | ||
} | ||
|
||
export abstract class SpecificationExtensionsMixin extends BaseModel implements SpecificationExtensionsMixinInterface { | ||
hasExtensions(): boolean; | ||
hasExtensions(name: string): boolean; | ||
hasExtensions(name?: string): boolean { | ||
const extensions = this.extensions(name!); | ||
if (typeof name === 'string') { | ||
return Boolean(extensions); | ||
} | ||
return Object.keys(extensions || {}).length > 0; | ||
}; | ||
|
||
extensions(): any[]; | ||
extensions(name: string): any; | ||
extensions(name?: string): any | any[] { | ||
if (typeof name === 'string') { | ||
name = name.startsWith('x-') ? name : `x-${name}`; | ||
return this._json[name]; | ||
} | ||
|
||
const result: Record<string, any> = {}; | ||
Object.entries(this._json).forEach(([key, value]) => { | ||
if (EXTENSION_REGEX.test(key)) { | ||
result[String(key)] = value; | ||
} | ||
}); | ||
return result; | ||
}; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,36 @@ | ||
import { BaseModel } from "../base"; | ||
|
||
export interface TagsMixinInterface { | ||
hasTags(): boolean; | ||
hasTags(name: string): boolean; | ||
tags(): any[]; // TODO: Change type to Tag | ||
tags(name: string): any; // TODO: Change type to Tag | ||
} | ||
|
||
export abstract class TagsMixin extends BaseModel implements TagsMixinInterface { | ||
hasTags(): boolean; | ||
hasTags(name: string): boolean; | ||
hasTags(name?: string): boolean { | ||
if (!Array.isArray(this._json.tags) || !this._json.tags.length) { | ||
return false; | ||
} | ||
if (typeof name === 'string') { | ||
return this._json.tags.some((t: any) => t.name === name); | ||
} | ||
return true; | ||
}; | ||
|
||
|
||
// TODO: return instance(s) of Tag model when the Tag class will be implemented | ||
tags(): any[]; // TODO: Change type to Tag | ||
tags(name: string): any; // TODO: Change type to Tag | ||
tags(name?: string): any | any[] { // TODO: Change type to Tag | ||
if (typeof name === 'string') { | ||
if (Array.isArray(this._json.tags)) { | ||
return this._json.tags.find((t: any) => t.name === name); | ||
} | ||
return; | ||
} | ||
return this._json.tags || []; | ||
}; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
import { BaseModel } from '../../../src/models/base'; | ||
import { BindingsMixin, Mixin } from '../../../src/models/mixins'; | ||
|
||
class Model extends Mixin(BaseModel, BindingsMixin) {}; | ||
|
||
const doc1 = { bindings: { amqp: { test: 'test1' } } }; | ||
const doc2 = { bindings: {} }; | ||
const doc3 = {}; | ||
const d1 = new Model(doc1); | ||
const d2 = new Model(doc2); | ||
const d3 = new Model(doc3); | ||
|
||
describe('Bindings mixin', function() { | ||
describe('.hasBindings()', function() { | ||
it('should return a boolean indicating if the object has bindings', function() { | ||
expect(d1.hasBindings()).toEqual(true); | ||
expect(d2.hasBindings()).toEqual(false); | ||
expect(d3.hasBindings()).toEqual(false); | ||
}); | ||
|
||
it('should return a boolean indicating if the bindings object has appropriate binding by name', function() { | ||
expect(d1.hasBindings('amqp')).toEqual(true); | ||
expect(d1.hasBindings('http')).toEqual(false); | ||
expect(d2.hasBindings('amqp')).toEqual(false); | ||
expect(d3.hasBindings('amqp')).toEqual(false); | ||
}); | ||
}); | ||
|
||
describe('.bindings()', function() { | ||
it('should return a map of bindings', function() { | ||
expect(d1.bindings()).toEqual(doc1.bindings); | ||
}); | ||
|
||
it('should return an empty object', function() { | ||
expect(d2.bindings()).toEqual({}); | ||
expect(d3.bindings()).toEqual({}); | ||
}); | ||
|
||
it('should return a binding object', function() { | ||
expect(d1.bindings('amqp')).toEqual(doc1.bindings.amqp); | ||
}); | ||
|
||
it('should return a undefined', function() { | ||
expect(d1.bindings('http')).toEqual(undefined); | ||
expect(d2.bindings('amqp')).toEqual(undefined); | ||
expect(d3.bindings('amqp')).toEqual(undefined); | ||
}); | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
import { BaseModel } from '../../../src/models/base'; | ||
import { DescriptionMixin, Mixin } from '../../../src/models/mixins'; | ||
|
||
class Model extends Mixin(BaseModel, DescriptionMixin) {}; | ||
|
||
const doc1 = { description: 'Testing' }; | ||
const doc2 = { description: '' }; | ||
const doc3 = {}; | ||
const d1 = new Model(doc1); | ||
const d2 = new Model(doc2); | ||
const d3 = new Model(doc3); | ||
|
||
describe('Description mixin', function() { | ||
describe('.hasDescription()', function() { | ||
it('should return a boolean indicating if the object has description', function() { | ||
expect(d1.hasDescription()).toEqual(true); | ||
expect(d2.hasDescription()).toEqual(false); | ||
expect(d3.hasDescription()).toEqual(false); | ||
}); | ||
}); | ||
|
||
describe('.description()', function() { | ||
it('should return a value', function() { | ||
expect(d1.description()).toEqual(doc1.description); | ||
expect(d2.description()).toEqual(''); | ||
}); | ||
|
||
it('should return an undefined', function() { | ||
expect(d3.description()).toEqual(undefined); | ||
}); | ||
}); | ||
}); |
Oops, something went wrong.