最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

NGINX?權(quán)限控制文件預(yù)覽和下載的實(shí)現(xiàn)原理

 更新時(shí)間:2022年01月12日 10:15:06   作者:隔壁老瓦  
我們知道,使用nginx作為文件下載服務(wù)器,可以極大地降低對后端Java服務(wù)器的負(fù)載沖擊,但是nginx本身并不提供授權(quán)控制,這下該如何操作呢,下面小編給大家?guī)砹薔GINX?權(quán)限控制文件預(yù)覽和下載的實(shí)現(xiàn)原理,感興趣的朋友跟隨小編一起看看吧

@date: 2020-07-31 06:00

基于 Nginx + Java(SpringBoot) 實(shí)現(xiàn)帶權(quán)限驗(yàn)證的靜態(tài)文件服務(wù)器,支持文件下載、PDF預(yù)覽和圖片預(yù)覽。

需要注意的是,無需權(quán)限判斷的圖片不建議使用此方法,大量的圖片訪問會(huì)增加后臺(tái)服務(wù)器的處理壓力。

一、實(shí)現(xiàn)原理

本質(zhì)上是使用了X-Sendfile功能來實(shí)現(xiàn),X-Sendfile 是一種將文件下載請求重定向到Web 服務(wù)器處理的機(jī)制,該Web服務(wù)器只需負(fù)責(zé)處理請求(例如權(quán)限驗(yàn)證),而無需執(zhí)行讀取文件并發(fā)送給用戶的任務(wù)。

X-Sendfile可顯著提高后臺(tái)服務(wù)器的性能,消除了后端程序既要讀文件又要處理發(fā)送的壓力,尤其是處理大文件下載的情形下!

Nginx也具有此功能,但實(shí)現(xiàn)方式略有不同。在Nginx中,此功能稱為X-Accel-Redirect。

用戶請求文件,權(quán)限控制時(shí)序圖:

二、實(shí)現(xiàn)步驟

1. NGINX配置

1、靜態(tài)文件通過file_server訪問,會(huì)被設(shè)置為internal,即只能內(nèi)部訪問不允許外部直接訪問。
2、所有靜態(tài)資源請求均被重定向到Java后臺(tái),經(jīng)過權(quán)限驗(yàn)證后才能訪問。

# 文件下載服務(wù)
location ^~ /file_server {
    # 內(nèi)部請求(即一次請求的Nginx內(nèi)部請求),禁止外部訪問,重要。
    internal;
    # 文件路徑
    alias U:/file/private/;
    limit_rate 200k;
    # 瀏覽器訪問返回200,然后轉(zhuǎn)由后臺(tái)處理
    error_page 404 =200 @backend;
}
# 文件下載鑒權(quán)
location @backend {
    # 去掉訪問路徑中的 /file_server/,然后定義新的請求地址。
    rewrite ^/file_server/(.*)$ /uecom/attach/$1 break;
    # 這里的url后面不可以再拼接地址
    proxy_pass http://192.168.12.68:9023;
    proxy_redirect   off;
    proxy_set_header Host $host;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}

2. JAVA SPRINGBOOT 后臺(tái)權(quán)限驗(yàn)證

用戶請求只需要傳遞附件參數(shù)和身份token,不再需要傳遞服務(wù)器的真實(shí)路徑。例如:

http://192.168.12.68:9022/file_server/preview_file?id=13e9d1887b46455a96842c503c2434cb&access_token=eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOiJ3ZWJfMSIsImV4cCI6MTU5NjE1NzkxOH0.eR4yYlDjIMXZmNNTq2gdghkYhw6I30NgZlvuPUmRoyk

2.1 權(quán)限校驗(yàn)文件下載

response.setHeader("X-Accel-Redirect", "/file_server" + attach.getAttachPath()); ,重點(diǎn)是X-Accel-Redirect配置返回服務(wù)器文件的真實(shí)路徑,該路徑返回后由Nginx內(nèi)部請求處理,不會(huì)暴露給請求用戶。

/**
 * @describe 使用token鑒權(quán)的文件下載
 * @author momo
 * @date 2020-7-30 13:44
 * @param id 文件唯一編碼 uuid
 * @return void
 */
@GetMapping("/download_file")
public void downloadFile(@NotNull String id) throws IOException {
    HttpServletResponse response = super.getHttpServletResponse();
    // 通過唯一編碼查詢附件
    Attach attach = attachService.getById(id);
    if (attach == null) {
        // 附件不存在,跳轉(zhuǎn)404
        this.errorPage(404);
        return;
    }
 
     // 從訪問token中獲取用戶id。 token也可以通過 參數(shù) access_token 傳遞
     Integer userId = UserKit.getUserId();
     if (userId == null || ) {
        // 無權(quán)限訪問,跳轉(zhuǎn)403
         this.errorPage(403);
         return;
     }
     
    // 已被授權(quán)訪問
    // 文件下載
    response.setHeader("Content-Disposition", "attachment; filename=\"" + new String(attach.getAttachName().getBytes("GBK"), "iso-8859-1") + "\"");
    // 文件以二進(jìn)制流傳輸
    response.setHeader("Content-Type", "application/octet-stream;charset=utf-8");
    // 返回真實(shí)文件路徑交由 Nginx 處理,保證前端無法看到真實(shí)的文件路徑。
    // 這里的 "/file_server" 為 Nginx 中配置的下載服務(wù)名
    response.setHeader("X-Accel-Redirect", "/file_server" + attach.getAttachPath());
    // 限速,單位字節(jié),默認(rèn)不限
    // response.setHeader("X-Accel-Limit-Rate","1024");
    // 是否使用Nginx緩存,默認(rèn)yes
    // response.setHeader("X-Accel-Buffering","yes");
	response.setHeader("X-Accel-Charset", "utf-8");
    
    // 禁止瀏覽器緩存
    response.setHeader("Pragma", "No-cache");
    response.setHeader("Cache-Control", "No-cache");
    response.setHeader("Expires", "0");
}

后臺(tái)可配置屬性:

Content-Type: 
Content-Disposition: : 
Accept-Ranges: 
Set-Cookie: 
Cache-Control: 
Expires: 
 
# 設(shè)置文件真實(shí)路徑的URI,默認(rèn)void
X-Accel-Redirect: void
# 限制下載速度,單位字節(jié)。默認(rèn)不限速度off。
X-Accel-Limit-Rate: 1024|off
# 設(shè)置此連接的代理緩存,將此設(shè)置為no將允許適用于Comet和HTTP流式應(yīng)用程序的無緩沖響應(yīng)。將此設(shè)置為yes將允許響應(yīng)被緩存。默認(rèn)yes。
X-Accel-Buffering: yes|no
# 如果已傳輸過的文件被緩存下載,設(shè)置Nginx文件緩存過期時(shí)間,單位秒,默認(rèn)不過期 off。
X-Accel-Expires: off|seconds
# 設(shè)置文件字符集,默認(rèn)utf-8。
X-Accel-Charset: utf-8

2.2 權(quán)限校驗(yàn)文件預(yù)覽

文件下載和文件預(yù)覽本質(zhì)上沒有區(qū)別,只是response返回時(shí)告訴瀏覽器執(zhí)行下載還是執(zhí)行打開預(yù)覽。即response.setHeader("Content-Disposition", "inline; filename="xxx.pdf");, 然后修改返回?cái)?shù)據(jù)的格式Content-Type即可。

Content-Disposition 響應(yīng)頭指示回復(fù)的內(nèi)容該以何種形式展示,是以內(nèi)聯(lián)inline)的形式(即網(wǎng)頁或者頁面的一部分),還是以附件attachment)的形式下載并保存到本地。

/**
 * @describe 使用token鑒權(quán)的文件預(yù)覽(支持pdf和圖片)
 * @author momo
 * @date 2020-7-30 13:44
 * @param id 文件唯一編碼 uuid
 * @return void
 */
@GetMapping("/preview_file")
public void previewFile(@NotNull String id) throws IOException {
    HttpServletResponse response = super.getHttpServletResponse();
    // 通過唯一編碼查詢附件
	Attach attach = attachService.getById(id);
    if (attach == null) {
        // 附件不存在,跳轉(zhuǎn)404
        this.errorPage(404);
        return;
    }
 
     // 從訪問token中獲取用戶id。 token也可以通過 參數(shù) access_token 傳遞
      Integer userId = UserKit.getUserId();
      if (userId == null || ) {
         // 無權(quán)限訪問,跳轉(zhuǎn)403
          this.errorPage(403);
          return;
      }
 
    // 已被授權(quán)訪問
    // 文件直接顯示
    response.setHeader("Content-Disposition", "inline; filename=\"" + new String(attach.getAttachName().getBytes("GBK"), "iso-8859-1") + "\"");
    if ("pdf".equals(attach.getAttachType().toLowerCase())) {
        // PDF
        response.setHeader("Content-Type", "application/pdf;charset=utf-8");
    } else {
        // 圖片
        response.setHeader("Content-Type", "image/*;charset=utf-8");
    }
    // 返回真實(shí)文件路徑交由 Nginx 處理,保證前端無法看到真實(shí)的文件路徑。
    // 這里的 "/file_server" 為 Nginx 中配置的下載服務(wù)名
    response.setHeader("X-Accel-Redirect", "/file_server" + attach.getAttachPath());
    // 瀏覽器緩存 1 小時(shí)
    response.setDateHeader("Expires", System.currentTimeMillis() + 1000 * 60 * 60);
}

三、擴(kuò)展功能

1. 下載統(tǒng)計(jì)、訪問日志

// 自由發(fā)揮

2. 下載限速

// 限速,單位字節(jié),默認(rèn)不限
response.setHeader("X-Accel-Limit-Rate","1024");

3. 防盜鏈

//判斷 Referer
String referer = request.getHeader("Referer");
if (referer == null || !referer.startsWith("https://www.itmm.wang")) {
    // 無權(quán)限訪問,跳轉(zhuǎn)403
    this.errorPage(403);
    return;
}

4. X-SENDFILE

X-Sendfile是一項(xiàng)功能,每個(gè)代理服務(wù)器都有自己不同的實(shí)現(xiàn)。

Web ServerHeader
NginxX-Accel-Redirect
ApacheX-Sendfile
LighttpdX-LIGHTTPD-send-file
SquidX-Accelerator-Vary

使用 X-SendFile 的缺點(diǎn)是你失去了對文件傳輸機(jī)制的控制。例如如果你希望在完成文件下載后執(zhí)行某些操作,比如只允許用戶下載文件一次,這個(gè) X-Sendfile 是沒法做到的,因?yàn)檎埱蠼唤o了后臺(tái),你并不知道下載是否成功。

參考資料

  1. X-Sendfile-從Web應(yīng)用程序有效地提供大型靜態(tài)文件
  2. Nginx-X-Accel-Redirect
  3. Nginx -XSendfile
  4. Content-Disposition
  5. Http Content-Type

到此這篇關(guān)于NGINX 權(quán)限控制文件預(yù)覽和下載的文章就介紹到這了,更多相關(guān)nginx文件預(yù)覽下載內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Nginx四層負(fù)載均衡的實(shí)現(xiàn)示例

    Nginx四層負(fù)載均衡的實(shí)現(xiàn)示例

    Nginx?不支持傳統(tǒng)的四層負(fù)載均衡,但可以通過stream模塊配合TCP實(shí)現(xiàn)類似的功能,本文主要介紹了Nginx四層負(fù)載均衡的實(shí)現(xiàn)示例,具有一定的參考價(jià)值,感興趣的可以了解一下
    2024-04-04
  • Nginx制作下載站點(diǎn)的方法步驟

    Nginx制作下載站點(diǎn)的方法步驟

    本文主要介紹了Nginx制作下載站點(diǎn)的方法步驟,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2024-10-10
  • 在Nginx中增加對OAuth協(xié)議的支持的教程

    在Nginx中增加對OAuth協(xié)議的支持的教程

    這篇文章主要介紹了在Nginx中增加對OAuth協(xié)議的支持的教程,OAuth協(xié)議如今廣泛用于社交網(wǎng)絡(luò)的API中,需要的朋友可以參考下
    2015-06-06
  • Nginx配置server_name為域名后無法訪問的問題解決

    Nginx配置server_name為域名后無法訪問的問題解決

    在Nginx的配置文件中增加服務(wù)器,其server_name設(shè)置為域名時(shí),該網(wǎng)址不能正常訪問,所以本文給大家介紹了Nginx配置server_name為域名后無法訪問的問題解決,需要的朋友可以參考下
    2024-01-01
  • 使用nginx+lua進(jìn)行token鑒權(quán)的方法

    使用nginx+lua進(jìn)行token鑒權(quán)的方法

    使用nginx和lua腳本實(shí)現(xiàn)對Minio服務(wù)器圖片鏈接的token鑒權(quán),通過反向代理隱藏真實(shí)IP,增強(qiáng)安全性,介紹了整個(gè)鑒權(quán)流程,包括nginx配置和lua腳本的具體實(shí)現(xiàn),適用于需要保護(hù)圖片不被未授權(quán)訪問的場景
    2022-05-05
  • 服務(wù)器報(bào)錯(cuò)nginx?502?Bad?Gateway的原因及如何解決詳解

    服務(wù)器報(bào)錯(cuò)nginx?502?Bad?Gateway的原因及如何解決詳解

    項(xiàng)目啟動(dòng)時(shí)莫名其妙網(wǎng)站訪問不了,502 Bad Gateway,下面這篇文章主要給大家介紹了關(guān)于服務(wù)器報(bào)錯(cuò)nginx?502?Bad?Gateway的原因及如何解決的相關(guān)資料,文中通過實(shí)例代碼介紹的非常詳細(xì),需要的朋友可以參考下
    2023-06-06
  • 詳解Nginx啟用proxy_buffer緩沖

    詳解Nginx啟用proxy_buffer緩沖

    本篇文章主要介紹了Nginx啟用proxy_buffer緩沖,Nginx啟用proxy_buffer緩沖,本文詳細(xì)的介紹了基本用法,具有一定的參考價(jià)值,有興趣的可以了解一下
    2018-01-01
  • Docker Nginx容器和Tomcat容器實(shí)現(xiàn)負(fù)載均衡與動(dòng)靜分離操作

    Docker Nginx容器和Tomcat容器實(shí)現(xiàn)負(fù)載均衡與動(dòng)靜分離操作

    這篇文章主要介紹了Docker Nginx容器和Tomcat容器實(shí)現(xiàn)負(fù)載均衡與動(dòng)靜分離操作,具有很好的參考價(jià)值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2020-11-11
  • nginx修改默認(rèn)運(yùn)行80端口的方法

    nginx修改默認(rèn)運(yùn)行80端口的方法

    這篇文章主要給大家介紹了關(guān)于nginx是如何修改默認(rèn)運(yùn)行80端口的方法,文中介紹的非常詳細(xì),需要的朋友可以參考借鑒,下面來一起看看吧。
    2017-04-04
  • Nginx服務(wù)優(yōu)化配置方案

    Nginx服務(wù)優(yōu)化配置方案

    這篇文章主要介紹了Nginx服務(wù)優(yōu)化配置方案,非常不錯(cuò),具有參考借鑒價(jià)值,需要的朋友可以參考下
    2018-03-03

最新評論

庆元县| 射洪县| 芦山县| 高青县| 炎陵县| 获嘉县| 兴仁县| 来宾市| 油尖旺区| 德保县| 平罗县| 忻州市| 沽源县| 沧源| 伊吾县| 万全县| 宜川县| 乐都县| 兴宁市| 花垣县| 柳林县| 梁河县| 霍邱县| 安康市| 富民县| 宜昌市| 宁都县| 万安县| 玉门市| 东阳市| 中江县| 安平县| 临清市| 阿拉善左旗| 韩城市| 肇州县| 潮安县| 黄龙县| 正蓝旗| 遂平县| 新平|