响应 Ktor 中图像的缓存标头

Posted

技术标签:

【中文标题】响应 Ktor 中图像的缓存标头【英文标题】:Respond with Cache headers for images in Ktor 【发布时间】:2020-01-18 14:09:33 【问题描述】:

为 Ktor 提供的静态图像发回缓存标头的正确方法是什么?

我有以下 Ktor 设置:

在我的main:

embeddedServer(
        Netty,
        watchPaths = listOf("module"),
        module = Application::module,
        port = if (ENV.env == LOCAL) 
            8080
         else 
            80
        
    ).apply 
        start(wait = true)
    

然后在main之外:

fun Application.module() 
    if (ENV.env != LOCAL) 
        install(ForwardedHeaderSupport)
        install(XForwardedHeaderSupport)
        install(HttpsRedirect)
    
    install(CachingHeaders) 
        options  outgoingContent ->
            when (outgoingContent.contentType?.withoutParameters()) 
                ContentType.Image.Any -> CachingOptions(CacheControl.MaxAge(maxAgeSeconds = 30 * 24 * 60 * 60))
                else -> null
            
        
    
    install(Compression) 
        gzip 
            priority = 1.0
        
        deflate 
            priority = 10.0
            minimumSize(1024) // condition
        
    

    routing 
        static("/js/") 
            resources("/js/")
        

        static("/css/") 
            resources("/css/")
        

        static("/favicons") 
            resources("/favicons/")
        

        static("/img/") 
            resources("/static/img/")
            resources("/static/images/")
            resources("/background/")
            resources("/logos/")
            resources("/icons/")
        
    

但是图像返回时没有缓存标头,有什么想法吗?

更新

ContentType.Image.Any 更改为ContentType.Image.JPEG 似乎可行。查看Image的源代码,它似乎映射到ContentType(image, *) 但根本不匹配任何图像类型。

install(CachingHeaders) 
    options  outgoingContent ->
        when (outgoingContent.contentType?.withoutParameters()) 
            ContentType.Image.JPEG -> CachingOptions(
                cacheControl = CacheControl.MaxAge(
                    mustRevalidate = false,
                    maxAgeSeconds = 30 * 24 * 60 * 60,
                    visibility = CacheControl.Visibility.Public
                )
            )
            else -> null
        
    

同时提交了一个错误: https://github.com/ktorio/ktor/issues/1366

【问题讨论】:

【参考方案1】:

原来是对* 进行标准的 eqauls 检查,而不是实际的文件类型,所以使用 match 来解决这个问题:

install(CachingHeaders) 
    options  outgoingContent ->
        if (outgoingContent.contentType?.withoutParameters()?.match(ContentType.Image.Any) == true) 
            CachingOptions(
                cacheControl = CacheControl.MaxAge(
                    mustRevalidate = false,
                    maxAgeSeconds = 6 * 30 * 24 * 60 * 60,
                    visibility = CacheControl.Visibility.Public
                )
            )
         else 
            null
        
    

【讨论】:

【参考方案2】:

您可以使用以下内容按内容类型设置缓存标头:https://ktor.io/servers/features/caching-headers.html

【讨论】:

就像我在问题中的代码中所做的那样? ContentType.Image.Any -> CachingOptions(CacheControl.MaxAge(maxAgeSeconds = 30 * 24 * 60 * 60))

以上是关于响应 Ktor 中图像的缓存标头的主要内容,如果未能解决你的问题,请参考以下文章

OpenCV中图像的格式Mat 图像深度

Swift导航栏中图像的动画变化

用于 Numpy 数组中图像的图像数据生成器

wordpress主题中图像的最大图像宽度(函数.php)

如何获取相册中图像的图像文件名和标签?

matlab中图像的熵与边缘检测之间的关系是啥