@lakutata-module/service
v1.2.7
Published
Lakutata Service Module
Downloads
250
Maintainers
Readme
Features
- Micro-service
- Distributed Events
- Cross nodes service invoking (directly|chain|parallel)
- Scalable
Quickstart
Service Examples
Service Registry Example
const serviceRegistryApp = await createApp({
id: 'registry.service.test.app',
name: 'test-service-registry',
modules: {
registry: {
class: ServiceRegistry,
logger: true,
redisOptions: {
host: '192.168.0.132'
},
token: '123456'
}
}
})
serviceRegistryApp.Logger.info(serviceRegistryApp.getID(), 'is running')
Service Provider Example
const serviceProviderApp = await createApp({
id: 'provider.service.test.app',
name: 'test-service-provider',
modules: {
provider: {
class: Service,
registry: '127.0.0.1',
token: '123456',
controllers: [
`${path.resolve(__dirname, '../controllers')}/**/*`
],
logger: true
}
}
})
serviceProviderApp.Logger.info(serviceProviderApp.getID(), 'is running')
Service Consumer Example
const serviceConsumerApp = await createApp({
id: 'consumer.service.test.app',
name: 'test-service-consumer',
modules: {
consumer: {
class: Service,
registry: '127.0.0.1',
token: '123456',
services: [
`${path.resolve(__dirname, '../services')}/**/*`
],
logger: true
}
}
})
serviceConsumerApp.Logger.info(serviceConsumerApp.getID(), 'is running')
setTimeout(async () => {
serviceConsumerApp.Logger.info('Service consumer test begin:')
const consumer = serviceConsumerApp.Modules.get<Service>('consumer')
consumer.channel('test').on('test', (x, y, z) => {
serviceConsumerApp.Logger.debug('Received channel event [test] data:', x, y, z)
})
consumer.channel('test').triggerOne('test', 'a', 'b', 'c')
try {
serviceConsumerApp.Logger.info('Start test manually service invoking:')
serviceConsumerApp.Logger.debug('Service chain invoke result:', await consumer.invoke({
serviceId: 'provider.service.test.app',
data: {test: true},
transform: (response) => {
return {name: response}
}
},
{
serviceId: 'provider.service.test.app',
data: {
test: true,
ccc: true
},
transform: (response) => {
return `this is response:${response}`
}
}))
serviceConsumerApp.Logger.debug('Service parallel invoke result:', await consumer.parallel({
serviceId: 'provider.service.test.app',
data: {test: true},
transform: (response) => {
return `this is response:${response}`
}
}, [
{
serviceId: 'provider.service.test.app',
data: {test: true},
transform: (response) => {
return {test: true}
}
},
{
serviceId: 'provider.service.test.app',
data: {
test: true,
name: 'manually service invoking',
ccc: true
},
transform: (response) => {
return `this is response:${response}`
}
}
]
))
} catch (e) {
serviceConsumerApp.Logger.error(e)
}
}, 3000)
Service Controller Examples (For Service Provider)
TestController1
@Controller()
export class TestController1 extends BaseController {
@Accept(Validator.Object({
name: Validator.String.required()
}))
@PATTERN({test: true, ccc: true})
public async serviceTest(a: any) {
return a.name
}
@PATTERN({test: true, abd: true})
public async serviceTest2() {
return [true, true]
}
}
TestController2
@Controller()
export class TestController2 extends BaseController {
@PATTERN({test: true})
public async tc2Test() {
return 'this is tc2 test'
}
}
@lakutata/core required.
Documentations
Configure Service Module (Registry|Provider|Consumer)
Service Registry Options
| Name | DataType | Default | Required | Description | |--------------|----------------|---------|----------|-------------------------------------------------------------------------------------------------------------| | port | Number | 6911 | No | Service registry listen port | | token | String | | No | Service registry access toke for clients | | logger | Boolean/Logger | false | No | Log service registry activities | | redisOptions | RedisOptions | | No | If not set, the service registry is running in single node mode, else it will build a cluster automatically |
Service Options
| Name | DataType | Default | Required | Description | |-------------|-----------------|-----------|----------|------------------------------------------------------------------------------------------------------------------------------------------| | registry | String | | Yes | Service registry address url,if port not specified, it will be 6911 | | controllers | String\String[] | | No | The service controllers load path/paths | | timeout | Number | 60000(ms) | No | Service consumer invoke remote service timeout | | retry | Number | 0 | No | If service consumer invoke remote service return a retryable error, it will retry to invoke again until the retry chances decreases to 0 | | token | String | | No | Service registry access token | | logger | Boolean\Logger | false | No | Log service consumer activities |
Service Controller
A valid service controller MUST extend BaseController, and it MUST decorate by @Controller(), the @Controller() decorator has an optional parameter:
@Controller(basicPattern: TPattern = {})
if basicPattern set, all patterns declared in the controller will contain it.
In the service controller, @PATTERN() decorator is for decorate method, the parameter is the invoking pattern.
@PATTERN(pattern: TPattern)
Classes
ServiceRegistry (Module)
- fetchServices(appId?: string | RegExp): { [appId: string]: IServiceInfo[] }
Service (Module)
- async invoke(...params: TInvokeObject[]): Promise
- async parallel(...params: (TInvokeObject | TInvokeObject[])[]): Promise<any[]>
- channel(name: string): Channel
- trigger(event: string, ...args: any[]): boolean
- triggerAll(event: string, ...args: any[]): boolean
- triggerOne(event: string, ...args: any[]): boolean
- directTrigger(serviceId: string, event: string, ...args: any[]): boolean
- directTriggerAll(serviceId: string, event: string, ...args: any[]): boolean
- directTriggerOne(serviceId: string, event: string, ...args: any[]): boolean
- privateTrigger(event: string, ...args: any[]): boolean
- privateTriggerAll(event: string, ...args: any[]): boolean
- privateTriggerOne(event: string, ...args: any[]): boolean
- on(event: string, listener: (...args: any[]) => void): Channel
- once(event: string, listener: (...args: any[]) => void): Channel
- off(event?: string, listener?: (...args: any[]) => void): Channel
- channels(): string[]
- async fetchServices(appId?: string | RegExp): Promise<{ [appId: string]: IServiceInfo[] }>
BaseController
Decorators
- @Controller
- @PATTERN
Exceptions
- BrokenServiceInvokeException
- IncorrectTokenException
- InvalidRegistryProtocolException
- PatternNotFoundException
- RequestException
- RequestTimeoutException
- ServiceClientInitializationException
- ServiceInvokeTimeoutException
- ServiceProviderNotFoundException
- ServiceRegistryInitializationException
Examples
Examples can be found in project src/tests.
How to Contribute
Please let us know how can we help. Do check out issues for bug reports or suggestions first.