javascript 通过NodeJS加载带有HTML文件的JS文件的正确方法

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/13339472/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-26 18:28:31  来源:igfitidea点击:

Correct way to Load JS Files With HTML files through NodeJS

javascriptnode.jsreadfilestatic-html

提问by sia

I cant get the contents included in the head of the served defualt.htm page to "work". The html loads in the dom, just the CSS and JS files fail. Is there a better alternative? Id like to keep the solution within NodeJS but alternatively open to socket.io and express as well.

我无法让所提供的 defualt.htm 页面头部包含的内容“工作”。html 加载到 dom 中,只有 CSS 和 JS 文件失败。有更好的选择吗?我想将解决方案保留在 NodeJS 中,但也可以对 socket.io 和 express 开放。

Thanks, below is what im using.

谢谢,下面是我正在使用的。

NodeJS Serving the Page

NodeJS 为页面提供服务

var http = require('http'),
fs = require('fs');

fs.readFile(__dirname+'/default.htm', function (err, html) {
    if (err) {
        throw err; 
    }       
    http.createServer(function(request, response) {  
        response.writeHeader(200, {"Content-Type": "text/html"});  
        response.write(html);  
        response.end();  
    }).listen(port.number);
});

Default.html Page

默认.html页面

<!DOCTYPE html>
<html>
<head lang="en">
    <meta charset="utf-8" />
    <title></title>
    <link rel="stylesheet" href="objects/css/site.css" type="text/css" />
    <script src="objects/js/jquery.min.js" type="text/javascript"></script>
    <script src="objects/js/site.min.js" type="text/javascript"></script>
</head>

<body></body>    

</html>

采纳答案by Henrik Andersson

I'm going to throw my two cents in here as well.

我也要把我的两分钱扔在这里。

The way I solved the same problem with serving static files is that I started using the Paperboy module, which is deprecated in favor of the Send module nowadays.

我解决与提供静态文件相同的问题的方法是我开始使用 Paperboy 模块,现在不推荐使用该模块以支持 Send 模块。

Anyhoo, the way I solved it was to "hiHyman" the request before it went into my GET method and check the path of it.

Anyhoo,我解决它的方法是在它进入我的 GET 方法之前“劫持”请求并检查它的路径。

The way I "hiHyman it" is as follows

我“劫持”的方式如下

self.preProcess(self, request, response);

and

preProcess: function onRequest(app, request, response){ //DO STUFF }

If the path contained the STATICFILES dir, I would do a diffrent serving of files otherwise I'd go with the "html"-path. Below is the //DO STUFFof the preProcess()function

如果路径包含 STATICFILES 目录,我会做不同的文件服务,否则我会使用“html”-path。下面是//DO STUFF对的preProcess()功能

var path = urllib.parse(request.url).pathname;
if(path.indexOf(settings.STATICFILES_DIR) != -1) {
    path = settings.STATICFILES_DIR;
    requestedFile = request.url.substring(request.url.lastIndexOf('/') + 1, request.url.length);
    return resolver.resolveResourceOr404(requestedFile, request, response);
}

There might be a better way of doing this but this works like a charm for the things that I need it to do.

可能有更好的方法来做到这一点,但这对于我需要它做的事情来说就像一个魅力。

Using the Paperboy module I then, using the resolver.resolveResourceOr404();function deliver the file like so

然后使用 Paperboy 模块,使用resolver.resolveResourceOr404();函数传递文件

resolveResourceOr404 : function (filename, httpRequest, httpResponse) {
    var root = path.join(path.dirname(__filename), '');

    paperboy.deliver(root, httpRequest, httpResponse)
    .error(function(e){
        this.raise500(httpResponse);
    })
    .otherwise(function(){
        this.raise404(httpResponse);
    });
}

回答by Daniel

Your Javascript and styles are failing because they don't exist. Your current webserver is only sending a single route, the root route. Instead you'll need to allow the use of multiple routes. ExpressJS does this for you in a simpler way, but still very possible without it.

您的 Javascript 和样式失败,因为它们不存在。您当前的网络服务器仅发送一条路由,即根路由。相反,您需要允许使用多个路由。ExpressJS 以一种更简单的方式为您完成了这项工作,但没有它仍然很有可能。

    var http = require('http');
    var fs   = require('fs');


    var server = http.createServer(function(request, response){
       var header_type = "";
       var data        = "";
       var get = function (uri, callback) {
           // match `request.url` with uri with a regex or something.
           var regex = uri;
           if (request.url.match(regex)) {
               callback();
           }
       };    

       var render = function (resource) {
           // resource = name of resource (i.e. index, site.min, jquery.min)
           fs.readFile( __dirname + "/" + resource, function(err, file) {
              if (err) return false; // Do something with the error....
              header_type = ""; // Do some checking to find out what header type you must send.
              data = file;
           }
       };

       get('/', function(req, res, next) {
           // Send out the index.html
           render('index.html');
           next();
       });


       get('/javascript.min', function(req, res, next) {
          render('javascript.js');
          next();
       });


    });

    server.listen(8080);

This might get you started, but you'll have to implement some things like next()yourself. A pretty simple solution, but a working one.

这可能会让你开始,但你必须实现一些像next()你自己一样的东西。一个非常简单的解决方案,但一个有效的解决方案。

Another solution for responding to static files would be to create a catcher within the http.createServercallback. Within the getmethod, if the uris don't match, then you would look within a publicfolder matching the full uri to the file system structure.

响应静态文件的另一个解决方案是在http.createServer回调中创建一个捕获器。在该get方法中,如果publicuri不匹配,那么您将在将完整 uri 与文件系统结构匹配的文件夹中查找。

回答by surjikal

Well, you are serving your default.htmfile on all requests. So, when the browser asks for objects/js/jquery.min.js, your server returns the contents of default.htm.

好吧,您正在为default.htm所有请求提供文件。因此,当浏览器请求 时objects/js/jquery.min.js,您的服务器会返回default.htm.

You should really consider using expressor some other framework.

您真的应该考虑使用express或其他一些框架。

回答by Serdar Dogruyol

You're better off with using Express for this kind of stuff.

您最好将 Express 用于此类内容。

Something like this will do the job.

像这样的事情将完成这项工作。

App.js

应用程序.js

var express = require('express')
  , http = require('http')
  , path = require('path');

var app = express();

//Configure Your App and Static Stuff Like Scripts Css
app.configure(function(){
  app.set('port', process.env.PORT || 3000);
  app.set('views', __dirname + '/views'); // Your view folder
  app.set('view engine', 'jade');  //Use jade as view template engine
  // app.set("view options", {layout: false});  
  // app.engine('html', require('ejs').renderFile); //Use ejs as view template engine
  app.use(express.logger('dev'));

  app.use(express.bodyParser());
  app.use(express.methodOverride());
  app.use(express.cookieParser());
  app.use(app.router); 
  app.use(require('stylus').middleware(__dirname + '/public')); //Use Stylus as the CSS template engine
  app.use(express.static(path.join(__dirname, 'public'))); //This is the place for your static stuff
});


app.get('/',function(req,res){
  res.render('index.jade',{
    title:"Index Page 
    }
});

Index is a jade template page.Which renders into static html and works pretty good with express.

索引是一个玉模板页面。它呈现为静态 html 并且与 express 工作得很好。

For a global static header to all of your pages you can make a template like this and include it in any.

对于所有页面的全局静态标题,您可以制作这样的模板并将其包含在任何模板中。

static_header.jade

static_header.jade

  doctype 5
html
  head
    title= title
    script(src='/javascripts/jquery-1.8.2.min.js')   
    block header 
    link(rel='stylesheet', href='/stylesheets/style.css')
  body
    block content

And finally your index.jade which is using the static_header and own dynamic header with its own scripts.

最后是您的 index.jade,它使用 static_header 和自己的动态标头及其自己的脚本。

extends static_header

block header
  script(src='/javascripts/jquery-ui-1.9.1.custom.js')
  script(src='http://jquery-ui.googlecode.com/svn/trunk/ui/i18n/jquery.ui.datepicker-tr.js')
  link(rel='stylesheet',href='/stylesheets/jquery-ui-1.9.1.custom.min.css')
block content
  h1= title

Put both of the files in your views folder and ready to roll.

将这两个文件放在您的视图文件夹中并准备好滚动。

回答by Hasan A Yousef

what about trying this:

试试这个怎么样:

var http = require('http');
var fs = require('fs');
var path = require('path');

http.createServer(function (request, response) {
console.log('request starting...');

var filePath = '.' + request.url;
if (filePath == './')
    filePath = './index.html';

var extname = path.extname(filePath);
var contentType = 'text/html';
switch (extname) {
    case '.js':
        contentType = 'text/javascript';
        break;
    case '.css':
        contentType = 'text/css';
        break;
    case '.json':
        contentType = 'application/json';
        break;
    case '.png':
        contentType = 'image/png';
        break;      
    case '.jpg':
        contentType = 'image/jpg';
        break;
    case '.wav':
        contentType = 'audio/wav';
        break;
}

fs.readFile(filePath, function(error, content) {
    if (error) {
        if(error.code == 'ENOENT'){
            fs.readFile('./404.html', function(error, content) {
                response.writeHead(200, { 'Content-Type': contentType });
                response.end(content, 'utf-8');
            });
        }
        else {
            response.writeHead(500);
            response.end('Sorry, check with the site admin for error: '+error.code+' ..\n');
            response.end(); 
        }
    }
    else {
        response.writeHead(200, { 'Content-Type': contentType });
        response.end(content, 'utf-8');
    }
});

}).listen(8125);
console.log('Server running at http://127.0.0.1:8125/');