Skip to content

Commit

Permalink
Merge branch 'release/1.0.2' into main
Browse files Browse the repository at this point in the history
  • Loading branch information
cecric committed Oct 23, 2021
2 parents f740e50 + 7e854f3 commit 7a0dc13
Show file tree
Hide file tree
Showing 61 changed files with 11,225 additions and 1,793 deletions.
2 changes: 1 addition & 1 deletion .eslintrc.json
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,7 @@
"warn",
{
"selector": "CallExpression[callee.object.name='console']",
"message": "Please use the trf object 'terminal' for logging in production"
"message": "Please use the object 'logger' for logging in production"
}
],
"block-scoped-var": "error",
Expand Down
4 changes: 3 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -29,8 +29,10 @@ build/Release
node_modules

dist

dist/*

documentation
documentation/*

.env
.env.test
69 changes: 60 additions & 9 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,18 @@ Hexagonal Architecture API Framework/Skeleton in TypeScript and using nodeJS wit

## Why this Framework/Skeleton ?

Since I use typescript in my nodejs projects, I didn't find good architectures skeletons or frameworks that suit my needs. I practiced a lot the **hexagonal architecture** in projects and I think it is a vey good architecture for code projects to works with small/medium sized team. The aim of this project is to help developers to start a new REST API project (GraphQL will come soon) and concentrate only on their business code.
All API project I made used expressJS, and all of them start with the same code. That's the reason why we add a preconfigured initialization of expressJS.
Since I used typescript in my nodejs projects, I didn't find good architectures skeletons or frameworks that suit my needs. I practiced a lot the **hexagonal architecture** in projects and I find it is a vey good architecture for code projects to works with small/medium sized team. The aim of this project is to help developers to start a new REST API project (GraphQL will come soon) and concentrate only on their business code.
All nodejs API project I made used expressJS which is pretty complete and simple, and all of them start with the same code. That's the reason why it includes a preconfigured initialization of expressJS.
It use also the following projects for example (full list in package.json)
- [Express JS](https://expressjs.com/)
- [commander](https://github.com/tj/commander.js#readme)
- [Luxon](https://moment.github.io/luxon/#/)
- [Chalk](https://github.com/chalk/chalk)
- [AJV](https://ajv.js.org/)
- [TypeORM](https://typeorm.io/#/)

We aim to use a **KISS** (**Keep It Simple, Stupid**) strategy to build it, so we didn't take all the the names and the required interfaces from the hexagonal architecture which could be very complex (if you want to explore the complete hexagonal architecture, I recommend to read the following post: [DDD, Hexagonal, Onion, Clean, CQRS, ... How I put it all together](https://herbertograca.com/2017/11/16/explicit-architecture-01-ddd-hexagonal-onion-clean-cqrs-how-i-put-it-all-together/) from @hgraca).
We bring the hexagonal structure with the following folders:
I aim to use a **KISS** (**Keep It Simple, Stupid**) strategy to build it, so I didn't take all the the names and the required interfaces from the hexagonal architecture which could be very complex (if you want to explore the complete hexagonal architecture, I recommend to read the following post: [DDD, Hexagonal, Onion, Clean, CQRS, ... How I put it all together](https://herbertograca.com/2017/11/16/explicit-architecture-01-ddd-hexagonal-onion-clean-cqrs-how-i-put-it-all-together/) from @hgraca).
I bring the hexagonal structure with the following folders:
```
src
+-- application : This contain the code of the adapters for your input part. In our case, we integrate the REST Api input, the CLI input and the test input. SocketIO and GraphQL will come later.
Expand All @@ -40,7 +41,9 @@ src
```

### Comments
It doesn't involve any ORM currently, except a self made quite simple code to populate object with the result of a query. I am not convinced by the existings ORM. If you have any suggestions about it, feel free to propose.
This project use currently TypeORM and also an internal ORM quite simple code to populate object with the result of a query.
I added a wrapper to call command line from typeOrm directly with the framework.


## Prerequisites

Expand All @@ -49,16 +52,20 @@ The following commands are for linux debian, but it might work on Windows and Ma

## Installation

We didn't make an installer yet, so you have to pull the project in a temporary folder.
I didn't make an installer yet, so you have to pull the project in a temporary folder.
```
cd /my/temporary/folder
mkdir /tmp/mytemporaryfolder
cd /tmp/mytemporaryfolder
git clone https://github.com/cecric/hexapinod.git
```

You can then extract into your project folder :
You can then extract into your project folder (replace of course /my/project/folder by your destination for the project) :
```
mkdir /my/project/folder
cd ./hexapinod
git archive master | tar -xzf /my/project/folder
git archive --format=tar.gz v1.0.2 > hexapinod-1.0.2.tar.gz
tar -xzf ./hexapinod-1.0.2.tar.gz -C /my/project/folder
rm -rf /tmp/mytemporaryfolder
cd /my/project/folder
```

Expand Down Expand Up @@ -94,9 +101,53 @@ You can launch other command line that you defined by using other parameters in
node dist/bundle.js test
```

### ORM specifics
#### TypeORM
To perform ORM manipulation (in our case TypeORM), you can use the command line. To adapt to our specific directory structure, we wrapped the TypeORM CLI commands into a command line from the executable, like that :
```
npm run cli typeorm
```

Or if you have already compiled the project :
```
node dist/bundle.js typeorm <typeorm-command>...
```

Before starting anything with the ORM, you have to update the configurations with your needs into the folder:
```
config/dependencies/typeorm.json
```

#### Our native ORM
The native ORM I included into this framework is not a real ORM, but it will helps you if you don't want to use an ORM for any reason in your project (that's up to you), but still make requests to your database.
It only support mariadb/mysql databases at this time (PostgreSQL will come soon) and before start anything you have to update the configurations with your needs into the folder:
```
config/dependencies/mysql-manager.json
```

# Contributing
Feel free to use it in your projects and to fix some issues you can find by submiting a pull requests. Please let me know if you have any suggestions to improve this framework structure or some features you want/need!
And if you want [to buy me a coffee](https://www.buymeacoffee.com/cecric), I will be the most happy developper in the world.

# Roadmap and upcoming releases
Here you will find a list of the next features to include into the project and the upcoming development:
- Add GraphQL requests
- Add postgreSQL support on native ORM.
- Add right management on serialization of models.
- Add nosql (mongodb, redis and elasticsearch) support on native ORM.

## Upcoming release
- v1.0.3 - Release:
- Add API documentation system (OpenAPI and APIDocJS)
- Add Socket.IO full support

## Releases
- v1.0.2 - Pre-release:
- Add of TypeORM support and improvement of directory structure and documentation.
- Add comments on published code (JSDoc/Tsdoc)
- v1.0.1 - Pre-release: fix a small issue on the first commit.
- v1.0.0 - Pre-release: first release, includes the hexagonal architecture.


# License
This project is licensed under the MIT license.
29 changes: 17 additions & 12 deletions app.ts
Original file line number Diff line number Diff line change
@@ -1,28 +1,33 @@

//import app from './src/application/graphQL/server';
import * as dotenv from 'dotenv';
import { Command } from 'commander';
import terminal from '@dependencies/terminal/terminal';
import { logger } from '@dependencies/logger/logger';
import { BaseCommand } from './src/application/cli/basecommand';
import { SubProcessUsecases } from '@core/hexapinod/usecases/subprocess.usecases';
import { ApplicationServer } from '@application/api/server';
dotenv.config({ path: process.env.PWD + '/.env' });


const cliinstance = new Command();
/**
* Instance of Commander used to launch all Command.
* @date 21/10/2021 - 15:51:55
* @author cecric
*
* @type {Command}
*/
const cliinstance: Command = new Command();

// terminal.log(process.env.PWD + '/.env');
// terminal.log(process.env);
// // cliinstance.option('-h, --help', 'output help');
cliinstance.option('-d, --debug', 'output extra debugging');

cliinstance.command('server').description('launch the global server')
.option('--rest', 'launch the REST server')
.option('--graphql', 'launch the GraphQL server').action(() => {
import('./src/application/api/server').then((module) => {
module.default.launch();
}).catch(_err => {
terminal.error('cannot load app (api) module', _err);
});
try {
const server = new ApplicationServer();
server.launch();
} catch(_error) {
logger.error('cannot load application server (api) module', _error);
}
});

cliinstance.command('subprocess').description('launch a subprocess to perform an action in parallel (should not be called outside)')
Expand All @@ -34,5 +39,5 @@ cliinstance.command('subprocess').description('launch a subprocess to perform an
BaseCommand.importCommands (cliinstance).then(() => {
cliinstance.parse(process.argv);
}).catch ((e) => {
terminal.error('cannot load CLI commands', e);
logger.error('cannot load CLI commands', e);
});
18 changes: 18 additions & 0 deletions config/dependencies/typeorm.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
[
{
"type": "mysql",
"host": "{{process.env.DB_MAIN_HOST}}",
"port": "{{process.env.DB_MAIN_PORT}}",
"username": "{{process.env.DB_MAIN_USER}}",
"password": "{{process.env.DB_MAIN_PWD}}",
"database": "{{process.env.DB_MAIN_DBNAME}}",
"synchronize": true,
"logging": true,
"migrations": [
"src/infrastructure/migration/**/*.ts"
],
"subscribers": [
"src/infrastructure/subscriber/**/*.ts"
]
}
]
Loading

0 comments on commit 7a0dc13

Please sign in to comment.