NestJS, Vue and nginx in different docker containers gives an CORS error - docker

NestJS container with enabled CORS:
import { NestFactory } from '#nestjs/core';
import { AppModule } from './app.module';
import { ValidationPipe } from '#nestjs/common';
import * as cors from 'cors';
async function bootstrap() {
const app = await NestFactory.create(AppModule);
app.use(cors({ origin: '*' }));
app.useGlobalPipes(new ValidationPipe());
await app.listen(8802);
}
bootstrap();
Vue container with requests to adress: https://api:8802
Error messages:
In Firefox:
Cross-Origin Request Blocked: The Same Origin Policy disallows reading the remote resource
In Chrome:
net::ERR_HTTP2_PROTOCOL_ERROR
I tried everything and nothing works

As per the NestJS docs, you should be able to use:
app.enableCors();
Or:
const app = await NestFactory.create(AppModule, { cors: true });
Instead of:
app.use(cors({ origin: '*' }));

Related

Having problems to add SSL to nuxt-axios web app on DOCKER

Well after many tests and brain burns trying with nginx, caddy and other resources to apply SSL I resort to this medium.
all the services are running on docker container.
I can't fully apply the certificates, rather I can't get my site to work with SSL, I can get to the login with https but then I can't get past that barrier:
to formalize:
https://example.com:3000/login (basic web domain)
https://example.com:3001/api (all my resources)
for https i have to change the axios BASEurl form: (recomendations from caddy forum)
this: http://example.com:3001/api
to this: https://example.com/api
to stop having the error of ERR_SSL_PROTOCOL_ERROR
I share my settings from my last failed attempt with caddy.
The truth is that at this point I don't know if it is a bad configuration problem on the caddy side or on the node-nuxt-axios side.
caddyfile:
{
debug
}
example.com {
handle_path /api/* {
reverse_proxy /api/* node:3001
}
handle {
reverse_proxy node:3000
}
}
emqx.example.com {
reverse_proxy emqx:18083
}
ws.example.com {
reverse_proxy emqx:8083
}
wss.example.com {
reverse_proxy emqx:8084
}
portainer.example.com {
reverse_proxy portainer:9000
}
here it goes nuxt.config.js
axios: {
baseURL: process.env.AXIOS_BASE_URL
},
env: {
mqtt_prefix: process.env.MQTT_PREFIX,
mqtt_host: process.env.MQTT_HOST,
mqtt_port: process.env.MQTT_PORT
},
server: {
https: true,
port: 3000,
host: '0.0.0.0',
},
serverMiddleware: {
https: true,
'/api': '~/api'
},
here is the index.js for api
const express = require("express");
const mongoose = require("mongoose");
const morgan = require("morgan");
const cors = require("cors");
const colors = require("colors");
const app = express();
require("dotenv").config();
//express config
app.use(morgan("tiny"));
app.use(express.json());
app.use(express.urlencoded({
extended: true,
})
);
app.use(cors());
app.use("/api", require("./routes/devices.js"));
app.use("/api", require("./routes/users.js"));
app.use("/api", require("./routes/templates.js"));
app.use("/api", require("./routes/datas.js"));
app.use("/api", require("./routes/webhooks.js"));
app.use("/api", require("./routes/emqxapi.js"));
app.use("/api", require("./routes/alarms.js"));
app.use("/api", require("./routes/controls.js")); // nueva funcion
app.use("/api", require("./routes/dataprovider.js"));
module.exports = app;
//listener
app.listen(process.env.API_PORT, () => {
console.log("API server listening on port " + process.env.API_PORT);
}); //api port 3001
for the record all services works like a charm on http, but having problems with secure comunication.

HonoJS CORS with cloudflare worker

I'm starting with cloudflare worker and used the recommended routing framework HonoJS.
Now the documented way of implementing cors functionallity doesn't work for me on my developement machine (npm run dev). I didn't test it on production, since I need it to work on development environment.
The problem is: The OPTION request gets an 404 returned.
How do I set a global CORS configuration?
My code is currently this:
import { Hono } from 'hono'
import { cors } from 'hono/cors'
import { basicAuth } from 'hono/basic-auth'
import { default as register } from './register.js'
const app = new Hono()
app.use('*', cors())
const user = new Hono()
// also tried: user.use('/*', cors())
user.post('/register', register)
// Register route groups
app.route('/user', user)
export default app
Also tried following cors call:
cors({
origin: 'http://localhost:5173',
allowHeaders: ['X-Custom-Header', 'Upgrade-Insecure-Requests'],
allowMethods: ['POST', 'GET', 'OPTIONS'],
exposeHeaders: ['Content-Length', 'X-Kuma-Revision'],
maxAge: 600,
credentials: true,
})
Thank you very much for your time!
I fixed it by adding a wildcard for options.
app.use('*', cors({
origin: 'http://localhost:5173',
allowHeaders: ['Content-Type', 'Authorization'],
allowMethods: ['POST', 'GET', 'OPTIONS'],
exposeHeaders: ['Content-Length'],
maxAge: 600,
credentials: true,
}))
app.options('*', (c) => {
return c.text('', 204)
})

Ionic 5 - API request working on browser, not on emulated IOS

I have this Ionic 5/Capacitor app, which I'm making an API call to a local server from, that server running on docker at localhost:3000. When I test from the browser, the request is made fine. From Postman it requests fine, too. In my XCode logs the emulator, I see this
[error] - ERROR {"headers":{"normalizedNames":{},"lazyUpdate":null,"headers":{}},"status":0,"statusText":"Unknown Error","url":"http://localhost:3000/pins","ok":false,"name":"HttpErrorResponse","message":"Http failure response for http://localhost:3000/pins: 0 Unknown Error","error":{"isTrusted":true}}
The really interesting part, is that I'm running Fiddler to monitor the request as it's made. Fiddler gets a 200 as well, I can even see the response data. So, Fiddler sees the proper network call, but then my Ionic app gets that error. That makes me feel like it's an Ionic/Emulator/IOS problem, but I don't have enough familiarity with Ionic to know right off the bat what it is.
Here's the code responsible for making the request:
ngOnInit() {
const request = this.http.get('http://localhost:3000/pins');
this.refresh$.subscribe(
(lastPos: { latitude?: any; longitude?: number }) => {
request.subscribe(data => {
if (data) {
this.addMarkersToMap(data, lastPos);
}
});
}
);
}
And the HTTPClient imported in the constructor is from Angular:
import { HttpClient } from '#angular/common/http';
I ended up having to use this package, doing a check on if I'm on mobile or not.
https://ionicframework.com/docs/native/http/
Try with this :
const request = this.http.get('http://localhost:3000/pins', { observe: 'response', withCredentials: true });
Solution 2 : capacitor.config.json
"server": {
"hostname": "localhost", (maybe try precising the port number too)
}
Solution 3 : On your Express server (from https://ionicframework.com/docs/troubleshooting/cors)
const express = require('express');
const cors = require('cors');
const app = express();
const allowedOrigins = [
'capacitor://localhost',
'ionic://localhost',
'http://localhost',
'http://localhost:8080',
'http://localhost:8100'
];
// Reflect the origin if it's in the allowed list or not defined (cURL, Postman, etc.)
const corsOptions = {
origin: (origin, callback) => {
if (allowedOrigins.includes(origin) || !origin) {
callback(null, true);
} else {
callback(new Error('Origin not allowed by CORS'));
}
}
}
// Enable preflight requests for all routes
app.options('*', cors(corsOptions));
app.get('/', cors(corsOptions), (req, res, next) => {
res.json({ message: 'This route is CORS-enabled for an allowed origin.' });
})
app.listen(3000, () => {
console.log('CORS-enabled web server listening on port 3000');
});

How to mqtt publish on NestJS?

I am making mqtt client using NestJS
I used #MessagePattern to confirm the subscription. (#Ctx, #Payload information is also checked normally.)
By the way, mqtt client information is created in app.module
I tried to use MqttClient using #Inject in Controller
The following error occurs in client.push.
Help me
(The controller's client.publish does not work.)
[main.ts]
async function bootstrap() {
/*const app = await NestFactory.create(AppModule);
await app.listen(3000);*/
const app = await NestFactory.createMicroservice<MicroserviceOptions>(
AppModule,{
transport:Transport.MQTT,
options:{
url : 'serverIp',
username : 'name',
password : 'pwd',
port : 1883,
protocol : 'mqtt'
}
},
);
app.listen(() =>{
console.log('[Agent Server is Listening...]');
})
}
bootstrap();
[app.module.ts]
#Module({
imports: [
ClientsModule.register([
{
name: 'MQ_CLIENT',
transport: Transport.MQTT,
options: {
host:'serverIp',
port:1883,
//protocol:'mqtt',
username:'name',
password:'pwd'
}
},
]),
ConfigModule
],
controllers: [AppController, VcController],
providers: [AppService, VcService],
})
export class AppModule {}
[Controller]
#Controller('vc')
export class VcController {
constructor(
#Inject(WINSTON_MODULE_NEST_PROVIDER) private readonly logger : LoggerService,
#Inject('MQ_CLIENT') private client : MqttClient
) {}
#MessagePattern('SomeTopic)
private tempFunction(#Ctx() context: MqttContext, #Payload() data){
this.client.publish('Publish TopicId', 'tttaaaaaa'); //The problem arises here
}
}
[Error Messgae]
TypeError: callback is not a function
at ClientMqtt.publish (C:\Wrok_Git\Demo\20201013_nestjsMqtt\mqtt-agent-02\node_modules\#nestjs\microservices\client\client-mqtt.js:104:13)
at VcController.vcTest (C:\Wrok_Git\Demo\20201013_nestjsMqtt\mqtt-agent-02\dist\controller\vc\vc.controller.js:40:21)
at C:\Wrok_Git\Demo\20201013_nestjsMqtt\mqtt-agent-02\node_modules\#nestjs\microservices\context\rpc-context-creator.js:44:33
at processTicksAndRejections (internal/process/task_queues.js:97:5)
at async C:\Wrok_Git\Demo\20201013_nestjsMqtt\mqtt-agent-02\node_modules\#nestjs\microservices\context\rpc-proxy.js:11:32
at async ServerMqtt.handleEvent (C:\Wrok_Git\Demo\20201013_nestjsMqtt\mqtt-agent-02\node_modules\#nestjs\microservices\server\server.js:61:32)
I did a little digging and came up with the following:
https://github.com/nestjs/nest/issues/6403
The gist of it, you need to call mqttClient.connect() beforehand, but you will not find that function in the interface for it.
This works for me -
constructor(#Inject('MQ_CLIENT') private client: ClientProxy) {
client.connect();
}
#MessagePattern('SomeTopic')
private tempFunction(#Ctx() context: MqttContext, #Payload() data) {
this.client.emit('help', 'data');
}
The code of question is all OK.
Only replace the line
this.client.publish('Publish TopicId', 'tttaaaaaa');
with
this.client.emit('Publish TopicId', 'tttaaaaaa')

using headers in HTTP client

I am trying to develop a dashboard in angular 7. I wanted to access an URL and get the JSON response in my dashboard. the problem is that my code works fine with an open source URL. but there are few end points, which have authorization request. Aim is to add the headers like the JWT token, authorization to my service and display the data in my dashboard.
I found few resources on the internet which are confusing.
Below is my code I tried in my service.ts
import { Injectable } from '#angular/core';
import {HttpClient} from "#angular/common/http";
#Injectable({
providedIn: 'root'
})
export class DataService {
constructor(private http: HttpClient) { }
getlocations() {
return this.http.get('https://jsonplaceholder.typicode.com/users')
}
}
Any lead on how to add the header and access them would be really helpful.
The simplest way is to modify a specific request by adding HttpHeaders with the authorization parameter. Here's an example:
getlocations() {
return this.http.get(
'https://jsonplaceholder.typicode.com/users',
{ headers: new HttpHeaders({'Authorization': 'Bearer ' + token}) }
);
}

Resources