Background Together with folks at , we have developed a tool, with some of magic that dependency injection provides, to make it more enjoyable and easy to implement CRUD API. Brainhub is a lightweight, open-source framework that can be used with some tools like Express.js (at the moment, Express is the only supported web framework) and database management tools like TypeORM. Hadron even consists of packages like , which makes it possible to simply structure the data that API outputs, even with selected fields visible only to some “groups”. Hadron hadron-serialization Hadron does not affect backend performance in any negative way, it’s aim is to improve the experience while building and maintaining API and providing high efficiency. A short overview of Hadron + use cases Setting up the backend with Hadron requires just a few lines of code. Firstly, I will show you how to set up a basic hello world route using and . Hadron Express.js A hello-world example built with Hadron The most important thing here is the object. We specify there the configuration for Hadron packages ( for ). The constructor method returns a promise with the object, which is used for dependency injection. We will dig deeper into that later in this article. config routes hadron-express container As you’ve probably noticed, developing a larger app can be a nightmare while using more Hadron packages. The config object would be massive — just imagine all routes there. Of course, we can merely divide routes to multiple files and import them. This is where the package comes in. This standalone package allows you to specify the path and extensions for files to be automatically imported for you. [hadron-json-provider](https://github.com/brainhubeu/hadron/tree/master/packages/hadron-json-provider) It is quite useful for splitting our routes into different files. By default, the package accepts key in Hadron’s config which accepts an array of paths and extensions and then uses the package to load routes from these files. hadron-express routePaths hadron-json-provider Hadron vs plain express.js Remember that Hadron — tested using with . does not affect the performance of your backend application api-benchmark 10000 runs sampled with concurrency: 10000 Hadron provides you the space and tools that over your project and creates an abstract layer over frameworks like . boost productivity and maintainability Express.js The main advantage of using Hadron is that you can quickly and to manage databases, , and shape your output based on user type. Everything is simply done for you and easily configured by you. easily select various tools provide security Creating API using Hadron is so simple that you can split your routes into different files without caring about dependencies, instances, etc. This is because of dependency injection, which is used in the route’s callback function. When you register any package, it is initialized using the provided config and put in the container under the specific key(s) that you can later use in the route’s callback functions. Hadron’s dependency injection Hadron provides the option to store data or object instances in something we call the . It also keeps data initialized by Hadron packages, for example, database repositories in the package. container hadron-typeorm While registering an item in the container, you can choose one of the lifetime options, which are: — this is the default behavior. While getting data from the container, you get back the same thing that was registered. value — always returns the same instance of registered class/constructor function. singleton — always returns a new instance of registered class/constructor function. transient Dependency injection is used in the route’s callbacks, which allows you to access any container values easily. Let’s assume we will store a string in our container under the key and we would like to access it on our route. Hello World message After sending a request to , you will receive: http://localhost:8080/ "Message stored in container: Hello World" That is how you can access container items. Most packages store items there so you can easily perform some actions or retrieve data you want. You may now think about accessing variables that are very often used in our routes like , , , etc.. These data are provided as the first parameter in the callback’s function. request headers params body query In this case, the route’s response will return the requests’ header object. Hadron packages quick overview We’ve only discovered a few packages so far, especially . Let’s discuss some of the official Hadron packages. hadron-express All examples presented in this article are . Feel free to play with them. available at GitHub here Hadron-typeorm This package wraps and integrates the package with Hadron. It gives us the ability to register and access or the easy way. TypeORM repositories migrations To connect with your database, you simply import the package and provide the connection object to Hadron’s configuration. hadron-typeorm Let’s say we have a table with users. To retrieve one record with its ID we will use an endpoint like . Our callback may look like this: /user/1 Looks easy, right? But what about a connection to our database? As I mentioned before, we need to provide a connection object to our config while initializing Hadron. In the example below, we will use the MySQL database. To create a repository in TypeORM we need to provide an . Hadron will then register a repository from it and register under the key containing the entity name and suffix — entity will register in a container under the key. entity Repository User userRepository Hadron-serialization Serializer allows you to specify the shape of your JSON output. Imagine a user sends a request to the API with an auth token. With a package, we can easily take care of fields this user will see based on his permissions. hadron-serialization In the example below, there is only one endpoint — (we will take care of two groups, mod and admin). **/:group?** In our case, there will be a list of users that will be returned as a response for that endpoints. Every user should see the user’s first and last name, users in the group should also see an email and will see all of them with an additional ID field. mod admin This is the data we will use: So to make the package work, we need to initialize it. But before that, we should define a schema for our data. We can define it in another file or simply provide an object literal in Hadron’s config. We will save it as an external JSON file. hadron-serialization So, to make it clear — a schema is an object and should contain: — simply the schema’s name. We will need that to recognize the schema when serializing data. name — these field contains an array of objects. Each object holds the name of the key that will be serialized, it’s type and groups that it should be visible to (if groups are empty, they’re visible to everyone). properties Notice that if you don’t specify some key in a schema, it ! won’t be visible Okay, now we have our data defined and the schema needed in the serialization package, let’s define next our Hadron instance. Our file should look like this: index.js The above example is basically an example of an entire app made using Hadron. So it’s simple to set up the package — all we need to do is to declare schema objects, which will be used to shape our data and provide them in the config. hadron-serialization Next when we would like to serialize our data, simply take the object from the container and execute the serialize method. serializer Hadron-events The package allows you to make use of built-in events or even declare your own custom events, bind listeners to them and simply emit them at any point of the application lifecycle. Hadron-events Currently, in Hadron, there are few built-in events which are listed in the package docs, which you can find . here To initialize our simple event handlers, we need to provide listeners to events. In the example below, we will provide the package configuration in ’s bootstrapping function. hadron-events hadron-core So we are including our listeners in an external file. In our example, we will try the , which will emit events right before every request happens. handleRequestCallbackEvent In the package, we can also emit our own events at any part of application’s lifecycle. We are going to listen for 2 events with a simple name like and . We will then emit that event when user send a request to , if the has have a value of . hadron-events successEvent failEvent _/:key_ key foo And the last step in our example will be to implement listeners. As said before, we are going to create 2 listeners, one for successEvent and one for failEvent. That will allow us to emit these custom events from any place in our app. For simplicity in our example, that place is the request’s callback. Links — If you are looking for more open source projects. Brainhub’s Github — If you are looking for PROs to help you build your JavaScript Application. Brainhub About and it’s official packages are maintained by the Brainhub development team. It is funded by Brainhub and the names and logos for Brainhub are trademarks of Brainhub Sp. z o.o.. You can check other supported/developed by our teammates. Hadron open-source projects We love open-source JavaScript software! See our other projects or hire us to build your next web, . desktop and mobile application with JavaScript o_riginally published at_ Post written by Damian Bartosik , Brainhub.eu
Share Your Thoughts