【Go】gin框架生成压缩包与下载文件

在没有加入下面这串代码之前,下载的压缩包一直为空。遂debug了两个小时。。。
可以在服务端本地创建压缩包。单独将服务端本地的压缩包发送给客户端也是没问题的。但是两个合起来,客户端接收到的压缩包内容就为空了。
期间也尝试了
zipFile.Close()
zipWriter.Close()
但是zipFile不能立刻关

	// 关闭 ZIP 归档,确保所有数据都被写入压缩包文件err = zipWriter.Close()if err != nil {fmt.Println("无法关闭 ZIP 归档:", err)return}

将缓冲区中的数据刷新到磁盘上的压缩包文件。
在创建 ZIP 归档后,需要调用 zipWriter.Close() 来确保所有的数据都被写入压缩包文件。在 zipWriter.Close() 被调用之前,压缩包文件可能仍然处于打开状态,并且尚未完全写入磁盘。

func download(c *gin.Context) {tmpData := make(map[string]interface{})if err := c.ShouldBindJSON(&tmpData); err != nil {log.Println(err)c.JSON(http.StatusBadRequest, gin.H{"msg": "请求参数错误"})return}// 获取要下载的文件列表filePaths := tmpData["selectedIds"].([]interface{})// 获取当前时间currentTime := time.Now()// 格式化为特定格式formattedTime := currentTime.Format("2006-01-02-15-04")zipFilename := formattedTime + ".zip"tempZipPath := filepath.Join(zipFilename)// 创建压缩包文件zipFile, err := os.Create(tempZipPath)if err != nil {fmt.Println("无法创建压缩包文件:", err)return}defer zipFile.Close()// 创建 ZIP 归档zipWriter := zip.NewWriter(zipFile)defer zipWriter.Close()for _, filePath := range filePaths {idStr := fmt.Sprintf("%v", filePath)filePath := filepath.Join("nuclei-templates-original", idStr+".yaml")fmt.Printf(filePath)// 添加文件到 ZIP 归档err = addFileToZip(zipWriter, filePath)if err != nil {fmt.Println("无法添加文件到压缩包:", err)return}fmt.Println("文件已成功添加到压缩包中。")}// 关闭 ZIP 归档,确保所有数据都被写入压缩包文件err = zipWriter.Close()if err != nil {fmt.Println("无法关闭 ZIP 归档:", err)return}file, err := os.Open(tempZipPath)if err != nil {c.String(http.StatusInternalServerError, "无法打开压缩包")return}// 获取文件信息fileInfo, err := file.Stat()if err != nil {c.String(http.StatusInternalServerError, "无法获取压缩包信息")return}// 设置响应头c.Header("Content-Type", "application/zip")c.Header("Content-Disposition", "attachment; filename="+tempZipPath)c.Header("Content-Length", strconv.FormatInt(fileInfo.Size(), 10))// 将压缩包内容发送给客户端_, err = io.Copy(c.Writer, file)if err != nil {c.String(http.StatusInternalServerError, "无法发送压缩包")return}}func addFileToZip(zipWriter *zip.Writer, filePath string) error {// 打开要添加的文件file, err := os.Open(filePath)if err != nil {return err}defer file.Close()// 获取文件信息info, err := file.Stat()if err != nil {return err}// 创建 ZIP 归档中的文件header, err := zip.FileInfoHeader(info)if err != nil {return err}// 设置 ZIP 归档中的文件名header.Name = filepath.Base(filePath)// 写入文件到 ZIP 归档writer, err := zipWriter.CreateHeader(header)if err != nil {return err}_, err = io.Copy(writer, file)return err
}

gin框架跟着 狂神说,一个小时速成,讲的很好
这是老师课上的源码

package main
import ("encoding/json""log""net/http""github.com/gin-gonic/gin""github.com/thinkerou/favicon"
)
//自定义go中间件即拦截器
//给所有请求使用  则不不写在下列方法里,写了则拦截指定方法的请求func myHandler() (gin.HandlerFunc) {//通过自定义的中间件,设置的值,在后续处理只要调用了这个中间件的都可以拿到这里的参数return func(context *gin.Context) {context.Set("usersession","userid-1")//if ...context.Next() //放行context.Abort() //阻止}
}
func main() {//创建一个服务ginServer := gin.Default()ginServer.Use(favicon.New("./favicon.ico"))//加载静态页面ginServer.LoadHTMLGlob("templates/*")//加载资源目录ginServer.Static("/static","./static")//Gin RestfulginServer.GET("/hello",myHandler(),func(Context *gin.Context) {//取出中间件中的值usersession := Context.MustGet("userSession").(string) //空接口转换为stringlog.Println("------->",usersession)Context.JSON(200,gin.H{"msg":"hello,world"})})ginServer.POST("/user",func(c *gin.Context) {c.JSON(200,gin.H{"msg":"post,user"})})ginServer.PUT("/user")ginServer.DELETE("/user")//响应一个页面给前端ginServer.GET("/index",func(Context *gin.Context) {Context.HTML(http.StatusOK,"index.html",gin.H{"msg":"这是go后台传递来的数据",})      //接收前端传递过来的参数//info?userid=xxx&username=kuangshen// ginServer.GET("/user/info",func(context *gin.Context) {//  userid := context.Query("userid")//  username := context.Query("username")//  context.JSON(http.StatusOK,gin.H{//      "userid": userid,//      "username": username,//  })  // })//info/1/kaungshenginServer.GET("/user/info/:userid/:username",func(context *gin.Context) {userid := context.Param("userid")username := context.Param("username")context.JSON(200,gin.H{"userid": userid,"username": username,})})//掌握技术后面的应用- 掌握基础知识,加以了解web知识// 前端给后端传递 jsonginServer.POST("/json",func(context *gin.Context) {//request.body//[]body 返回的是切片data,_ := context.GetRawData()var m map[string]interface{}//包装为json数据 []byte_ = json.Unmarshal(data,&m)context.JSON(200,m)})//支持表单ginServer.POST("/user/add",func(context *gin.Context) {username := context.PostForm("username")password := context.PostForm("password")context.JSON(200,gin.H{"msg":"ok","username":username,"password":password,})})//路由ginServer.GET("/test",func(context *gin.Context) {//重定向context.Redirect(301,"http://baidu.com")        })//404 NoRouteginServer.NoRoute(func(context *gin.Context) {context.HTML(http.StatusNotFound,"404.html",nil)})//路由组userGroup := ginServer.Group("/user"){userGroup.GET("/add")userGroup.POST("/login")userGroup.POST("/logout")}orderGroup := ginServer.Group("order"){orderGroup.GET("/add")orderGroup.DELETE("/delete")}  
})//服务器端口ginServer.Run(":8082")
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/102908.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

解决Springboot集成RabbitMQ不自动生成队列的问题

1.RabbitMQ消息的消费端服务 RabbitMQ懒加载模式, 需要配置消费者监听才会创建 RabbitListener(queues "test.queue")另外一种方式(若Mq中无相应名称的队列,会自动创建Queue),改为如下 RabbitListener(queuesToDeclare { Queue(value "test.queu…

MAX17058_MAX17059 STM32 iic 驱动设计

本文采用资源下载链接,含完整工程代码 MAX17058-MAX17059STM32iic驱动设计内含有代码、详细设计过程文档,实际项目中使用代码,稳定可靠资源-CSDN文库 简介 MAX17058/MAX17059 IC是微小的锂离子(Li )在手持和便携式设备的电池电量计。MAX170…

关于Win系统提示由于找不到msvcr120.dll文件问题解决办法

在我使用电脑的过程中,突然弹出了一个错误提示框,提示我系统中缺少msvcp120.dll文件。这个文件是系统运行所必需的,缺少它可能会导致一些软件无法正常运行。经过一番搜索和咨询,我找到了以下几种解决方案,分享给大家&a…

OpenCV中initUndistortRectifyMap ()函数与十四讲中去畸变公式的区别探究

文章目录 1.十四讲中的去畸变公式2. OpenCV中的去畸变公式3. 4个参数和8个参数之间的区别4.initUndistortRectifyMap()函数源码 最近在使用OpenCV对鱼眼相机图像去畸变时发现一个问题,基于针孔模型去畸变时所使用的参数和之前十四讲以及视觉SLAM中的畸变系数有一点不…

UEFI基础——Protocol服务

一、Protocol 介绍 Protocol是UEFI中重要概念之一,Protocol在UEFI中的角色相当于UEFI的接口函数。实际上,Proctol是UEFI环境的提供者何使用者之间的一种约定,双方根据这个协定进行通信。 UEFI中的Proctol引入了面向对象的思想: 使用struct来模拟 class 。用函数指针(Pro…

Vue-2.3v-model原理

原理:v-model本质上是一个语法糖,例如应用在输入框上,就是value属性和input事件的合写。 作用:提供数据的双向绑定 1)数据变,视图跟着变:value 2)视图变,数据跟着变input 注意&a…

把短信验证码储存在Redis

校验短信验证码 接着上一篇博客https://blog.csdn.net/qq_42981638/article/details/94656441,成功实现可以发送短信验证码之后,一般可以把验证码存放在redis中,并且设置存放时间,一般短信验证码都是1分钟或者90s过期,…

伦敦金的交易时间究竟多长?

接触过伦敦金交易的投资者,应该都知道自己根本不用担心市场上没有交易的机会,因为它全天的交易时间长达20多个小时,也就是在每一个正常的交易日,除去交易平台中途短暂的系统维护时间,投资者几乎全天都可以做盘。 伦敦金…

Maven导入程序包jakarta.servlet,但显示不存在

使用前提:(Tomcat10版本)已知tomcat10版本之后,使用jakart.servlet。而tomcat9以及之前使用javax.servlet。 问题描述:在maven仓库有导入了Jakarta程序包,但是界面仍然显示是javax。(下图&…

Unity实现设计模式——适配器模式

Unity实现设计模式——适配器模式 适配器模式又称为变压器模式、包装模式(Wrapper) 将一个类的接口变换成客户端所期待的另一种接口,从而使原本因接口不匹配而无法在一起工作的两个类能够在一起工作。 在一个在役的项目期望在原有接口的基础…

一文带你上手自动化测试中的PO模式!

在UI的自动化测试中,我们需要把测试使用到的数据分离到文件中,如果单纯的写在我们的测试模块里面,不是一个好的设计,所以不管是什么类型的自动化测试,都是需要把数据分离出来的。当然分离到具体的文件里面,…

智能井盖传感器:数智赋能让城市管理更智慧

智能井盖传感器:数智赋能让城市管理更智慧 在城市化快速发展的今天,保护和增强城市基础设施生命线的需求至关重要。而井盖作为守护城市地下空间的安全门,其智能化管理与城市生命线安全工程建设息息相关。在这篇文章中将为大家详细介绍智能井…

OpenCV级联分类器识别车辆实践笔记

1. OpenCV 级联分类器的基本原理 基于Haar特征的级联分类器的目标检测是Paul Viola和Michael Jones在2001年的论文中提出的一种有效的目标检测方法。这是一种基于机器学习的方法,从大量的正面和负面图像中训练级联函数。然后用它来检测其他图像中的物体。 Haar特征…

CTF Misc(3)流量分析基础以及原理

前言 流量分析在ctf比赛中也是常见的题目,参赛者通常会收到一个网络数据包的数据集,这些数据包记录了网络通信的内容和细节。参赛者的任务是通过分析这些数据包,识别出有用的信息,例如登录凭据、加密算法、漏洞利用等等 工具安装…

平面设计师要会3D吗 优漫动游

所谓物以稀为贵,对于设计人才也一样。越是稀缺的能力,能够发挥的价值就越高。于是现在很多互联网名企在招聘的时候都加了一条:会3D设计者优先。 其实这些看起来很厉害的设计,归结起来无非就三种形式:插画、三维、合成…

共生与共享:线程与进程的关系

🌍前言 在计算机科学和操作系统领域,线程(Thread)和进程(Process)是两个关键概念。它们之间存在密切的关系,但又有着明显的区别。本文将深入探讨线程和进程之间的关系,以及它们在并…

【错误:No package snapd available.】在 CentOS 上启用 snap 并安装 snapd

参考:Install snapd on CentOS using the Snap Store | Snapcraft sudo yum install epel-releasesudo yum install snapd

使用Perl脚本编写爬虫程序的一些技术问题解答

网络爬虫是一种强大的工具,用于从互联网上收集和提取数据。Perl 作为一种功能强大的脚本语言,提供了丰富的工具和库,使得编写的爬虫程序变得简单而灵活。在使用的过程中大家会遇到一些问题,本文将通过问答方式,解答一些…

telnet 连接闪退

目录 问题查找问题解决参考 问题 在使用 telnet 连接板子时,出现了 telnet 界面一闪而逝的情况。正常板子开机,查看其存在 telnetd 进程,而使用 telnet 后,登录界面一闪而逝,板子上的 telnetd 进程消失。 查找问题 …

python psutil库之——获取网络信息(网络接口信息、网络配置信息、以太网接口、ip信息、ip地址信息)

文章目录 使用Python psutil库获取网络信息安装psutil库获取网络连接信息查看所有网络连接过滤特定状态的连接 获取网络接口信息获取网络IO统计信息实例1实例2 总结 使用Python psutil库获取网络信息 Python的psutil库是一个跨平台库,能够方便地获取系统使用情况和…