nestjs-web-console
v1.1.2
Published
Web console for NestJs
Readme
Web Console for NestJS
Command from anywhere.
The goal is to create a simple web interface to run commands on the server.
Installation
npm install nestjs-web-console --save
yarn add nestjs-web-consoleThis library is a NestJs module with express dependency so make sure following libs are also installed.
npm install @nestjs/common @nestjs/core express rxjs --save
yarn add @nestjs/common @nestjs/core express rxjsUsage
Simple usage
import {Module} from '@nestjs/common';
import {WebConsoleModule} from "nestjs-web-console";
@Module({
imports: [WebConsoleModule.forRoot({
endpoint: 'console',
options: {
name: 'My App',
masterPin: 'very-secure-pin'
}
})]
})
export class AppModule {}Async usage
import {Module} from '@nestjs/common';
import {WebConsoleModule} from "nestjs-web-console";
@Module({
imports: [WebConsoleModule.forRootAsync({
endpoint: 'console',
useFactory: (configService: ConfigService) => ({
name: configService.get('SERVICE_NAME'),
masterPin: configService.get('MASTER_PIN')
}),
inject: [ConfigService]
})]
})
export class AppModule {}To use csv temp files run
npm install csv-express --saveand in main.ts file
import 'csv-express';Running more than one instance
By default sessions live in the memory of the process that created them. That is correct for a single instance and only for that — behind a load balancer, a request served by any other instance finds no session, and the console appears to reset. Point the console at a shared store instead:
import {Module} from '@nestjs/common';
import Redis from 'ioredis';
import {RedisConsoleSessionStore, WebConsoleModule} from "nestjs-web-console";
@Module({
imports: [WebConsoleModule.forRootAsync({
endpoint: 'console',
useFactory: (configService: ConfigService) => ({
name: configService.get('SERVICE_NAME'),
masterPin: configService.get('MASTER_PIN'),
store: new RedisConsoleSessionStore(new Redis({
host: configService.get('REDIS_HOST'),
port: +configService.get('REDIS_PORT'),
password: configService.get('REDIS_PASSWORD'),
}))
}),
inject: [ConfigService]
})]
})
export class AppModule {}RedisConsoleSessionStore takes the client you already have — the library keeps
no redis dependency of its own. The expected shape follows ioredis; node-redis
names its methods differently and needs a thin adapter. It opens one extra
connection (client.duplicate()) for the bus, because a subscribed Redis
connection cannot run ordinary commands; pass {subscriber} in the options if
you would rather supply it yourself. Implement ConsoleSessionStore for anything
else.
What is shared and what is not. Session logs, the login flag, and temp files
move to the store, so any instance can render the console and serve a download.
A running command does not move: a command suspended on readLine is a live
promise in the process that started it, and no store can carry that. So the
instance that starts a command keeps it until it ends, and input typed into any
other instance is forwarded there. If that instance dies mid-command, the session
says so and accepts the next command — the half-finished one is gone, which is
the honest outcome for a migration that was halfway through.
No sticky sessions are needed at the load balancer.
Test
npm run test