当前位置: 首页 > news >正文

企业级-实现Nginx的静态文件服务器映射

作者:fyupeng
技术专栏:☞ https://github.com/fyupeng
项目地址:☞ https://github.com/fyupeng/distributed-blog-system-api


留给读者

开发人员往往会经常需要通过浏览器下载文件、图片或者PDF或者缩略图等,这时候我们可以根据自己的需求自定义设置,安全性就可以由自己来把握。

一、介绍

难点主要在于把文件路径当成参数传给后端,后端根据一定的规则处理,将结果写入响应返回给浏览器。

优点

  • 使用懒加载方式,如果本地有,就不从OSS获取,本地没有先从OSS下载到本地,以便频繁下载文件时降低OSS的出入流量。
  • 待补充

二、代码

/*** @Auther: fyp* @Date: 2024/7/26* @Description: 文件预览处理器* @Package: com.gwssi.common.web* @Version: 1.0*/@Controller
public class FilePreviewController {//本地测试可改为自己的路径//private static final String FILE_DIRECTORY = "D:/upload/";private static final String FILE_DIRECTORY = "/data/hqzr/";@ResponseBody@RequestMapping(value = "/file/{fileUrl}/**",  method = RequestMethod.GET)public void getFile(@PathVariable String fileUrl, HttpServletRequest req, HttpServletResponse resp) throws IOException {String path = req.getAttribute(HandlerMapping.PATH_WITHIN_HANDLER_MAPPING_ATTRIBUTE).toString();String path2 = req.getAttribute(HandlerMapping.BEST_MATCHING_PATTERN_ATTRIBUTE).toString();String args = new AntPathMatcher().extractPathWithinPattern(path2, path);args = args.replace(".do", "");fileUrl = fileUrl + "/" + args;File file = new File(FILE_DIRECTORY + fileUrl);byte[] bytes = null;// 添加安全检查,确保文件确实在预期的目录中if (!file.exists() || !file.isFile() || !file.getCanonicalPath().startsWith(new File(FILE_DIRECTORY).getCanonicalPath())) {// 处理非法访问,例如返回404File parentDir = file.getParentFile();if (!parentDir.exists()) {parentDir.mkdirs(); // 确保文件所在的目录存在}bytes = OssUtil.downloadByBytes(FILE_DIRECTORY + fileUrl);if (null != bytes) {FileOutputStream fos = new FileOutputStream(file);fos.write(bytes);fos.close();resp.reset(); // 非常重要} else {Map<String, String> map = new HashMap<String, String>();map.put("code", "-100");map.put("msg", "文件预览失败");ResponseUtil.returnFrontByJSON(map, resp);}}// 设置适当的响应头(纯下载方式)//resp.setContentType("application/octet-stream; charset=utf-8");//resp.setHeader("Content-Disposition", "attachment;filename=" + file.getName());// 直接预览打开resp.setContentType("image/png"); // 设置返回的文件类型resp.addHeader("Content-Length", String.valueOf(file.length()));  //文件大小// 使用ServletOutputStream将图片数据写入响应try (ServletOutputStream outputStream = resp.getOutputStream();BufferedInputStream inputStream = new BufferedInputStream(new FileInputStream(file))) {// 从文件服务器获取if (null != bytes) {outputStream.write(bytes);} else {// 从本地获取byte[] buffer = new byte[4096];int bytesRead = -1;// 读取文件内容并写入响应while ((bytesRead = inputStream.read(buffer)) != -1) {outputStream.write(buffer, 0, bytesRead);}}// 刷新输出流,确保所有数据都被发送outputStream.flush();}}private String getMimeType(File file) {// 这里可以根据文件扩展名返回相应的MIME类型// 这里只是一个简单的示例,实际应用中可能需要更复杂的逻辑String filename = file.getName().toLowerCase();if (filename.endsWith(".png")) {return MediaType.IMAGE_PNG_VALUE;} else if (filename.endsWith(".jpg") || filename.endsWith(".jpeg")) {return MediaType.IMAGE_JPEG_VALUE;}// 添加更多MIME类型判断...return MediaType.APPLICATION_OCTET_STREAM_VALUE; // 默认类型}
}

三、总结

简洁、高效、实用!

相关文章:

企业级-实现Nginx的静态文件服务器映射

作者&#xff1a;fyupeng 技术专栏&#xff1a;☞ https://github.com/fyupeng 项目地址&#xff1a;☞ https://github.com/fyupeng/distributed-blog-system-api 留给读者 开发人员往往会经常需要通过浏览器下载文件、图片或者PDF或者缩略图等&#xff0c;这时候我们可以根据…...

CTF Web SQL注入 10000字详解

这里写目录标题 涉及的数据库知识unionorder bydatabase()information_schemalimit--空格注释replaceinto outfilelikeGROUP BYHAVINGGROUP BY、HAVING、WHERE之间的关系regexp 原理信息收集操作系统数据库判断注入点注入点类型POST注入数字型注入字符型注入搜索型注入Insert/u…...

动态SLAM:如何判断一个特征是动态特征(对极几何)

文章目录 1.什么是极线、极点和极面2.如何判断其为动态点特征3.如何判断其为动态线特征 1.什么是极线、极点和极面 由图可知&#xff0c;C1,C2,X(X1,X2)组成了一个三角平面&#xff0c;这个三角所在的平面就是极面 在这个极平面中&#xff0c;和成像平面相交的线是极线&#xf…...

【C++】初识C++基础篇·一(命名空间,函数重载,缺省参数,引用);

文章目录 前言1.输入与输出输出输入cin和scanf的对比 2.命名空间2.1namespace存在的意义2.2namespace的使用3.缺省参数4.函数重载重载函数的调用规则 5.引用 前言 我们先通过一段简单的代码来拉开C的序幕&#xff1b; //text.cpp #include<iostream> #include<stdio…...

2024年道路运输安全员考试题库及答案

一、判断题 1.国家制订《中华人民共和国道路交通安全法》的目的是为了维护道路交通秩序&#xff0c;预防和减少交通事故&#xff0c;保护人身安全&#xff0c;保护公民、法人和其他组织的财产安全及其他合法权益&#xff0c;提高通行效率。 答案&#xff1a;正确 2.依据《中…...

Linux Vim教程(十二):语法高亮与代码折叠

目录 1. 语法高亮 1.1 启用语法高亮 1.2 设置配色方案 1.3 自定义语法高亮 2. 代码折叠 2.1 启用代码折叠 2.2 设置折叠方法 2.3 手动折叠 2.4 基于缩进的折叠 2.5 基于语法的折叠 3. 案例 3.1 配置文件 3.2 编辑Python文件 3.3 使用折叠功能 4. 高级使用技巧 …...

JavaScript(18)——事件类型,事件对象

事件类型 鼠标事件&#xff1a; click&#xff1a;鼠标点击 mouseenter&#xff1a;鼠标经过 mouseleave&#xff1a;鼠标离开 焦点事件&#xff1a; focus&#xff1a;获得焦点 blur&#xff1a;失去焦点 键盘事件&#xff1a; Keydown&#xff1a;键盘按下触发 Keyup&#…...

有效组织离散变量:指针数组在C语言中的应用

把离散变量组织起来&#xff0c;访问起来更加方便&#xff0c;无需一个个变量单独赋值。 如modbus读写reg&#xff0c; 把a\b\c\d实时变化分散的变量组织成一个数组reg&#xff0c;方便获取 相当于变量的内存地址池 int main() {int a 10, b 20, c 30, d 40;int i;int *re…...

qt 应用正在运行时,如何更新升级exe文件

在Qt应用正在运行时&#xff0c;直接替换同名的.exe文件可能会导致文件正在使用中的错误。为了安全地更新.exe文件&#xff0c;你可以采取以下步骤&#xff1a; 创建一个临时的.exe文件。 等待当前.exe文件的进程关闭。 删除原有的.exe文件。 将临时.exe文件重命名为原有的.…...

git的rebase 和 merge 的区别

rebase 和 merge 的区别 Merge&#xff08;合并&#xff09;和 Rebase&#xff08;变基&#xff09;是 Git 中两种常用的分支整合方式&#xff0c;它们有不同的工作原理和适用场景&#xff1a; Merge&#xff08;合并&#xff09;&#xff1a; ● Merge 操作将两个分支的不同提…...

django基于大数据的电影推荐系统-计算机毕业设计源码71246

目 录 摘 要 1 绪论 1.1 选题背景与意义 1.2研究现状 1.3研究内容 1.4 开发环境 1.5论文结构与章节安排 2 相关理论和技术 2.1 协同过滤算法 2.2 B/S体系结构介绍 2.3 Python爬虫技术 2.4 Django框架介绍 2.5 MySQL数据库 3 电影推荐系统系统分析 3.1 可行性分析…...

reverse_re3-入土为安的第十天

一个迷宫题 shirtf12发现flag字样 点进去发现迷宫 675 应该是3 * 15*15 即有三个迷宫 shifte提取 import numpy as np# 你的数据&#xff08;长度应为 225 的倍数&#xff09; dword_202020 [1,1,1,1,1,0,0,0,0,0,0,0,0,0,0,1,1,1,1,1,0,3,1,1,0,0,0,0,0,0,1,1,1,1,1,0,0,…...

fastapi之一

文章目录 安装运行HTTP 请求方法示例 POSTMAN 检验GETPOSTPUTDELETE HTTP 状态码示例GETPOST 综合示例POSTGETPUTDELETE 总结 安装 pip install fastapi或者 pip install fastapi -i https://mirrors.aliyun.com/pypi/simple上面两种方法均可以&#xff0c;选择一个即可&…...

【C语言报错已解决】Format String Vulnerability

&#x1f3ac; 鸽芷咕&#xff1a;个人主页 &#x1f525; 个人专栏: 《C干货基地》《粉丝福利》 ⛺️生活的理想&#xff0c;就是为了理想的生活! 引言 在日常开发中&#xff0c;我们经常会遇到各种各样的bug&#xff0c;其中格式化字符串漏洞报错可能是最让人头疼的一种。这…...

关于一个简单的顺序表代码

1.首先是头文件SeqList.h的代码&#xff1a; #pragma once #include<stdio.h> #include<assert.h> #include<stdlib.h> typedef int SXBint; typedef struct SL {SXBint* a;int size;int capacity; }SLnode; //初始化 void SeqLsitInit(SLnode* ps); //尾插…...

【资料分享】2024第三届钉钉杯大学生大数据挑战赛B题思路解析+双语言代码

2024钉钉杯大学生大数据挑战赛&#xff0c;B题解题思路和双语言代码分享&#xff0c;资料预览&#xff1a;...

Typescript学习笔记(2.0)

ts编译选项 tsc app.ts -w 参数-w&#xff0c;就是对app.ts进行监视&#xff0c;每次该文件改变时就会自动编译 **:任意目录 *&#xff1a;任意文件 接口 接口用来定义一个类结构&#xff0c;用来定义一个类中应该包含哪些属性和方法&#xff0c;同时接口也可以当做类型…...

【IJHE】:微通道反应器中全氢二苄基甲苯脱氢产氢

Highlight 微通道反应器中全氢二苄基甲苯脱氢产氢两种不同反应器的比较&#xff1a;搅拌釜和连续微通道反应器连续微通道反应器是一种很有前途的脱氢技术 摘要: 本文对全氢二苄基甲苯作为液态有机氢载体从搅拌槽反应器转换为连续流微通道反应器进行脱氢进行了初步研究。与搅拌槽…...

Spring踩坑:抽象类作为父类,使用子类@Autowired属性进行填充,属性值为null

Spring踩坑&#xff1a;抽象类作为父类&#xff0c;使用子类Autowired属性进行填充&#xff0c;属性值为null Spring Boot中抽象类和依赖注入的最佳实践引言在抽象类中使用Autowired注解protected vs private修饰符低版本Spring Boot的注意事项 构造器中的依赖注入陷阱为什么不…...

C#网络连接:TCP/IP模式下的网络连接与同步

1&#xff0c;目的 为了测试局域网的消息同步&#xff0c;简单写了下TCP/IP模式的同步&#xff0c;参考这个帖子。 2&#xff0c;核心库部分 using System; using System.Net; using System.Net.Sockets; using System.Text;namespace Coldairarrow.Util.Sockets {/// <s…...

React 第五十五节 Router 中 useAsyncError的使用详解

前言 useAsyncError 是 React Router v6.4 引入的一个钩子&#xff0c;用于处理异步操作&#xff08;如数据加载&#xff09;中的错误。下面我将详细解释其用途并提供代码示例。 一、useAsyncError 用途 处理异步错误&#xff1a;捕获在 loader 或 action 中发生的异步错误替…...

利用ngx_stream_return_module构建简易 TCP/UDP 响应网关

一、模块概述 ngx_stream_return_module 提供了一个极简的指令&#xff1a; return <value>;在收到客户端连接后&#xff0c;立即将 <value> 写回并关闭连接。<value> 支持内嵌文本和内置变量&#xff08;如 $time_iso8601、$remote_addr 等&#xff09;&a…...

基于数字孪生的水厂可视化平台建设:架构与实践

分享大纲&#xff1a; 1、数字孪生水厂可视化平台建设背景 2、数字孪生水厂可视化平台建设架构 3、数字孪生水厂可视化平台建设成效 近几年&#xff0c;数字孪生水厂的建设开展的如火如荼。作为提升水厂管理效率、优化资源的调度手段&#xff0c;基于数字孪生的水厂可视化平台的…...

unix/linux,sudo,其发展历程详细时间线、由来、历史背景

sudo 的诞生和演化,本身就是一部 Unix/Linux 系统管理哲学变迁的微缩史。来,让我们拨开时间的迷雾,一同探寻 sudo 那波澜壮阔(也颇为实用主义)的发展历程。 历史背景:su的时代与困境 ( 20 世纪 70 年代 - 80 年代初) 在 sudo 出现之前,Unix 系统管理员和需要特权操作的…...

.Net Framework 4/C# 关键字(非常用,持续更新...)

一、is 关键字 is 关键字用于检查对象是否于给定类型兼容,如果兼容将返回 true,如果不兼容则返回 false,在进行类型转换前,可以先使用 is 关键字判断对象是否与指定类型兼容,如果兼容才进行转换,这样的转换是安全的。 例如有:首先创建一个字符串对象,然后将字符串对象隐…...

Device Mapper 机制

Device Mapper 机制详解 Device Mapper&#xff08;简称 DM&#xff09;是 Linux 内核中的一套通用块设备映射框架&#xff0c;为 LVM、加密磁盘、RAID 等提供底层支持。本文将详细介绍 Device Mapper 的原理、实现、内核配置、常用工具、操作测试流程&#xff0c;并配以详细的…...

基于matlab策略迭代和值迭代法的动态规划

经典的基于策略迭代和值迭代法的动态规划matlab代码&#xff0c;实现机器人的最优运输 Dynamic-Programming-master/Environment.pdf , 104724 Dynamic-Programming-master/README.md , 506 Dynamic-Programming-master/generalizedPolicyIteration.m , 1970 Dynamic-Programm…...

ABAP设计模式之---“简单设计原则(Simple Design)”

“Simple Design”&#xff08;简单设计&#xff09;是软件开发中的一个重要理念&#xff0c;倡导以最简单的方式实现软件功能&#xff0c;以确保代码清晰易懂、易维护&#xff0c;并在项目需求变化时能够快速适应。 其核心目标是避免复杂和过度设计&#xff0c;遵循“让事情保…...

Reasoning over Uncertain Text by Generative Large Language Models

https://ojs.aaai.org/index.php/AAAI/article/view/34674/36829https://ojs.aaai.org/index.php/AAAI/article/view/34674/36829 1. 概述 文本中的不确定性在许多语境中传达,从日常对话到特定领域的文档(例如医学文档)(Heritage 2013;Landmark、Gulbrandsen 和 Svenevei…...

LLMs 系列实操科普(1)

写在前面&#xff1a; 本期内容我们继续 Andrej Karpathy 的《How I use LLMs》讲座内容&#xff0c;原视频时长 ~130 分钟&#xff0c;以实操演示主流的一些 LLMs 的使用&#xff0c;由于涉及到实操&#xff0c;实际上并不适合以文字整理&#xff0c;但还是决定尽量整理一份笔…...