# Roadmap
## The breaking changes
+ replace env provider by simple env function helper >> env(key, fallback) => process.env
+ refactor config provider in order to remove file autoload >> config: {}
+ replace middleware property by middleware decorator in handler
+ move rpc feature from core to transport
+ move handler registry to service container
+ move 'service' decorator from handler to service provider 'prefix' + 'suffix'
## The cool features
+ allow functional handler > function(app) { return { method: 'aa', middlerares: [], handler: (params, context) => result; };
+ allow functional middleware > function (app) { return () => result }
* outside of core, only use container based class (ex: queueHandlerFactory => container factory for QueueHandler)
+ new functional bootstrap/serviceprovider API see [here](#Zoom-on-functionnal-API)
+ add test tools package
+ CI tools
* new packages :
* @alex tu as des besoins particulier ?
* add a generic handler factory
## The cleanup
+ update documentation
+ add examples
+ a serial medium posts :santa:
* increase code coverage
+ move core to root projet
+ rename packages to extensions
* extension API future **dropped**
+ package clean up
* cli :
* **drop** http start by cli
* **move** scafolding > ?
* **keep** command for now :)
* config: **refactor**
* connection manager: **dropped**
* connection-*: **move** to other repository
* ~~env~~ : **dropped**
* handler-http: **move** to extension
* handler-redis: **move** to extension
* logger: **move** to extension
* notification: **move** to other repository
* package-acl: **move** to pdc repository
* queue: **move** to extension
* repository: **move** to pdc repository
* template: **move** to pdc repository
* transport-http: **move** to extension
* transport-redis: **move** to extension
* validator: **move** to extension
* the context object: to any // generic >> low level configuration in builder
## Zoom on functionnal API
### Current syntax
*ServiceProvider.ts*
```typescript=
@serviceProvider({
nativeextension1config: ...
nativeextension2config: ...
customextension3config: ...
...
})
export class ServiceProvider extends AbstractServiceProvider {
extensions: [CustomExtension3];
}
```
*bootstrap.ts*
```typescript=
export const bootstrap = Bootstrap.create([
serviceProviders: [ServiceProvider],
transports: {
http: CustomHttp...
...
},
...
])
```
### Proposal
Motivations :
* avoid verbose boilerplate
* increase control over bootstraping
* reduce basic bundle size
```typescript=
export const ServiceProvider = Builder
.create()
.prefix('serviceName')
.config({
toto: 1,
})
.use(new ProviderExtension([
...,
...,
...,
]))
.use(new ConnectionExtension([
[MongoConnection, 'connections.mongo'],
[RedisConnection, 'connections.redis'],
]))
.use((builder) => build.bind(...).expose())
.bind(new Config({
...
}))
.expose(Action)
.plug(ExtAction) // .inject() ?
.build()
```
At this point, we have a parametred service provider tagged class.
We could use transport directly (or not).
```typescript=+
.transport(HttpTransport)
.start(8000);
```
Or we could use this anywhere
```typescript=
Builder
.create()
.load(myChildrenServiceProvider)
.build();
```
### API
- `prefix(k: string)`: set the prefix for service provider
- `use(extension: RegisterHookInterface)`: add extension on service provider
- `load(serviceProvider: ServiceContainerInterface)`: add a child service provider
- `bind(function.. )`: add a container binding
- `expose(action: Newable<HandlerInterface>)`: add an action
- `build():Newable<ServiceContainerInterface>`: compile this to a new ServiceProvider
- `transport(transport: Newable<TransportInterface>)`: set the transport > sugar for `bind(tranport, TransportInterfaceResolver)`
- `start(...transportParams: string)`: start app
```
export const handler = {
method: 'get',
middlewares: [
['validate', {}]
],
handle: function (app) {
return (params, context) => {
const mongo = app.get(MongoConnection);
mongo....
return ...
}
},
}
let init = app
.create()
.prefix('user/')
.bind(AjvValidator)
.bind(new MongoConnection(url))
.build()
.init();
let handler = init.wrap(handler);
```