Contains the Concourse pipeline definition for building a line-server container
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

97 lines
1.9 KiB

  1. package main
  2. import (
  3. "bytes"
  4. "io"
  5. "net/http"
  6. "net/url"
  7. "os"
  8. "path"
  9. "strings"
  10. "github.com/zenazn/goji/web"
  11. )
  12. func fileServeHandler(c web.C, w http.ResponseWriter, r *http.Request) {
  13. fileName := c.URLParams["name"]
  14. filePath := path.Join(Config.filesDir, fileName)
  15. err := checkFile(fileName)
  16. if err == NotFoundErr {
  17. notFoundHandler(c, w, r)
  18. return
  19. } else if err == BadMetadata {
  20. oopsHandler(c, w, r, RespAUTO, "Corrupt metadata.")
  21. return
  22. }
  23. if !Config.allowHotlink {
  24. referer := r.Header.Get("Referer")
  25. u, _ := url.Parse(referer)
  26. p, _ := url.Parse(Config.siteURL)
  27. if referer != "" && !sameOrigin(u, p) {
  28. w.WriteHeader(403)
  29. return
  30. }
  31. }
  32. w.Header().Set("Content-Security-Policy", Config.fileContentSecurityPolicy)
  33. http.ServeFile(w, r, filePath)
  34. }
  35. var staticCache = make(map[string][]byte)
  36. func staticHandler(c web.C, w http.ResponseWriter, r *http.Request) {
  37. path := r.URL.Path
  38. if path[len(path)-1:] == "/" {
  39. notFoundHandler(c, w, r)
  40. return
  41. } else {
  42. if path == "/favicon.ico" {
  43. path = "/static/images/favicon.gif"
  44. }
  45. filePath := strings.TrimPrefix(path, "/static/")
  46. _, exists := staticCache[filePath]
  47. if !exists {
  48. file, err := staticBox.Open(filePath)
  49. if err != nil {
  50. notFoundHandler(c, w, r)
  51. return
  52. }
  53. buf := bytes.NewBuffer(nil)
  54. io.Copy(buf, file)
  55. staticCache[filePath] = buf.Bytes()
  56. }
  57. w.Header().Set("Etag", timeStartedStr)
  58. w.Header().Set("Cache-Control", "max-age=86400")
  59. http.ServeContent(w, r, filePath, timeStarted, bytes.NewReader(staticCache[filePath]))
  60. return
  61. }
  62. }
  63. func checkFile(filename string) error {
  64. filePath := path.Join(Config.filesDir, filename)
  65. _, err := os.Stat(filePath)
  66. if err != nil {
  67. return NotFoundErr
  68. }
  69. expired, err := isFileExpired(filename)
  70. if err != nil {
  71. return err
  72. }
  73. if expired {
  74. os.Remove(path.Join(Config.filesDir, filename))
  75. os.Remove(path.Join(Config.metaDir, filename))
  76. return NotFoundErr
  77. }
  78. return nil
  79. }