在节点

时间:2017-04-03 00:42:38

标签: node.js proxy

我需要能够通过我的节点服务器提供副本站点(到www.google.comwww.facebook.com等任何站点)。我找到了这个库:

https://github.com/nodejitsu/node-http-proxy

我在代理请求时使用了以下代码:

options = {
  ignorePath: true,
  changeOrigin: false
}

var proxy = httpProxy.createProxyServer({options});

router.get(function(req, res) {
  proxy.web(req, res, { target: req.body.url });
});

但是,此配置会导致大多数网站出错。根据网站的不同,我会收到来自目标网址的Unknown service错误,或Invalid host ...这些内容。但是,当我通过

changeOrigin: true

我获得了正常运行的代理服务,但我的用户浏览器被重定向到他们请求的实际网址,而不是我的(因此,如果req.body.url = http://www.google.com,请求将转到http://www.google.com

我怎样才能让我的网站的网址显示出来,但是我可以完全复制正在显示的内容?我需要能够在请求中添加一些JS文件,我正在使用另一个库。

为了澄清,以下是问题摘要:

  1. 用户请求具有url属性

  2. 的资源
  3. url的格式为http://www.example.com

  4. www.pv.com上运行的我的服务器需要能够指示 用户到www.pv.com/http://www.example.com

  5. 同时返回HTTP响应 www.pv.com/http://www.example.com是完整的代表 http://www.example.com。我需要能够添加自己的 此回复中的Javascript / HTML文件。

3 个答案:

答案 0 :(得分:5)

查看https://stackoverflow.com/a/32704647/1587329,唯一的区别是它使用了不同的目标参数:

var http = require('http');
var httpProxy = require('http-proxy');
var proxy = httpProxy.createProxyServer({});

http.createServer(function(req, res) {
    proxy.web(req, res, { target: 'http://www.google.com' });
}).listen(3000);

这可以解释Invalid host错误:您需要将主机作为target参数传递,而不是整个URL。因此,以下可能有效:

options = {
  ignorePath: true,
  changeOrigin: false
}

var proxy = httpProxy.createProxyServer({options});

router.get(function(req, res) {
  var url = req.body.url;
  proxy.web(req, res, { target: url.protocol + '//' + url.host });
});

the URL object, see the NodeJS website

答案 1 :(得分:2)

使用无头浏览器导航到网站并获取网站的HTML。然后发送HTML作为对所请求网站的响应。使用无头浏览器的一个优点是它允许您从使用JavaScript呈现的网站获取HTML。 Nightmare.js(一个用于electron.js的API或库)是一个不错的选择,因为它在引擎盖下使用了Electron.js。电子框架比Phantom.js(另一种选择)更快。使用Nightmare.js,您可以将JavaScript文件注入页面,如下面的代码片段所示。您可能需要调整代码以添加其他功能。目前,我只允许添加两个链接,因此指向其他资源的链接位于代码段中。

apt-get update && apt-get install -y xvfb x11-xkb-utils xfonts-100dpi
xfonts-75dpi xfonts-scalable xfonts-cyrillic x11-apps clang
libdbus-1-dev libgtk2.0-dev libnotify-dev libgnome-keyring-dev
libgconf2-dev libasound2-dev libcap-dev libcups2-dev libxtst-dev
libxss1 libnss3-dev gcc-multilib g++-multilib

-

// example: http://hostname.com/http://www.tutorialspoint.com/articles/how-to-configure-and-install-redis-on-ubuntu-linux
//X server: http://www.linfo.org/x_server.html

var express = require('express')
var Nightmare = require('nightmare')// headless browser
var Xvfb = require('xvfb')// run headless browser using X server
var vo = require('vo')// run generator function
var app = express()
var xvfb = new Xvfb()


app.get('/', function (req, res) {
  res.end('')
})

// start the X server to run nightmare.js headless browser
xvfb.start(function (err, xvfbProcess) {
  if (!err) {
    app.get('/*', function (req, res) {
      var run = function * () {
        var nightmare = new Nightmare({
          show: false,
          maxAuthRetries: 10,
          waitTimeout: 100000,
          electronPath: require('electron'),
          ignoreSslErrors: 'true',
          sslProtocol: 'tlsv1'
        })

        var result = yield nightmare.goto(req.url.toString().substring(1))
        .wait()
        // .inject('js', '/path/to/.js') inject a javascript file to manipulate or inject html
        .evaluate(function () {
          return document.documentElement.outerHTML
        })
        .end()
        return result
      }

      // execute generator function
      vo(run)(function (err, result) {
        if (!err) {
          res.end(result)
        } else {
          console.log(err)
          res.status(500).end()
        }
      })
    })
  }
})

app.listen(8080, '0.0.0.0')

答案 2 :(得分:0)

您需要拥有HTTPS,因为您提到的大多数网站都会重定向到其网站的HTTPS版本。也许,如果您希望从禁止/阻止这些网站的地方访问某些网站,而不是使用http代理,您最好使用SOCKS代理。