nginx介紹(六) - 經過反向代理實現跨域訪問

前言

  跨域訪問問題, 相信不少人都遇到過, 而且都用不一樣的辦法去解決過. 方法有不少種, 不一一敘述了. 這裏主要使用nginx反向代理來解決跨域問題.html

 

啥是跨域

  假如你是百度開發人員, 在百度頁面去請求谷歌的資源, 算不算跨域?前端

  跨域是指一個域名的網頁去請求另外一個域名的資源. 只要協議, 域名, 端口中, 有任何一個不一樣, 都是跨域.jquery

 

誰限制了咱們跨域

  罪魁禍首, 是瀏覽器. 爲了安全考慮. 若是一個網站能夠隨意的訪問另外一個網站的資源, 那麼就有可能在客戶不知情的狀況下, 出現安全問題.nginx

  好比:  web

    1. 用戶訪問淘寶, 進行了付錢操做, 這時cookie都生成, 存放在瀏覽器端.ajax

    2. 付完錢後, 小夥去看了看蒼老師(雖然她要結婚了, 可是不影響嘛)apache

    3. 這時候, 看蒼老師的網站, 拿到了淘寶的cookie, 那是否能夠替他買東西呢?api

    4. 若是瀏覽器不限制, 且淘寶也沒有作相應的安全處理, 那麼仍是有可能替他消費的.跨域

 

爲啥要跨域

  前端時間, 公司.net 項目的成員找到咱們, 說想訪問咱們的資源, 但願咱們修改配置, 支持他們跨域訪問. 那不能拒絕啊, 都是爲了工做嘛(主要是沒有拒絕的權利嘛)瀏覽器

  即便是同一家公司, 都會出現跨域訪問的問題, 那我能不讓他訪問我這邊的資源嗎? 很明顯, 作不到嘛, 那不仍是要跨域!

 

  Ok, 前面說了那麼多, 該進入主題了. 今天就用nginx來實現跨域訪問, 消除 服務提供者的配置操做.

 

一. 重現跨域問題

新建兩個項目, 一個用來提供數據, 一個用來訪問數據 

server: 提供數據, 8081端口

  建一個項目 : server, 在其中加入一個控制器, 提供數據

  我只貼一些主要代碼了.

@RestController
@RequestMapping("data")
public class DataController {

    @RequestMapping("get")
    public List<Book> get(){
        List<Book> list = new ArrayList<>();

        list.add(new Book("海底兩萬裏", 3000L));
        list.add(new Book("三體", 1000L));
        list.add(new Book("大鯨魚", 2000L));
        list.add(new Book("是什麼限制了咱們的想象力", 4000L));

        return list;
    }
}

 

client: 訪問數據, 8082端口

<html>
<body>
<h2>Hello World! client</h2>

<script src="js/jquery-1.9.1.js"></script>
<script>
    $(function () {
        console.log("ajax start ...");
        $.ajax({
            url:'http://localhost:8081/server/data/get',
            type:'get',
            success:function (data) {
                console.log(data);
            },
            error:function (data) {
              console.log(data);
            }
        });
    });
</script>
</body>
</html>

 

發佈到本地tomcat中

1. 將webapps拷貝兩份, 分別命名爲 webappsclient, webappsserver

將發佈獲取到的解壓文件夾, 分別放進去. 

2. 修改tomcat配置文件

在server.xml文件中, 加入兩個節點

<Service name="Catalina1">  
     
    <Connector port="8081" maxHttpHeaderSize="8192"  
               maxThreads="150" minSpareThreads="25" maxSpareThreads="75"  
               enableLookups="false" redirectPort="8443" acceptCount="100"  
               connectionTimeout="20000" disableUploadTimeout="true" />  
      
    <Connector port="8009"  enableLookups="false" redirectPort="8443" protocol="AJP/1.3" />  
  
  
    <Engine name="Catalina1" defaultHost="localhost">    
  
      <Realm className="org.apache.catalina.realm.UserDatabaseRealm" resourceName="UserDatabase"/>  
        
      <Host name="localhost" appBase="webappsserver"  
         unpackWARs="true" autoDeploy="true"  
         xmlValidation="false" xmlNamespaceAware="false">                
      </Host>    
    </Engine>  
  
  
</Service> 

<Service name="Catalina2">  
     
    <Connector port="8082" maxHttpHeaderSize="8192"  
               maxThreads="150" minSpareThreads="25" maxSpareThreads="75"  
               enableLookups="false" redirectPort="8443" acceptCount="100"  
               connectionTimeout="20000" disableUploadTimeout="true" />  
      
    <Connector port="8009" enableLookups="false" redirectPort="8443" protocol="AJP/1.3" />  
  
  
    <Engine name="Catalina2" defaultHost="localhost">    
  
      <Realm className="org.apache.catalina.realm.UserDatabaseRealm" resourceName="UserDatabase"/>  
        
      <Host name="localhost" appBase="webappsclient"
         unpackWARs="true" autoDeploy="true"  
         xmlValidation="false" xmlNamespaceAware="false">                
      </Host>    
  
    </Engine>    
  
</Service> 

3. 啓動tomcat, 驗證訪問結果

別急, 按下 f12 看看.

報錯, 不給數據給我.

 

二. 解決跨域問題

1. 修改nginx配置文件, 反向代理這兩個服務. 而後啓動nginx服務

server {
        listen       8081;
        server_name  localhost;

        #charset koi8-r;

        #access_log  logs/host.access.log  main;

        location / {
            proxy_pass http://10.10.21.11:8081;
            index  index.html index.htm;
        }
    }
    
    server {
        listen       8082;
        server_name  localhost;

        #charset koi8-r;

        #access_log  logs/host.access.log  main;

        location / {
            proxy_pass http://10.10.21.11:8082;
            index  index.html index.htm;
            proxy_redirect default;
        }
        
        location /apis{
            rewrite ^.+apis/?(.*)$ /$1 break;
            proxy_pass http://10.10.21.11:8081; }
    }

2. 修改ajax訪問地址, 別的不須要動

3. 查看訪問結果

這裏的ip是nginx服務器的ip

這纔是我須要的數據. 

接下來看一下, 發送出去的請求是啥樣的.

從地址上看, 並無訪問別的地址資源, 那麼瀏覽器, 就認爲, 沒有跨域, 是同源的. 

事實上, nginx經過反向代理, 將請求轉發給 8081 了. 就這麼的, 騙過了瀏覽器.

 參考:

  跨域與跨域訪問

相關文章
相關標籤/搜索