Live video on the AT Protocol
1package remote
2
3import (
4 "crypto/sha256"
5 "encoding/hex"
6 "fmt"
7 "io"
8 "net/http"
9 "os"
10 "path/filepath"
11 "strings"
12)
13
14// Streamplace team can add new files here with hack/upload-fixture.sh
15
16var fixtureURL = "https://storage.googleapis.com/streamplace-fixtures"
17
18func RemoteFixture(name string) string {
19 parts := strings.Split(name, "/")
20 if len(parts) != 2 {
21 panic("fixture name must be in format HASH/FILENAME")
22 }
23 expectedHash := parts[0]
24 filename := parts[1]
25
26 // Check if file already exists in cache
27 homeDir, err := os.UserHomeDir()
28 if err != nil {
29 panic(err)
30 }
31 cacheDir := filepath.Join(homeDir, ".streamplace-test-cache")
32 finalPath := filepath.Join(cacheDir, expectedHash, filename)
33 if _, err := os.Stat(finalPath); err == nil {
34 return finalPath
35 }
36
37 // Create temp dir if it doesn't exist
38 if err := os.MkdirAll(cacheDir, 0755); err != nil {
39 panic(err)
40 }
41
42 // Download to temporary file
43 resp, err := http.Get(fixtureURL + "/" + name)
44 if err != nil {
45 panic(err)
46 }
47 defer resp.Body.Close()
48
49 tmpFile, err := os.CreateTemp(cacheDir, "download-*")
50 if err != nil {
51 panic(err)
52 }
53 tmpPath := tmpFile.Name()
54 defer os.Remove(tmpPath)
55
56 // Calculate hash while downloading
57 hash := sha256.New()
58 writer := io.MultiWriter(tmpFile, hash)
59
60 if _, err := io.Copy(writer, resp.Body); err != nil {
61 panic(err)
62 }
63 tmpFile.Close()
64
65 // Verify hash
66 actualHash := hex.EncodeToString(hash.Sum(nil))
67 if actualHash != expectedHash {
68 panic(fmt.Sprintf("hash mismatch: expected %s, got %s", expectedHash, actualHash))
69 }
70
71 // Move to final location
72 finalDir := filepath.Join(cacheDir, expectedHash)
73 if err := os.MkdirAll(finalDir, 0755); err != nil {
74 panic(err)
75 }
76
77 if err := os.Rename(tmpPath, finalPath); err != nil {
78 panic(err)
79 }
80
81 return finalPath
82}