2016-04-15 46 views
0

我有一個vanilla node.js http服務器。除了我的圖像文件以外的所有東西都可以使我只是在頁面上看到了破碎的圖像圖標。爲什麼節點不能服務我的圖像文件?

這裏是我的服務器代碼:

"use strict"; 

class app { 
    constructor() { 
      app.loadServer(); 
    } 

    static loadServer() { 
      const HTTP = require('http'), 
       PORT = 1337, 
       SERVER = HTTP.createServer(function(req, res) { 
        let httpHandler = function(err, str, contentType) { 
         console.log('\n\n' + 'Content type: ' + contentType + '\n\n'); 
         if (err) { 
           res.writeHead(500, {'Content-Type': 'text/plain'}); 
           res.end('An error has occurred: ' + err.message); 
         } else if (contentType.indexOf('image') >= 0) { 
           res.writeHead(200, { 'Content-Type': contentType }); 
           res.end(str, 'binary'); 
         } else { 
           res.writeHead(200, { 'Content-Type': contentType }); 
           res.end(str); 
         } 
        }; 

        if (req.headers['x-requested-with'] === 'XMLHttpRequest') { 
         if (req.method == 'POST') { 
           app.getFormData(req, res); 
         } else { 
           console.log("[405] " + req.method + " to " + req.url); 
           res.writeHead(405, "Method not supported", { 'Content-Type': 'text/html' }); 
           res.end('<html><head><title>405 - Method not supported</title></head><body><h1>Method not supported.</h1></body></html>'); 
         } 
        } else if (req.url.indexOf('/javascripts/') >= 0) { 
         app.render(req.url.slice(1), 'application/ecmascript', httpHandler); 
        } else if (req.url.indexOf('/css/') >= 0) { 
         app.render(req.url.slice(1), 'text/css', httpHandler); 
        } else if (req.url.indexOf('/images/') >= 0) { 
         app.render(req.url.slice(1), 'image/jpg', httpHandler); 
        } else { 
         app.render('public/views/index.html', 'text/html', httpHandler); 
        } 

       }).listen(PORT, function() { 
        console.log('-= Francis Server Listening at http://127.0.0.1:' + PORT + ' =-'); 
       }); 
    } 

    static render(path, contentType, callback) { 
      const FS = require('fs'); 
      FS.readFile(__dirname + '/' + path, 'utf-8', function(err, str) { 
       callback(err, str, contentType); 
      }); 
    } 

    static getFormData(req, res) { 
      const FORMIDABLE = require('formidable'), 
       DO_NAMES = require('./node/NameClass'); 
      let formData = {}; 
      new FORMIDABLE.IncomingForm().parse(req) 
       .on('field', function(field, name) { 
        formData[field] = name; 
       }) 
       .on('error', function(err) { 
        next(err); 
       }) 
       .on('end', function() { 
        let finalName = new DO_NAMES(formData); 
        res.writeHead(200, {'content-type': 'text/plain'}); 
        res.write('-= Received form: '); 
        res.end(finalName.getFirstName() + ' ' + finalName.getLastName()); 
       }); 
    } 
} 

module.exports = app; 

感覺就像它試圖以服務形象作爲文本而不是圖片。我證實圖像在那裏並且可讀。

+0

瀏覽器開發窗口中的NET標籤說什麼?是404嗎? – danday74

+0

說圖像文件的'狀態200'。 – BackPacker777

+0

確定這意味着它找到圖像文件 - 響應頭中的內容類型是什麼?你會發現在NET選項卡中,你也應該能夠擴展請求信息。我猜測它是以文本/純文本的形式提供的,但應該將其作爲圖像/ png或其他內容提供 - 您提供的是哪種類型的圖像? PNG? JPG? GIF? (我會猜它是一個GIF) – danday74

回答

1

我發現了這個問題。

它發生在這裏:

FS.readFile(__dirname + '/' + path, 'utf-8', function(err, str) { 
    callback(err, str, contentType); 
}); 

你讀的圖像文件作爲UTF-8,但它是一個二進制文件。這就是圖像數據損壞的原因。相反,您必須使用binary作爲編碼。 你可以改變你的代碼是這樣的:

static render(path, contentType, callback, encoding) { 
    const FS = require('fs'); 
    FS.readFile(__dirname + '/' + path, encoding ? encoding : 'utf-8', function(err, str) { 
     callback(err, str, contentType); 
    }); 
} 

,然後調用render這樣的:

app.render(req.url.slice(1), 'image/jpeg', httpHandler, 'binary'); 

明明有更好的方法來做到這一點,但這需要改變你的代碼的最小量。只要確保readFile()編碼是binary二進制文件。

此外,jpg的正確MIME類型是image/jpeg而不是image/jpg。大多數(如果不是全部的話)瀏覽器都不會在乎,但它更加乾淨。

+0

我確認文件沒有損壞。下面是響應頭: HTTP/1.1 200 OK 內容類型:圖像/ JPEG 日期:星期六,2016年4月16日10時02分24秒GMT 連接:保持活躍 傳輸編碼:分塊 – BackPacker777

+0

@ BackPacker777我想我發現你的錯誤。我改變了我的答案,這應該現在工作。 – x4rf41

+0

這樣做,非常感謝解釋! – BackPacker777

1

它看起來像你的NODE服務器設置錯誤的MIME類型。您可以自己設置MIME類型,但這會非常痛苦。我會建議使用一個MIME類型的節點模塊,這是爲了這個確切的目的。

https://www.npmjs.com/package/mime

這NPM包正是這樣做的用很少的努力。

+0

我很欣賞這一點,我將使用更多的庫以及Koa框架,但我首先想知道爲什麼會出現這個問題... – BackPacker777

+0

也許你的圖像已損壞嘗試一個圖像你知道的很好 – danday74

+0

嗨Dan。我是幾位編輯之一,他們一直在修改你帖子中的瑣碎和宗教材料。我們非常熱衷於在帖子和答案中保留簽名,稱呼和不必要的疏忽,現在我們處於一個讓你多次被問及更簡潔的位置,而你現在[忽略版主意見]( http://stackoverflow.com/a/36553286/472495)並回滾有用的編輯。你願意在評論中對此進行對話嗎? – halfer

相關問題