1.2.33 • Published 5 years ago

@jeaks03/overseer v1.2.33

Weekly downloads
-
License
MIT
Repository
github
Last release
5 years ago

Overseer

Overseer is a Typescript Aspect-Oriented framework for backend which takes inspiration from Spring-boot and Angular.

Installation

Before you begin, make sure your development environment includes Node.js® and an npm package manager.

Node.js

Overseer requires Node.js version 8.x or 10.x.

  • To check your version, run node -v in a terminal/console window.
  • To get Node.js, go to nodejs.org.

Creating a Overseer project is as simple as:

npx @jeaks03/typescript-base -o

The npx @jeaks03/typescript-base part creates a base for a typescript project and the -o flag lets the installer know that it is an Overseer framework and makes the proper adjustments.

Minimal 'Hello World' example

index.ts

import { Overseer } from '@jeaks03/overseer-core';
Overseer.serve(module, 8000);

my.controller.ts

import { Requisite, Pathway } from '@jeaks03/overseer-core';

@Requisite
export class MyController {

    @Pathway({ path:'/hello' })
    sayHello() {
        return {
            message: 'hello world!'
        }
    }
}

This example opens a http server that listens on port 8000 and registers a GET endpoint /hello that returns the "hello world" message. To start the application run:

npm run dev

Explaining the magic

  • The Overseer.serve(8000) line lets the framework know where the sources root is located, and what the port desired port is.
  • @Requisite makes transforms the class into an injectable and lets the framework find it. More on injectables and this decorator later.
  • @Pathway marks the method as a handler for the given path. The method is called when the endpoint is reached. More on this later.

Documentation

Section in which I explain how the framework functions.

Project Structure

For the framework to work correctly it must have it's directory structure as follows:

  • index.ts -- doesn't matter where it is. Preferably in /src
  • resources -- ( directory ) it must be one level above index.ts file. So if your main file is /src/index.ts then the resources directory must be /resources/.
  • public -- ( directory ) it must be inside the resources directory. /resources/public

In the resources directory can be stored any kind of project files you need and access them freely. Inside it is the public directory where all the files are visible to the http server.

Let's say that you have a file named index.html inside and the server open on port 8000. If you make a request on localhost:8000/index.html the file will be sent. Note: If the file is named index.html then the file will be available on both localhost:8000/index.html and localhost:8000/

Decorators

Documentation details regarding the decorators.

@Requisite -- and dependency injection

This decorator is used to mark the class as an injectable. Yes, Overseer also handles dependency injection in a manner similar to Angular's. In order to inject a requisite it must be a parameter for the constructor.

In order to let the framework find the requisites, all files that contain such classes must have their name ending in

  • .controller.ts
  • .service.ts
  • .component.ts

    Example of dependency injection:

    my.service.ts

    import { Requisite } from '@jeaks03/overseer-core';
    
    @Requisite
    export class MyService {
        public log(message: string): void {
            console.log(message);
        }
     }

    my-other.service.ts

    import { Requisite } from '@jeaks03/overseer-core';
    import MyService from './my.service';
    
    @Requisite
    export class MyOtherService {
       constructor(private myService: MyService) {}
    
        private onInit(): void {
            this.myService.log('I got initialized!');
        }
     }

@Pathway

This decorator marks a method as the handler of the given path. It requires an argument of type WayDetails which has the following attributes:

  • path -- string: the path for the endpoint to map. Default: /
  • method -- string: http method. Default: GET
  • statusCode -- number: http status code. Default: 200
  • produces -- string[]: list of content types that can be produced by this handler. Default: ['application/json']
  • consumes -- string[]: list of content types that can be consumed by this handler. Default: ['application/json', 'multipart/form-data', 'application/x-www-form-urlencoded']
  • guards -- Guard[]: list of Guard implementations. This works just like Angular's guard security. Default: []

@LifecycleEvent

This decorator is used on requisites to mark a method as a lifecycle event. These events are triggered at a certain time during their life.

It accepts a string as a sort of event type to let it know when to trigger the method. These arguments are:

  • "onInit" -- method is triggered shortly after the instantiation
  • "afterInit" -- method is triggered after all requisites have been instantiated

@OnInit

Shorthand version of @LifecycleEvent('onInit')

@AfterInit

Shorthand version of @LifecycleEvent('afterInit')

Base classes 101

RequisiteManager

This class handles and contains all the requisites.

An instance of this class can be imported under the name of Requisites as a RestrictedRequisiteManager interface.

RestrictedRequisiteManager:

interface RestrictedRequisiteManager {
    addInstance: (instance, isController?: boolean) => void;
    find: <T>(clazz: Class<T>) => T;
    findByName: <T>(className: string) => T;
    findAll: <T>(clazz: Class<T>) => T[];
}

Authentication

In order to secure your application, you must provide an implementation of this class as a requisite. The default authentication implementation provided is NoAuthentication which basically behaves as if there is no security.

In order to create an instance for any Authentication implementation you have to pass a UserProvider to the constructor. UserProvider interface is a function that looks like this: (username: string) => UserDetails | Promise<UserDetails>

Overseer ships with the following implementations:

  • NoAuthentication
  • BasicAuthentication
  • JWTAuthentication

Here is an example of how to secure your application using basic auth:

export class SecurityComponent {
    constructor(private database: DatabasePlaceHolder) { }

    @OnInit()
    secureApp() {
        const auth = new BasicAuthentication((username: string) => this.database.findUser(username));
        Requisites.addInstance(auth);
    }
}

Converter

This class can be extended to create converters that understand other content types, and it looks like this:

export class Converter {
    public getContentType(): string;

    public canRead(target: string, contentType: string): boolean;
    public canWrite(target: any, contentType: string): boolean;
    
    public doWrite(target: any): string;
    public doRead(target: string): any;
}

This documentation is a work in progress. More will be added later.

License

MIT License

1.2.33

5 years ago

1.2.32

5 years ago

1.2.31

5 years ago

1.2.30

5 years ago

1.2.29

5 years ago

1.2.28

5 years ago

1.2.27

5 years ago

1.2.26

5 years ago

1.2.25

5 years ago

1.2.24

5 years ago

1.2.23

5 years ago

1.2.22

5 years ago

1.2.21

5 years ago

1.2.20

5 years ago

1.2.19

5 years ago

1.2.18

5 years ago

1.2.17

5 years ago

1.2.16

5 years ago

1.2.15

5 years ago

1.2.14

5 years ago

1.2.13

5 years ago

1.2.12

5 years ago

1.2.11

5 years ago

1.2.10

5 years ago

1.2.9

5 years ago

1.2.8

5 years ago

1.2.7

5 years ago

1.2.6

5 years ago

1.2.5

5 years ago

1.2.4

5 years ago

1.2.3

5 years ago

1.2.2

5 years ago

1.2.1

5 years ago

1.1.26

5 years ago

1.1.24

5 years ago

1.1.23

5 years ago

1.1.22

5 years ago

1.1.21

5 years ago

1.1.20

5 years ago

1.1.19

5 years ago

1.1.18

5 years ago

1.1.17

5 years ago

1.1.16

5 years ago

1.1.15

5 years ago

1.1.14

5 years ago

1.1.13

5 years ago

1.1.12

5 years ago

1.1.11

5 years ago

1.1.10

5 years ago

1.1.9

5 years ago

1.1.8

5 years ago

1.1.7

5 years ago

1.1.6

5 years ago

1.1.5

5 years ago

1.1.2

5 years ago

1.1.1

5 years ago

1.1.0

5 years ago

1.0.7

5 years ago

1.0.6

5 years ago

1.0.5

5 years ago

1.0.4

5 years ago

1.0.3

5 years ago

1.0.2

5 years ago

1.0.1

5 years ago

1.0.0

5 years ago