作者:张富春(ahfuzhang),转载时请注明作者和引用链接,谢谢!


经过反复测试,只要换一个写法就能开启/重现这个怪异的问题。

请看出现异常的代码:

//go:embed index.html
var indexFileTemplate string
var indexTempate = template.New("index") //go:embed mysql_data_source.html
var mysqlDataSourceFileTemplate string var mysqlDataSourceTempate = template.New("mysql_data_source") // var mysqlDataSourceTempate = template.Must(template.New("mysql_data_source").Parse(mysqlDataSourceFileTemplate)) func init() {
indexTempate = template.Must(indexTempate.Parse(indexFileTemplate))
mysqlDataSourceTempate = template.Must(indexTempate.Parse(mysqlDataSourceFileTemplate))
}

使用上述的代码,gin框架中访问首页,在执行模版的时候报这样的错误:

template: index:9:49: executing "index" at <.Name>: can't evaluate field Name in type *page.templateParam

我在index.html中没有{{.Name}},只在mysql_data_source.html中有使用。不管怎么样,我访问首页,和另一个页面没关系鸭!

换个写法就能正常打开首页:

//go:embed index.html
var indexFileTemplate string
var indexTempate = template.New("index") //go:embed mysql_data_source.html
var mysqlDataSourceFileTemplate string var mysqlDataSourceTempate = template.New("mysql_data_source") var mysqlDataSourceTempate = template.Must(template.New("mysql_data_source").Parse(mysqlDataSourceFileTemplate)) func init() {
indexTempate = template.Must(indexTempate.Parse(indexFileTemplate))
//mysqlDataSourceTempate = template.Must(indexTempate.Parse(mysqlDataSourceFileTemplate))
}

简直是无语了……


猜测可能的原因:

embed对应的字符串的加载,是比init()函数还要晚的。当init函数执行的时候,embed的字符串还没加载,这样就导致了模版解析出错。然而,template.Must()并不会导致panic,只是默默地记录下了这个错误。等到模版真正被使用的时候,抛出模版加载期导致的错误,进而出现上述的现象。解决办法就是不要在init函数中写模版加载的代码。

已经把这个问题提到了官方:https://github.com/golang/go/issues/56952


11-29补充:

已经得到了官方的回答,原因还是赋值语句和init()函数的先后顺序导致的。

我自己的代码,假定赋值先执行,然后init()函数再执行。

但是,如果init()先执行,而赋值后执行,就会导致indexTempate对象处于未初始化的状态。

因此,解决办法是不要假定初始化执行的顺序,统一只在一个地方初始化。

【遇到一个怪异的问题】使用embed来加载模版,只要写在init()函数中就会导致HTTP服务出错的更多相关文章

  1. 一个页面从输入URL到页面加载显示完成,这个过程都发生了什么?

    对于网址栏的URL不同的操作方式有不同的加载资源.获取数据的方式,下面的详细过程针对"在地址栏输入URL,按enter(回车)键加载资源"此种操作方式做解析,其它的方式的过程大同小 ...

  2. 一个页面从输入url到页面加载显示完成,中间都经历了什么

    第一种解释: 一般会经历以下几个过程: 1.首先,在浏览器地址栏中输入url 2.浏览器先查看浏览器缓存-系统缓存-路由器缓存,如果缓存中有,会直接在屏幕中显示页面内容.若没有,则跳到第三步操作. 3 ...

  3. 一个页面从输入URL到页面加载完成发生了...待细化

    一个页面从输入URL到页面加载完成发生了... 1.查找浏览器缓存 2.寻址:DNS解析 查找该域名对应的IP地址, 如果需要重定向(301),则再次发起请求 3. 进行HTTP协议会话 4.客户端发 ...

  4. JS window对象 返回下一个浏览的页面 forward()方法,加载 history 列表中的下一个 URL。

    返回下一个浏览的页面 forward()方法,加载 history 列表中的下一个 URL. 如果倒退之后,再想回到倒退之前浏览的页面,则可以使用forward()方法,代码如下: window.hi ...

  5. 一个页面从输入URL 到页面加载显示完成的过程中都发生了什么

    前端面试/笔试必考问题,越详细越好 先简单得讲: 浏览器根据请求的URL交给DNS域名解析,找到真实IP,向服务器发起请求: 服务器交给后台处理完成后返回数据,浏览器接收文件(HTML.JS.CSS. ...

  6. Vue-上拉加载与下拉刷新(mint-ui:loadmore)一个页面使用多个上拉加载后冲突问题

    所遇问题: 该页面为双选项卡联动,四个部分都需要上拉加载和下拉刷新功能,使用的mint-ui的loadmore插件,分别加上上拉加载后,只有最后一个的this.$refs.loadmore.onTop ...

  7. android 分享一个处理BaseAdapter,getView()多次加载的方法

    一:BaseAdapter介绍 BaseAdapter是listview,gridview等列表,使用的数据适配器,它的主要用途是将一组数据传到ListView.Spinner.Gallery及Gri ...

  8. SeaJS:一个适用于 Web 浏览器端的模块加载器

    什么是SeaJS?SeaJS是一款适用于Web浏览器端的模块加载器,它同时又与Node兼容.在SeaJS的世界里,一个文件就是一个模块,所有模块都遵循CMD(Common Module Definit ...

  9. 8.一个页面从输入 URL 到页面加载显示完成,这个过程中都发生了什么?

    注:这题胜在区分度高,知识点覆盖广,再不懂的人,也能答出几句, 而高手可以根据自己擅长的领域自由发挥,从URL规范.HTTP协议.DNS.CDN.数据库查询. 到浏览器流式解析.CSS规则构建.lay ...

  10. 一个页面从输入URL 到页面加载显示完成,这个过程中都发生了什么?

    1.当发送一个URL请求时,浏览器会开启一个线程来处理这个请求,同时在远程DNS服务器上启动一个DNS查询,解析获取网址的IP地址:2.浏览器与远程Web服务器通过TCP三次握手协商来建立一个TCP/ ...

随机推荐

  1. 字节跳动基于ClickHouse优化实践之“资源隔离”

    更多技术交流.求职机会,欢迎关注字节跳动数据平台微信公众号,回复[1]进入官方交流群 相信大家都对大名鼎鼎的 ClickHouse 有一定的了解了,它强大的数据分析性能让人印象深刻.但在字节大量生产使 ...

  2. Axure 获取验证码

    拖两个矩形框,一个用来做文档输入,一个做获取验证码的按钮 设置全局变量OnLoadVariable的初如值为60 1.用例中的条件:当OnLoadVariable的值不等于0 2.用例中的步骤 禁用& ...

  3. Windows 2016 安装 Docker

    打开 PowerShell Windows PowerShell 版权所有 (C) 2016 Microsoft Corporation.保留所有权利. PS C:\Users\Administrat ...

  4. Dom4j 保存XML HL7-V3

    dom4j selectNodes 取不到值 因为XML带有命名空间 HL7 Dom4j 保存XML String xmlPath = "D:\\BS004.xml"; Strin ...

  5. 微服务网关 —— SpringCloud Gateway

    Gateway 简介 Spring Cloud Gateway 基于 Spring 5.Spring Boot 2 和 Project Reactor 等技术,是在 Spring 生态系统之上构建的 ...

  6. 【Java爬虫】如何通过 API 递归分页爬取网页数据

    前言 在最近的互联网项目开发中,需要获取用户的访问ip信息进行统计的需求,用户的访问方式可能会从微信内置浏览器.Windows浏览器等方式对产品进行访问. 当然,获取这些关于ip的信息是合法的.但是, ...

  7. peewee update和save性能分析

    背景 python项目中使用了peewee这款orm框架,在对数据库更新时有两种语法,分别是save和update方法.有同事说从peewee的日志来看,update比save更快,于是做了一个简单的 ...

  8. Python网络编程:ZeroMQ

    大家好,我是老胡.最近在和小伙伴们一起搞事情,我是学统计出身,编程能力其实很差,有点拖后腿了.所以需要恶补基础,这个系列会更新几篇,感兴趣的同学可以一起学习交流. ZeroMQ概述 ZeroMQ(又名 ...

  9. Sunshine + Moonlight 纯软件实现全平台设备作 Linux 副屏

    目录 初识 Moonlight 部署 Sunshine 服务端与 Moonlight 客户端 创建虚拟显示屏 写一个创建屏幕的脚本(可选) 将副屏进行串流 已知问题 最近,我想要通过视频学习一些技术知 ...

  10. Python | PyQt5 Could not find the Qt platform plugin windows错误解决方法

    在写Python大作业的时候发现运行PyQt5时有报错 出现该问题的原因是环境变量没有添加. 解决方法: 在环境变量中增加: QT_QPA_PLATFORM_PLUGIN_PATH 样例路径(这里填你 ...