Xitrum学习笔记10 - 静态文件Static Files

在磁盘上的静态文件(Static Files)

Xitrum项目路径结构

config
public
  favicon.ico
  robots.txt
  404.html
  500.html
  img
    myimage.png
  css
    mystyle.css
  js
    myscript.js
src
build.sbt

Xitrum会自动注册 public/ 下的文件和路径。它们的URL格式是:

/img/myimage.png
/css/mystyle.css
/css/mystyle.min.css

引用它们的方法,publicUrl:

<img src={publicUrl("img/myimage.png")} />

在开发环境上引用普遍版本(本例为mystyle.css),在生产环境上使用最小版本(本例为mystyle.min.css)

<img src={publicUrl("css", "mystyle.css", "mystyle.min.css")} />

把静态文件传给action,使用 respondFile

respondFile("<绝对路径>")
respondFile("<相对于当前工作路径的路径>")

要优化静态文件的使用效率,就要避免不需要的文件能被正则表达式过滤器(pathRegex)查找到。

如果请求的url不能匹配pathRegex,Xitrum返回响应404。

pathRegex在 config/xitrum.conf进行设置

index.html fallback

如果一个URL没有对应的路径(Action)存在,那么Xitrum会试着找 public/这个URL/index.tml。如果这个index.html存在,将被返回给客户端。

404和500的html文件

public/404.html和500.html是用来处理没找到和处理出错的请求的。可以通过以下方式使用自定义的处理Action

import xitrum.Action
import xitrum.annotation.{Error404, Error500}
@Error404
class My404ErrorHandlerAction extends Action {
  def execute() {
    if (isAjax)
      jsRespond("alert(" + jsEscape("Not Found") + ")")
    else
      renderInlineView("Not Found")
  }
}
@Error500
class My500ErrorHandlerAction extends Action {
  def execute() {
    if (isAjax)
      jsRespond("alert(" + jsEscape("Internal Server Error") + ")")
    else
      renderInlineView("Internal Server Error")
  }
}

响应状态码 在action被执行之前 就已经设置好了,所以不用自己再设置

使用classpath中WebJar文件中的源文件

1. WebJars

WebJars以jar包的形式包装了很多客户端web库文件(如jQuery和Bootstrap),可以利用maven、SBT、Gradle等工具在项目中添加这些库的依赖

webjars官网:http://www.webjars.org/

要使用WebJars中的静态文件,如 Underscore.js,

1)要先在build.sbt中声明

libraryDependencies += "org.webjars" % "underscorejs" % "1.6.0-3"

2)然后在 .jade 模板文件中

script(src={webJarsUrl("underscorejs/1.6.0", "underscore.js", "underscore-min.js")})

Xitrum会自动在开发环境中使用underscore.js,在生产环境中使用underscore-min.js。

结果类似于:/webjars/underscorejs/1.6.0/underscore.js?XOKgP8_KIpqz9yUqZ1aVzw

如果在开发和生产环境都使用相同的文件,则

script(src={webJarsUrl("underscorejs/1.6.0/underscore.js")})

依赖包会自动下载(一般路径是 /Users/user/.ivy2),

可以使用sbt xitrum-package然后在target/xitrum/lib下查看依赖包以及所开发项目的jar包(如xitrum-new_2.12-1.0-SNAPSHOT.jar)。

如果依赖包版本与期望不符,可以在build.sbt中设置 dependencyOverrides以替代libraryDependencies中的版本。例如已经选择使用了jQuery2但必须使用jQuery1:

dependencyOverrides += "org.webjars" % "jquery" % "1.11.3"

2. 通过WebJar在jar包中保存源文件

例如要把 myimage.png通过 WebJar保存到mylib库中相关的jar包里:

META-INF/resources/webjars/mylib/1.0/myimage.png

在使用时,<img src={webJarsUrl("mylib/1.0/myimage.png")} />

在开发和生产环境中相应的URL是 /webjars/mylib/1.0/myimage.png?xyz123 

3. 返回在classpath中的文件

要向客户端响应返回在classpath jar包或路径中的文件内容,即使该文件没有保存在WebJars库里,使用

respondResource("相对于classpath的路径") 

示例:

respondResource("akka/actor/Actor.class")
respondResource("META-INF/resources/webjars/underscorejs/1.6.0/underscore.js")
respondResource("META-INF/resources/webjars/underscorejs/1.6.0/underscore-min.js")

客户端缓存 ETag 和 max-age

Xitrum会为磁盘上或是classpath中的静态文件自动添加 Etag。

小文件的ETag是文件内容的MD5,ETags被缓存起来供以后使用。缓存项的key是(file path,modified time)。

因为modified time在不同的server上可能不同,一个集群中的每一个web server都有它自己的本地ETag缓存。

publicUrl和webJarsUrl自动把ETag添加到它们问文件生成的URL上。如:

webJarsUrl("jquery/2.1.1/jquery.min.js")
=> /webjars/jquery/2.1.1/jquery.min.js?0CHJg71ucpG0OlzB-y6-mQ

Xitrum将响应头信息中的 max-age和Expire设置为1年。当磁盘上的文件变化时,它的修改时间就会改变,

因此由publicUrl和webJarsUrl生成的URL也会变化。相应地,它的ETag缓存也会因缓存项key的变化而改变

GZIP

Xitrum自动以gzip压缩文本响应内容,Xitrum会检查Content-Type头以确定响应内容是否为文本(text/html, xml/application)

Xitrum一直以gzip压缩静态文本文件,但是对于动态的文本响应,出于整体性能原因,它不会压缩小于1K的响应内容。

服务端缓存

为避免从磁盘上装载文件,Xitrum利用最近最少使用的算法把小的静态文件缓存到内存中。

可以通过config/xitrum.conf中的small_static_file_size_in_kb和max_cached_small_static_files进行配置

posted @ 2017-05-12 15:18  子秦  阅读(559)  评论(0编辑  收藏  举报