Get application url from DI with Nest.js - nestjs

In the main.ts we can get the application url with app.getUrl().
Is is possible to get it from a service via DI ?
async function bootstrap() {
const app = await NestFactory.create(AppModule);
await app.listen(3000);
console.log(`Application is running on: ${await app.getUrl()}`);
}
bootstrap();

You can define app variable outside of bootstrap method and export it:
export let app: INestApplication;
async function bootstrap() {
app = await NestFactory.create(AppModule);
await app.listen(3000);
console.log(`Application is running on: ${await app.getUrl()}`);
}
bootstrap();

Related

How to run Koa server before Tests in Mocha?

I read a lot of answers to similar questions already but can't figure out what is wrong in my code.
this is my server.js file
const Koa = require('koa')
const Router = require('koa-router')
const app = new Koa()
app.use(require('koa-bodyparser')())
const login = (ctx, next) => {
ctx.body = ctx.request.body
}
const router = new Router({ prefix: '/api' })
router.get('/test', (ctx, next) => {
ctx.body = { resp: 'GET REQUEST /test WORKING' }
})
router.post('/login', login)
app.use(router.routes())
module.exports = app
this is my index.js file
const server = require('./server')
server.listen(3000, () => {
console.log('App is running on http://localhost:3000')
})
and this is my mocha test file
const axios = require('axios').default
const expect = require('chai').expect
const app = require('./server')
describe('7-module-3-task', () => {
describe('test', function () {
let server
before(done => {
server = app.listen(3000, done)
})
after(async () => {
server.close()
})
it('should return response from server', async () => {
const response = await axios.get('http://localhost:3000/api/test')
expect(response.data, 'should return object with key "resp').to.have.property('resp')
})
})
})
It's working okay when I make a request in Postman. I tried multiple options already but I still get 404 response, as I understand test is performed before server started running...? How can I make it working ?
First, I would move the startup (app.listen) directly into the server.js (not critical, but maybe more simpler because the require in your test would then already start your server:
const Koa = require('koa')
const Router = require('koa-router')
const app = new Koa()
app.use(require('koa-bodyparser')())
const router = new Router({ prefix: '/api' })
router.get('/test', (ctx, next) => {
ctx.body = { resp: 'GET REQUEST /test WORKING' }
})
app.use(router.routes())
app.listen(3000); // can be a parameter but for simplicity hardcoded here
module.exports = app
In your test you then do:
let chai = require('chai');
let chaiHttp = require('chai-http');
let server = require('./server'); // this will already start up your server
describe('API Tests', () => {
describe('TEST endpoint', () => {
it('It should GET response from test endpoint', (done) => {
chai.request('http://localhost:3000')
.get('/api/test/') // be sure to have a trailing '/' !!
.end((err, res) => {
res.body.should.have.property('resp');
done();
});
})
});
});
One more hint: maybe in your original code you just have to make sure, that you have a trailing / when calling your route in the test.
Code snippets not testet but I hope you get the idea.
I shared the same code with 2 of my friends and they managed to run tests successfully.
I tested it on my other laptop after this and tests worked as well.
The problem was in the port. 3000 port was used as a default one in the debugger in Webstorm, not sure why but still.
Launching the server on port 3000 in a regular way, not in mocha tests, worked very well but in tests, it did not work, not sure why.
So for those who ever face something similar, check the default port of the debugger or any other built-in server.

TS newb question: compile error starting Apollo Server trying to resolve promise

Hopefully someone can help with this -- I'm trying to start apollo server in a TypeScript project running Express. My app.ts is below. I am getting the following error:
Argument of type '(value: unknown) => void' is not assignable to parameter of type '() => void'.ts(2769)
I think this has something to do with resolving that last promise to actually start the server. Thanks for answering this presumably very basic question!
import express from 'express';
import { ApolloServer } from 'apollo-server-express';
import depthLimit from 'graphql-depth-limit';
import compression from 'compression';
import cors from 'cors';
import schema from './schema';
const corsConfig = {
origin: '*',
credentials: true
};
async function startApolloServer() {
const server = new ApolloServer({ schema, validationRules: [depthLimit(7)] });
await server.start();
const app = express();
app.use(cors(corsConfig));
app.use(compression());
server.applyMiddleware({ app });
await new Promise(resolve => app.listen({ port: 4000 }, resolve));
console.log(`🚀 Server ready at http://localhost:4000${server.graphqlPath}`);
}
Try the following to match the expected callback signature:
async function startApolloServer() {
const server = new ApolloServer({ schema, validationRules: [depthLimit(7)] });
await server.start();
const app = express();
app.use(cors(corsConfig));
app.use(compression());
server.applyMiddleware({ app });
await new Promise(resolve => app.listen({ port: 4000 }, (value) => resolve(value)));
console.log(`🚀 Server ready at http://localhost:4000${server.graphqlPath}`);
}
Hopefully that helps!

Ensure express app is running before starting mocha tests

I built an API for a couchbase database, using express and node.js. My problem is that when I run my tests some of them fail, because the server is not fully running. I found a solution here https://mrvautin.com/ensure-express-app-started-before-tests on how to solve this issue. The article stated that in order to solve this issue, you have to add an event emitter in your server file like this
app.listen(app_port, app_host, function () {
console.log('App has started');
app.emit("appStarted");
});
and then add this, in your test file
before(function (done) {
app.on("appStarted", function(){
done();
});
});
I have tried this, here is my implementation
Server File
app.listen(config['server']['port'], function(){
app.emit("appStarted");
logger.info("Listening")
})
Test File
before(function(done){
app.on("appStarted", function(){
done();
})
});
I keep on getting the following error
1) "before all" hook in "{root}":
Error: Timeout of 2000ms exceeded. For async tests and hooks, ensure "done()" is called; if returning a Promise, ensure it resolves.
at listOnTimeout (internal/timers.js:549:17)
at processTimers (internal/timers.js:492:7)
The article is from 2016, so I was thinking that maybe the syntax has been deprecated. I was wondering if someone could please help point me in the right direction?
You can add the below condition, more info see "Accessing the main module".
if (require.main === module) {
// this module was run directly from the command line as in node xxx.js
} else {
// this module was not run directly from the command line and probably loaded by something else
}
E.g.
index.ts:
import express from 'express';
const app = express();
const port = 3000;
app.get('/', (req, res) => {
res.sendStatus(200);
});
if (require.main === module) {
app.listen(port, () => {
console.log('App has started');
});
}
export { app, port };
index.test.ts:
import { app, port } from './';
import http from 'http';
import request from 'supertest';
describe('63822664', () => {
let server: http.Server;
before((done) => {
server = app.listen(port, () => {
console.log('App has started');
done();
});
});
after((done) => {
server.close(done);
console.log('App has closed');
});
it('should pass', () => {
return request(server)
.get('/')
.expect(200);
});
});
integration test result:
(node:22869) ExperimentalWarning: The fs.promises API is experimental
63822664
App has started
✓ should pass
App has closed
1 passing (26ms)
!Hi World! My little solution here:
Check this: All depends of your testing markup...
For example, I'm using Mocha and Chai Assertion Library.
const express = require('express');
const request = require("request");
const http = require("http");
const expect = require("chai").expect;
require('dotenv').config();
describe('Server', function() {
const { PORT } = process.env;
const app = express();
before((done) => {
http.Server = app.listen(PORT, () => {
console.log(`Listening Node.js server on port: ${PORT}`);
done();
});
});
it('should return 404 response code status', () => {
const url = `http://localhost:${PORT}/api/v1/yourPath`;
return request(url, (err, response, body) => {
/* Note this result 'cause I don't have any get('/')
controller o function to return another code status
*/
expect(response.statusCode).to.equal(404);
});
})
});

How get response from express server for ajax query in nuxtjs

I'm want to get data from the node/express server after send ajax query from any page of the nuxtjs app.
Usually, for getting and sending ajax query in PHP server, I'm do like this $_GET['var']; echo json_encode('Server got data');
Now I want to use node server express for saving data in mongodb.
When I trying to send a query, response return full code of file test.js.
File index.vue
methods: {
onServer() {
this.$axios.get('/server/test').then(res => {
console.log('res', res.data)
})
}
}
File test.js
var express = require('express');
var app = express();
app.get('*', function (req, res) {
res.send('Hello World!');
});
app.listen(3000, function () {
console.log('Example app listening on port 3000!');
});
File server/index.js
const express = require('express')
const consola = require('consola')
const { Nuxt, Builder } = require('nuxt')
const app = express()
// Import and Set Nuxt.js options
const config = require('../nuxt.config.js')
config.dev = !(process.env.NODE_ENV === 'production')
async function start() {
// Init Nuxt.js
const nuxt = new Nuxt(config)
const { host, port } = nuxt.options.server
// Build only in dev mode
if (config.dev) {
const builder = new Builder(nuxt)
await builder.build()
} else {
await nuxt.ready()
}
// Give nuxt middleware to express
app.use(nuxt.render)
// Listen the server
app.listen(port, host)
consola.ready({
message: `Server listening on http://${host}:${port}`,
badge: true
})
}
start()
I'm a new user node, please help me!
Your main issue is that you are targeting "test.js" in your axios url. This is why it responds with the file rather than what the get route should respond with.
So try with:
this.$axios.get('http://nuxt-profi/server/test').then(...
and see what you get. You should also be able to access that in the browser, just go to your url http://nuxt-profi/server/test and it should show your "Hello World" reponse.
However I can't be sure how you have set all this up. Are you running this as development? In which case maybe you should access it as http://localhost:3000/server/test but maybe you have virtual hosts configured like this. Also, is this a separate backend api or are you trying this as server middleware?
If this doesn't help please give us more info about your project setup and we'll go from there.

jest-puppeteer on bitbucket / no exit, stuck on success

Running jest-puppeteer with the following express config :
import express from "express";
import path from "path";
import webpack from 'webpack';
import config from '../webpack.config';
const port = 3200;
const app = express();
const compiler = webpack(config);
app.use(require('webpack-dev-middleware')(compiler, {
noInfo: true,
publicPath: config.output.publicPath
}));
app.listen(port, function (error) {
if(error) console.log(error);
});
with the following simple test :
describe('Google', () => {
beforeAll(async () => {
await page.goto('http://localhost:3200')
})
it('should display "demo" text on page', async (done) => {
await expect(page).toMatch('Your cart');
done();
});
});
The jest-puppeteer config is the following :
module.exports = {
server: {
command: './node_modules/babel-watch/babel-watch.js ./test/server.js',
port: 3200,
},
};
I'm having trouble on my bitbucket pipeline; all tests are passing but the commands never exits
What would be the reason for it being stuck ? Is the webpack conf involved ?
Just ran the very same test scripts on semaphore, everything works smoothly
thx a lot for any advised answers

Resources