我问过这个问题before并没有得到满意的答复,所以这一次我会尝试更具体。
我想在golang中实现一个服务器,它以svg的形式输出动态状态更新。 (想想“构建传递/失败”GitHub徽章。)目的是应该能够在GitHub自述文件中嵌入到服务器地址的链接,并且自述文件应根据服务器状态自动更新。
这是我想出的golang代码,但它似乎不适用于GitHub积极缓存。我是否需要添加更多Cache-Control标头?我需要添加ETag吗?
我正在使用以下内容将图像嵌入GitHub自述文件中。
[![Mine](http://58dcd0b5.ngrok.com/view)]()
理想情况下,我希望GitHub自述文件每次加载时都会更改图像 - 在两个图像之间翻转“正确”/“错误”。 (这只是一个概念证明。)
package main
import (
"log"
"net/http"
_ "time"
)
var mymap map[string][]byte
var state bool = false
func viewHandler(w http.ResponseWriter, r *http.Request) {
log.Printf("State %v", state)
state = !state
w.Header().Set("Content-Type", "image/svg+xml")
w.Header().Set("Cache-Control", "no-cache, no-store, must-revalidate")
if state {
w.Write(mymap["correct"])
} else {
w.Write(mymap["wrong"])
}
}
func main() {
mymap = make(map[string][]byte)
mymap["correct"] = []byte(`<svg xmlns="http://www.w3.org/2000/svg" width="104" height="20"><linearGradient id="b" x2="0" y2="100%"><stop offset="0" stop-color="#bbb" stop-opacity=".1"/><stop offset="1" stop-opacity=".1"/></linearGradient><mask id="a"><rect width="104" height="20" rx="3" fill="#fff"/></mask><g mask="url(#a)"><path fill="#555" d="M0 0h54v20H0z"/><path fill="#4c1" d="M54 0h50v20H54z"/><path fill="url(#b)" d="M0 0h104v20H0z"/></g><g fill="#fff" text-anchor="middle" font-family="DejaVu Sans,Verdana,Geneva,sans-serif" font-size="11"><text x="28" y="15" fill="#010101" fill-opacity=".3">solution</text><text x="28" y="14">solution</text><text x="78" y="15" fill="#010101" fill-opacity=".3">correct</text><text x="78" y="14">correct</text></g></svg>`)
mymap["wrong"] = []byte(`<svg xmlns="http://www.w3.org/2000/svg" width="99" height="20"><linearGradient id="b" x2="0" y2="100%"><stop offset="0" stop-color="#bbb" stop-opacity=".1"/><stop offset="1" stop-opacity=".1"/></linearGradient><mask id="a"><rect width="99" height="20" rx="3" fill="#fff"/></mask><g mask="url(#a)"><path fill="#555" d="M0 0h54v20H0z"/><path fill="#e05d44" d="M54 0h45v20H54z"/><path fill="url(#b)" d="M0 0h99v20H0z"/></g><g fill="#fff" text-anchor="middle" font-family="DejaVu Sans,Verdana,Geneva,sans-serif" font-size="11"><text x="28" y="15" fill="#010101" fill-opacity=".3">solution</text><text x="28" y="14">solution</text><text x="75.5" y="15" fill="#010101" fill-opacity=".3">wrong</text><text x="75.5" y="14">wrong</text></g></svg>`)
mux := http.NewServeMux()
mux.HandleFunc("/view", viewHandler)
http.ListenAndServe(":8085", mux)
}
答案 0 :(得分:4)
以下是关于它的Github问题:https://github.com/github/markup/issues/224
资产必须包括Cache-Control:no-cache和ETag标头。如果一个 徽章未更新,则表示它们未正确设置 这些标题。
和
资产可能还需要包含ETag或Expires标头。 Fastly's docs on Cache-Control说无缓存意味着“重新验证 在提供此内容之前“,但它没有说明它的作用 “重新验证”。我猜这是重新验证,但没有 表明资产已经发生变化,因此它继续服务于 缓存资产。
一个ETag将是最大的胜利,因为它将保证 缓存在更改时会刷新,但仍会节省带宽。
答案 1 :(得分:3)
这是特拉维斯为他们的图像服务的内容:
Age:0
Cache-Control:no-cache
Content-Length:0
Date:Mon, 30 Mar 2015 07:49:10 GMT
ETag:"88e168c2d5cdb30ee9af739765e78e4d"
Expires:Mon, 30 Mar 2015 07:49:10 GMT
Keep-Alive:timeout=10, max=48
Last-Modified:Wed, 07 Jan 2015 11:26:53 GMT
Timing-Allow-Origin:https://github.com
X-Timer:S1427701750.146025,VS0,VE156
尝试这些可能是一个良好的开端,看看哪些有效。
答案 2 :(得分:1)
关注this commit to shields.io server后,我对上述代码进行了以下更改,现在可以正常运行。
w.Header().Set("Date", date)
w.Header().Set("Expires", date)
为了完整性(如果有人想尝试一下),这里是完整的代码。 (也在GitHub。)
package main
import (
"log"
"net/http"
"time"
)
var mymap map[string][]byte
var state bool = false
func viewHandler(w http.ResponseWriter, r *http.Request) {
date := time.Now().Format(http.TimeFormat)
log.Printf("%v", date)
log.Printf("State %v", state)
state = !state
w.Header().Set("Content-Type", "image/svg+xml")
w.Header().Set("Cache-Control", "no-cache, no-store, must-revalidate")
w.Header().Set("Date", date)
w.Header().Set("Expires", date)
if state {
w.Write(mymap["correct"])
} else {
w.Write(mymap["wrong"])
}
}
func main() {
mymap = make(map[string][]byte)
mymap["correct"] = []byte(`<svg xmlns="http://www.w3.org/2000/svg" width="104" height="20"><linearGradient id="b" x2="0" y2="100%"><stop offset="0" stop-color="#bbb" stop-opacity=".1"/><stop offset="1" stop-opacity=".1"/></linearGradient><mask id="a"><rect width="104" height="20" rx="3" fill="#fff"/></mask><g mask="url(#a)"><path fill="#555" d="M0 0h54v20H0z"/><path fill="#4c1" d="M54 0h50v20H54z"/><path fill="url(#b)" d="M0 0h104v20H0z"/></g><g fill="#fff" text-anchor="middle" font-family="DejaVu Sans,Verdana,Geneva,sans-serif" font-size="11"><text x="28" y="15" fill="#010101" fill-opacity=".3">solution</text><text x="28" y="14">solution</text><text x="78" y="15" fill="#010101" fill-opacity=".3">correct</text><text x="78" y="14">correct</text></g></svg>`)
mymap["wrong"] = []byte(`<svg xmlns="http://www.w3.org/2000/svg" width="99" height="20"><linearGradient id="b" x2="0" y2="100%"><stop offset="0" stop-color="#bbb" stop-opacity=".1"/><stop offset="1" stop-opacity=".1"/></linearGradient><mask id="a"><rect width="99" height="20" rx="3" fill="#fff"/></mask><g mask="url(#a)"><path fill="#555" d="M0 0h54v20H0z"/><path fill="#e05d44" d="M54 0h45v20H54z"/><path fill="url(#b)" d="M0 0h99v20H0z"/></g><g fill="#fff" text-anchor="middle" font-family="DejaVu Sans,Verdana,Geneva,sans-serif" font-size="11"><text x="28" y="15" fill="#010101" fill-opacity=".3">solution</text><text x="28" y="14">solution</text><text x="75.5" y="15" fill="#010101" fill-opacity=".3">wrong</text><text x="75.5" y="14">wrong</text></g></svg>`)
mux := http.NewServeMux()
mux.HandleFunc("/view", viewHandler)
log.Println("Server started. Listening on 8085...")
http.ListenAndServe(":8085", mux)
}