How to open port with Fastify? - nestjs

I'm trying to use Fastify with my project, but when I want to start the server, it isn't opening the specific port.
I'm creating the server like this:
import { NestFactory } from "#nestjs/core";
import { NestFastifyApplication, FastifyAdapter } from "#nestjs/platform-fastify";
import { AppModule } from "./app.module";
async function bootstrap() {
const app = await NestFactory.create<NestFastifyApplication>(
AppModule,
new FastifyAdapter()
);
await app.listen(3000, '0.0.0.0');
}
bootstrap();
It says the application is successfully started, but when I check with netstat -ano,
the address(0.0.0.0:3000) isn't there.
The server logs:

Related

How to resolve socket.io Error "TransportError: xhr poll error"

I want to make a socket.io server using NestJS.
I'm trying communication between server and client on localhost.
however, client(socket.io-client) throw the following error.
TransportError: xhr poll error
the server was running on localhost:3000. and the client was run from node command(node index.js)
server (mock.gateway.ts)
import { SubscribeMessage, WebSocketGateway, MessageBody, ConnectedSocket, WebSocketServer} from '#nestjs/websockets';
import { Socket } from 'socket.io';
#WebSocketGateway()
export class MockGateway {
#WebSocketServer()
server;
#SubscribeMessage('mock')
mock(
#MessageBody() data: string,
#ConnectedSocket() socket: Socket
): void {
console.log(data);
}
}
server (main.ts)
import { NestFactory } from '#nestjs/core';
import { AppModule } from './app.module';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
await app.listen(3000);
}
bootstrap();
client
import { io, Socket } from 'socket.io-client';
const socket = io('ws://localhost:3000', {
path: '/socket.io',
});
socket.emit('mock', 'mock');
I tried set transports to the sockect.io-client. but it makes a timeout error.
import { io, Socket } from 'socket.io-client';
const socket = io('ws://localhost:3000', {
path: '/socket.io',
transports: ['websocket'],
});
socket.emit('mock', 'mock');
Maybe a mistake in module settings. so I use the wscat is debug-tool. It throws the following error, I'm wondering why wscat can connest Nest server.
$ wscat -c ws://localhost:3000/socket.io/\?transport=websocket
Connected (press CTRL+C to quit)
error: Invalid WebSocket frame: RSV1 must be clear
If anyone has any ideas, please comment.

How do I serve static files in NestJS using fastify?

How does one serve static files in NestJS using fastify? I can't seem to find any recent examples of setting this up properly. I have my main.ts set up like this:
main.ts
// This must be the first thing imported in the app
import 'src/tracing';
import * as winston from 'winston';
import fastifyStatic, { FastifyStaticOptions } from '#fastify/static';
import { NestFactory } from '#nestjs/core';
import {
FastifyAdapter,
NestFastifyApplication,
} from '#nestjs/platform-fastify';
import { path } from 'app-root-path';
import { WinstonModule } from 'nest-winston';
import { doc } from 'prettier';
import { AppModule } from 'src/app.module';
import join = doc.builders.join;
async function bootstrap() {
const app = await NestFactory.create<NestFastifyApplication>(
AppModule,
new FastifyAdapter(),
{
logger: WinstonModule.createLogger({
format: winston.format.combine(
winston.format.timestamp(),
winston.format.json(),
),
transports: [new winston.transports.Console()],
}),
rawBody: true,
},
);
await app.register(require('#fastify/static'), {
root: require('app-root-path').resolve('/client'),
prefix: '/client/', // optional: default '/'
});
// eslint-disable-next-line #typescript-eslint/ban-ts-comment
// #ts-ignore
app.get('/another/path', function (req, reply) {
reply.sendFile('index.html');
});
app.enableShutdownHooks(); // terminus needs this to listen for SIGTERM/SIGKILL
await app.listen(3002, '0.0.0.0');
console.log(`Application is running on: ${await app.getUrl()}`);
}
bootstrap();
The static file I'm attempting to serve is client/index.html.
However, when I run my app I get the following error: Nest could not find /another/path element (this provider does not exist in the current context).
I've also tried setting up my app.module.ts Modules like this:
app.module.ts
#Module({
imports: [
...configModules,
...domainModules,
...libraryModules,
ServeStaticModule.forRoot({
rootPath: require('app-root-path').resolve('/client'),
renderPath: '/client/*',
}),
],
controllers: [AppController],
providers: [AppService],
})
This leads to the following error:
/Users/ewu/Desktop/Projects/janus/node_modules/#nestjs/platform-fastify/node_modules/fastify/lib/route.js:286
throw new FST_ERR_DUPLICATED_ROUTE(opts.method, opts.url)
^
FastifyError: Method 'HEAD' already declared for route '/'
at Object.addNewRoute (/Users/ewu/Desktop/Projects/janus/node_modules/#nestjs/platform-fastify/node_modules/fastify/lib/route.js:286:19)
at Object.route (/Users/ewu/Desktop/Projects/janus/node_modules/#nestjs/platform-fastify/node_modules/fastify/lib/route.js:211:19)
at Object.prepareRoute (/Users/ewu/Desktop/Projects/janus/node_modules/#nestjs/platform-fastify/node_modules/fastify/lib/route.js:144:18)
at Object._head [as head] (/Users/ewu/Desktop/Projects/janus/node_modules/#nestjs/platform-fastify/node_modules/fastify/fastify.js:247:34)
at fastifyStatic (/Users/ewu/Desktop/Projects/janus/node_modules/#fastify/static/index.js:370:17)
Here are the relevant packages and their versions:
"#nestjs/serve-static": "^3.0.0",
"fastify-static": "^4.7.0",
"fastify": "^4.8.1",
"#nestjs/platform-fastify": "^9.1.2",
"#fastify/static": "^6.0.0",
I'm using version 9.0.0 of Nest and v16.15.0 of Node.
You most likely have a #Get() under a #Controller() (most likely your AppController) which is binding the GET / route already. Fastify won't let you bind two handlers to the same route. Because of this, you either need to change the #Get() to have some sort of route associated with it, change the ServeStaticModule to have a different served route, or use a global prefix to modify the rest of the server routes (I believe this leaves the server static module unaffected).

NestJS: Initialize certain MongoDB collection as soon as connection is made

I am very new to NestJs and I would like to build a web app that uses MongoDB.
So what I gonna do is whenever as soon as app is loading mongodb connection should be made and add some logic in callback function.
With Express framework this is the code of logic what I wanna do.
mongoose
.connect(mongoDB, {
user: process.env.MONGODB_USER,
pass: process.env.MONGODB_PASSWORD,
useNewUrlParser: true,
useUnifiedTopology: true,
})
.then(async () => {
//don't show the log when it is test
if (process.env.NODE_ENV !== "test") {
console.log("Connected to %s", mongoDB);
console.log("MongoDB is connected ... \n");
initDB.InitializeDB();
dailyReport.DailyReport();
}
})
.catch((err) => {
console.error("App starting error:", err.message);
process.exit(1);
});
In above code there are two functions.
1st: Logging if DB connection is successful or failed
2nd: When successful I initialize some collections and exit app if failed
I saw NestJs documentation to implement this logic here
import { Module } from '#nestjs/common';
import { MongooseModule } from '#nestjs/mongoose';
#Module({
imports: [MongooseModule.forRoot('mongodb://localhost/nest')],
})
export class AppModule {}
But I am not sure where is the callback function for MongoDB connection.
Can anyone give me answer for this by implementing Express logic using NestJs?
You could do the initialization in the onModuleInit() lifecycle method. Check here for more information: https://docs.nestjs.com/fundamentals/lifecycle-events#lifecycle-events
Code would look like this:
#Module({
imports: [MongooseModule.forRoot('mongodb://localhost/nest')],
})
export class AppModule {
#InjectConnection() private connection: Connection;
onModuleInit() {
// execute logic + access mongoDB via this.connection
}
}

Fastify Passport on application loading getting "initialize not a function"

While trying to use the fastify-passport plugin as per documented on the npm documentation i am getting the beloe error while the application is initializing:
server.register(fastifypassport.initialize());
^
TypeError: fastifypassport.initialize is not a function
my index.js looks as below:
'use strict'
import fastify from 'fastify'
import fasifyPassport from 'fastify-passport'
import fastifySecureSession from 'fastify-secure-session'
import loginController from './controller/loginController.js';
import { readFileSync } from 'fs';
import { join } from 'path';
const server = fastify({
logger: true
})
// set up secure sessions for fastify-passport to store data in
server.register(fastifySecureSession, { key: readFileSync(join("", "secret-key")) });
// initialize fastify-passport and connect it to the secure-session storage. Note: both of these plugins are mandatory.
server.register(fasifyPassport.initialize());
server.register(fasifyPassport.secureSession());
server.listen(3000, function (err, address) {
if (err) {
fastify.log.error(err)
process.exit(1)
}
server.log.info(`server listening on ${address}`)
})
Have tried a couple of options like import of the function in {} as well but that also did not work.. Any help would be highly appreciated...

Socket connection from NextJS to a node backend

I am trying to implement a basic socket connection from my NextJS client side (running on localhost:3000) to my NestJs server (running on localhost:3003).
The server code looks like this
ChatGateway.ts
import {
SubscribeMessage,
WebSocketGateway,
OnGatewayInit,
WebSocketServer,
OnGatewayConnection,
OnGatewayDisconnect,
} from '#nestjs/websockets';
import {
Logger
} from '#nestjs/common';
import {
Socket,
Server
} from 'socket.io';
#WebSocketGateway()
export class ChatGateway implements OnGatewayInit, OnGatewayConnection, OnGatewayDisconnect {
#WebSocketServer() server: Server;
private logger: Logger = new Logger('ChatGateway');
#SubscribeMessage('msgToServer')
handleMessage(client: Socket, payload: string): void {
console.log(payload);
this.server.emit('msgToClient', payload);
}
afterInit(server: Server) {
this.logger.log('Init');
}
handleDisconnect(client: Socket) {
this.logger.log(`Client disconnected: ${client.id}`);
}
handleConnection(client: Socket, ...args: any[]) {
this.logger.log(`Client connected: ${client.id}`);
this.server.emit('msgToClient', "payload");
}
}
ChatModule.ts
import { Module } from '#nestjs/common';
import { TypeOrmModule } from '#nestjs/typeorm';
import { ChatGateway } from "./chat.gateway";
#Module({
imports: [],
controllers: [],
providers: [ChatGateway],
})
export class ChatModule {}
AppModule.ts
#Module({
imports: [TypeOrmModule.forRoot(), NewsletterModule, AuthModule, UsersModule, ListingsModule, ChatModule]
})
export class AppModule {
constructor(private connection: Connection) {}
But when I try to connect to the socket from my client side
import {
io
} from "socket.io-client";
function Chat() {
const socket = io("http://127.0.0.1:3003");
useEffect(() => {
console.log("chat useEffect")
socket.emit('msgToServer', "message")
}, [])
socket.on('msgToClient', (message) => {
console.log(message)
})
I am not getting any errors, but also there is nothing happening when I emit or try to receive events from the server.
Even the server console doesnt log the emit events. The only thing that happens on the server is that the client gets connected and disconnected all the time without even me doing anything
Any idea why cant I connect to the sockets and why is the server constantly connecting and disconnecting even if I disable the socket connection form the client side.
Thanks!
Socket.io client needs to be version 2. Version 3 and 4 are breaking changes and don't communicate with a v2 server. Once Nest v8 hits, socket.io v4 will be used by default.

Resources