浏览代码

added expressjs error handler/native npm package

Andi Dittrich 8 年之前
父节点
当前提交
019dcc81af
共有 24 个文件被更改,包括 479 次插入24 次删除
  1. 1 0
      .gitignore
  2. 34 0
      README.md
  3. 11 0
      dist/HTTP0.html
  4. 1 2
      dist/HTTP400.html
  5. 1 2
      dist/HTTP401.html
  6. 1 2
      dist/HTTP403.html
  7. 1 2
      dist/HTTP404.html
  8. 1 2
      dist/HTTP500.html
  9. 1 2
      dist/HTTP501.html
  10. 1 2
      dist/HTTP502.html
  11. 1 2
      dist/HTTP503.html
  12. 1 2
      dist/HTTP520.html
  13. 1 2
      dist/HTTP521.html
  14. 1 2
      dist/HTTP533.html
  15. 二进制
      dist/pages.tar
  16. 二进制
      dist/pages.zip
  17. 22 0
      express-demo.js
  18. 8 1
      generator.php
  19. 47 0
      lib/dispatcher.js
  20. 27 0
      lib/error-handler.js
  21. 27 0
      lib/page-renderer.js
  22. 33 0
      package.json
  23. 1 1
      template.phtml
  24. 257 0
      yarn.lock

+ 1 - 0
.gitignore

@@ -4,4 +4,5 @@
 .buildpath
 .git
 gfx/*
+node_modules*
 PublicHtml/*

+ 34 - 0
README.md

@@ -60,6 +60,40 @@ location /ErrorPages/ {
 }
 ```
 
+## expressjs Integration ##
+
+HttpErrorPages are available as NPM-Package - just install `http-error-pages` via **npm/yarn**
+
+```terminal
+npm install http-error-pages --save
+```
+
+Example
+
+```js
+var _express = require('express');
+var _webapp = _express();
+var _httpErrorPages = require('http-error-pages');
+
+// demo handler
+_webapp.get('/', function(req, res){
+    res.type('.txt').send('HttpErrorPages Demo');
+});
+
+// throw an 403 error
+_webapp.get('/my403error', function(req, res, next){
+    var myError = new Error();
+    myError.status = 403;
+    next(myError);
+});
+
+// use http error pages handler (final statement!)
+_httpErrorPages(_webapp);
+
+// start service
+_webapp.listen(8888);
+```
+
 ## Apache Httpd Integration ##
 [Apache Httpd 2.x](http://httpd.apache.org/) supports custom error-pages using multiple [ErrorDocument](http://httpd.apache.org/docs/2.4/mod/core.html#errordocument) directives.
 

文件差异内容过多而无法显示
+ 11 - 0
dist/HTTP0.html


+ 1 - 2
dist/HTTP400.html

@@ -18,6 +18,5 @@
         <p class="lead">The server cannot process the request due to something that is perceived to be a client error.</p>
     </div>
     
-        
-</body>
+    </body>
 </html>

+ 1 - 2
dist/HTTP401.html

@@ -18,6 +18,5 @@
         <p class="lead">The requested resource requires an authentication.</p>
     </div>
     
-        
-</body>
+    </body>
 </html>

+ 1 - 2
dist/HTTP403.html

@@ -18,6 +18,5 @@
         <p class="lead">The requested resource requires an authentication.</p>
     </div>
     
-        
-</body>
+    </body>
 </html>

+ 1 - 2
dist/HTTP404.html

@@ -18,6 +18,5 @@
         <p class="lead">The requested resource could not be found but may be available again in the future.</p>
     </div>
     
-        
-</body>
+    </body>
 </html>

+ 1 - 2
dist/HTTP500.html

@@ -19,6 +19,5 @@
 Our service team has been dispatched to bring it back online.</p>
     </div>
     
-        
-</body>
+    </body>
 </html>

+ 1 - 2
dist/HTTP501.html

@@ -18,6 +18,5 @@
         <p class="lead">The Webserver cannot recognize the request method.</p>
     </div>
     
-        
-</body>
+    </body>
 </html>

+ 1 - 2
dist/HTTP502.html

@@ -19,6 +19,5 @@
 Our service team has been dispatched to bring it back online.</p>
     </div>
     
-        
-</body>
+    </body>
 </html>

+ 1 - 2
dist/HTTP503.html

@@ -19,6 +19,5 @@
 Our service team has been dispatched to bring it back online.</p>
     </div>
     
-        
-</body>
+    </body>
 </html>

+ 1 - 2
dist/HTTP520.html

@@ -18,6 +18,5 @@
         <p class="lead">The requested hostname is not routed. Use only hostnames to access resources.</p>
     </div>
     
-        
-</body>
+    </body>
 </html>

+ 1 - 2
dist/HTTP521.html

@@ -19,6 +19,5 @@
 Our service team has been dispatched to bring it back online.</p>
     </div>
     
-        
-</body>
+    </body>
 </html>

+ 1 - 2
dist/HTTP533.html

@@ -19,6 +19,5 @@
 Our service team is working hard to bring it back online soon.</p>
     </div>
     
-        
-</body>
+    </body>
 </html>

二进制
dist/pages.tar


二进制
dist/pages.zip


+ 22 - 0
express-demo.js

@@ -0,0 +1,22 @@
+var _express = require('express');
+var _webapp = _express();
+var _httpErrorPages = require('./lib/error-handler');
+
+// demo handler
+_webapp.get('/', function(req, res){
+    res.type('.txt').send('HttpErrorPages Demo');
+});
+
+// throw an 403 error
+_webapp.get('/my403error', function(req, res, next){
+    var myError = new Error();
+    myError.status = 403;
+    next(myError);
+});
+
+// use http error pages handler (final statement!)
+_httpErrorPages(_webapp);
+
+// start service
+_webapp.listen(8888);
+console.log('Running Demo on Port 8888');

+ 8 - 1
generator.php

@@ -30,12 +30,19 @@ file_put_contents('dist/pages.json', json_encode($pages));
 // load inline css
 $css = trim(file_get_contents('assets/Layout.css'));
 
+// js template page
+$pages['{{code}}'] = array(
+    'title' => '{{title}}',
+    'message' => '{{message}}',
+    'footer' => '{{footer}}'
+);
+
 // generate each error page
 foreach ($pages as $code => $page){
     echo 'Generating Page ', $page['title'], ' (', $code, ')..', PHP_EOL;
 
     // assign variables
-    $v_code = intval($code);
+    $v_code = $code;
     $v_title = nl2br(htmlspecialchars($page['title']));
     $v_message = nl2br(htmlspecialchars($page['message']));
     $v_footer = (isset($config['footer']) ? $config['footer'] : '');

+ 47 - 0
lib/dispatcher.js

@@ -0,0 +1,47 @@
+var _pages = require('../dist/pages.json');
+var _renderer = require('./page-renderer');
+
+// multi-type support
+// @see https://github.com/expressjs/express/blob/master/examples/error-pages/index.js
+function dispatchRequest(page, httpStatusCode, req, res){
+    // page available ?
+    if (!_pages[page]){
+        // use "internal server error" as default
+        page = '500';
+        httpStatusCode = null;
+    }
+
+    // set http status code
+    res.status(httpStatusCode || 500);
+
+    // extract page date
+    var pageData = _pages[page];
+
+    // multiple response formats
+    res.format({
+        // standard http-error-pages
+        html: function(){
+            res.type('.html');
+            res.send(_renderer({
+                code: httpStatusCode,
+                title: pageData.title,
+                message: pageData.message
+            }))
+        },
+
+        // json
+        json: function(){
+            res.json({
+                error: pageData.title + ' - ' + pageData.message
+            })
+        },
+
+        // text response
+        default: function(){
+            // plain text
+            res.type('.txt').send(pageData.title + ' - ' + pageData.message);
+        }
+    })
+}
+
+module.exports = dispatchRequest;

+ 27 - 0
lib/error-handler.js

@@ -0,0 +1,27 @@
+var _dispatcher = require('./dispatcher');
+
+// http404 handler
+function notfoundHandler(req, res){
+    _dispatcher('404', 404, req, res);
+}
+
+// default error handler
+function errorHandler(err, req, res, next){
+    // status code given ?
+    if (err.status){
+        // custom errorpage set ?
+        _dispatcher(err.errorpage || err.status, err.status, req, res);
+
+    // use default http500 page
+    }else{
+        _dispatcher('500', 500, req, res);
+    }
+};
+
+module.exports = function(router){
+    // 404
+    router.use(notfoundHandler);
+
+    // internal errors (all)
+    router.use(errorHandler);
+};

+ 27 - 0
lib/page-renderer.js

@@ -0,0 +1,27 @@
+var _path = require('path');
+var _fs = require('fs');
+var _basedir = _path.dirname(__dirname);
+
+// load template file (1 time)
+var _template = _fs.readFileSync(_path.join(_basedir, 'dist/HTTP0.html'), 'utf8');
+
+// simple template renderer
+function renderPage(vars){
+    var tpl = _template;
+
+    // add vars
+    tpl = tpl.replace(/{{([a-z]+)}}/gm, function(match, name){
+
+        // var available ?
+        if (vars[name]){
+            return vars[name];
+        // remove unused vars
+        }else{
+            return '';
+        }
+    });
+
+    return tpl;
+}
+
+module.exports = renderPage;

+ 33 - 0
package.json

@@ -0,0 +1,33 @@
+{
+  "name": "http-error-pages",
+  "version": "0.1.0",
+  "description": "Simple HTTP Error Pages for expressjs",
+  "keywords": [
+    "http",
+    "https",
+    "error",
+    "errorpage",
+    "express",
+    "expressjs",
+    "router",
+    "handler"
+  ],
+  "files": [
+    "bin",
+    "dist",
+    "express-demo.js",
+    "CHANGED.md",
+    "LICENSE.md",
+    "README.md"
+  ],
+  "bin": {},
+  "main": "./lib/router.js",
+  "author": "Andi Dittrich (https://andidittrich.de)",
+  "homepage": "https://github.com/AndiDittrich/HttpErrorPages",
+  "bugs": "https://github.com/AndiDittrich/HttpErrorPages/issues",
+  "repository": "AndiDittrich/HttpErrorPages",
+  "license": "MIT",
+  "devDependencies": {
+    "express": "^4.15.2"
+  }
+}

+ 1 - 1
template.phtml

@@ -22,6 +22,6 @@
     <footer>
         <p><?php echo $v_footer; ?></p>
     </footer>
-    <?php } ?>    
+    <?php } ?>
 </body>
 </html>

+ 257 - 0
yarn.lock

@@ -0,0 +1,257 @@
+# THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY.
+# yarn lockfile v1
+
+
+accepts@~1.3.3:
+  version "1.3.3"
+  resolved "https://registry.yarnpkg.com/accepts/-/accepts-1.3.3.tgz#c3ca7434938648c3e0d9c1e328dd68b622c284ca"
+  dependencies:
+    mime-types "~2.1.11"
+    negotiator "0.6.1"
+
+array-flatten@1.1.1:
+  version "1.1.1"
+  resolved "https://registry.yarnpkg.com/array-flatten/-/array-flatten-1.1.1.tgz#9a5f699051b1e7073328f2a008968b64ea2955d2"
+
+content-disposition@0.5.2:
+  version "0.5.2"
+  resolved "https://registry.yarnpkg.com/content-disposition/-/content-disposition-0.5.2.tgz#0cf68bb9ddf5f2be7961c3a85178cb85dba78cb4"
+
+content-type@~1.0.2:
+  version "1.0.2"
+  resolved "https://registry.yarnpkg.com/content-type/-/content-type-1.0.2.tgz#b7d113aee7a8dd27bd21133c4dc2529df1721eed"
+
+cookie-signature@1.0.6:
+  version "1.0.6"
+  resolved "https://registry.yarnpkg.com/cookie-signature/-/cookie-signature-1.0.6.tgz#e303a882b342cc3ee8ca513a79999734dab3ae2c"
+
+cookie@0.3.1:
+  version "0.3.1"
+  resolved "https://registry.yarnpkg.com/cookie/-/cookie-0.3.1.tgz#e7e0a1f9ef43b4c8ba925c5c5a96e806d16873bb"
+
+debug@2.6.1:
+  version "2.6.1"
+  resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.1.tgz#79855090ba2c4e3115cc7d8769491d58f0491351"
+  dependencies:
+    ms "0.7.2"
+
+debug@2.6.4:
+  version "2.6.4"
+  resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.4.tgz#7586a9b3c39741c0282ae33445c4e8ac74734fe0"
+  dependencies:
+    ms "0.7.3"
+
+depd@1.1.0, depd@~1.1.0:
+  version "1.1.0"
+  resolved "https://registry.yarnpkg.com/depd/-/depd-1.1.0.tgz#e1bd82c6aab6ced965b97b88b17ed3e528ca18c3"
+
+destroy@~1.0.4:
+  version "1.0.4"
+  resolved "https://registry.yarnpkg.com/destroy/-/destroy-1.0.4.tgz#978857442c44749e4206613e37946205826abd80"
+
+ee-first@1.1.1:
+  version "1.1.1"
+  resolved "https://registry.yarnpkg.com/ee-first/-/ee-first-1.1.1.tgz#590c61156b0ae2f4f0255732a158b266bc56b21d"
+
+encodeurl@~1.0.1:
+  version "1.0.1"
+  resolved "https://registry.yarnpkg.com/encodeurl/-/encodeurl-1.0.1.tgz#79e3d58655346909fe6f0f45a5de68103b294d20"
+
+escape-html@~1.0.3:
+  version "1.0.3"
+  resolved "https://registry.yarnpkg.com/escape-html/-/escape-html-1.0.3.tgz#0258eae4d3d0c0974de1c169188ef0051d1d1988"
+
+etag@~1.8.0:
+  version "1.8.0"
+  resolved "https://registry.yarnpkg.com/etag/-/etag-1.8.0.tgz#6f631aef336d6c46362b51764044ce216be3c051"
+
+express@^4.15.2:
+  version "4.15.2"
+  resolved "https://registry.yarnpkg.com/express/-/express-4.15.2.tgz#af107fc148504457f2dca9a6f2571d7129b97b35"
+  dependencies:
+    accepts "~1.3.3"
+    array-flatten "1.1.1"
+    content-disposition "0.5.2"
+    content-type "~1.0.2"
+    cookie "0.3.1"
+    cookie-signature "1.0.6"
+    debug "2.6.1"
+    depd "~1.1.0"
+    encodeurl "~1.0.1"
+    escape-html "~1.0.3"
+    etag "~1.8.0"
+    finalhandler "~1.0.0"
+    fresh "0.5.0"
+    merge-descriptors "1.0.1"
+    methods "~1.1.2"
+    on-finished "~2.3.0"
+    parseurl "~1.3.1"
+    path-to-regexp "0.1.7"
+    proxy-addr "~1.1.3"
+    qs "6.4.0"
+    range-parser "~1.2.0"
+    send "0.15.1"
+    serve-static "1.12.1"
+    setprototypeof "1.0.3"
+    statuses "~1.3.1"
+    type-is "~1.6.14"
+    utils-merge "1.0.0"
+    vary "~1.1.0"
+
+finalhandler@~1.0.0:
+  version "1.0.2"
+  resolved "https://registry.yarnpkg.com/finalhandler/-/finalhandler-1.0.2.tgz#d0e36f9dbc557f2de14423df6261889e9d60c93a"
+  dependencies:
+    debug "2.6.4"
+    encodeurl "~1.0.1"
+    escape-html "~1.0.3"
+    on-finished "~2.3.0"
+    parseurl "~1.3.1"
+    statuses "~1.3.1"
+    unpipe "~1.0.0"
+
+forwarded@~0.1.0:
+  version "0.1.0"
+  resolved "https://registry.yarnpkg.com/forwarded/-/forwarded-0.1.0.tgz#19ef9874c4ae1c297bcf078fde63a09b66a84363"
+
+fresh@0.5.0:
+  version "0.5.0"
+  resolved "https://registry.yarnpkg.com/fresh/-/fresh-0.5.0.tgz#f474ca5e6a9246d6fd8e0953cfa9b9c805afa78e"
+
+http-errors@~1.6.1:
+  version "1.6.1"
+  resolved "https://registry.yarnpkg.com/http-errors/-/http-errors-1.6.1.tgz#5f8b8ed98aca545656bf572997387f904a722257"
+  dependencies:
+    depd "1.1.0"
+    inherits "2.0.3"
+    setprototypeof "1.0.3"
+    statuses ">= 1.3.1 < 2"
+
+inherits@2.0.3:
+  version "2.0.3"
+  resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.3.tgz#633c2c83e3da42a502f52466022480f4208261de"
+
+ipaddr.js@1.3.0:
+  version "1.3.0"
+  resolved "https://registry.yarnpkg.com/ipaddr.js/-/ipaddr.js-1.3.0.tgz#1e03a52fdad83a8bbb2b25cbf4998b4cffcd3dec"
+
+media-typer@0.3.0:
+  version "0.3.0"
+  resolved "https://registry.yarnpkg.com/media-typer/-/media-typer-0.3.0.tgz#8710d7af0aa626f8fffa1ce00168545263255748"
+
+merge-descriptors@1.0.1:
+  version "1.0.1"
+  resolved "https://registry.yarnpkg.com/merge-descriptors/-/merge-descriptors-1.0.1.tgz#b00aaa556dd8b44568150ec9d1b953f3f90cbb61"
+
+methods@~1.1.2:
+  version "1.1.2"
+  resolved "https://registry.yarnpkg.com/methods/-/methods-1.1.2.tgz#5529a4d67654134edcc5266656835b0f851afcee"
+
+mime-db@~1.27.0:
+  version "1.27.0"
+  resolved "https://registry.yarnpkg.com/mime-db/-/mime-db-1.27.0.tgz#820f572296bbd20ec25ed55e5b5de869e5436eb1"
+
+mime-types@~2.1.11, mime-types@~2.1.15:
+  version "2.1.15"
+  resolved "https://registry.yarnpkg.com/mime-types/-/mime-types-2.1.15.tgz#a4ebf5064094569237b8cf70046776d09fc92aed"
+  dependencies:
+    mime-db "~1.27.0"
+
+mime@1.3.4:
+  version "1.3.4"
+  resolved "https://registry.yarnpkg.com/mime/-/mime-1.3.4.tgz#115f9e3b6b3daf2959983cb38f149a2d40eb5d53"
+
+ms@0.7.2:
+  version "0.7.2"
+  resolved "https://registry.yarnpkg.com/ms/-/ms-0.7.2.tgz#ae25cf2512b3885a1d95d7f037868d8431124765"
+
+ms@0.7.3:
+  version "0.7.3"
+  resolved "https://registry.yarnpkg.com/ms/-/ms-0.7.3.tgz#708155a5e44e33f5fd0fc53e81d0d40a91be1fff"
+
+negotiator@0.6.1:
+  version "0.6.1"
+  resolved "https://registry.yarnpkg.com/negotiator/-/negotiator-0.6.1.tgz#2b327184e8992101177b28563fb5e7102acd0ca9"
+
+on-finished@~2.3.0:
+  version "2.3.0"
+  resolved "https://registry.yarnpkg.com/on-finished/-/on-finished-2.3.0.tgz#20f1336481b083cd75337992a16971aa2d906947"
+  dependencies:
+    ee-first "1.1.1"
+
+parseurl@~1.3.1:
+  version "1.3.1"
+  resolved "https://registry.yarnpkg.com/parseurl/-/parseurl-1.3.1.tgz#c8ab8c9223ba34888aa64a297b28853bec18da56"
+
+path-to-regexp@0.1.7:
+  version "0.1.7"
+  resolved "https://registry.yarnpkg.com/path-to-regexp/-/path-to-regexp-0.1.7.tgz#df604178005f522f15eb4490e7247a1bfaa67f8c"
+
+proxy-addr@~1.1.3:
+  version "1.1.4"
+  resolved "https://registry.yarnpkg.com/proxy-addr/-/proxy-addr-1.1.4.tgz#27e545f6960a44a627d9b44467e35c1b6b4ce2f3"
+  dependencies:
+    forwarded "~0.1.0"
+    ipaddr.js "1.3.0"
+
+qs@6.4.0:
+  version "6.4.0"
+  resolved "https://registry.yarnpkg.com/qs/-/qs-6.4.0.tgz#13e26d28ad6b0ffaa91312cd3bf708ed351e7233"
+
+range-parser@~1.2.0:
+  version "1.2.0"
+  resolved "https://registry.yarnpkg.com/range-parser/-/range-parser-1.2.0.tgz#f49be6b487894ddc40dcc94a322f611092e00d5e"
+
+send@0.15.1:
+  version "0.15.1"
+  resolved "https://registry.yarnpkg.com/send/-/send-0.15.1.tgz#8a02354c26e6f5cca700065f5f0cdeba90ec7b5f"
+  dependencies:
+    debug "2.6.1"
+    depd "~1.1.0"
+    destroy "~1.0.4"
+    encodeurl "~1.0.1"
+    escape-html "~1.0.3"
+    etag "~1.8.0"
+    fresh "0.5.0"
+    http-errors "~1.6.1"
+    mime "1.3.4"
+    ms "0.7.2"
+    on-finished "~2.3.0"
+    range-parser "~1.2.0"
+    statuses "~1.3.1"
+
+serve-static@1.12.1:
+  version "1.12.1"
+  resolved "https://registry.yarnpkg.com/serve-static/-/serve-static-1.12.1.tgz#7443a965e3ced647aceb5639fa06bf4d1bbe0039"
+  dependencies:
+    encodeurl "~1.0.1"
+    escape-html "~1.0.3"
+    parseurl "~1.3.1"
+    send "0.15.1"
+
+setprototypeof@1.0.3:
+  version "1.0.3"
+  resolved "https://registry.yarnpkg.com/setprototypeof/-/setprototypeof-1.0.3.tgz#66567e37043eeb4f04d91bd658c0cbefb55b8e04"
+
+"statuses@>= 1.3.1 < 2", statuses@~1.3.1:
+  version "1.3.1"
+  resolved "https://registry.yarnpkg.com/statuses/-/statuses-1.3.1.tgz#faf51b9eb74aaef3b3acf4ad5f61abf24cb7b93e"
+
+type-is@~1.6.14:
+  version "1.6.15"
+  resolved "https://registry.yarnpkg.com/type-is/-/type-is-1.6.15.tgz#cab10fb4909e441c82842eafe1ad646c81804410"
+  dependencies:
+    media-typer "0.3.0"
+    mime-types "~2.1.15"
+
+unpipe@~1.0.0:
+  version "1.0.0"
+  resolved "https://registry.yarnpkg.com/unpipe/-/unpipe-1.0.0.tgz#b2bf4ee8514aae6165b4817829d21b2ef49904ec"
+
+utils-merge@1.0.0:
+  version "1.0.0"
+  resolved "https://registry.yarnpkg.com/utils-merge/-/utils-merge-1.0.0.tgz#0294fb922bb9375153541c4f7096231f287c8af8"
+
+vary@~1.1.0:
+  version "1.1.1"
+  resolved "https://registry.yarnpkg.com/vary/-/vary-1.1.1.tgz#67535ebb694c1d52257457984665323f587e8d37"

部分文件因为文件数量过多而无法显示