esBuild serve over HTTPS - https

esBuild makes it pretty easy to serve http requests over it's own dev server, e.g.
require('esbuild').serve({
servedir: 'www',
}, {
entryPoints: ['src/app.js'],
outdir: 'www/js',
bundle: true,
}).then(server => {
// Call "stop" on the web server to stop serving
server.stop()
})
How do I enable HTTPS serving in this case? I can make it serve on port 443, but how do I attach a self-signed certificate?

I've found two solutions, that worked for me:
using http-proxy, in an extra file or inside your esbuild config. The limitation I've found here, you cannot use esbuild's --serve and --watch together (https://github.com/evanw/esbuild/issues/805), so if you need auto reload/live server functionality, you have to create this on your own, which is slightly complicated (https://github.com/evanw/esbuild/issues/802)
httpProxy.createServer({
target: {
host: 'localhost',
port: 3000
},
ssl: {
key: fs.readFileSync('key.pem', 'utf8'),
cert: fs.readFileSync('cert.pem', 'utf8')
}
}).listen(3001);
Using servor, here with npm scripts only, but you can also use servor in an esbuild config. Be aware to name your certificate files servor.crt and servor.key (https://github.com/lukejacksonn/servor/issues/79). I prefer this solution because of even less dependencies, simpler setup and auto reload/live server already build in.
"scripts": {
"build": "esbuild --bundle src/index.tsx --outfile=public/bundle.js",
"start": "npm run server & npm run build -- --watch",
"server": "servor public index.html 3000 --reload --secure"
}

Related

Can't get proxying a websocket working with create-react-app

I created a CRA in a docker container and I'm trying to proxy websockets over to another container running a python backend. I for the life of me cannot get the connection working.
I have verified that the server works by exposing the port outside of docker and connecting to it from the browser directly - it connects and works.
I can also verify that the connection within my CRA docker is set up properly - within it I start up a shell and do
> WS = require('ws')
> new WS(`ws://server:8765/ws/foo`).addEventListener('open', e => console.log('open'))
and that connects and prints open too. (This is why I don't have the docker tag on here, from my understanding this eliminates docker from being a possible issue since I've confirmed I can connect from one to the other)
The only thing that I can think of is that the proxy configuration is wrong
Here's what I'm trying to do on the client
const socket = new WebSocket(`ws:localhost/ws/foo`)
my proxy setup
const proxy = require("http-proxy-middleware")
module.exports = (app) => {
as I can tell. Need to circle back
app.use(`/ws*`, proxy({
target: 'ws://server:8765/ws',
changeOrigin: true,
ws: true,
}))
}
I have tried that with /ws and with putting the url in the proxy clause instead o the use and...still nothing
I'm really not sure what more I can be missing.
Here are my dependency versions
"dependencies": {
"#reach/router": "^1.2.1",
"http-proxy-middleware": "^0.20.0",
"react": "^16.10.2",
"react-dom": "^16.10.2",
"react-scripts": "3.2.0",
"styled-components": "^4.4.0"
},

Can't Make Network Requests with gcr.io/cloud-builders/npm

I'm having trouble getting integration tests to run on Google's Cloud Build.
Unit tests run fine, but integration tests that make requests to an external API (using Axios) display this error in Cloud Build: connect ECONNREFUSED 127.0.0.1:80.
It's a React app built with Create React App. Here's the cloudbuild.json:
{
"steps": [
{
"name": "gcr.io/cloud-builders/npm",
"entrypoint": "npm",
"args": [
"install"
],
},
{
"name": "gcr.io/cloud-builders/npm",
"entrypoint": "npm",
"args": [
"run", "build"
],
},
{
"name": "gcr.io/cloud-builders/npm",
"entrypoint": "npm",
"args": [
"test"
],
"env": [
"CI=true",
],
}
]
}
Here's an example error:
Step #1: src/reducers/readings › should update state appropriately when starting a fetch readings request
Step #1:
Step #1: connect ECONNREFUSED 127.0.0.1:80
Any help would be appreciated!
--
Follow up:
I finally traced down the issue with this. The external API url was defined in an .env file. Since Cloudbuild didn't have access to these variables, Axios calls defaulted to 127.0.0.1 (localhost), which failed.
The issue was fixed by encrypting the env file, storing it as a Cloud KMS key, and giving the cloud builder access to it.
# Decrypt env variables
- name: gcr.io/cloud-builders/gcloud
args:
- kms
- decrypt
- --ciphertext-file=.env.enc
- --plaintext-file=.env
- --location=global
- --keyring=[KEYRING]
- --key=[KEY]
Thanks for the pointers #ffd03e.
Is the external API running in Cloud Build or somewhere else? It would be helpful to see a test. Also, is CI=true getting picked up or do the tests hang on watch mode? (https://facebook.github.io/create-react-app/docs/running-tests#linux-macos-bash)
It seems like your test is trying to connect to localhost, which fails because nothing is running on localhost:80. Cloud Build should be able to connect to an external API. Here is an example:
mkdir gcb-connect-test && cd gcb-connect-test
npx create-react-app .
touch cloudbuild.yaml
add tests to src/App.test.js
// This test fails
it('connects with localhost', async () => {
const response = await axios.get('localhost');
console.log('axios localhost response: ' + response.data);
expect(response).toBeTruthy();
});
// This test passes
it('connect with external source', async () => {
const response = await axios.get('https://jsonplaceholder.typicode.com/users/10');
console.log('axios external response: ' + response.data.name);
expect(response.data.name).toBeTruthy();
});
edit cloudbuild.yaml (I prefer yaml because you can add comments (-: )
steps:
# npm install
- name: 'gcr.io/cloud-builders/npm'
args: ['install']
# npm run build
- name: 'gcr.io/cloud-builders/npm'
args: ['run', 'build']
# bash -c | CI=true npm test
# syntax to add commands before npm (-:
- name: 'gcr.io/cloud-builders/npm'
entrypoint: 'bash'
args:
- '-c'
- |
CI=true npm test
gcloud builds submit .
If this ends up being a weirder issue than just accidentally connecting to localhost the #cloudbuild channel on gcp slack is a good resource: slack sign up link

webpack dev server proxy has an error : HPE_INVALID_CHUNK_SIZE

I use webpack-dev-server on my project.
Project uses Spring boot + Tiles + Vue + webpack.
Environment:
OS: Mac OS
Node Version: 9.4.0
NPM Version: 5.6.0
Webpack Version: 4.25.1
webpack-dev-server Version: 3.1.10
In local environment, FE port use 8080 and webpack-dev-server port is 9090.
Bundled files by webpack are created in /front/static-dev/build/.
So, I use proxy options like below.
devServer: {
publicPath: 'http://localhost:9090/front/static-dev/build/',
port: 9090,
proxy: {
'/**': {
target: 'http://localhost:8080',
secure: false,
changeOrigin: true
}
},
open: true
}
After starting webpack-dev-server, static resources like (JSP, bundled js files, CSS files or image, ...) are loaded normally. However, whenever I request some api, webpack-dev-server occured same error. Error logs are like below.
[HPM] Error occurred while trying to proxy
request /api/v1/users/name from localhost:9090 to
http://localhost:8080 (HPE_INVALID_CHUNK_SIZE)
(https://nodejs.org/api/errors.html#errors_common_system_errors)
After request some API, I checked logs on Eclipse and Api requests are normally being made. In Chrome Consloe log like below.
http://localhost:9090/api/v1/users/name net::ERR_CONTENT_DECODING_FAILED 502 (Bad Gateway)
I think the problems are in response part.
Searching HPE_INVALID_CHUNK_SIZE with Webpack in google, I can find no information.
How can I solve this problem.
Thanks.
I resolve this issue using Connection options.
proxy: {
'/**': {
target: 'http://localhost:8080/',
secure: false,
changeOrigin: true,
headers: {
Connection: 'keep-alive'
}
}
This error might be caused by wrong headers sent to your proxy. In case of any further problems you could try Transport-Encoding: chunked or set Content-Length http headers. You can see this answer https://stackoverflow.com/a/55433376/996895

proxy.conf.json is not working in angular 6 when i use ng build

I am trying to create a project using proxy to connect to the backend, but when generating the project with ng build, the proxy configuration does not work as it does with ng serve.
To generate use the following command:
ng build --prod --base-href = / myproyect /
Next I pass the files that I have of configuration:
proxy.conf.json:
{
"/api/*": {
"target": "http://localhost:8080/cystock/",
"secure": false,
"pathRewrite": {"^/api" : ""},
"changeOrigin": true,
"logLevel": "debug"
}
}
global.ts:
export const GLOBAL = {
production: true,
url: 'api'//<-- 'API/' prefix needed for proxy configuration
};
Note: The idea is to be able to consume localhost services, which is developed with JAVA using Spring as framework
As #vikas said, the proxy-config is strictly for development. It makes it easy to "mock" your endpoints while you're developing your application without the need for multiple configuration files.
The idea with proxy-config is that you proxy your production URL to a dev server (remote or local), and when you build your code without the proxy, it points to your production server.
To solve your issue specifically, just change /api to your production endpoint, and map it to a development server.

Webpack dev server reload doesn't work on virtual box

I'm running a webpack server on virtual box with Ubuntu 15.10 using vagrant over mac OSX.
The webpack config is pretty clean:
var HtmlWebpackPlugin = require('html-webpack-plugin');
var path = require('path');
var webpack = require('webpack');
var MINIFY = process.env.MINIFY === true;
var FRONTEND_ROOT = './static'
var SRC_PATCH = FRONTEND_ROOT + '/scripts';
var BUILD_PATH = './dist';
module.exports = {
entry: SRC_PATCH + '/main.js',
devtool: 'source-map',
output: {
path: BUILD_PATH,
filename: 'bundle.js'
},
resolve: {
extensions: ['', '.js', '.jsx'],
modulesDirectories: [SRC_PATCH, 'node_modules']
},
plugins: [
new HtmlWebpackPlugin({
filename: 'index.html',
template: path.resolve(FRONTEND_ROOT, 'index-template.html'),
minify: MINIFY
})
],
module: {
loaders: [
{
test: /\.jsx|js$/,
exclude: /node_modules/,
loader: 'babel-loader'
}
]
},
eslint: {
configFile: './.eslintrc'
}
};
Webpack was run on VM by
vagrant#vagrant-ubuntu-wily-64:/vagrant$ webpack-dev-server --port 8080 --devtool eval --progress --colors --hot --content-base dist
And when I edit a file from OSX it doesn't reload, but if I edit the same file from VM it'll reload.
What is the problem? How can I fix it?
I've solved my problem with vagrant rsync-auto
https://docs.vagrantup.com/v2/cli/rsync-auto.html
I'd added the line config.vm.synced_folder ".", "/vagrant", type: "rsync", rsync_auto: true, rsync_exclude: ".git/" to my Vagrantfile, and run vagrant rsync-auto under a separate tab.
This is answered under another question:
https://stackoverflow.com/a/34937378/5114
If you add the --watch-poll option it changes the way webpack looks for file changes.
webpack-dev-server --watch-poll --port 8080 --devtool eval --progress --colors --hot --content-base dist
This makes webpack poll for changes to the files every N milliseconds. Polling works in the Vagrant shared directories when the normal method doesn't because it doesn't look for mtime or other filesystem attributes, just reads the files on an interval. It's slower and uses more cpu/memory, so don't use polling unless you have to.
https://webpack.github.io/docs/cli.html#watch
Long story short: no any changes made to the files on the host system (MacOS) are propagated as events to the guest box synced_folder.
So features relying on filesystem events like Webpack's "hot reload" (webpack-hot-middleware), nodemon's --watch option and so forth won't work.
The underlying reason is, VirtualBox has decided not to implement inotify.
Quote:
The reason is that the host and the guest might have different file systems and vboxsf would have to implement a generic protocol to forward that information from the host to the guest. And this would have to work between many different host/guest combinations. Therefore marking this ticket as "won't fix", sorry.
The workaround is to use rsync as desribed in this answer from Maxim Shepelin.
the first thing you need to see is if in the console where you're running the server, the recompiled process is happening or not. If' not the answer is in the SyncFolder line that #maxim-schepelin said above. If is recompiling and the web page is not reloading maybe the webPack solution.
Edit
Another reason for the folder sync not working the righ way could be this https://github.com/guard/listen/wiki/Increasing-the-amount-of-inotify-watchers

Resources