revel.AppPath 是 Revel 应用的绝对根路径,所有文件加载(如 conf/app.conf、messages/、public/)必须基于它拼接;app/ 下 controllers、models、views 为强制约定目录,路径错误将导致编译或运行失败。

revel.AppPath 是整个目录结构的起点
Revel 项目启动时,revel.AppPath 会被自动设为应用根目录(即你运行 revel run myapp 时所在的路径),所有相对路径都基于它解析。别指望靠当前工作目录或 ./ 去找文件——revel.AppPath 才是唯一可靠的锚点。
常见错误现象:在 app/controllers 里读 messages/home.en 报 “file not found”,其实是硬编码了相对路径,没拼上 revel.AppPath;或者把 conf/app.conf 放错位置,导致 revel.Config 加载失败,报 "Cannot load database ip from app.conf" 这类 fatal 错误。
-
revel.AppPath + "/conf/app.conf"是配置入口,必须存在且格式合法(INI) -
revel.AppPath + "/messages"是 i18n 文件默认加载路径,文件名需符合xxx.lang格式(如home.en、news.zh-CN) -
revel.AppPath + "/public"对应 HTTP 静态资源根路径,但 Revel 不自动 serve,需在控制器中显式调用StaticFile或配路由
app/ 下的 controllers、models、views 不是可选模块,而是强制约定
Revel 的 MVC 调度器在初始化阶段会扫描 app/controllers/ 下所有 *Controller.go 文件,自动注册路由;app/views/ 下的模板按 ControllerName/ActionName.html 规则匹配;app/models/ 虽不被框架自动加载,但若你在 controller 里 import 它,就必须放这儿——否则 go build 会因包路径错乱失败。
容易踩的坑:把 User.go 放到 app/ 根下或 app/utils/,然后在 app/controllers/app.go 里写 import "myapp/app/models" —— Go 编译器找不到这个包,因为 app/models 并不是一个合法的 Go 包路径(缺少 models/ 目录下的 package models 声明和 go.mod 可见性)。
-
app/controllers/:必须含AppController,且所有 controller 结构体需嵌入*revel.Controller -
app/views/:模板文件后缀固定为.html,不能用.tmpl或.gotmpl -
app/models/:不是 Revel 内置概念,纯业务约定;若要用 ORM(如 mgo),建议在此目录定义 struct 并配Dal类型
messages/ 和 conf/ 的加载时机早于任何 controller 初始化
i18n 消息和配置项是在 Revel 启动早期(revel.Init() 阶段)就完成加载的,这意味着你在 init() 函数或 AppInit() 回调里就能安全使用 revel.Message 或 revel.Config.String,但不能依赖任何 controller 实例或 session 数据。
典型误用:在 app/init.go 的 init() 函数里调用 revel.BEFORE 注册一个需要访问 c.Params.Route.Name 的拦截器——此时请求上下文 c 还不存在,会 panic。
-
messages/下的 INI 文件由robfig/config解析,键名不支持点号(.)嵌套,只能是扁平 key,如home.title = "Welcome",不能写home.title.text = "Welcome" -
conf/app.conf中的[dev]、[prod]等 section 必须与REVEL_RUN_MODE环境变量一致,否则配置不会生效 - 修改
conf/app.conf后需重启 Revel 进程,它不支持热重载;而messages/文件在 dev 模式下是每次请求重新读取的
public/ 和 assets/ 的区别:一个走 HTTP,一个走 Go 构建
public/ 是 Revel 的静态文件服务根目录,浏览器可直接通过 /css/app.css 访问 public/css/app.css;但 assets/ 不是 Revel 的标准目录——如果你看到项目里有它,那是开发者自己加的构建产物输出目录(比如用 webpack 打包后把 JS 放进去),Revel 完全不感知也不处理它。
性能影响明显:把大体积的 vendor.js 放进 public/,会导致每次 HTTP 请求都走 Revel 的静态文件 handler,而 Revel 的 static handler 没有内置 gzip、ETag 或强缓存头,生产环境务必用 Nginx 做前置代理并接管 /public/ 路径。
-
public/下的文件不参与 Go 编译,上线时需确保它被完整打包进部署包 - 不要在
public/里放敏感配置(如config.js暴露 API 密钥),它对公网完全可见 - 若用 Webpack/Vite 构建前端,建议把输出目录设为
public/assets/,再在 HTML 模板里用{{asset "assets/main.js"}}(需自行实现该函数)生成带 hash 的引用
revel.AppPath 的绝对性——所有路径拼接漏掉它,90% 的文件加载失败都源于此。


















