Sharing Windows Server with Nodebb and Wordpress
-
Hi Rich. We will help you with Linux. Nothing to worry about.
-
@RichG said:
@julian Thanks for the generous offer. I am a big fan, and helping you, is more of an incentive than you know. The idea of starting from scratch with the workpress site, and the nodebb site is a daunting proposal.... everything is working except the rerouting the port :8080 thing. I have put so much time and effort into the whole 'self-hosting' deal, and I know nothing about linux. On the other hand, I do hate Windows. I need to think this over Sir...
Rich
Because you need to install NGINX, change Apache port to 8080, and Proxy Forward the Port 4567 to Port 80.
-
@RichG , you could try to create a reverse proxy inside IIS. I'm a fulltime sysadmin and have done this before, but it's been some time
If you still want to pull this off, I'll look at our servers at work. -
@Moritz-Friedrich ... I really do want to pull this off. I have invested too much time, and I will not be the only one running into this issue. So far this is the best articiel I have come across that does not use iisnode.
http://dvisagie.blogspot.com/2013/02/running-nodejs-alongside-iis-on-windows.html
I installed in IIS.
ARR (Application Request Routing) URL Rewrite
and used rewitre to create this web.config file in the 'empty' directory FORUM that I created and pointed the application Forum to...
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<system.webServer>
<rewrite>
<rules>
<rule name="ReverseProxyInboundRule1" stopProcessing="true">
<match url="(.*)" />
<action type="Rewrite" url="http://theamericanbulletin.com:8080/{R:1}" />
</rule>
</rules>
</rewrite>
</system.webServer>
</configuration>http://theamericanbulletin.com/forum produces this...
-
As you can see the /forum does get hit and passed by IIS, but it does not stream back to the client all the .css, and other information to the browser. Plus if you click on a path deeper than the main page like 'Announcements' you get this server error. IIS is looking for a 'physical' path.
Here is the json.config....
{
"url": "http://theamericanbulletin.com:8080",
"secret": "bbbbbvvvccc",
"database": "redis",
"redis": {
"host": "127.0.0.1",
"port": "6379",
"password": "xxxxxxx",
"database": "0"
}
} -
Okay. First off: Change the secret in your config.json immediately, you should never post it anywhere online.
You should change the url here to "http://theamericanbulletin.com/forum". That way, NodeBB can deliver static resources with the correct path (remember, the client will request each resource based on this address which gets then parsed in the IIS).What are the rewrite rules shown in the ISS console?
-
I am almost 100% sure that I need a proxy server in-front of IIS to traffic the http request, but now we get into another level of complexity. That is why I hate Windows. I am going to explore finding a Nodejs app to set on port 80 and do the routing to IIS and noebb. Just to keep things simple. KISS.
-
@Moritz-Friedrich said:
Okay. First off: Change the secret in your config.json immediately, you should never post it anywhere online.
You should change the url here to "http://theamericanbulletin.com/forum". That way, NodeBB can deliver static resources with the correct path (remember, the client will request each resource based on this address which gets then parsed in the IIS).What are the rewrite rules shown in the ISS console?
Done. I will try your suggestion. The rules...
-
@Moritz-Friedrich... "You should change the url here to "http://theamericanbulletin.com/forum"". Sorry.... no go. When I make your suggested change the nodebb start listening on it's default port 4567. Even changing web.config fro, :8080 to :4567 does not do the trick. and when access the forum from http:thaamericanbulletin.com:4567 then produces this result.... "/forum is append to 'all' the paths confusing nodebb. I think I need to write a 'small' node proxy to sit on :80. Isn't that where node shines...
-
It's important that you know what these URLs mean. Look at this:
- Client requests
theamericanbulletin.com/forum
. - IIS revieves a request for
theamericanbulletin.com/forum
and routes it tolocalhost:8080
orlocalhost:4567
. - NodeBB recieves a request from the client and uses
theamericanbulletin.com/forum
as a base URL to construct its relative links, eg.theamericanbulletin.com/forum/category/1/test
. - The client recieves the NodeBB page from
theamericanbulletin.com/forum
.
That means, you have to configure the IIS to rewrite
theamericanbulletin.com/forum
tolocalhost:4567
(or:8080
respectively, that doesn't really matter apart from convention). NodeBB instead will think it sits ontheamericanbulletin.com/forum
all along.
If you need further help setting up the rewrite rules, let me know. - Client requests
-
Best of luck to you @RichG. I did quite a bit of windows admin with IIS back in the day but I couldn't explain to you now how to do it without being on your system.
If you still can't get IIS to play nice, may I suggest giving WAMP a try? It's basically the most popular linux web server: Apache, on windows. It will allow you to stick with windows but also use the suggestions and instructions from the nodebb documentation to get your proxy pass setup correctly. Additionally, configuring wordpress to use Apache instead of IIS is trivial.
If you decide to go this route I can walk you through setting up apache and the vhosts required, just start a chat with me here.
-
@Julian if I have some time this weekend, I could write a setup guide for IIS w/ screenshots, if you guys want it for the docs? With a big warning at the top, "Stop reading, use linux!"
-
@KingCat @Moritz-Friedrich @nhl-pl @julian Thank you all for your help and support. I have just completed setting up a nodejs proxy server sitting on port 80. The thought of sending anyone back into the burning building and horrors of dealing with the windows platform was just too much for me. I just could not allow you gallant people to relive the scars that took so many of you to years to heal.
I choose this solution because it distances the proxy from whatever server happens to be running. If IIS is listening on port 8001, and the nodeBB is listening on port 8080 so be it. I don't care... do not want to deal with a windows proxy, and the horrors of rewrite and all the other super secret your in the club handshaking. I am a programer.... I want control to change things as I see fit... dependent on none other that myself to achieve my goals.
Holy crap. The hours spent reading... the hundreds of posts I have read just to get windows to hand 'forum.theamercianbulletin.com' to port 8080 was mind numbing. And there still was not a clear solution. It maybe easier with linux... but still tinkering with Linux is still... tinkering with Linux... and not the proper solution ( IMHO). Anyway... this is the code that solved my problem. I will be making a post here to explain how everything works and all the steps needed to help others with this solution. Again... thanks for all the help, effort, and thoughts. Just a great group of people.....
ISS wordpress is now listening on 8081
Nodebb is listening on 8080
Proxy listening on 80This code is rough and needs some clean-up and featurers added to it, but is is working as I write this post.
var util = require('util'),
http = require('http'),
url = require('url'),
domain = require('domain')
httpProxy = require('../../lib/http-proxy'),
proxy = httpProxy.createProxyServer({});
serverDomain = domain.create();
serverDomain.run(function () {http.createServer(function(req, res)
{
var reqd = domain.create()
reqd.add(req)
reqd.add(res)
// On error dispose of the domain
reqd.on('error', function (error) {
console.error('Error', error, req.url)
reqd.dispose()
});
var hostname = req.headers.host.split(":")[0];
var pathname = url.parse(req.url).pathname;
switch(hostname)
{
case 'forum.theamericanbulletin.com':
proxy.web(req, res, { target: 'http://localhost:8080' });
break;
default:
proxy.web(req, res, { target: 'http://localhost:8081' });
};
proxy.on('error', function(err, req, res)
{
console.log('Error 500');
});
console.log(hostname);
console.log(pathname);
}).listen(80,function(){
console.log('proxy listening on port 80');
});
}); -
@Moritz-Friedrich said:
@Julian if I have some time this weekend, I could write a setup guide for IIS w/ screenshots, if you guys want it for the docs? With a big warning at the top, "Stop reading, use linux!"
That would be a great idea. There are still a lot of Windows user out there and your expertise would surly be a help.
-
I started off this quest with just a simple problem. To have the ability for users to address my nodebb forum (http://theamericanbulletin.com:8080) as (“http://forum.theamericanbulletin.com”). This simple problem turned into a quest through countless videos and reading ( at least fifty) mindnumbing posts on blogs and other forums. I am running a Windows server ( 2008 ) with IIS to service my Wordpress main site. My NodeBB forum is listening on port 8080. All advice was to work within the framework of Windows and IIS, using 'Rewrite', to route traffic on the Server. After days of frustration, I had to come up with a better plan. One that gets me above proprietary nuances. The only way to do that was to get hold of port 80 myself..my own proxy server.. and what better webserver than Nodejs. With little of a search I came accoss this project.
https://github.com/nodejitsu/node-http-proxy
- I git cloned the above link.
- Renamed the new directory to nodeproxy
- e:\nodeproxy> npm install ( pulls all the needed modules)
- created a new directory under the new 'nodeproxy' entitled MyProxy
- Created the MyProxy.js file ( contents below )
- Moved my WordPress to listen on port 8081 in IIS
- Started new proxy server (e:\nodeproxy\myproxy> node myproxy.js )
- Done!
Some notes about the js file. When I first started I used this post as a guideline. It used a routing table... exactly what I was looking for. Although I was not needing to spin-up three test servers, this provided some insight into the power if this little application. I could, if I wanted to.... spin-up as many listeners as I wanted..... listening on whatever, or as many port(s) as I wanted.
http://stackoverflow.com/questions/25896608/nodejs-routing-table-using-http-proxy
var httpProxy = require("http-proxy"); var url = require("url"); httpProxy.createServer(function(req, res, proxy) { var hostname = req.headers.host.split(":")[0]; var pathname = url.parse(req.url).pathname; // Options for the outgoing proxy request. var options = { host: hostname }; // Routing logic if(hostname == "127.0.0.1") { options.port = 8083; } else if(pathname == "/upload") { options.port = 8082; options.path = "/"; } else { options.port = 8081; } // (add more conditional blocks here) proxy.proxyRequest(req, res, options); }).listen(8080); console.log("Proxy listening on port 8080"); // We simulate the 3 target applications var http = require("http"); http.createServer(function(req, res) { res.end("Request received on 8081"); }).listen(8081); http.createServer(function(req, res) { res.end("Request received on 8082"); }).listen(8082); http.createServer(function(req, res) { res.end("Request received on 8083"); }).listen(8083);
I modified the above code to tailor it to my routes, but the server kept breaking. The proxy would throw a “socket hang up” when I moved between the Wordpress site and the NodeBB site. The error was not getting caught and the proxy would just break and go back to a system prompt. Another day of research lead me to this post.
It was in this post where the idea of wrapping the proxy-server within a domain arose. Perfect! I can pass the error up to the domain and let it dispose of it while the proxy keeps serving ( at least that's how I think it works). Plus the added benefit of having and overlord (parent) to all the potential listeners that could be spun-up to report to. But that is a whole different subject.
So I added a Domain to the mix and came-up with a working solution. While this only apples to those with 'full' control over their servers, it does add a layer of control over proprietary systems running on your machine, and frees the developer (to a point) from those systems. I do not have to mess with rewrite... or some Apache routine tables. This is 'clean' and simple.
Please feel free to improve on this concept and tighten this up. There is room for lots of improvement here. Please add to the knowledge.
Rich
MyProxy.Js
var util = require('util'),
http = require('http'),
url = require('url'),
domain = require('domain')
httpProxy = require('../lib/http-proxy'),
proxy = httpProxy.createProxyServer({});
serverDomain = domain.create();
proxy.on('error', function(err, req, res)
{
console.log(err.message);
});
serverDomain.run(function () {http.createServer(function(req, res)
{
var reqd = domain.create()
reqd.add(req)
reqd.add(res)
// On error dispose of the domain
reqd.on('error', function (error) {
console.error('Error', error, req.url)
reqd.dispose()
});
var oUrl = url.parse(req.url);
if (typeof req.headers !== 'undefined' && req.headers.host.split)
{
var hostname = req.headers.host.split(":")[0];
var pathname = oUrl.pathname;
switch(hostname)
{
case 'forum.theamericanbulletin.com':
proxy.web(req, res, { target: 'http://localhost:8080' });
break;
default:
proxy.web(req, res, { target: 'http://localhost:8081' });
};
console.log(hostname);
console.log(pathname);
}
}).listen(80,function(){
console.log('proxy listening on port 80');
});
});