I want to use Node because it\'s swift, uses the same language I am using on the client side, and it\'s non-blocking by definition. But the guy who I hired to write the pro
Instructions to run node server
along apache2(v2.4.xx) server
:
In order to pipe all requests on a particular URL to your Node.JS application create CUSTOM.conf
file inside /etc/apache2/conf-available
directory, and add following line to the created file:
ProxyPass /node http://localhost:8000/
Change 8000 to the prefered port number for node server
.
Enable custom configurations with following command:
$> sudo a2enconf CUSTOM
CUSTOM is your newly created filename without extension, then enable proxy_http
with the command:
$> sudo a2enmod proxy_http
it should enable both proxy
and proxy_http
modules. You can check whether module is enabled or not with:
$> sudo a2query -m MODULE_NAME
After configuration and modules enabled, you will need to restart apache server:
$> sudo service apache2 restart
Now you can execute node server. All requests to the URL/node
will be handled by node server.
Running Node and Apache on one server is trivial as they don't conflict. NodeJS is just a way to execute JavaScript server side. The real dilemma comes from accessing both Node and Apache from outside. As I see it you have two choices:
Set up Apache to proxy all matching requests to NodeJS, which will do the file uploading and whatever else in node.
Have Apache and Node on different IP:port combinations (if your server has two IPs, then one can be bound to your node listener, the other to Apache).
I'm also beginning to suspect that this might not be what you are actually looking for. If your end goal is for you to write your application logic in Nodejs and some "file handling" part that you off-load to a contractor, then its really a choice of language, not a web server.
I combined the answer above with certbot SSL cert and CORS access-control-allow-headers and got it working so I thought I would share the results.
Apache httpd.conf added to the bottom of the file:
LoadModule proxy_module modules/mod_proxy.so
LoadModule proxy_http_module modules/mod_proxy_http.so
Apache VirtualHost settings (doc root for PHP is under Apache and SSL with Certbot, while node.js/socket.io site runs on port 3000 - and uses SSL cert from Apache) Also notice the node.js site uses the proxy for the folder /nodejs, socket.io, and ws (websockets):
<IfModule mod_ssl.c>
<VirtualHost *:443>
ServerName www.example.com
ServerAlias www.example.com
DocumentRoot /var/html/www.example.com
ErrorLog /var/html/log/error.log
CustomLog /var/html/log/requests.log combined
SSLCertificateFile /etc/letsencrypt/live/www.example.com/fullchain.pem
SSLCertificateKeyFile /etc/letsencrypt/live/www.example.com/privkey.pem
Include /etc/letsencrypt/options-ssl-apache.conf
RewriteEngine On
RewriteCond %{REQUEST_URI} ^socket.io [NC]
RewriteCond %{QUERY_STRING} transport=websocket [NC]
RewriteRule /{.*} ws://localhost:3000/$1 [P,L]
RewriteCond %{HTTP:Connection} Upgrade [NC]
RewriteRule /(.*) ws://localhost:3000/$1 [P,L]
ProxyPass /nodejs http://localhost:3000/
ProxyPassReverse /nodejs http://localhost:3000/
ProxyPass /socket.io http://localhost:3000/socket.io
ProxyPassReverse /socket.io http://localhost:3000/socket.io
ProxyPass /socket.io ws://localhost:3000/socket.io
ProxyPassReverse /socket.io ws://localhost:3000/socket.io
</VirtualHost>
</IfModule>
Then my node.js app (app.js):
var express = require('express');
var app = express();
app.use(function(req, res, next) {
res.header("Access-Control-Allow-Origin", "*");
res.header("Access-Control-Allow-Headers", "X-Requested-With");
res.header("Access-Control-Allow-Headers", "Content-Type");
res.header("Access-Control-Allow-Methods", "PUT, GET, POST, DELETE, OPTIONS");
next();
});
var http = require('http').Server(app);
var io = require('socket.io')(http);
http.listen({host:'0.0.0.0',port:3000});
I force a ip4 listener, but that is optional - you can substitute:
http.listen(3000);
node.js app (app.js) code continues with:
io.of('/nodejs').on('connection', function(socket) {
//optional settings:
io.set('heartbeat timeout', 3000);
io.set('heartbeat interval', 1000);
//listener for when a user is added
socket.on('add user', function(data) {
socket.join('AnyRoomName');
socket.broadcast.emit('user joined', data);
});
//listener for when a user leaves
socket.on('remove user', function(data) {
socket.leave('AnyRoomName');
socket.broadcast.emit('user left', data);
});
//sample listener for any other function
socket.on('named-event', function(data) {
//code....
socket.broadcast.emit('named-event-broadcast', data);
});
// add more listeners as needed... use different named-events...
});
finally, on the client side (created as nodejs.js):
//notice the /nodejs path
var socket = io.connect('https://www.example.com/nodejs');
//listener for user joined
socket.on('user joined', function(data) {
// code... data shows who joined...
});
//listener for user left
socket.on('user left', function(data) {
// code... data shows who left...
});
// sample listener for any function:
socket.on('named-event-broadcast', function(data) {
// this receives the broadcast data (I use json then parse and execute code)
console.log('data1=' + data.data1);
console.log('data2=' + data.data2);
});
// sample send broadcast json data for user joined:
socket.emit('user joined', {
'userid': 'userid-value',
'username':'username-value'
});
// sample send broadcast json data for user left
//(I added the following with an event listener for 'beforeunload'):
// socket.emit('user joined', {
// 'userid': 'userid-value',
// 'username':'username-value'
// });
// sample send broadcast json data for any named-event:
socket.emit('named-event', {
'data1': 'value1',
'data2':'value2'
});
In this example when the JS loads, it will emit to the socket a "named-event" sending the data in JSON to the node.js/socket.io server.
Using the io and socket on the server under path /nodejs (connected by client), receives the data an then resends it as a broadcast. Any other users in the socket would receive the data with their listener "named-event-broadcast". Note that the sender does not receive their own broadcast.
ProxyPass /node http://localhost:8000/