go/twitterchiver/viewer: switch media to gocloud s3

This commit is contained in:
Luke Granger-Brown 2021-03-31 21:19:57 +00:00
parent fe393a47c7
commit 5924ded23d
2 changed files with 44 additions and 4 deletions

View file

@ -23,6 +23,9 @@
depot.third_party.gopkgs."github.com".jackc.pgtype depot.third_party.gopkgs."github.com".jackc.pgtype
depot.third_party.gopkgs."github.com".jackc.pgx.v4.pgxpool depot.third_party.gopkgs."github.com".jackc.pgx.v4.pgxpool
depot.third_party.gopkgs."github.com".pomerium.sdk-go depot.third_party.gopkgs."github.com".pomerium.sdk-go
depot.third_party.gopkgs."gocloud.dev".blob
depot.third_party.gopkgs."gocloud.dev".blob.s3blob
depot.third_party.gopkgs."gocloud.dev".gcerrors
]; ];
dockerData = [ ( dockerData = [ (
depot.pkgs.runCommand "source" {} '' depot.pkgs.runCommand "source" {} ''

View file

@ -24,13 +24,18 @@ import (
"github.com/jackc/pgtype" "github.com/jackc/pgtype"
"github.com/jackc/pgx/v4/pgxpool" "github.com/jackc/pgx/v4/pgxpool"
pomerium "github.com/pomerium/sdk-go" pomerium "github.com/pomerium/sdk-go"
"gocloud.dev/blob"
"gocloud.dev/gcerrors"
_ "gocloud.dev/blob/s3blob"
) )
var ( var (
listen = flag.String("listen", ":8080", "Listen address")
databaseURL = flag.String("database_url", "", "Database URL") databaseURL = flag.String("database_url", "", "Database URL")
userMapping = userMap{} userMapping = userMap{}
localDisableAuth = flag.String("local_auth_override_user", "", "Disable authn/authz - used for dev - set to username") localDisableAuth = flag.String("local_auth_override_user", "", "Disable authn/authz - used for dev - set to username")
mediaDirectory = flag.String("media_dir", "/media", "Archived media directory") mediaURL = flag.String("media_url", "s3://public-lukegb-twitterchiver?endpoint=objdump.zxcvbnm.ninja&region=london", "Blob URL")
funcMap = template.FuncMap{ funcMap = template.FuncMap{
"rewriteURL": rewriteURL, "rewriteURL": rewriteURL,
@ -40,6 +45,10 @@ var (
tweetsTmpl = template.Must(template.New("tweets.html").Funcs(funcMap).ParseFiles("templates/tweets.html")) tweetsTmpl = template.Must(template.New("tweets.html").Funcs(funcMap).ParseFiles("templates/tweets.html"))
) )
const (
redirectExpiry = 5 * time.Minute
)
func init() { func init() {
flag.Var(userMapping, "user_to_twitter", "Space-separated list of <username>:<comma-separated Twitter usernames>") flag.Var(userMapping, "user_to_twitter", "Space-separated list of <username>:<comma-separated Twitter usernames>")
} }
@ -115,6 +124,11 @@ func main() {
flag.Parse() flag.Parse()
ctx := context.Background() ctx := context.Background()
mediaBucket, err := blob.OpenBucket(ctx, *mediaURL)
if err != nil {
log.Fatalf("blob.OpenBucket: %v", err)
}
pool, err := pgxpool.Connect(ctx, *databaseURL) pool, err := pgxpool.Connect(ctx, *databaseURL)
if err != nil { if err != nil {
log.Fatalf("pgxpool.Connect: %v", err) log.Fatalf("pgxpool.Connect: %v", err)
@ -161,7 +175,30 @@ func main() {
fmt.Fprintf(rw, "<p>%s</p>", wrap) fmt.Fprintf(rw, "<p>%s</p>", wrap)
} }
authR.PathPrefix("/media/").Handler(http.StripPrefix("/media/", http.FileServer(http.Dir(*mediaDirectory)))) authR.PathPrefix("/media/{filepath:.*}").HandlerFunc(func(rw http.ResponseWriter, r *http.Request) {
ctx := r.Context()
vars := mux.Vars(r)
_, err := userFromContext(ctx)
if err != nil {
http.Error(rw, fmt.Errorf("userFromContext: %w", err).Error(), http.StatusInternalServerError)
return
}
u, err := mediaBucket.SignedURL(ctx, vars["filepath"], &blob.SignedURLOptions{
Expiry: redirectExpiry,
})
switch gcerrors.Code(err) {
case gcerrors.NotFound:
// This is unlikely to get returned.
http.Error(rw, "not found", http.StatusNotFound)
return
case gcerrors.OK:
http.Redirect(rw, r, u, http.StatusFound)
return
default:
log.Printf("media SignedURL: %v", vars["filepath"], err)
}
http.Error(rw, err.Error(), http.StatusInternalServerError)
})
authR.HandleFunc("/", func(rw http.ResponseWriter, r *http.Request) { authR.HandleFunc("/", func(rw http.ResponseWriter, r *http.Request) {
ctx := r.Context() ctx := r.Context()
user, err := userFromContext(ctx) user, err := userFromContext(ctx)
@ -542,8 +579,8 @@ LIMIT $2
} }
}) })
log.Printf("now listening on :8080") log.Printf("now listening on %s", *listen)
log.Print(http.ListenAndServe(":8080", r)) log.Print(http.ListenAndServe(*listen, r))
} }
func agoFriendly(now, at time.Time) string { func agoFriendly(now, at time.Time) string {
ago := now.Sub(at) ago := now.Sub(at)