Node.js nut-ioc usage

nut-ioc npm package is a simple, lightweight and fast IoC Container Framework.

nut-ioc injects dependencies run-time so that developers don't need to require modules.

Developers can implement in their codes following OOP basics, principles, patterns and concepts and probably more than that 🙂

  • Separation of Concern(SoC)
  • Single Responsibility Principle(SRP)
  • Open Closed Principle
  • Dipendency Inversion(Injection) Principle(DIP)
  • Chain of Responsibility Pattern
  • Aspect Oriented Programming

you can reach github repository.

https://github.com/nodejs-projects-kenanhancer/nut-ioc

Installing nut-ioc with npm

npm i nut-ioc

Demo GitHub Repository

You can find different usages of nut-ioc framework in separate brances.

https://github.com/nodejs-projects-kenanhancer/nut-ioc-basic-demo.git

Branch list
load-dependencies-with-dependencyPath
load-dependencies-with-dependencyPath-and_dynamically
load-dependencies-with-different-loaders
load-dependencies-with-interceptors
load-dependencies-with-new-loaders-and-filters
load-dependencies-with-programatic-notation
nut-swagger-usage

Real life Example

This example code is very simple. But, developers never have this kind of simple scenario in real life project.

Classic code

Suppose that we have greeting service like below. This code example is very usual in Node.js world.

nut-ioc Syntax

nut-ioc can use your node.js modules automatically. But, you need to export from your module and nut-ioc specific object.

Dependency Basic Syntax

No need to specify ServiceName and Namespace.

you can consume helper.js node.js module with helper name. But, if you don't want to update fileName, then you can change serviceName in ServiceName field.

if you want to export any object or function, then use Service field.

Dependency Basic Constructor Syntax

As you can see I didn't use ServiceName and Namespace fields, those fields will have default values.

nut-ioc is injecting dependencies from function always so if you have any dependency, use module.exports.Service = ({ helper }) => this syntax then you can use helper dependency in your code, then this constructor function should return an object or function.

one more time, if you have any dependency you should return one function(constructor function) and that constructor function should return an object or direct function.

nut-ioc loading dependencies with directory path

if you want to ignore some files or folder in your project, then use ignoredDependencies field in use function as below.

For example, node_modules folder has many folder and files, so you should ignore that folder.

nut-ioc loading dependencies with programatic dependency definition

you don't have to write your code in JavaScript files, nut-ioc is definition specific framework, so you just provide your dependency definition programmaticaly then nut-ioc will do its job again 🙂

nut-ioc loading dependencies with directory path and programatic dependency definition

nut-ioc loading dependencies with interceptors

I think that this is the most delicious part of code. The benefit of nut-ioc is not only Dependency Injection in run-time, nut-ioc can intercept your function calls. So that you can implement Aspect Oriented Programming, Separation of Concern etc 🙂

nut-ioc decreases your development time on any project and provide you many of best programming practices.

Output of above code

As you can see from output, it should function calls sequentialy with parameters and elapsed milliseconds. This is very simple implementation of nut-ioc, I am sure that you can extend this example better than me 🙂

$ node index

ENTRY: sayHello({"firstName":"Kenan","lastName":"Hancer","city":"London","mail":"kenanhancer@gmail.com"}) function
ENTRY: getFullName({"firstName":"Kenan","lastName":"Hancer"}) function
SUCCESS: getFullName function returns //Kenan Hancer: Elapsed milliseconds is 0
SUCCESS: sayHello function returns //Hello Kenan Hancer: Elapsed milliseconds is 0
Hello Kenan Hancer
ENTRY: sayGoodbye({"firstName":"Kenan","lastName":"Hancer","city":"London","mail":"kenanhancer@gmail.com"}) function
ENTRY: getFullName({"firstName":"Kenan","lastName":"Hancer"}) function
SUCCESS: getFullName function returns //Kenan Hancer: Elapsed milliseconds is 0
SUCCESS: sayGoodbye function returns //Goodbye, Kenan Hancer: Elapsed milliseconds is 0
Goodbye, Kenan Hancer

nut-ioc loading and grouping YAML and JSON dependencies

I thought that nut-ioc can do more that above features. So, I added dependency loader functionality, there are three default loaders in nut-ioc (node.js module, JSON, YAML dependency loaders)

In addition to this, if you want to group dependencies under one folder and later consume with folder name, then you need to add metadata.js file under folder. nut-ioc will collect all dependencies under swaggerDefinitions variable in run-time. Notice that metadata.js content standard nut-ioc dependency definition file, so if you don't want to use folder name as a group variable name then just use Namespace field 🙂

Output of above code

Notice that swaggerDefinitions is written in output console, greeting-definition-json.json and greeting-definition-yaml.yaml files are converted to JavaScript object in run-time.

$ node index

ENTRY: sayHello({"firstName":"Kenan","lastName":"Hancer","city":"London","mail":"kenanhancer@gmail.com"}) function
ENTRY: getFullName({"firstName":"Kenan","lastName":"Hancer"}) function
SUCCESS: getFullName function returns //Kenan Hancer: Elapsed milliseconds is 0
SUCCESS: sayHello function returns //Hello Kenan Hancer: Elapsed milliseconds is 0
Hello Kenan Hancer
ENTRY: sayGoodbye({"firstName":"Kenan","lastName":"Hancer","city":"London","mail":"kenanhancer@gmail.com"}) function
ENTRY: getFullName({"firstName":"Kenan","lastName":"Hancer"}) function
SUCCESS: getFullName function returns //Kenan Hancer: Elapsed milliseconds is 0
SUCCESS: sayGoodbye function returns //Goodbye, Kenan Hancer: Elapsed milliseconds is 0
Goodbye, Kenan Hancer

swaggerDefinitions: {
  greetingDefinitionJson: {
    swagger: '2.0',
    info: {
      description: 'English Greeting API',
      version: '1.0.0',
      title: 'English Greeting API'
    },
    basePath: '/greeting-api/v1',
    schemes: [ 'http' ],
    paths: { '/sayHello': [Object], '/sayGoodbye': [Object] }
  },
  greetingDefinitionYaml: {
    swagger: '2.0',
    info: {
      description: 'English Greeting API',
      version: '1.0.0',
      title: 'English Greeting API'
    },
    basePath: '/greeting-api/v1',
    schemes: [ 'http' ],
    paths: { '/sayHello': [Object], '/sayGoodbye': [Object] }
  }
}

nut-ioc loading dependencies with new dependency loaders and filters

I thought that this features will never be enough, as I said before, nut-ioc has YAML, JSON, Node.js module loaders by default, but if you need to load CSV, CSS, JPEG, TXT, XML, HTML, BSON files as a JavaScript object or string, then you can inject new dependency loaders in nut-ioc with useConfiguration or useDependencyLoader functions.

There is also dependency filter functionality in nut-ioc. nut-ioc already has one default dependency filter which filters ignored files. But, if you need more custom filters then use useConfiguration or useDependencyLoader functions.

Shortly, nut-ioc can use your custom dependency loaders and filters in run-time.

Leave a Reply