2013-01-16 20 views
1

我正在開發一個完全基於外部API的站點。我沒有任何服務器端邏輯。所有數據將從外部API獲取。後端服務器主要用於資產管理和路由。已經決定在後臺運行nodejs以及expressjs。我想知道在expressjs路由中需要做哪些修改(作爲代理),將所有來自瀏覽器的跨域ajax API調用路由到適當的站點,並將json數據路由回瀏覽器?使用Expressjs作爲跨域AJAX調用的代理

回答

3

我寫了一個將代理路由到API的小代理,但我最終放棄了它,因此可能需要更多的工作。其基本思想是:

  • 阿賈克斯不能在所有的瀏覽器跨域請求
  • 你必須在http://api.example.com/
  • 您的應用程序生命http://foo.com/
  • 你希望代理的一切外部的API,去http://foo.com/api/*http://api.example.com/*

最好的辦法是使用Streams。您想過濾所有請求到foo.com/api/,然後根據收到的URL向api.example.com發送請求。然後,您將有4個對象:

  • foo.com
  • 響應對象提出該請求
  • api.example.com
  • 從API服務器的響應提出請求時請求

所有這些都是Streams。第一個和最後一個是可讀流,其他是可寫流。所以你想要做的是將可讀流中的任何內容寫入可寫流。你用可讀流的pipe方法做到這一點。這看起來像:

requestFromBrowser.pipe(requestToAPI(function (responseFromAPI) { 
    responseFromAPI.pipe(responseToBrowser); 
})); 

你仍然需要手工編寫標題,並可能處理其他細節。這是我的基本代碼的樣子。它是Connect/Express的中間件。

var http = require('http'); 

exports.proxy = function (prefix) { 
    return function (req, res, next) { 
    var options = { 
     port: 3000, 
     // the server receives a url like http://foo.com/api/(*) 
     // send the proxy only (*) 
     path: req.url.substr(prefix.length), 
     // headers and the method need to be written explicitely 
     method: req.method, 
     headers: req.headers 
    }; 
    if (req.url.indexOf(prefix) === 0) { 
     req.pipe(http.request(options, function (proxy) { 
     res.writeHead(proxy.statusCode, proxy.headers); 
     proxy.pipe(res); 
     }).on('error', next)); 
    } else { 
     next(); 
    } 
    }; 
}; 

我建議你找一個已經做到這一點的模塊。 NPM註冊表中可能有不止一個。另外,請閱讀Streams的更多內容,因爲它們非常適合編寫代理等。