diff --git a/cmd/local/main.go b/cmd/local/main.go index caefd9b..96e3a5b 100644 --- a/cmd/local/main.go +++ b/cmd/local/main.go @@ -73,7 +73,7 @@ func main() { } subscriber := subscribe.NewMemorySubscriber() server, err := pkg.NewPageServer(http.DefaultClient, - provider, domain, "gh-pages", memory, subscriber, memory, 0, &nopCache{}, 0, + provider, domain, memory, subscriber, memory, 0, &nopCache{}, 0, func(w http.ResponseWriter, r *http.Request, err error) { if errors.Is(err, os.ErrNotExist) { http.Error(w, "page not found.", http.StatusNotFound) diff --git a/cmd/server/main.go b/cmd/server/main.go index bf7b1b4..fbd25ad 100644 --- a/cmd/server/main.go +++ b/cmd/server/main.go @@ -38,7 +38,7 @@ func main() { log.Fatalf("fail to load config file: %v", err) } - gitea, err := providers.NewGitea(http.DefaultClient, config.Auth.Server, config.Auth.Token) + gitea, err := providers.NewGitea(http.DefaultClient, config.Auth.Server, config.Auth.Token, config.Page.DefaultBranch) if err != nil { log.Fatalln(err) } @@ -52,7 +52,7 @@ func main() { log.Fatalln(err) } defer cacheBlob.Close() - backend := providers.NewProviderCache(gitea, cacheMeta, config.Cache.MetaTTL, + backend := providers.NewProviderCache(gitea, cacheBlob.Child("backend"), uint64(config.Cache.BlobLimit), ) defer backend.Close() @@ -71,13 +71,12 @@ func main() { } defer event.Close() if config.Filters == nil { - config.Filters = map[string]map[string]any{} + config.Filters = make(map[string]map[string]any) } pageServer, err := pkg.NewPageServer( http.DefaultClient, backend, config.Domain, - config.Page.DefaultBranch, cdb, event, cacheMeta, diff --git a/go.mod b/go.mod index 4f9f72e..405d482 100644 --- a/go.mod +++ b/go.mod @@ -5,7 +5,7 @@ go 1.25.3 require ( code.gitea.io/sdk/gitea v0.22.1 github.com/alecthomas/units v0.0.0-20240927000941-0f3dac36c52b - github.com/dop251/goja v0.0.0-20251103141225-af2ceb9156d7 + github.com/dop251/goja v0.0.0-20251201205617-2bb4c724c0f9 github.com/dop251/goja_nodejs v0.0.0-20251015164255-5e94316bedaf github.com/go-task/slim-sprig/v3 v3.0.0 github.com/gobwas/glob v0.2.3 @@ -36,10 +36,10 @@ require ( github.com/go-sourcemap/sourcemap v2.1.4+incompatible // indirect github.com/gogo/protobuf v1.3.2 // indirect github.com/golang/protobuf v1.5.4 // indirect - github.com/google/pprof v0.0.0-20251114195745-4902fdda35c8 // indirect + github.com/google/pprof v0.0.0-20251213031049-b05bdaca462f // indirect github.com/grpc-ecosystem/grpc-gateway/v2 v2.27.3 // indirect - github.com/hashicorp/go-version v1.7.0 // indirect - github.com/klauspost/compress v1.18.1 // indirect + github.com/hashicorp/go-version v1.8.0 // indirect + github.com/klauspost/compress v1.18.2 // indirect github.com/klauspost/cpuid/v2 v2.3.0 // indirect github.com/klauspost/crc32 v1.3.0 // indirect github.com/minio/crc64nvme v1.1.1 // indirect @@ -49,17 +49,17 @@ require ( github.com/philhofer/fwd v1.2.0 // indirect github.com/pmezard/go-difflib v1.0.0 // indirect github.com/rs/xid v1.6.0 // indirect - github.com/tinylib/msgp v1.5.0 // indirect - go.etcd.io/etcd/api/v3 v3.6.6 // indirect - go.etcd.io/etcd/client/pkg/v3 v3.6.6 // indirect - go.etcd.io/etcd/client/v3 v3.6.6 // indirect + github.com/tinylib/msgp v1.6.1 // indirect + go.etcd.io/etcd/api/v3 v3.6.7 // indirect + go.etcd.io/etcd/client/pkg/v3 v3.6.7 // indirect + go.etcd.io/etcd/client/v3 v3.6.7 // indirect go.uber.org/multierr v1.11.0 // indirect - golang.org/x/crypto v0.45.0 // indirect - golang.org/x/net v0.47.0 // indirect - golang.org/x/sys v0.38.0 // indirect - golang.org/x/text v0.31.0 // indirect - google.golang.org/genproto/googleapis/api v0.0.0-20251111163417-95abcf5c77ba // indirect - google.golang.org/genproto/googleapis/rpc v0.0.0-20251111163417-95abcf5c77ba // indirect + golang.org/x/crypto v0.46.0 // indirect + golang.org/x/net v0.48.0 // indirect + golang.org/x/sys v0.39.0 // indirect + golang.org/x/text v0.32.0 // indirect + google.golang.org/genproto/googleapis/api v0.0.0-20251213004720-97cd9d5aeac2 // indirect + google.golang.org/genproto/googleapis/rpc v0.0.0-20251213004720-97cd9d5aeac2 // indirect google.golang.org/grpc v1.77.0 // indirect - google.golang.org/protobuf v1.36.10 // indirect + google.golang.org/protobuf v1.36.11 // indirect ) diff --git a/go.sum b/go.sum index 629b64d..8e1f140 100644 --- a/go.sum +++ b/go.sum @@ -25,6 +25,8 @@ github.com/dop251/base64dec v0.0.0-20231022112746-c6c9f9a96217 h1:16iT9CBDOniJwF github.com/dop251/base64dec v0.0.0-20231022112746-c6c9f9a96217/go.mod h1:eIb+f24U+eWQCIsj9D/ah+MD9UP+wdxuqzsdLD+mhGM= github.com/dop251/goja v0.0.0-20251103141225-af2ceb9156d7 h1:jxmXU5V9tXxJnydU5v/m9SG8TRUa/Z7IXODBpMs/P+U= github.com/dop251/goja v0.0.0-20251103141225-af2ceb9156d7/go.mod h1:MxLav0peU43GgvwVgNbLAj1s/bSGboKkhuULvq/7hx4= +github.com/dop251/goja v0.0.0-20251201205617-2bb4c724c0f9 h1:3uSSOd6mVlwcX3k5OYOpiDqFgRmaE2dBfLvVIFWWHrw= +github.com/dop251/goja v0.0.0-20251201205617-2bb4c724c0f9/go.mod h1:MxLav0peU43GgvwVgNbLAj1s/bSGboKkhuULvq/7hx4= github.com/dop251/goja_nodejs v0.0.0-20251015164255-5e94316bedaf h1:gbmvliZnCut4NjaPSNOQlfqBoZ9C5Dpf72mHMMYhgVE= github.com/dop251/goja_nodejs v0.0.0-20251015164255-5e94316bedaf/go.mod h1:Tb7Xxye4LX7cT3i8YLvmPMGCV92IOi4CDZvm/V8ylc0= github.com/dustin/go-humanize v1.0.1 h1:GzkhY7T5VNhEkwH0PVJgjz+fX1rhBrR7pRT3mDkpeCY= @@ -55,6 +57,8 @@ github.com/google/go-cmp v0.7.0 h1:wk8382ETsv4JYUZwIsn6YpYiWiBsYLSJiTsyBybVuN8= github.com/google/go-cmp v0.7.0/go.mod h1:pXiqmnSA92OHEEa9HXL2W4E7lf9JzCmGVUdgjX3N/iU= github.com/google/pprof v0.0.0-20251114195745-4902fdda35c8 h1:3DsUAV+VNEQa2CUVLxCY3f87278uWfIDhJnbdvDjvmE= github.com/google/pprof v0.0.0-20251114195745-4902fdda35c8/go.mod h1:I6V7YzU0XDpsHqbsyrghnFZLO1gwK6NPTNvmetQIk9U= +github.com/google/pprof v0.0.0-20251213031049-b05bdaca462f h1:HU1RgM6NALf/KW9HEY6zry3ADbDKcmpQ+hJedoNGQYQ= +github.com/google/pprof v0.0.0-20251213031049-b05bdaca462f/go.mod h1:67FPmZWbr+KDT/VlpWtw6sO9XSjpJmLuHpoLmWiTGgY= github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0= github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/gorilla/websocket v1.5.3 h1:saDtZ6Pbx/0u+bgYQ3q96pZgCzfhKXGPqt7kZ72aNNg= @@ -63,12 +67,16 @@ github.com/grpc-ecosystem/grpc-gateway/v2 v2.27.3 h1:NmZ1PKzSTQbuGHw9DGPFomqkkLW github.com/grpc-ecosystem/grpc-gateway/v2 v2.27.3/go.mod h1:zQrxl1YP88HQlA6i9c63DSVPFklWpGX4OWAc9bFuaH4= github.com/hashicorp/go-version v1.7.0 h1:5tqGy27NaOTB8yJKUZELlFAS/LTKJkrmONwQKeRZfjY= github.com/hashicorp/go-version v1.7.0/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA= +github.com/hashicorp/go-version v1.8.0 h1:KAkNb1HAiZd1ukkxDFGmokVZe1Xy9HG6NUp+bPle2i4= +github.com/hashicorp/go-version v1.8.0/go.mod h1:fltr4n8CU8Ke44wwGCBoEymUuxUHl09ZGVZPK5anwXA= github.com/hashicorp/golang-lru/v2 v2.0.7 h1:a+bsQ5rvGLjzHuww6tVxozPZFVghXaHOwFs4luLUK2k= github.com/hashicorp/golang-lru/v2 v2.0.7/go.mod h1:QeFd9opnmA6QUJc5vARoKUSoFhyfM2/ZepoAG6RGpeM= github.com/kisielk/errcheck v1.5.0/go.mod h1:pFxgyoBC7bSaBwPgfKdkLd5X25qrDl4LWUI2bnpBCr8= github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck= github.com/klauspost/compress v1.18.1 h1:bcSGx7UbpBqMChDtsF28Lw6v/G94LPrrbMbdC3JH2co= github.com/klauspost/compress v1.18.1/go.mod h1:ZQFFVG+MdnR0P+l6wpXgIL4NTtwiKIdBnrBd8Nrxr+0= +github.com/klauspost/compress v1.18.2 h1:iiPHWW0YrcFgpBYhsA6D1+fqHssJscY/Tm/y2Uqnapk= +github.com/klauspost/compress v1.18.2/go.mod h1:R0h/fSBs8DE4ENlcrlib3PsXS61voFxhIs2DeRhCvJ4= github.com/klauspost/cpuid/v2 v2.0.1/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg= github.com/klauspost/cpuid/v2 v2.3.0 h1:S4CRMLnYUhGeDFDqkGriYKdfoFlDnMtqTiI/sFzhA9Y= github.com/klauspost/cpuid/v2 v2.3.0/go.mod h1:hqwkgyIinND0mEev00jJYCxPNVRVXFQeu1XKlok6oO0= @@ -112,14 +120,22 @@ github.com/stretchr/testify v1.11.1 h1:7s2iGBzp5EwR7/aIZr8ao5+dra3wiQyKjjFuvgVKu github.com/stretchr/testify v1.11.1/go.mod h1:wZwfW3scLgRK+23gO65QZefKpKQRnfz6sD981Nm4B6U= github.com/tinylib/msgp v1.5.0 h1:GWnqAE54wmnlFazjq2+vgr736Akg58iiHImh+kPY2pc= github.com/tinylib/msgp v1.5.0/go.mod h1:cvjFkb4RiC8qSBOPMGPSzSAx47nAsfhLVTCZZNuHv5o= +github.com/tinylib/msgp v1.6.1 h1:ESRv8eL3u+DNHUoSAAQRE50Hm162zqAnBoGv9PzScPY= +github.com/tinylib/msgp v1.6.1/go.mod h1:RSp0LW9oSxFut3KzESt5Voq4GVWyS+PSulT77roAqEA= github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= go.etcd.io/etcd/api/v3 v3.6.6 h1:mcaMp3+7JawWv69p6QShYWS8cIWUOl32bFLb6qf8pOQ= go.etcd.io/etcd/api/v3 v3.6.6/go.mod h1:f/om26iXl2wSkcTA1zGQv8reJRSLVdoEBsi4JdfMrx4= +go.etcd.io/etcd/api/v3 v3.6.7 h1:7BNJ2gQmc3DNM+9cRkv7KkGQDayElg8x3X+tFDYS+E0= +go.etcd.io/etcd/api/v3 v3.6.7/go.mod h1:xJ81TLj9hxrYYEDmXTeKURMeY3qEDN24hqe+q7KhbnI= go.etcd.io/etcd/client/pkg/v3 v3.6.6 h1:uoqgzSOv2H9KlIF5O1Lsd8sW+eMLuV6wzE3q5GJGQNs= go.etcd.io/etcd/client/pkg/v3 v3.6.6/go.mod h1:YngfUVmvsvOJ2rRgStIyHsKtOt9SZI2aBJrZiWJhCbI= +go.etcd.io/etcd/client/pkg/v3 v3.6.7 h1:vvzgyozz46q+TyeGBuFzVuI53/yd133CHceNb/AhBVs= +go.etcd.io/etcd/client/pkg/v3 v3.6.7/go.mod h1:2IVulJ3FZ/czIGl9T4lMF1uxzrhRahLqe+hSgy+Kh7Q= go.etcd.io/etcd/client/v3 v3.6.6 h1:G5z1wMf5B9SNexoxOHUGBaULurOZPIgGPsW6CN492ec= go.etcd.io/etcd/client/v3 v3.6.6/go.mod h1:36Qv6baQ07znPR3+n7t+Rk5VHEzVYPvFfGmfF4wBHV8= +go.etcd.io/etcd/client/v3 v3.6.7 h1:9WqA5RpIBtdMxAy1ukXLAdtg2pAxNqW5NUoO2wQrE6U= +go.etcd.io/etcd/client/v3 v3.6.7/go.mod h1:2XfROY56AXnUqGsvl+6k29wrwsSbEh1lAouQB1vHpeE= go.opentelemetry.io/auto/sdk v1.2.1 h1:jXsnJ4Lmnqd11kwkBV2LgLoFMZKizbCi5fNZ/ipaZ64= go.opentelemetry.io/auto/sdk v1.2.1/go.mod h1:KRTj+aOaElaLi+wW1kO/DZRXwkF4C5xPbEe3ZiIhN7Y= go.opentelemetry.io/otel v1.38.0 h1:RkfdswUDRimDg0m2Az18RKOsnI8UDzppJAtj01/Ymk8= @@ -144,6 +160,8 @@ golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPh golang.org/x/crypto v0.0.0-20210513164829-c07d793c2f9a/go.mod h1:P+XmwS30IXTQdn5tA2iutPOUgjI07+tq3H3K9MVA1s8= golang.org/x/crypto v0.45.0 h1:jMBrvKuj23MTlT0bQEOBcAE0mjg8mK9RXFhRH6nyF3Q= golang.org/x/crypto v0.45.0/go.mod h1:XTGrrkGJve7CYK7J8PEww4aY7gM3qMCElcJQ8n8JdX4= +golang.org/x/crypto v0.46.0 h1:cKRW/pmt1pKAfetfu+RCEvjvZkA9RimPbh7bhFjGVBU= +golang.org/x/crypto v0.46.0/go.mod h1:Evb/oLKmMraqjZ2iQTwDwvCtJkczlDuTmdJXoZVzqU0= golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= @@ -153,6 +171,8 @@ golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwY golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= golang.org/x/net v0.47.0 h1:Mx+4dIFzqraBXUugkia1OOvlD6LemFo1ALMHjrXDOhY= golang.org/x/net v0.47.0/go.mod h1:/jNxtkgq5yWUGYkaZGqo27cfGZ1c5Nen03aYrrKpVRU= +golang.org/x/net v0.48.0 h1:zyQRTTrjc33Lhh0fBgT/H3oZq9WuvRR5gPC70xpDiQU= +golang.org/x/net v0.48.0/go.mod h1:+ndRgGjkh8FGtu1w1FGbEC31if4VrNVMuKTgcAAnQRY= golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -162,6 +182,8 @@ golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7w golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.38.0 h1:3yZWxaJjBmCWXqhN1qh02AkOnCQ1poK6oF+a7xWL6Gc= golang.org/x/sys v0.38.0/go.mod h1:OgkHotnGiDImocRcuBABYBEXf8A9a87e/uXjp9XT3ks= +golang.org/x/sys v0.39.0 h1:CvCKL8MeisomCi6qNZ+wbb0DN9E5AATixKsvNtMoMFk= +golang.org/x/sys v0.39.0/go.mod h1:OgkHotnGiDImocRcuBABYBEXf8A9a87e/uXjp9XT3ks= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.37.0 h1:8EGAD0qCmHYZg6J17DvsMy9/wJ7/D/4pV/wfnld5lTU= golang.org/x/term v0.37.0/go.mod h1:5pB4lxRNYYVZuTLmy8oR2BH8dflOR+IbTYFD8fi3254= @@ -169,6 +191,8 @@ golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.31.0 h1:aC8ghyu4JhP8VojJ2lEHBnochRno1sgL6nEi9WGFGMM= golang.org/x/text v0.31.0/go.mod h1:tKRAlv61yKIjGGHX/4tP1LTbc13YSec1pxVEWXzfoeM= +golang.org/x/text v0.32.0 h1:ZD01bjUt1FQ9WJ0ClOL5vxgxOI/sVCNgX1YtKwcY0mU= +golang.org/x/text v0.32.0/go.mod h1:o/rUWzghvpD5TXrTIBuJU77MTaN0ljMWE47kxGJQ7jY= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20200619180055-7c47624df98f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= @@ -181,12 +205,18 @@ gonum.org/v1/gonum v0.16.0 h1:5+ul4Swaf3ESvrOnidPp4GZbzf0mxVQpDCYUQE7OJfk= gonum.org/v1/gonum v0.16.0/go.mod h1:fef3am4MQ93R2HHpKnLk4/Tbh/s0+wqD5nfa6Pnwy4E= google.golang.org/genproto/googleapis/api v0.0.0-20251111163417-95abcf5c77ba h1:B14OtaXuMaCQsl2deSvNkyPKIzq3BjfxQp8d00QyWx4= google.golang.org/genproto/googleapis/api v0.0.0-20251111163417-95abcf5c77ba/go.mod h1:G5IanEx8/PgI9w6CFcYQf7jMtHQhZruvfM1i3qOqk5U= +google.golang.org/genproto/googleapis/api v0.0.0-20251213004720-97cd9d5aeac2 h1:7LRqPCEdE4TP4/9psdaB7F2nhZFfBiGJomA5sojLWdU= +google.golang.org/genproto/googleapis/api v0.0.0-20251213004720-97cd9d5aeac2/go.mod h1:+rXWjjaukWZun3mLfjmVnQi18E1AsFbDN9QdJ5YXLto= google.golang.org/genproto/googleapis/rpc v0.0.0-20251111163417-95abcf5c77ba h1:UKgtfRM7Yh93Sya0Fo8ZzhDP4qBckrrxEr2oF5UIVb8= google.golang.org/genproto/googleapis/rpc v0.0.0-20251111163417-95abcf5c77ba/go.mod h1:7i2o+ce6H/6BluujYR+kqX3GKH+dChPTQU19wjRPiGk= +google.golang.org/genproto/googleapis/rpc v0.0.0-20251213004720-97cd9d5aeac2 h1:2I6GHUeJ/4shcDpoUlLs/2WPnhg7yJwvXtqcMJt9liA= +google.golang.org/genproto/googleapis/rpc v0.0.0-20251213004720-97cd9d5aeac2/go.mod h1:7i2o+ce6H/6BluujYR+kqX3GKH+dChPTQU19wjRPiGk= google.golang.org/grpc v1.77.0 h1:wVVY6/8cGA6vvffn+wWK5ToddbgdU3d8MNENr4evgXM= google.golang.org/grpc v1.77.0/go.mod h1:z0BY1iVj0q8E1uSQCjL9cppRj+gnZjzDnzV0dHhrNig= google.golang.org/protobuf v1.36.10 h1:AYd7cD/uASjIL6Q9LiTjz8JLcrh/88q5UObnmY3aOOE= google.golang.org/protobuf v1.36.10/go.mod h1:HTf+CrKn2C3g5S8VImy6tdcUvCska2kB7j23XfzDpco= +google.golang.org/protobuf v1.36.11 h1:fV6ZwhNocDyBLK0dj+fg8ektcVegBBuEolpbTQyBNVE= +google.golang.org/protobuf v1.36.11/go.mod h1:HTf+CrKn2C3g5S8VImy6tdcUvCska2kB7j23XfzDpco= gopkg.d7z.net/middleware v0.0.0-20251120123709-5d4e16e0d6fb h1:2+IskB2qGQshl67tHdnzEXCm46+9E/QevYL3xpMul0E= gopkg.d7z.net/middleware v0.0.0-20251120123709-5d4e16e0d6fb/go.mod h1:/1/EuissKhUbuhUe01rcWuwpA5mt7jASb4uKVNOLtR8= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= diff --git a/pkg/core/alias.go b/pkg/core/alias.go index 64055a1..17fcce3 100644 --- a/pkg/core/alias.go +++ b/pkg/core/alias.go @@ -10,9 +10,8 @@ import ( ) type Alias struct { - Owner string `json:"owner"` - Repo string `json:"repo"` - Branch string `json:"branch"` + Owner string `json:"owner"` + Repo string `json:"repo"` } type DomainAlias struct { @@ -35,9 +34,9 @@ func (a *DomainAlias) Query(ctx context.Context, domain string) (*Alias, error) return rel, nil } -func (a *DomainAlias) Bind(ctx context.Context, domains []string, owner, repo, branch string) error { +func (a *DomainAlias) Bind(ctx context.Context, domains []string, owner, repo string) error { oldDomains := make([]string, 0) - rKey := base64.URLEncoding.EncodeToString([]byte(fmt.Sprintf("%s/%s/%s", owner, repo, branch))) + rKey := base64.URLEncoding.EncodeToString([]byte(fmt.Sprintf("%s/%s", owner, repo))) if oldStr, err := a.config.Get(ctx, rKey); err == nil { _ = json.Unmarshal([]byte(oldStr), &oldDomains) } @@ -50,9 +49,8 @@ func (a *DomainAlias) Bind(ctx context.Context, domains []string, owner, repo, b return nil } aliasMeta := &Alias{ - Owner: owner, - Repo: repo, - Branch: branch, + Owner: owner, + Repo: repo, } aliasMetaRaw, _ := json.Marshal(aliasMeta) domainsRaw, _ := json.Marshal(domains) diff --git a/pkg/core/backend.go b/pkg/core/backend.go index a42b2c7..9046aee 100644 --- a/pkg/core/backend.go +++ b/pkg/core/backend.go @@ -7,17 +7,14 @@ import ( "time" ) -type BranchInfo struct { +type Metadata struct { ID string `json:"id"` LastModified time.Time `json:"last_modified"` } type Backend interface { io.Closer - // Repos return repo name + default branch - Repos(ctx context.Context, owner string) (map[string]string, error) - // Branches return branch + commit id - Branches(ctx context.Context, owner, repo string) (map[string]*BranchInfo, error) + Meta(ctx context.Context, owner, repo string) (*Metadata, error) // Open return file or error (error) - Open(ctx context.Context, owner, repo, commit, path string, headers http.Header) (*http.Response, error) + Open(ctx context.Context, owner, repo, id, path string, headers http.Header) (*http.Response, error) } diff --git a/pkg/core/domain.go b/pkg/core/domain.go index 39d8197..c5897eb 100644 --- a/pkg/core/domain.go +++ b/pkg/core/domain.go @@ -12,15 +12,13 @@ import ( type PageDomain struct { *ServerMeta - baseDomain string - defaultBranch string + baseDomain string } -func NewPageDomain(meta *ServerMeta, baseDomain, defaultBranch string) *PageDomain { +func NewPageDomain(meta *ServerMeta, baseDomain string) *PageDomain { return &PageDomain{ - baseDomain: baseDomain, - defaultBranch: defaultBranch, - ServerMeta: meta, + baseDomain: baseDomain, + ServerMeta: meta, } } @@ -32,10 +30,7 @@ type PageContent struct { Path string } -func (p *PageDomain) ParseDomainMeta(ctx context.Context, domain, path, branch string) (*PageContent, error) { - if branch == "" { - branch = p.defaultBranch - } +func (p *PageDomain) ParseDomainMeta(ctx context.Context, domain, path string) (*PageContent, error) { pathArr := strings.Split(strings.TrimPrefix(path, "/"), "/") if !strings.HasSuffix(domain, "."+p.baseDomain) { alias, err := p.Alias.Query(ctx, domain) // 确定 alias 是否存在内容 @@ -44,7 +39,7 @@ func (p *PageDomain) ParseDomainMeta(ctx context.Context, domain, path, branch s return nil, os.ErrNotExist } zap.L().Debug("alias hit", zap.String("domain", domain), zap.Any("alias", alias)) - return p.returnMeta(ctx, alias.Owner, alias.Repo, alias.Branch, pathArr) + return p.returnMeta(ctx, alias.Owner, alias.Repo, pathArr) } owner := strings.TrimSuffix(domain, "."+p.baseDomain) repo := pathArr[0] @@ -53,9 +48,9 @@ func (p *PageDomain) ParseDomainMeta(ctx context.Context, domain, path, branch s if repo == "" { // 回退到默认仓库 (路径未包含仓库) zap.L().Debug("fail back to default repo", zap.String("repo", domain)) - returnMeta, err = p.returnMeta(ctx, owner, domain, branch, pathArr) + returnMeta, err = p.returnMeta(ctx, owner, domain, pathArr) } else { - returnMeta, err = p.returnMeta(ctx, owner, repo, branch, pathArr[1:]) + returnMeta, err = p.returnMeta(ctx, owner, repo, pathArr[1:]) } if err != nil && !errors.Is(err, os.ErrNotExist) { return nil, err @@ -63,14 +58,14 @@ func (p *PageDomain) ParseDomainMeta(ctx context.Context, domain, path, branch s return returnMeta, nil } // 发现 repo 的情况下回退到默认页面 - return p.returnMeta(ctx, owner, domain, branch, pathArr) + return p.returnMeta(ctx, owner, domain, pathArr) } -func (p *PageDomain) returnMeta(ctx context.Context, owner, repo, branch string, path []string) (*PageContent, error) { +func (p *PageDomain) returnMeta(ctx context.Context, owner, repo string, path []string) (*PageContent, error) { result := &PageContent{} - meta, err := p.GetMeta(ctx, owner, repo, branch) + meta, err := p.GetMeta(ctx, owner, repo) if err != nil { - zap.L().Debug("repo does not exists", zap.Error(err), zap.Strings("meta", []string{owner, repo, branch})) + zap.L().Debug("repo does not exists", zap.Error(err), zap.Strings("meta", []string{owner, repo})) if meta != nil { // 解析错误汇报 return nil, errors.New(meta.ErrorMsg) diff --git a/pkg/core/meta.go b/pkg/core/meta.go index 89398d8..a663da7 100644 --- a/pkg/core/meta.go +++ b/pkg/core/meta.go @@ -16,6 +16,8 @@ import ( "gopkg.d7z.net/middleware/tools" "gopkg.in/yaml.v3" + stdErr "errors" + "github.com/pkg/errors" "gopkg.d7z.net/gitea-pages/pkg/utils" @@ -71,7 +73,14 @@ func (m *PageMetaContent) String() string { return string(marshal) } -func NewServerMeta(client *http.Client, backend Backend, domain string, alias *DomainAlias, cache kv.KV, ttl time.Duration) *ServerMeta { +func NewServerMeta( + client *http.Client, + backend Backend, + domain string, + alias *DomainAlias, + cache kv.KV, + ttl time.Duration, +) *ServerMeta { return &ServerMeta{ Backend: backend, Domain: domain, @@ -82,40 +91,14 @@ func NewServerMeta(client *http.Client, backend Backend, domain string, alias *D } } -func (s *ServerMeta) GetMeta(ctx context.Context, owner, repo, branch string) (*PageMetaContent, error) { - repos, err := s.Repos(ctx, owner) - if err != nil { - return nil, err - } - - defBranch := repos[repo] - if defBranch == "" { - return nil, os.ErrNotExist - } - - if branch == "" { - branch = defBranch - } - - branches, err := s.Branches(ctx, owner, repo) - if err != nil { - return nil, err - } - - info := branches[branch] - if info == nil { - return nil, os.ErrNotExist - } - - key := fmt.Sprintf("%s/%s/%s", owner, repo, branch) - +func (s *ServerMeta) GetMeta(ctx context.Context, owner, repo string) (*PageMetaContent, error) { + key := fmt.Sprintf("%s/%s", owner, repo) if cache, found := s.cache.Load(ctx, key); found { if cache.IsPage { return &cache, nil } return nil, os.ErrNotExist } - mux := s.locker.Open(key) mux.Lock() defer mux.Unlock() @@ -127,6 +110,10 @@ func (s *ServerMeta) GetMeta(ctx context.Context, owner, repo, branch string) (* return nil, os.ErrNotExist } + info, err := s.Meta(ctx, owner, repo) + if err != nil { + return nil, stdErr.Join(err, os.ErrNotExist) + } rel := NewEmptyPageMetaContent() vfs := NewPageVFS(s.Backend, owner, repo, info.ID) rel.CommitID = info.ID @@ -147,7 +134,7 @@ func (s *ServerMeta) GetMeta(ctx context.Context, owner, repo, branch string) (* return nil, err } // todo: 优化保存逻辑 ,减少写入 - if err = s.Alias.Bind(ctx, rel.Alias, owner, repo, branch); err != nil { + if err = s.Alias.Bind(ctx, rel.Alias, owner, repo); err != nil { zap.L().Warn("alias binding error.", zap.Error(err)) return nil, err } diff --git a/pkg/providers/cache.go b/pkg/providers/cache.go index b5d86ae..e630a3e 100644 --- a/pkg/providers/cache.go +++ b/pkg/providers/cache.go @@ -15,14 +15,10 @@ import ( "gopkg.d7z.net/gitea-pages/pkg/core" "gopkg.d7z.net/gitea-pages/pkg/utils" "gopkg.d7z.net/middleware/cache" - "gopkg.d7z.net/middleware/kv" - "gopkg.d7z.net/middleware/tools" ) type ProviderCache struct { - parent core.Backend - cacheRepo *tools.KVCache[map[string]string] - cacheBranch *tools.KVCache[map[string]*core.BranchInfo] + parent core.Backend cacheBlob cache.Cache cacheBlobLimit uint64 @@ -34,66 +30,26 @@ func (c *ProviderCache) Close() error { func NewProviderCache( backend core.Backend, - cacheMeta kv.KV, - cacheMetaTTL time.Duration, cacheBlob cache.Cache, cacheBlobLimit uint64, ) *ProviderCache { - repoCache := tools.NewCache[map[string]string](cacheMeta, "repos", cacheMetaTTL) - branchCache := tools.NewCache[map[string]*core.BranchInfo](cacheMeta, "branches", cacheMetaTTL) return &ProviderCache{ - parent: backend, - cacheRepo: repoCache, - cacheBranch: branchCache, - + parent: backend, cacheBlob: cacheBlob, cacheBlobLimit: cacheBlobLimit, } } -func (c *ProviderCache) Repos(ctx context.Context, owner string) (map[string]string, error) { - if load, b := c.cacheRepo.Load(ctx, owner); b { - return load, nil - } - ret, err := c.parent.Repos(ctx, owner) - if err != nil { - if errors.Is(err, os.ErrNotExist) { - _ = c.cacheRepo.Store(ctx, owner, map[string]string{}) - } - return nil, err - } - err = c.cacheRepo.Store(ctx, owner, ret) - if len(ret) == 0 { - return nil, os.ErrNotExist - } - return ret, err +func (c *ProviderCache) Meta(ctx context.Context, owner, repo string) (*core.Metadata, error) { + return c.parent.Meta(ctx, owner, repo) } -func (c *ProviderCache) Branches(ctx context.Context, owner, repo string) (map[string]*core.BranchInfo, error) { - key := fmt.Sprintf("%s/%s", owner, repo) - if load, b := c.cacheBranch.Load(ctx, key); b { - return load, nil - } - ret, err := c.parent.Branches(ctx, owner, repo) - if err != nil { - if errors.Is(err, os.ErrNotExist) { - _ = c.cacheBranch.Store(ctx, key, map[string]*core.BranchInfo{}) - } - return nil, err - } - err = c.cacheBranch.Store(ctx, key, ret) - if len(ret) == 0 { - return nil, os.ErrNotExist - } - return ret, err -} - -func (c *ProviderCache) Open(ctx context.Context, owner, repo, commit, path string, headers http.Header) (*http.Response, error) { +func (c *ProviderCache) Open(ctx context.Context, owner, repo, id, path string, headers http.Header) (*http.Response, error) { if headers != nil && headers.Get("Range") != "" { // ignore custom header - return c.parent.Open(ctx, owner, repo, commit, path, headers) + return c.parent.Open(ctx, owner, repo, id, path, headers) } - key := fmt.Sprintf("%s/%s/%s/%s", owner, repo, commit, path) + key := fmt.Sprintf("%s/%s/%s/%s", owner, repo, id, path) lastCache, err := c.cacheBlob.Get(ctx, key) if err != nil && !errors.Is(err, os.ErrNotExist) { return nil, err @@ -125,7 +81,7 @@ func (c *ProviderCache) Open(ctx context.Context, owner, repo, commit, path stri Header: respHeader, }, nil } - open, err := c.parent.Open(ctx, owner, repo, commit, path, http.Header{}) + open, err := c.parent.Open(ctx, owner, repo, id, path, http.Header{}) if err != nil || open == nil { if open != nil { _ = open.Body.Close() diff --git a/pkg/providers/gitea.go b/pkg/providers/gitea.go index db964b3..c99f458 100644 --- a/pkg/providers/gitea.go +++ b/pkg/providers/gitea.go @@ -4,105 +4,43 @@ import ( "context" "net/http" "net/url" - "os" - - "gopkg.d7z.net/gitea-pages/pkg/core" "code.gitea.io/sdk/gitea" + "gopkg.d7z.net/gitea-pages/pkg/core" ) -const GiteaMaxCount = 9999 - type ProviderGitea struct { BaseURL string Token string - gitea *gitea.Client - client *http.Client + gitea *gitea.Client + client *http.Client + defaultBranch string } -func NewGitea(httpClient *http.Client, url, token string) (*ProviderGitea, error) { +func NewGitea(httpClient *http.Client, url, token, defaultBranch string) (*ProviderGitea, error) { client, err := gitea.NewClient(url, gitea.SetGiteaVersion(""), gitea.SetToken(token)) if err != nil { return nil, err } return &ProviderGitea{ - BaseURL: url, - Token: token, - gitea: client, - client: httpClient, + BaseURL: url, + Token: token, + gitea: client, + client: httpClient, + defaultBranch: defaultBranch, }, nil } -func (g *ProviderGitea) Repos(_ context.Context, owner string) (map[string]string, error) { - result := make(map[string]string) - if repos, resp, err := g.gitea.ListOrgRepos(owner, gitea.ListOrgReposOptions{ - ListOptions: gitea.ListOptions{ - PageSize: GiteaMaxCount, - }, - }); err != nil { - if resp != nil { - _ = resp.Body.Close() - } - } else { - if resp != nil { - _ = resp.Body.Close() - } - for _, item := range repos { - result[item.Name] = item.DefaultBranch - } - return result, nil - } - if len(result) == 0 { - if repos, resp, err := g.gitea.ListUserRepos(owner, gitea.ListReposOptions{ - ListOptions: gitea.ListOptions{ - PageSize: GiteaMaxCount, - }, - }); err != nil { - if resp != nil { - _ = resp.Body.Close() - } - } else { - if resp != nil { - _ = resp.Body.Close() - } - for _, item := range repos { - result[item.Name] = item.DefaultBranch - } - } - } - if len(result) == 0 { - return nil, os.ErrNotExist - } - return result, nil -} - -func (g *ProviderGitea) Branches(_ context.Context, owner, repo string) (map[string]*core.BranchInfo, error) { - result := make(map[string]*core.BranchInfo) - branches, resp, err := g.gitea.ListRepoBranches(owner, repo, gitea.ListRepoBranchesOptions{ - ListOptions: gitea.ListOptions{ - PageSize: GiteaMaxCount, - }, - }) +func (g *ProviderGitea) Meta(_ context.Context, owner, repo string) (*core.Metadata, error) { + branch, _, err := g.gitea.GetRepoBranch(owner, repo, g.defaultBranch) if err != nil { - if resp != nil { - _ = resp.Body.Close() - } return nil, err } - if resp != nil { - _ = resp.Body.Close() - } - for _, branch := range branches { - result[branch.Name] = &core.BranchInfo{ - ID: branch.Commit.ID, - LastModified: branch.Commit.Timestamp, - } - } - if len(result) == 0 { - return nil, os.ErrNotExist - } - return result, nil + return &core.Metadata{ + ID: branch.Commit.ID, + LastModified: branch.Commit.Timestamp, + }, nil } func (g *ProviderGitea) Open(ctx context.Context, owner, repo, commit, path string, headers http.Header) (*http.Response, error) { diff --git a/pkg/providers/local.go b/pkg/providers/local.go index 7ef2acf..8d2410a 100644 --- a/pkg/providers/local.go +++ b/pkg/providers/local.go @@ -10,7 +10,6 @@ import ( "net/http/httptest" "os" "path/filepath" - "slices" "strconv" "strings" "time" @@ -43,31 +42,10 @@ func (l *LocalProvider) Close() error { return nil } -func (l *LocalProvider) Repos(_ context.Context, owner string) (map[string]string, error) { - item, ok := l.graph[owner] - if !ok { - return nil, os.ErrNotExist - } - result := make(map[string]string) - for _, s := range item { - result[s] = "gh-pages" - } - return result, nil -} - -func (l *LocalProvider) Branches(_ context.Context, owner, repo string) (map[string]*core.BranchInfo, error) { - item, ok := l.graph[owner] - if !ok { - return nil, os.ErrNotExist - } - if !slices.Contains(item, repo) { - return nil, os.ErrNotExist - } - return map[string]*core.BranchInfo{ - "gh-pages": { - ID: "adc83b19e793491b1c6ea0fd8b46cd9f32e592fc", - LastModified: time.Now(), - }, +func (l *LocalProvider) Meta(_ context.Context, _, _ string) (*core.Metadata, error) { + return &core.Metadata{ + ID: "localhost", + LastModified: time.Now(), }, nil } diff --git a/pkg/server.go b/pkg/server.go index 3396cdd..0e8f38a 100644 --- a/pkg/server.go +++ b/pkg/server.go @@ -44,7 +44,6 @@ func NewPageServer( client *http.Client, backend core.Backend, domain string, - defaultBranch string, db kv.CursorPagedKV, event subscribe.Subscriber, cacheMeta kv.KV, @@ -56,7 +55,7 @@ func NewPageServer( ) (*Server, error) { alias := core.NewDomainAlias(db.Child("config", "alias")) svcMeta := core.NewServerMeta(client, backend, domain, alias, cacheMeta, cacheMetaTTL) - pageMeta := core.NewPageDomain(svcMeta, domain, defaultBranch) + pageMeta := core.NewPageDomain(svcMeta, domain) globCache, err := lru.New[string, glob.Glob](512) if err != nil { return nil, err @@ -106,17 +105,17 @@ func (s *Server) ServeHTTP(w http.ResponseWriter, request *http.Request) { func (s *Server) Serve(writer *utils.WrittenResponseWriter, request *http.Request) error { ctx := request.Context() domain := portExp.ReplaceAllString(strings.ToLower(request.Host), "") - meta, err := s.meta.ParseDomainMeta(ctx, domain, request.URL.Path, request.URL.Query().Get("branch")) + meta, err := s.meta.ParseDomainMeta(ctx, domain, request.URL.Path) if err != nil { return err } - - cancel, cancelFunc := context.WithCancel(request.Context()) + writer.Header().Set("X-Page-ID", meta.CommitID) + cancelCtx, cancelFunc := context.WithCancel(request.Context()) filterCtx := core.FilterContext{ PageContent: meta, - Context: cancel, + Context: cancelCtx, PageVFS: core.NewPageVFS(s.backend, meta.Owner, meta.Repo, meta.CommitID), - Cache: tools.NewTTLCache(s.cacheBlob.Child("filter", meta.Owner, meta.Repo, meta.CommitID), time.Minute), + Cache: tools.NewTTLCache(s.cacheBlob.Child("filter", meta.Owner, meta.Repo, meta.CommitID), s.cacheBlobTTL), OrgDB: s.db.Child("org", meta.Owner).(kv.CursorPagedKV), RepoDB: s.db.Child("repo", meta.Owner, meta.Repo).(kv.CursorPagedKV), Event: s.event.Child("domain", meta.Owner, meta.Repo), diff --git a/tests/core/dummy.go b/tests/core/dummy.go index ada602d..87ce66f 100644 --- a/tests/core/dummy.go +++ b/tests/core/dummy.go @@ -30,35 +30,11 @@ func NewDummy() (*ProviderDummy, error) { }, nil } -func (p *ProviderDummy) Repos(_ context.Context, owner string) (map[string]string, error) { - dir, err := os.ReadDir(filepath.Join(p.BaseDir, owner)) - if err != nil { - return nil, err - } - repos := make(map[string]string) - for _, d := range dir { - if d.IsDir() { - repos[d.Name()] = "main" - } - } - return repos, nil -} - -func (p *ProviderDummy) Branches(_ context.Context, owner, repo string) (map[string]*core.BranchInfo, error) { - dir, err := os.ReadDir(filepath.Join(p.BaseDir, owner, repo)) - if err != nil { - return nil, err - } - branches := make(map[string]*core.BranchInfo) - for _, d := range dir { - if d.IsDir() { - branches[d.Name()] = &core.BranchInfo{ - ID: d.Name(), - LastModified: time.Time{}, - } - } - } - return branches, nil +func (p *ProviderDummy) Meta(_ context.Context, _, _ string) (*core.Metadata, error) { + return &core.Metadata{ + ID: "gh-pages", + LastModified: time.Now(), + }, nil } func (p *ProviderDummy) Open(_ context.Context, owner, repo, commit, path string, _ http.Header) (*http.Response, error) { diff --git a/tests/core/test.go b/tests/core/test.go index 187e77f..c3c5637 100644 --- a/tests/core/test.go +++ b/tests/core/test.go @@ -51,7 +51,6 @@ func NewTestServer(domain string) *TestServer { http.DefaultClient, dummy, domain, - "gh-pages", memoryKV, subscribe.NewMemorySubscriber(), memoryKV.Child("cache"),