Skip to content

Commit e05d99d

Browse files
committed
Add node.js server
1 parent bbe1d2a commit e05d99d

File tree

2 files changed

+181
-0
lines changed

2 files changed

+181
-0
lines changed

package.json

+20
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
{
2+
"name": "cesium-starter-app",
3+
"version": "1.4.0",
4+
"description": "A simple JavaScript starter app for creating apps with Cesium, the open-source WebGL virtual globe and map engine.",
5+
"homepage": "http://cesiumjs.org",
6+
"license": "Apache-2.0",
7+
"repository": {
8+
"type": "git",
9+
"url": "hhttps://github.com/pjcozzi/cesium-starter-app"
10+
},
11+
"dependencies": {
12+
"express": "~4.9.x",
13+
"compression": "1.0.8",
14+
"request": "2.36.0",
15+
"yargs": "1.2.6"
16+
},
17+
"engines": {
18+
"node": "0.10.x"
19+
}
20+
}

server.js

+161
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,161 @@
1+
(function() {
2+
"use strict";
3+
/*global console,require,__dirname,process*/
4+
/*jshint es3:false*/
5+
6+
var express = require('express');
7+
var compression = require('compression');
8+
var url = require('url');
9+
var request = require('request');
10+
11+
var yargs = require('yargs').options({
12+
'port' : {
13+
'default' : process.env.PORT || 8080,
14+
'description' : 'Port to listen on.'
15+
},
16+
'public' : {
17+
'type' : 'boolean',
18+
'description' : 'Run a public server that listens on all interfaces.'
19+
},
20+
'upstream-proxy' : {
21+
'description' : 'A standard proxy server that will be used to retrieve data. Specify a URL including port, e.g. "http://proxy:8000".'
22+
},
23+
'bypass-upstream-proxy-hosts' : {
24+
'description' : 'A comma separated list of hosts that will bypass the specified upstream_proxy, e.g. "lanhost1,lanhost2"'
25+
},
26+
'help' : {
27+
'alias' : 'h',
28+
'type' : 'boolean',
29+
'description' : 'Show this help.'
30+
}
31+
});
32+
var argv = yargs.argv;
33+
34+
if (argv.help) {
35+
return yargs.showHelp();
36+
}
37+
38+
// eventually this mime type configuration will need to change
39+
// https://github.com/visionmedia/send/commit/d2cb54658ce65948b0ed6e5fb5de69d022bef941
40+
var mime = express.static.mime;
41+
mime.define({
42+
'application/json' : ['czml', 'json', 'geojson', 'topojson', 'gltf'],
43+
'text/plain' : ['glsl']
44+
});
45+
46+
var app = express();
47+
app.use(compression());
48+
app.use(express.static(__dirname));
49+
50+
function getRemoteUrlFromParam(req) {
51+
var remoteUrl = req.params[0];
52+
if (remoteUrl) {
53+
// add http:// to the URL if no protocol is present
54+
if (!/^https?:\/\//.test(remoteUrl)) {
55+
remoteUrl = 'http://' + remoteUrl;
56+
}
57+
remoteUrl = url.parse(remoteUrl);
58+
// copy query string
59+
remoteUrl.search = url.parse(req.url).search;
60+
}
61+
return remoteUrl;
62+
}
63+
64+
var dontProxyHeaderRegex = /^(?:Host|Proxy-Connection|Connection|Keep-Alive|Transfer-Encoding|TE|Trailer|Proxy-Authorization|Proxy-Authenticate|Upgrade)$/i;
65+
66+
function filterHeaders(req, headers) {
67+
var result = {};
68+
// filter out headers that are listed in the regex above
69+
Object.keys(headers).forEach(function(name) {
70+
if (!dontProxyHeaderRegex.test(name)) {
71+
result[name] = headers[name];
72+
}
73+
});
74+
return result;
75+
}
76+
77+
var upstreamProxy = argv['upstream-proxy'];
78+
var bypassUpstreamProxyHosts = {};
79+
if (argv['bypass-upstream-proxy-hosts']) {
80+
argv['bypass-upstream-proxy-hosts'].split(',').forEach(function(host) {
81+
bypassUpstreamProxyHosts[host.toLowerCase()] = true;
82+
});
83+
}
84+
85+
app.get('/proxy/*', function(req, res, next) {
86+
// look for request like http://localhost:8080/proxy/http://example.com/file?query=1
87+
var remoteUrl = getRemoteUrlFromParam(req);
88+
if (!remoteUrl) {
89+
// look for request like http://localhost:8080/proxy/?http%3A%2F%2Fexample.com%2Ffile%3Fquery%3D1
90+
remoteUrl = Object.keys(req.query)[0];
91+
if (remoteUrl) {
92+
remoteUrl = url.parse(remoteUrl);
93+
}
94+
}
95+
96+
if (!remoteUrl) {
97+
return res.send(400, 'No url specified.');
98+
}
99+
100+
if (!remoteUrl.protocol) {
101+
remoteUrl.protocol = 'http:';
102+
}
103+
104+
var proxy;
105+
if (upstreamProxy && !(remoteUrl.host in bypassUpstreamProxyHosts)) {
106+
proxy = upstreamProxy;
107+
}
108+
109+
// encoding : null means "body" passed to the callback will be raw bytes
110+
111+
request.get({
112+
url : url.format(remoteUrl),
113+
headers : filterHeaders(req, req.headers),
114+
encoding : null,
115+
proxy : proxy
116+
}, function(error, response, body) {
117+
var code = 500;
118+
119+
if (response) {
120+
code = response.statusCode;
121+
res.header(filterHeaders(req, response.headers));
122+
}
123+
124+
res.send(code, body);
125+
});
126+
});
127+
128+
var server = app.listen(argv.port, argv.public ? undefined : 'localhost', function() {
129+
if (argv.public) {
130+
console.log('Cesium development server running publicly. Connect to http://localhost:%d/', server.address().port);
131+
} else {
132+
console.log('Cesium development server running locally. Connect to http://localhost:%d/', server.address().port);
133+
}
134+
});
135+
136+
server.on('error', function (e) {
137+
if (e.code === 'EADDRINUSE') {
138+
console.log('Error: Port %d is already in use, select a different port.', argv.port);
139+
console.log('Example: node server.js --port %d', argv.port + 1);
140+
} else if (e.code === 'EACCES') {
141+
console.log('Error: This process does not have permission to listen on port %d.', argv.port);
142+
if (argv.port < 1024) {
143+
console.log('Try a port number higher than 1024.');
144+
}
145+
}
146+
console.log(e);
147+
process.exit(1);
148+
});
149+
150+
server.on('close', function() {
151+
console.log('Cesium development server stopped.');
152+
});
153+
154+
process.on('SIGINT', function() {
155+
server.close(function() {
156+
process.exit(0);
157+
});
158+
});
159+
160+
})();
161+

0 commit comments

Comments
 (0)