Golang实践录:静态资源文件整合:初步使用
趁着五一放假,趁着有时间,把欠的一些技术集中研究研究,写写文章,好给自己一个交待。
本文介绍如何在 Golang 中整合静态资源文件,将静态资源文件编译到二进制可执行文件中,这与其它程序的打包可能是一个概念,也可能不是,后续有空研究再补充。
起因
大概10年前,即2011年,也研究一下这方面的内容,主要针对 C 语言,使用 ARM 板子测试。 那篇文章如下图:
当时对技术的兴趣比较浓厚,没想过房子车子的事,现在经常想房子车子,但也被迫对技术感兴趣。因此,使用 Golang 语言重新研究一下。
实践
经查,有2个类似的工具:go-bindata 和 go-bindata-assetfs。两者可以将文件转换成 golang 语言代码,后者似乎依赖于前者,本着使用的目的,暂未研究细节,看了一下生成的 golang 代码,有对外提供的接口,有文件映射表,有真正存储文件的字节流。
安装
使用go get
命令安装:
go get -u github.com/go-bindata/go-bindata/...
go get -u github.com/elazarl/go-bindata-assetfs/...
输入对应的命令验证:
go-bindata
go-bindata-assetfs
生成
为适合项目目录,本文约定使用 static 目录存放静态资源文件——即需要打包到可执行程序中的文件,生成的代码,存放到 bindata 目录,且其包名亦为 bindata。经研究发现似乎 go-bindata-assetfs 更好一些,因此本文使用该工具,生成命令如下:
go-bindata-assetfs -o=bindata/bindata.go -pkg=bindata -ignore="README.md" -prefix=static static/...
-o
指定了输出文件,-pkg
指定包名(一般与前者保持一致),-ignore
指定需忽略的文件,-prefix
指定文件路径前缀(本例中,指定了前缀,不需在代码中使用static
前缀)。如果不需要如此复杂,可将其生成的文件与包 main 在同一目录,包名亦为 main,可用于简单测试:
go-bindata-assetfs -o=bindata.go -ignore="README.md" -prefix=static static/...
为了调试方便——即不需要每次更新文件都要重新编译代码,则可以添加-debug
参数,命令如下:
go-bindata-assetfs -debug -o=bindata.go -ignore="README.md" -prefix=static static/...
该参数是在代码中指定静态资源文件绝对路径,因此,修改原文件无需重新编译即可生效,有兴趣可研读生成的代码。
测试
资源文件目录 static 如下:
$ tree static/
static/
|-- conf
| `-- config.toml
|-- html
| `-- foo.html
`-- libfoo.so2 directories, 3 files
主要使用的接口如下:
// 获取所有的文件名称
filenames := bindata.AssetNames()// 读取某一文件的内容
filename = "html/foo.html"
content, err = bindata.Asset(filename)
指定的文件,以static
为根目录,其形式与一般的路径无差异。
完整测试代码如下:
package mainimport ("fmt""strings""io/ioutil""bindata_test2/bindata"
)func main() {fmt.Println("bindata test..");// 遍历所有文件,打印文件名,并输出html的内容filenames := bindata.AssetNames()for _, item := range filenames {fmt.Println("got file: ", item)if !strings.HasSuffix(item, ".tmpl") && !strings.HasSuffix(item, ".html") {continue}content, err := bindata.Asset(item)if err != nil {fmt.Printf("not found file %s: %s\n", item, err.Error())}fmt.Println(string(content))fmt.Println("-----------------------------------\n")}// 单独测试filename := "assets/foo.html"content, err := bindata.Asset(filename)if err != nil {fmt.Printf("not found file %s: %s\n", filename, err.Error())}filename = "foo.html"content, err = bindata.Asset(filename)if err != nil {fmt.Printf("not found file %s: %s\n", filename, err.Error())}filename = "html/foo.html"content, err = bindata.Asset(filename)if err != nil {fmt.Printf("not found file %s: %s\n", filename, err.Error())}// content 为二进制buf,怎么用?filename = "conf/config.toml"content, err = bindata.Asset(filename)if err != nil {fmt.Printf("not found file %s: %s\n", filename, err.Error())}fmt.Println(string(content))// 读取so并保存filename = "libfoo.so"content, err = bindata.Asset(filename)if err != nil {fmt.Printf("not found file %s: %s\n", filename, err.Error())return}//filename = "libfoo.so"err = ioutil.WriteFile(filename, content, 0755)if err != nil {fmt.Println("write file error: ", err)return}fmt.Printf("write file %s ok\n", filename)}
以 libfoo.so 文件为例,原文件和保存的文件对比如下:
$ md5sum.exe static/libfoo.so libfoo.so
9416ab261b2867d9acbb563690116885 *static/libfoo.so
9416ab261b2867d9acbb563690116885 *libfoo.so
两者内容是相同的。
扩展
本文所述方法,有一定范围内可以使用,对于大型项目或多人协作项目,不建议使用。
针对该方法,笔者认为可以进行的事有:
1、将 web 服务有关的 css、js、html 等整合到可执行二进制文件中,方便部署。在笔者即将实现的 web 服务中,由于功能唯一,又是内部使用,且还只是由笔者个人实现,因此对技术栈拥有完全自主的决定权,通俗地讲,同事和上头不管技术细节,能实现功能即可,为了方便自己,故如此设计。
2、动态库整合,如果涉及动态库文件的使用,则可以将动态库打包到可执行文件,在运行时读取并保存到指定目录,再加载。此法将二者绑定一起,无法做到只更新动态库文件,因此需慎重。
3、配置文件整合,对于需配置文件的程序而言,在部署时需自带配置文件,或默认首次运行时生成。对于后者,有的直接在代码中固定配置,根据情况写到指定目录,使用本文,则直接将配置文件打包到二进制文件,如不存在,则再写到指定目录。
4、其它待探索发现并实施。
李迟 2021.5.5
Golang实践录:静态资源文件整合:初步使用相关推荐
- Golang实践录:静态资源文件整合:web服务
趁着五一放假,趁着有时间,把欠的一些技术集中研究研究,写写文章,好给自己一个交待. 本文研究静态资源文件的在 web 服务器的整合. 基础 Golang 中的 web 服务框架有很多种,本文选取 gi ...
- golang打包HTML为Android,使用Go开发Web服务,并打包html/js/css等静态资源文件
Go的高性能,使它天生适合开发io方面的服务,Web服务当然不再话下.同时,Go编译后生成的单文件不是字节码,而是对应平台的机器码,因此它效率更高.资源占用更低. 为了更好的进程程序管理,移动程序时更 ...
- 解决Spring MVC整合Shiro出现无法访问静态资源文件的问题
解决方案:shiro过滤器配置拦截器链中添加"/static/**=anno"即可,"/static/**"为静态资源文件路径. <property na ...
- golang将静态资源文件打包进二进制文件
默认情况下,将项目打包成二进制的时候是不会加入静态资源文件的,因此在部署的时候还需要捎带上这些文件,比如,一些配置文件,图片,样式表等. 很多时候,这些静态文件是不需要变的,如果能一并加入到二进制文件 ...
- python3读取网页_python3+selenium获取页面加载的所有静态资源文件链接操作
软件版本: python 3.7.2 selenium 3.141.0 pycharm 2018.3.5 具体实现流程如下,废话不多说,直接上代码: from selenium import webd ...
- vue-cli项目布署问题解决:空白页、静态资源文件404错误、refrenceError:promise未定义(部分浏览器不支持ES6语法)
(前言:文章记录vue-cli项目打包使用IIS布署遇到的几个错误及解决方式) 首先简单理解webpack打包: 个人理解:项目开发中我们构建 "低耦合高内聚" 的组件/模块来代码 ...
- Golang实践录:命令行cobra库实例再三优化
本文是上一文章<Golang实践录:命令行cobra库实例优化> 的优化,主要的子命令的业务实现的整理. 起因 上一版本实现的方式,还是有点不满意,格式也不对齐,重要的是,似乎不是正规的方 ...
- Golang实践录:命令行cobra库实例优化
本文上一文章<Golang实践录:命令行cobra库实例> 的优化,主要的子命令的业务实现的整理. 起因 旧版本中,每个子命令的入口函数,均需一一判断传入参数,并调用对应的业务实现函数,编 ...
- 在JSP中常见问题,防止SpringMVC拦截器拦截js等静态资源文件的解决方案
在JSP中常见问题,防止SpringMVC拦截器拦截js等静态资源文件的解决方案 参考文章: (1)在JSP中常见问题,防止SpringMVC拦截器拦截js等静态资源文件的解决方案 (2)https: ...
最新文章
- Oracle11gR2 64bit+Oracle11gR2Client32bit+pl/sql 9
- 揭秘Java网络爬虫程序原理
- 卷积神经网络Convolutional Neural Network (CNN)
- CentOS6.3中挂载NTFS移动硬盘的经历
- JVM内存管理(一)--GC简介
- 工程师软技能6:理财人生精神
- 智能仓储管理系统分析?
- XJOI 3281 A * B Problem again 题解
- ORACLE SQL优化大全
- Win11写字板怎么打开?Win11开启写字板的方法
- Typora+图床详解(小白都能学得会)
- 智能清晰锐化磨皮图片处理软件Perfectly Clear 3.8.0.1665 汉化版
- 图灵机器人 mysql_如何在微信小程序中制作图灵机器人?
- 算法导论第十五章:动态规划(一)
- 嵌入式系统的体系结构 图解
- 数学-上确界与下确界概念
- 【Android TV】Android 8.0下 ,TV系统通知音失效
- 酒店取消预订预测分析报告
- SettingsProvider单编生效
- Python正则去除中英文标点的操作手法
热门文章
- 富士通成功开发全球最快的36量子位量子模拟器
- 大众正式发布ID. Buzz 造型致敬经典
- 英伟达吞并ARM的交易计划失败!
- 彻底凉凉!两头部网红女主播账号被封,逃税被罚近亿元 还被曝不给员工交社保...
- DaDa英语宣布12月31日起全面停止所有外教服务
- 拼多多11.11:无定金、不预售,“好牌子、好实惠”底价直降
- 苹果 AirPods 固件更新,这个新功能上线!
- 霍兰德教育CEO被曝卷钱逃回英国 欠款超千万
- OPPO Reno6系列将推Bobbi Brown联名版
- 尊贵的iPhone 11用户们,苹果喊你们换显示屏模块了……