diff --git a/go.mod b/go.mod index 876de48..1d3a4fe 100644 --- a/go.mod +++ b/go.mod @@ -11,17 +11,18 @@ require ( github.com/dchest/siphash v1.2.3 github.com/gin-gonic/gin v1.10.1 github.com/go-faster/errors v0.7.1 - github.com/go-faster/jx v1.1.0 + github.com/go-faster/jx v1.2.0 github.com/nats-io/nats.go v1.37.0 - github.com/ogen-go/ogen v1.2.1 + github.com/ogen-go/ogen v1.18.0 + github.com/redis/go-redis/v9 v9.10.0 github.com/sirupsen/logrus v1.9.3 github.com/swaggo/files v1.0.1 github.com/swaggo/gin-swagger v1.6.0 github.com/swaggo/swag v1.16.6 github.com/urfave/cli/v2 v2.27.6 - go.opentelemetry.io/otel v1.32.0 - go.opentelemetry.io/otel/metric v1.32.0 - go.opentelemetry.io/otel/trace v1.32.0 + go.opentelemetry.io/otel v1.39.0 + go.opentelemetry.io/otel/metric v1.39.0 + go.opentelemetry.io/otel/trace v1.39.0 google.golang.org/grpc v1.48.0 gorm.io/driver/postgres v1.6.0 gorm.io/gorm v1.25.12 @@ -33,9 +34,11 @@ require ( github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578 // indirect github.com/bytedance/sonic v1.11.6 // indirect github.com/bytedance/sonic/loader v0.1.1 // indirect + github.com/cespare/xxhash/v2 v2.3.0 // indirect github.com/cloudwego/base64x v0.1.4 // indirect github.com/cloudwego/iasm v0.2.0 // indirect github.com/cpuguy83/go-md2man/v2 v2.0.5 // indirect + github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f // indirect github.com/gabriel-vasile/mimetype v1.4.3 // indirect github.com/gin-contrib/sse v0.1.0 // indirect github.com/go-openapi/jsonpointer v0.19.5 // indirect @@ -55,7 +58,7 @@ require ( github.com/jinzhu/now v1.1.5 // indirect github.com/josharian/intern v1.0.0 // indirect github.com/json-iterator/go v1.1.12 // indirect - github.com/klauspost/compress v1.17.6 // indirect + github.com/klauspost/compress v1.18.1 // indirect github.com/klauspost/cpuid/v2 v2.2.7 // indirect github.com/leodido/go-urn v1.4.0 // indirect github.com/mailru/easyjson v0.7.6 // indirect @@ -65,36 +68,38 @@ require ( github.com/nats-io/nuid v1.0.1 // indirect github.com/pelletier/go-toml/v2 v2.2.2 // indirect github.com/russross/blackfriday/v2 v2.1.0 // indirect + github.com/shopspring/decimal v1.4.0 // indirect github.com/twitchyliquid64/golang-asm v0.15.1 // indirect github.com/ugorji/go/codec v1.2.12 // indirect github.com/xrash/smetrics v0.0.0-20240521201337-686a1a2994c1 // indirect + go.opentelemetry.io/auto/sdk v1.2.1 // indirect golang.org/x/arch v0.8.0 // indirect - golang.org/x/crypto v0.32.0 // indirect - golang.org/x/mod v0.17.0 // indirect - golang.org/x/tools v0.21.1-0.20240508182429-e35e4ccd0d2d // indirect + golang.org/x/crypto v0.46.0 // indirect + golang.org/x/mod v0.31.0 // indirect + golang.org/x/tools v0.40.0 // indirect google.golang.org/genproto v0.0.0-20200526211855-cb27e3aa2013 // indirect google.golang.org/protobuf v1.34.1 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect ) require ( - github.com/dlclark/regexp2 v1.11.0 // indirect - github.com/fatih/color v1.17.0 // indirect + github.com/dlclark/regexp2 v1.11.5 // indirect + github.com/fatih/color v1.18.0 // indirect github.com/ghodss/yaml v1.0.0 // indirect github.com/go-faster/yaml v0.4.6 // indirect - github.com/go-logr/logr v1.4.2 // indirect + github.com/go-logr/logr v1.4.3 // indirect github.com/go-logr/stdr v1.2.2 // indirect // github.com/golang/protobuf v1.5.4 // indirect github.com/google/uuid v1.6.0 // indirect - github.com/mattn/go-colorable v0.1.13 // indirect + github.com/mattn/go-colorable v0.1.14 // indirect github.com/mattn/go-isatty v0.0.20 // indirect - github.com/segmentio/asm v1.2.0 // indirect + github.com/segmentio/asm v1.2.1 // indirect go.uber.org/multierr v1.11.0 // indirect - go.uber.org/zap v1.27.0 // indirect - golang.org/x/exp v0.0.0-20240531132922-fd00a4e0eefc // indirect - golang.org/x/net v0.34.0 // indirect - golang.org/x/sync v0.12.0 // indirect - golang.org/x/sys v0.29.0 // indirect - golang.org/x/text v0.23.0 // indirect + go.uber.org/zap v1.27.1 // indirect + golang.org/x/exp v0.0.0-20251219203646-944ab1f22d93 // indirect + golang.org/x/net v0.48.0 // indirect + golang.org/x/sync v0.19.0 // indirect + golang.org/x/sys v0.39.0 // indirect + golang.org/x/text v0.32.0 // indirect gopkg.in/yaml.v2 v2.4.0 // indirect ) diff --git a/go.sum b/go.sum index 344bdc5..0eba823 100644 --- a/go.sum +++ b/go.sum @@ -14,12 +14,18 @@ github.com/PuerkitoBio/purell v1.1.1/go.mod h1:c11w/QuzBsJSee3cPx9rAFu61PvFxuPbt github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578 h1:d+Bc7a5rLufV/sSk/8dngufqelfh6jnri85riMAaF/M= github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578/go.mod h1:uGdkoq3SwY9Y+13GIhn11/XLaGBb4BfwItxLd5jeuXE= github.com/antihax/optional v1.0.0/go.mod h1:uupD/76wgC+ih3iEmQUL+0Ugr19nfwCT1kdvxnR2qWY= +github.com/bsm/ginkgo/v2 v2.12.0 h1:Ny8MWAHyOepLGlLKYmXG4IEkioBysk6GpaRTLC8zwWs= +github.com/bsm/ginkgo/v2 v2.12.0/go.mod h1:SwYbGRRDovPVboqFv0tPTcG1sN61LM1Z4ARdbAV9g4c= +github.com/bsm/gomega v1.27.10 h1:yeMWxP2pV2fG3FgAODIY8EiRE3dy0aeFYt4l7wh6yKA= +github.com/bsm/gomega v1.27.10/go.mod h1:JyEr/xRbxbtgWNi8tIEVPUYZ5Dzef52k01W3YH0H+O0= github.com/bytedance/sonic v1.11.6 h1:oUp34TzMlL+OY1OUWxHqsdkgC/Zfc85zGqw9siXjrc0= github.com/bytedance/sonic v1.11.6/go.mod h1:LysEHSvpvDySVdC2f87zGWf6CIKJcAvqab1ZaiQtds4= github.com/bytedance/sonic/loader v0.1.1 h1:c+e5Pt1k/cy5wMveRDyk2X4B9hF4g7an8N3zCYjJFNM= github.com/bytedance/sonic/loader v0.1.1/go.mod h1:ncP89zfokxS5LZrJxl5z0UJcsk4M4yY2JpfqGeCtNLU= github.com/census-instrumentation/opencensus-proto v0.2.1/go.mod h1:f6KPmirojxKA12rnyqOA5BBL4O983OfeGPqjHWSTneU= github.com/cespare/xxhash/v2 v2.1.1/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= +github.com/cespare/xxhash/v2 v2.3.0 h1:UL815xU9SqsFlibzuggzjXhog7bL6oX9BbNZnL2UFvs= +github.com/cespare/xxhash/v2 v2.3.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= github.com/client9/misspell v0.3.4/go.mod h1:qj6jICC3Q7zFZvVWo7KLAzC3yx5G7kyvSDkc90ppPyw= github.com/cloudwego/base64x v0.1.4 h1:jwCgWpFanWmN8xoIUHa2rtzmkd5J2plF/dnLS6Xd/0Y= github.com/cloudwego/base64x v0.1.4/go.mod h1:0zlkT4Wn5C6NdauXdJRhSKRlJvmclQ1hhJgA0rcu/8w= @@ -39,8 +45,12 @@ github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/dchest/siphash v1.2.3 h1:QXwFc8cFOR2dSa/gE6o/HokBMWtLUaNDVd+22aKHeEA= github.com/dchest/siphash v1.2.3/go.mod h1:0NvQU092bT0ipiFN++/rXm69QG9tVxLAlQHIXMPAkHc= +github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f h1:lO4WD4F/rVNCu3HqELle0jiPLLBs70cWOduZpkS1E78= +github.com/dgryski/go-rendezvous v0.0.0-20200823014737-9f7001d12a5f/go.mod h1:cuUVRXasLTGF7a8hSLbxyZXjz+1KgoB3wDUb6vlszIc= github.com/dlclark/regexp2 v1.11.0 h1:G/nrcoOa7ZXlpoa/91N3X7mM3r8eIlMBBJZvsz/mxKI= github.com/dlclark/regexp2 v1.11.0/go.mod h1:DHkYz0B9wPfa6wondMfaivmHpzrQ3v9q8cnmRbL6yW8= +github.com/dlclark/regexp2 v1.11.5 h1:Q/sSnsKerHeCkc/jSTNq1oCm7KiVgUMZRDUoRu0JQZQ= +github.com/dlclark/regexp2 v1.11.5/go.mod h1:DHkYz0B9wPfa6wondMfaivmHpzrQ3v9q8cnmRbL6yW8= github.com/envoyproxy/go-control-plane v0.9.0/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4= github.com/envoyproxy/go-control-plane v0.9.1-0.20191026205805-5f8ba28d4473/go.mod h1:YTl/9mNaCwkRvm6d1a2C3ymFceY/DCBVvsKhRF0iEA4= github.com/envoyproxy/go-control-plane v0.9.4/go.mod h1:6rpuAdCZL397s3pYoYcLgu1mIlRU8Am5FuJP05cCM98= @@ -49,6 +59,8 @@ github.com/envoyproxy/go-control-plane v0.10.2-0.20220325020618-49ff273808a1/go. github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= github.com/fatih/color v1.17.0 h1:GlRw1BRJxkpqUCBKzKOw098ed57fEsKeNjpTe3cSjK4= github.com/fatih/color v1.17.0/go.mod h1:YZ7TlrGPkiz6ku9fK3TLD/pl3CpsiFyu8N92HLgmosI= +github.com/fatih/color v1.18.0 h1:S8gINlzdQ840/4pfAwic/ZE0djQEH3wM94VfqLTZcOM= +github.com/fatih/color v1.18.0/go.mod h1:4FelSpRwEGDpQ12mAdzqdOukCy4u8WUtOY6lkT/6HfU= github.com/gabriel-vasile/mimetype v1.4.3 h1:in2uUcidCuFcDKtdcBxlR0rJ1+fsokWf+uqxgUFjbI0= github.com/gabriel-vasile/mimetype v1.4.3/go.mod h1:d8uq/6HKRL6CGdk+aubisF/M5GcPfT7nKyLpA0lbSSk= github.com/ghodss/yaml v1.0.0 h1:wQHKEahhL6wmXdzwWG11gIVCkOv05bNOh+Rxn0yngAk= @@ -63,11 +75,13 @@ github.com/go-faster/errors v0.7.1 h1:MkJTnDoEdi9pDabt1dpWf7AA8/BaSYZqibYyhZ20AY github.com/go-faster/errors v0.7.1/go.mod h1:5ySTjWFiphBs07IKuiL69nxdfd5+fzh1u7FPGZP2quo= github.com/go-faster/jx v1.1.0 h1:ZsW3wD+snOdmTDy9eIVgQdjUpXRRV4rqW8NS3t+20bg= github.com/go-faster/jx v1.1.0/go.mod h1:vKDNikrKoyUmpzaJ0OkIkRQClNHFX/nF3dnTJZb3skg= +github.com/go-faster/jx v1.2.0 h1:T2YHJPrFaYu21fJtUxC9GzmluKu8rVIFDwwGBKTDseI= +github.com/go-faster/jx v1.2.0/go.mod h1:UWLOVDmMG597a5tBFPLIWJdUxz5/2emOpfsj9Neg0PE= github.com/go-faster/yaml v0.4.6 h1:lOK/EhI04gCpPgPhgt0bChS6bvw7G3WwI8xxVe0sw9I= github.com/go-faster/yaml v0.4.6/go.mod h1:390dRIvV4zbnO7qC9FGo6YYutc+wyyUSHBgbXL52eXk= github.com/go-logr/logr v1.2.2/go.mod h1:jdQByPbusPIv2/zmleS9BjJVeZ6kBagPoEUsqbVz/1A= -github.com/go-logr/logr v1.4.2 h1:6pFjapn8bFcIbiKo3XT4j/BhANplGihG6tvd+8rYgrY= -github.com/go-logr/logr v1.4.2/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= +github.com/go-logr/logr v1.4.3 h1:CjnDlHq8ikf6E492q6eKboGOC0T8CDaOvkHCIg8idEI= +github.com/go-logr/logr v1.4.3/go.mod h1:9T104GzyrTigFIr8wt5mBrctHMim0Nb2HLGrmQ40KvY= github.com/go-logr/stdr v1.2.2 h1:hSWxHoqTgW2S2qGc0LTAI563KZ5YKYRhT3MFKZMbjag= github.com/go-logr/stdr v1.2.2/go.mod h1:mMo/vtBO5dYbehREoey6XUKy/eSumjCCveDpRre4VKE= github.com/go-openapi/jsonpointer v0.19.3/go.mod h1:Pl9vOtqEWErmShwVjC8pYs9cog34VGT37dQOVbmoatg= @@ -113,8 +127,8 @@ github.com/google/go-cmp v0.4.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/ github.com/google/go-cmp v0.5.0/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.6/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= -github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI= -github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= +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/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= github.com/google/uuid v1.1.2/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.3.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= @@ -140,6 +154,8 @@ github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnr github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= github.com/klauspost/compress v1.17.6 h1:60eq2E/jlfwQXtvZEeBUYADs+BwKBWURIY+Gj2eRGjI= github.com/klauspost/compress v1.17.6/go.mod h1:/dCuZOvVtNoHsyb+cuJD3itjs3NbnF6KH9zAO4BDxPM= +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/cpuid/v2 v2.0.9/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg= github.com/klauspost/cpuid/v2 v2.2.7 h1:ZWSB3igEs+d0qvnxR/ZBzXVmxkgt8DdzP6m9pfuVLDM= github.com/klauspost/cpuid/v2 v2.2.7/go.mod h1:Lcz8mBdAVJIBVzewtcLocK12l3Y+JytZYpaMropDUws= @@ -159,6 +175,8 @@ github.com/mailru/easyjson v0.7.6 h1:8yTIVnZgCoiM1TgqoeTl+LfU5Jg6/xL3QhGQnimLYnA github.com/mailru/easyjson v0.7.6/go.mod h1:xzfreul335JAWq5oZzymOObrkdz5UnU4kGfJJLY9Nlc= github.com/mattn/go-colorable v0.1.13 h1:fFA4WZxdEF4tXPZVKMLwD8oUnCTTo08duU7wxecdEvA= github.com/mattn/go-colorable v0.1.13/go.mod h1:7S9/ev0klgBDR4GtXTXX8a3vIGJpMovkB8vQcUbaXHg= +github.com/mattn/go-colorable v0.1.14 h1:9A9LHSqF/7dyVVX6g0U9cwm9pG3kP9gSzcuIPHPsaIE= +github.com/mattn/go-colorable v0.1.14/go.mod h1:6LmQG8QLFO4G5z1gPvYEzlUgJ2wF+stgPZH1UqBm1s8= github.com/mattn/go-isatty v0.0.16/go.mod h1:kYGgaQfpe5nmfYZH+SKPsOc2e4SrIfOl2e/yFXSvRLM= github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY= github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y= @@ -176,11 +194,15 @@ github.com/nats-io/nuid v1.0.1/go.mod h1:19wcPz3Ph3q0Jbyiqsd0kePYG7A95tJPxeL+1OS github.com/niemeyer/pretty v0.0.0-20200227124842-a10e7caefd8e/go.mod h1:zD1mROLANZcx1PVRCS0qkT7pwLkGfwJo4zjcN/Tysno= github.com/ogen-go/ogen v1.2.1 h1:C5A0lvUMu2wl+eWIxnpXMWnuOJ26a2FyzR1CIC2qG0M= github.com/ogen-go/ogen v1.2.1/go.mod h1:P2zQdEu8UqaVRfD5GEFvl+9q63VjMLvDquq1wVbyInM= +github.com/ogen-go/ogen v1.18.0 h1:6RQ7lFBjOeNaUWu4getfqIh4GJbEY4hqKuzDtec/g60= +github.com/ogen-go/ogen v1.18.0/go.mod h1:dHFr2Wf6cA7tSxMI+zPC21UR5hAlDw8ZYUkK3PziURY= github.com/pelletier/go-toml/v2 v2.2.2 h1:aYUidT7k73Pcl9nb2gScu7NSrKCSHIDE89b3+6Wq+LM= github.com/pelletier/go-toml/v2 v2.2.2/go.mod h1:1t835xjRzz80PqgE6HHgN2JOsmgYu/h4qDAS4n929Rs= github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/prometheus/client_model v0.0.0-20190812154241-14fe0d1b01d4/go.mod h1:xMI15A0UPsDsEKsMN9yxemIoYk6Tm2C1GtYGdfGttqA= +github.com/redis/go-redis/v9 v9.10.0 h1:FxwK3eV8p/CQa0Ch276C7u2d0eNC9kCmAYQ7mCXCzVs= +github.com/redis/go-redis/v9 v9.10.0/go.mod h1:huWgSWd8mW6+m0VPhJjSSQ+d6Nh1VICQ6Q5lHuCH/Iw= github.com/rogpeppe/fastuuid v1.2.0/go.mod h1:jVj6XXZzXRy/MSR5jhDC/2q6DgLz+nrA6LYCDYWNEvQ= github.com/rogpeppe/go-internal v1.14.1 h1:UQB4HGPB6osV0SQTLymcB4TgvyWu6ZyliaW0tI/otEQ= github.com/rogpeppe/go-internal v1.14.1/go.mod h1:MaRKkUm5W0goXpeCfT7UZI6fk/L7L7so1lCWt35ZSgc= @@ -188,6 +210,10 @@ github.com/russross/blackfriday/v2 v2.1.0 h1:JIOH55/0cWyOuilr9/qlrm0BSXldqnqwMsf github.com/russross/blackfriday/v2 v2.1.0/go.mod h1:+Rmxgy9KzJVeS9/2gXHxylqXiyQDYRxCVz55jmeOWTM= github.com/segmentio/asm v1.2.0 h1:9BQrFxC+YOHJlTlHGkTrFWf59nbL3XnCoFLTwDCI7ys= github.com/segmentio/asm v1.2.0/go.mod h1:BqMnlJP91P8d+4ibuonYZw9mfnzI9HfxselHZr5aAcs= +github.com/segmentio/asm v1.2.1 h1:DTNbBqs57ioxAD4PrArqftgypG4/qNpXoJx8TVXxPR0= +github.com/segmentio/asm v1.2.1/go.mod h1:BqMnlJP91P8d+4ibuonYZw9mfnzI9HfxselHZr5aAcs= +github.com/shopspring/decimal v1.4.0 h1:bxl37RwXBklmTi0C79JfXCEBD1cqqHt0bbgBAGFp81k= +github.com/shopspring/decimal v1.4.0/go.mod h1:gawqmDU56v4yIKSwfBSFip1HdCCXN8/+DMd9qYNcwME= github.com/sirupsen/logrus v1.8.1/go.mod h1:yWOB1SBYBC5VeMP7gHvWumXLIWorT60ONWic61uBYv0= github.com/sirupsen/logrus v1.9.3 h1:dueUQJ1C2q9oE3F7wvmSGAaVtTmUizReu6fjN8uqzbQ= github.com/sirupsen/logrus v1.9.3/go.mod h1:naHLuLoDiP4jHNo9R0sCBMtWGeIprob74mVsIT4qYEQ= @@ -204,8 +230,9 @@ github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/ github.com/stretchr/testify v1.8.0/go.mod h1:yNjHg4UonilssWZ8iaSj1OCr/vHnekPRkoO+kdMU+MU= github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o6fzry7u4= github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= -github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= +github.com/stretchr/testify v1.11.1 h1:7s2iGBzp5EwR7/aIZr8ao5+dra3wiQyKjjFuvgVKu7U= +github.com/stretchr/testify v1.11.1/go.mod h1:wZwfW3scLgRK+23gO65QZefKpKQRnfz6sD981Nm4B6U= github.com/swaggo/files v1.0.1 h1:J1bVJ4XHZNq0I46UU90611i9/YzdrF7x92oX1ig5IdE= github.com/swaggo/files v1.0.1/go.mod h1:0qXmMNH6sXNf+73t65aKeB+ApmgxdnkQzVTAj2uaMUg= github.com/swaggo/gin-swagger v1.6.0 h1:y8sxvQ3E20/RCyrXeFfg60r6H0Z+SwpTjMYsMm+zy8M= @@ -221,12 +248,14 @@ github.com/urfave/cli/v2 v2.27.6/go.mod h1:3Sevf16NykTbInEnD0yKkjDAeZDS0A6bzhBH5 github.com/xrash/smetrics v0.0.0-20240521201337-686a1a2994c1 h1:gEOO8jv9F4OT7lGCjxCBTO/36wtF6j2nSip77qHd4x4= github.com/xrash/smetrics v0.0.0-20240521201337-686a1a2994c1/go.mod h1:Ohn+xnUBiLI6FVj/9LpzZWtj1/D6lUovWYBkxHVV3aM= github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY= -go.opentelemetry.io/otel v1.32.0 h1:WnBN+Xjcteh0zdk01SVqV55d/m62NJLJdIyb4y/WO5U= -go.opentelemetry.io/otel v1.32.0/go.mod h1:00DCVSB0RQcnzlwyTfqtxSm+DRr9hpYrHjNGiBHVQIg= -go.opentelemetry.io/otel/metric v1.32.0 h1:xV2umtmNcThh2/a/aCP+h64Xx5wsj8qqnkYZktzNa0M= -go.opentelemetry.io/otel/metric v1.32.0/go.mod h1:jH7CIbbK6SH2V2wE16W05BHCtIDzauciCRLoc/SyMv8= -go.opentelemetry.io/otel/trace v1.32.0 h1:WIC9mYrXf8TmY/EXuULKc8hR17vE+Hjv2cssQDe03fM= -go.opentelemetry.io/otel/trace v1.32.0/go.mod h1:+i4rkvCraA+tG6AzwloGaCtkx53Fa+L+V8e9a7YvhT8= +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.39.0 h1:8yPrr/S0ND9QEfTfdP9V+SiwT4E0G7Y5MO7p85nis48= +go.opentelemetry.io/otel v1.39.0/go.mod h1:kLlFTywNWrFyEdH0oj2xK0bFYZtHRYUdv1NklR/tgc8= +go.opentelemetry.io/otel/metric v1.39.0 h1:d1UzonvEZriVfpNKEVmHXbdf909uGTOQjA0HF0Ls5Q0= +go.opentelemetry.io/otel/metric v1.39.0/go.mod h1:jrZSWL33sD7bBxg1xjrqyDjnuzTUB0x1nBERXd7Ftcs= +go.opentelemetry.io/otel/trace v1.39.0 h1:2d2vfpEDmCJ5zVYz7ijaJdOF59xLomrvj7bjt6/qCJI= +go.opentelemetry.io/otel/trace v1.39.0/go.mod h1:88w4/PnZSazkGzz/w84VHpQafiU4EtqqlVdxWy+rNOA= go.opentelemetry.io/proto/otlp v0.7.0/go.mod h1:PqfVotwruBrMGOCsRd/89rSnXhoiJIqeYNgFYFoEGnI= go.uber.org/goleak v1.3.0 h1:2K3zAYmnTNqV73imy9J1T3WC+gmCePx2hEGkimedGto= go.uber.org/goleak v1.3.0/go.mod h1:CoHD4mav9JJNrW/WLlf7HGZPjdw8EucARQHekz1X6bE= @@ -234,6 +263,8 @@ go.uber.org/multierr v1.11.0 h1:blXXJkSxSSfBVBlC76pxqeO+LN3aDfLQo+309xJstO0= go.uber.org/multierr v1.11.0/go.mod h1:20+QtiLqy0Nd6FdQB9TLXag12DsQkrbs3htMFfDN80Y= go.uber.org/zap v1.27.0 h1:aJMhYGrd5QSmlpLMr2MftRKl7t8J8PTZPA732ud/XR8= go.uber.org/zap v1.27.0/go.mod h1:GB2qFLM7cTU87MWRP2mPIjqfIDnGu+VIO4V/SdhGo2E= +go.uber.org/zap v1.27.1 h1:08RqriUEv8+ArZRYSTXy1LeBScaMpVSTBhCeaZYfMYc= +go.uber.org/zap v1.27.1/go.mod h1:GB2qFLM7cTU87MWRP2mPIjqfIDnGu+VIO4V/SdhGo2E= golang.org/x/arch v0.0.0-20210923205945-b76863e36670/go.mod h1:5om86z9Hs0C8fWVUuoMHwpExlXzs5Tkyp9hOrfG7pp8= golang.org/x/arch v0.8.0 h1:3wRIsP3pM4yUptoR96otTUOXI367OS0+c9eeRi9doIc= golang.org/x/arch v0.8.0/go.mod h1:FEVrYAQjsQXMVJ1nsMoVVXPZg6p2JE2mx8psSWTDQys= @@ -242,15 +273,21 @@ golang.org/x/crypto v0.0.0-20200622213623-75b288015ac9/go.mod h1:LzIPMQfyMNhhGPh golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc= golang.org/x/crypto v0.32.0 h1:euUpcYgM8WcP71gNpTqQCn6rC2t6ULUPiOzfWaXVVfc= golang.org/x/crypto v0.32.0/go.mod h1:ZnnJkOaASj8g0AjIduWNlq2NRxL0PlBrbKVyZ6V/Ugc= +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/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20240531132922-fd00a4e0eefc h1:O9NuF4s+E/PvMIy+9IUZB9znFwUIXEWSstNjek6VpVg= golang.org/x/exp v0.0.0-20240531132922-fd00a4e0eefc/go.mod h1:XtvwrStGgqGPLc4cjQfWqZHG1YFdYs6swckp8vpsjnc= +golang.org/x/exp v0.0.0-20251219203646-944ab1f22d93 h1:fQsdNF2N+/YewlRZiricy4P1iimyPKZ/xwniHj8Q2a0= +golang.org/x/exp v0.0.0-20251219203646-944ab1f22d93/go.mod h1:EPRbTFwzwjXj9NpYyyrvenVh9Y+GFeEvMNh7Xuz7xgU= golang.org/x/lint v0.0.0-20181026193005-c67002cb31c3/go.mod h1:UVdnD1Gm6xHRNCYTkRU2/jEulfH38KcIWyp/GAMgvoE= golang.org/x/lint v0.0.0-20190227174305-5b3e6a55c961/go.mod h1:wehouNa3lNwaWXcvxsM5YxQ5yQlVC4a0KAMCusXpPoU= golang.org/x/lint v0.0.0-20190313153728-d0100b6bd8b3/go.mod h1:6SW0HCj/g11FgYtHlgUYUwCkIfeOF89ocIRzGO/8vkc= golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4= golang.org/x/mod v0.17.0 h1:zY54UmvipHiNd+pm+m0x9KhZ9hl1/7QNMyxXbc6ICqA= golang.org/x/mod v0.17.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c= +golang.org/x/mod v0.31.0 h1:HaW9xtz0+kOcWKwli0ZXy79Ix+UW/vOfmWI5QVd2tgI= +golang.org/x/mod v0.31.0/go.mod h1:43JraMp9cGx1Rx3AqioxrbrhNsLl2l/iNAvuBkrezpg= golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20190108225652-1e06a53dbb7e/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= @@ -266,6 +303,8 @@ golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug golang.org/x/net v0.7.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs= golang.org/x/net v0.34.0 h1:Mb7Mrk043xzHgnRM88suvJFwzVrRfHEHJEl5/71CKw0= golang.org/x/net v0.34.0/go.mod h1:di0qlW3YNM5oh6GqDGQr92MyTozJPmybPK4Ev/Gm31k= +golang.org/x/net v0.48.0 h1:zyQRTTrjc33Lhh0fBgT/H3oZq9WuvRR5gPC70xpDiQU= +golang.org/x/net v0.48.0/go.mod h1:+ndRgGjkh8FGtu1w1FGbEC31if4VrNVMuKTgcAAnQRY= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20200107190931-bf48bf16ab8d/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -275,6 +314,8 @@ golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJ golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.12.0 h1:MHc5BpPuC30uJk597Ri8TV3CNZcTLu6B6z4lJy+g6Jw= golang.org/x/sync v0.12.0/go.mod h1:1dzgHSNfp02xaA81J2MS99Qcpr2w7fw1gpm99rleRqA= +golang.org/x/sync v0.19.0 h1:vV+1eWNmZ5geRlYjzm2adRgW2/mcpevXNg50YZtPCE4= +golang.org/x/sync v0.19.0/go.mod h1:9KTHXmSnoGruLpwFjVSX0lNNA75CykiMECbovNTZqGI= golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -293,6 +334,8 @@ golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.29.0 h1:TPYlXGxvx1MGTn2GiZDhnjPA9wZzZeGKHHmKhHYvgaU= golang.org/x/sys v0.29.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= +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.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k= @@ -303,6 +346,8 @@ golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= golang.org/x/text v0.23.0 h1:D71I7dUrlY+VX0gQShAThNGHFxZ13dGLBHQLVl1mJlY= golang.org/x/text v0.23.0/go.mod h1:/BLNzu4aZCJ1+kcD0DNRotWKage4q2rGVAg4o22unh4= +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-20190114222345-bf090417da8b/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20190226205152-f727befe758c/go.mod h1:9Yl7xja0Znq3iFh3HoIrodX9oNMXvdceNzlUR8zjMvY= @@ -312,6 +357,8 @@ golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtn golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc= golang.org/x/tools v0.21.1-0.20240508182429-e35e4ccd0d2d h1:vU5i/LfpvrRCpgM/VPfJLg5KjxD3E+hfT1SH+d9zLwg= golang.org/x/tools v0.21.1-0.20240508182429-e35e4ccd0d2d/go.mod h1:aiJjzUbINMkxbQROHiO6hDPo2LHcIPhhQsa9DLh0yGk= +golang.org/x/tools v0.40.0 h1:yLkxfA+Qnul4cs9QA3KnlFu0lVmd8JJfoq+E41uSutA= +golang.org/x/tools v0.40.0/go.mod h1:Ik/tzLRlbscWpqqMRjyWYDisX8bG13FrdXp3o4Sr9lc= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= diff --git a/openapi.yaml b/openapi.yaml index 2cc7b7d..cc02f0b 100644 --- a/openapi.yaml +++ b/openapi.yaml @@ -1438,6 +1438,180 @@ paths: application/json: schema: $ref: "#/components/schemas/Error" + /thumbnails/assets: + post: + summary: Batch fetch asset thumbnails + operationId: batchAssetThumbnails + tags: + - Thumbnails + security: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - assetIds + properties: + assetIds: + type: array + items: + type: integer + format: uint64 + maxItems: 100 + description: Array of asset IDs (max 100) + size: + type: string + enum: + - "150x150" + - "420x420" + - "768x432" + default: "420x420" + description: Thumbnail size + responses: + "200": + description: Successful response + content: + application/json: + schema: + type: object + properties: + thumbnails: + type: object + additionalProperties: + type: string + description: Map of asset ID to thumbnail URL + default: + description: General Error + content: + application/json: + schema: + $ref: "#/components/schemas/Error" + /thumbnails/asset/{AssetID}: + get: + summary: Get single asset thumbnail + operationId: getAssetThumbnail + tags: + - Thumbnails + security: [] + parameters: + - name: AssetID + in: path + required: true + schema: + type: integer + format: uint64 + - name: size + in: query + schema: + type: string + enum: + - "150x150" + - "420x420" + - "768x432" + default: "420x420" + responses: + "302": + description: Redirect to thumbnail URL + headers: + Location: + description: URL to redirect to + schema: + type: string + default: + description: General Error + content: + application/json: + schema: + $ref: "#/components/schemas/Error" + /thumbnails/users: + post: + summary: Batch fetch user avatar thumbnails + operationId: batchUserThumbnails + tags: + - Thumbnails + security: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - userIds + properties: + userIds: + type: array + items: + type: integer + format: uint64 + maxItems: 100 + description: Array of user IDs (max 100) + size: + type: string + enum: + - "150x150" + - "420x420" + - "768x432" + default: "150x150" + description: Thumbnail size + responses: + "200": + description: Successful response + content: + application/json: + schema: + type: object + properties: + thumbnails: + type: object + additionalProperties: + type: string + description: Map of user ID to thumbnail URL + default: + description: General Error + content: + application/json: + schema: + $ref: "#/components/schemas/Error" + /thumbnails/user/{UserID}: + get: + summary: Get single user avatar thumbnail + operationId: getUserThumbnail + tags: + - Thumbnails + security: [] + parameters: + - name: UserID + in: path + required: true + schema: + type: integer + format: uint64 + - name: size + in: query + schema: + type: string + enum: + - "150x150" + - "420x420" + - "768x432" + default: "150x150" + responses: + "302": + description: Redirect to thumbnail URL + headers: + Location: + description: URL to redirect to + schema: + type: string + default: + description: General Error + content: + application/json: + schema: + $ref: "#/components/schemas/Error" components: securitySchemes: cookieAuth: diff --git a/pkg/api/oas_cfg_gen.go b/pkg/api/oas_cfg_gen.go index fc3ff34..5dafb54 100644 --- a/pkg/api/oas_cfg_gen.go +++ b/pkg/api/oas_cfg_gen.go @@ -5,14 +5,14 @@ package api import ( "net/http" - "go.opentelemetry.io/otel" - "go.opentelemetry.io/otel/metric" - "go.opentelemetry.io/otel/trace" - ht "github.com/ogen-go/ogen/http" "github.com/ogen-go/ogen/middleware" "github.com/ogen-go/ogen/ogenerrors" "github.com/ogen-go/ogen/otelogen" + "go.opentelemetry.io/otel" + "go.opentelemetry.io/otel/attribute" + "go.opentelemetry.io/otel/metric" + "go.opentelemetry.io/otel/trace" ) var ( @@ -32,6 +32,7 @@ type otelConfig struct { Tracer trace.Tracer MeterProvider metric.MeterProvider Meter metric.Meter + Attributes []attribute.KeyValue } func (cfg *otelConfig) initOTEL() { @@ -215,6 +216,13 @@ func WithMeterProvider(provider metric.MeterProvider) Option { }) } +// WithAttributes specifies default otel attributes. +func WithAttributes(attributes ...attribute.KeyValue) Option { + return otelOptionFunc(func(cfg *otelConfig) { + cfg.Attributes = attributes + }) +} + // WithClient specifies http client to use. func WithClient(client ht.Client) ClientOption { return optionFunc[clientConfig](func(cfg *clientConfig) { diff --git a/pkg/api/oas_client_gen.go b/pkg/api/oas_client_gen.go index bc5d28a..7716981 100644 --- a/pkg/api/oas_client_gen.go +++ b/pkg/api/oas_client_gen.go @@ -9,17 +9,16 @@ import ( "time" "github.com/go-faster/errors" - "go.opentelemetry.io/otel/attribute" - "go.opentelemetry.io/otel/codes" - "go.opentelemetry.io/otel/metric" - semconv "go.opentelemetry.io/otel/semconv/v1.26.0" - "go.opentelemetry.io/otel/trace" - "github.com/ogen-go/ogen/conv" ht "github.com/ogen-go/ogen/http" "github.com/ogen-go/ogen/ogenerrors" "github.com/ogen-go/ogen/otelogen" "github.com/ogen-go/ogen/uri" + "go.opentelemetry.io/otel/attribute" + "go.opentelemetry.io/otel/codes" + "go.opentelemetry.io/otel/metric" + semconv "go.opentelemetry.io/otel/semconv/v1.37.0" + "go.opentelemetry.io/otel/trace" ) func trimTrailingSlashes(u *url.URL) { @@ -176,6 +175,18 @@ type Invoker interface { // // POST /submissions/{SubmissionID}/status/reset-uploading ActionSubmissionValidated(ctx context.Context, params ActionSubmissionValidatedParams) error + // BatchAssetThumbnails invokes batchAssetThumbnails operation. + // + // Batch fetch asset thumbnails. + // + // POST /thumbnails/assets + BatchAssetThumbnails(ctx context.Context, request *BatchAssetThumbnailsReq) (*BatchAssetThumbnailsOK, error) + // BatchUserThumbnails invokes batchUserThumbnails operation. + // + // Batch fetch user avatar thumbnails. + // + // POST /thumbnails/users + BatchUserThumbnails(ctx context.Context, request *BatchUserThumbnailsReq) (*BatchUserThumbnailsOK, error) // CreateMapfix invokes createMapfix operation. // // Trigger the validator to create a mapfix. @@ -236,6 +247,12 @@ type Invoker interface { // // GET /maps/{MapID}/download DownloadMapAsset(ctx context.Context, params DownloadMapAssetParams) (DownloadMapAssetOK, error) + // GetAssetThumbnail invokes getAssetThumbnail operation. + // + // Get single asset thumbnail. + // + // GET /thumbnails/asset/{AssetID} + GetAssetThumbnail(ctx context.Context, params GetAssetThumbnailParams) (*GetAssetThumbnailFound, error) // GetMap invokes getMap operation. // // Retrieve map with ID. @@ -272,6 +289,12 @@ type Invoker interface { // // GET /submissions/{SubmissionID} GetSubmission(ctx context.Context, params GetSubmissionParams) (*Submission, error) + // GetUserThumbnail invokes getUserThumbnail operation. + // + // Get single user avatar thumbnail. + // + // GET /thumbnails/user/{UserID} + GetUserThumbnail(ctx context.Context, params GetUserThumbnailParams) (*GetUserThumbnailFound, error) // ListMapfixAuditEvents invokes listMapfixAuditEvents operation. // // Retrieve a list of audit events. @@ -439,8 +462,9 @@ func (c *Client) sendActionMapfixAccepted(ctx context.Context, params ActionMapf otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixAccepted"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/reset-validating"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/reset-validating"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -563,8 +587,9 @@ func (c *Client) sendActionMapfixReject(ctx context.Context, params ActionMapfix otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixReject"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/reject"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/reject"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -687,8 +712,9 @@ func (c *Client) sendActionMapfixRequestChanges(ctx context.Context, params Acti otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixRequestChanges"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/request-changes"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/request-changes"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -812,8 +838,9 @@ func (c *Client) sendActionMapfixResetSubmitting(ctx context.Context, params Act otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixResetSubmitting"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/reset-submitting"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/reset-submitting"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -936,8 +963,9 @@ func (c *Client) sendActionMapfixRetryValidate(ctx context.Context, params Actio otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixRetryValidate"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/retry-validate"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/retry-validate"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -1060,8 +1088,9 @@ func (c *Client) sendActionMapfixRevoke(ctx context.Context, params ActionMapfix otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixRevoke"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/revoke"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/revoke"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -1184,8 +1213,9 @@ func (c *Client) sendActionMapfixTriggerRelease(ctx context.Context, params Acti otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixTriggerRelease"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/trigger-release"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/trigger-release"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -1308,8 +1338,9 @@ func (c *Client) sendActionMapfixTriggerSubmit(ctx context.Context, params Actio otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixTriggerSubmit"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/trigger-submit"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/trigger-submit"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -1432,8 +1463,9 @@ func (c *Client) sendActionMapfixTriggerSubmitUnchecked(ctx context.Context, par otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixTriggerSubmitUnchecked"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/trigger-submit-unchecked"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/trigger-submit-unchecked"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -1556,8 +1588,9 @@ func (c *Client) sendActionMapfixTriggerUpload(ctx context.Context, params Actio otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixTriggerUpload"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/trigger-upload"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/trigger-upload"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -1680,8 +1713,9 @@ func (c *Client) sendActionMapfixTriggerValidate(ctx context.Context, params Act otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixTriggerValidate"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/trigger-validate"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/trigger-validate"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -1804,8 +1838,9 @@ func (c *Client) sendActionMapfixUploaded(ctx context.Context, params ActionMapf otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixUploaded"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/reset-releasing"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/reset-releasing"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -1928,8 +1963,9 @@ func (c *Client) sendActionMapfixValidated(ctx context.Context, params ActionMap otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionMapfixValidated"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/status/reset-uploading"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/status/reset-uploading"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -2052,8 +2088,9 @@ func (c *Client) sendActionSubmissionAccepted(ctx context.Context, params Action otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionSubmissionAccepted"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/status/reset-validating"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/status/reset-validating"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -2176,8 +2213,9 @@ func (c *Client) sendActionSubmissionReject(ctx context.Context, params ActionSu otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionSubmissionReject"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/status/reject"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/status/reject"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -2300,8 +2338,9 @@ func (c *Client) sendActionSubmissionRequestChanges(ctx context.Context, params otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionSubmissionRequestChanges"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/status/request-changes"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/status/request-changes"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -2425,8 +2464,9 @@ func (c *Client) sendActionSubmissionResetSubmitting(ctx context.Context, params otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionSubmissionResetSubmitting"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/status/reset-submitting"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/status/reset-submitting"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -2549,8 +2589,9 @@ func (c *Client) sendActionSubmissionRetryValidate(ctx context.Context, params A otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionSubmissionRetryValidate"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/status/retry-validate"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/status/retry-validate"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -2673,8 +2714,9 @@ func (c *Client) sendActionSubmissionRevoke(ctx context.Context, params ActionSu otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionSubmissionRevoke"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/status/revoke"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/status/revoke"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -2797,8 +2839,9 @@ func (c *Client) sendActionSubmissionTriggerSubmit(ctx context.Context, params A otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionSubmissionTriggerSubmit"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/status/trigger-submit"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/status/trigger-submit"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -2921,8 +2964,9 @@ func (c *Client) sendActionSubmissionTriggerSubmitUnchecked(ctx context.Context, otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionSubmissionTriggerSubmitUnchecked"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/status/trigger-submit-unchecked"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/status/trigger-submit-unchecked"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -3045,8 +3089,9 @@ func (c *Client) sendActionSubmissionTriggerUpload(ctx context.Context, params A otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionSubmissionTriggerUpload"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/status/trigger-upload"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/status/trigger-upload"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -3169,8 +3214,9 @@ func (c *Client) sendActionSubmissionTriggerValidate(ctx context.Context, params otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionSubmissionTriggerValidate"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/status/trigger-validate"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/status/trigger-validate"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -3294,8 +3340,9 @@ func (c *Client) sendActionSubmissionValidated(ctx context.Context, params Actio otelAttrs := []attribute.KeyValue{ otelogen.OperationID("actionSubmissionValidated"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/status/reset-uploading"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/status/reset-uploading"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -3404,6 +3451,158 @@ func (c *Client) sendActionSubmissionValidated(ctx context.Context, params Actio return result, nil } +// BatchAssetThumbnails invokes batchAssetThumbnails operation. +// +// Batch fetch asset thumbnails. +// +// POST /thumbnails/assets +func (c *Client) BatchAssetThumbnails(ctx context.Context, request *BatchAssetThumbnailsReq) (*BatchAssetThumbnailsOK, error) { + res, err := c.sendBatchAssetThumbnails(ctx, request) + return res, err +} + +func (c *Client) sendBatchAssetThumbnails(ctx context.Context, request *BatchAssetThumbnailsReq) (res *BatchAssetThumbnailsOK, err error) { + otelAttrs := []attribute.KeyValue{ + otelogen.OperationID("batchAssetThumbnails"), + semconv.HTTPRequestMethodKey.String("POST"), + semconv.URLTemplateKey.String("/thumbnails/assets"), + } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) + + // Run stopwatch. + startTime := time.Now() + defer func() { + // Use floating point division here for higher precision (instead of Millisecond method). + elapsedDuration := time.Since(startTime) + c.duration.Record(ctx, float64(elapsedDuration)/float64(time.Millisecond), metric.WithAttributes(otelAttrs...)) + }() + + // Increment request counter. + c.requests.Add(ctx, 1, metric.WithAttributes(otelAttrs...)) + + // Start a span for this request. + ctx, span := c.cfg.Tracer.Start(ctx, BatchAssetThumbnailsOperation, + trace.WithAttributes(otelAttrs...), + clientSpanKind, + ) + // Track stage for error reporting. + var stage string + defer func() { + if err != nil { + span.RecordError(err) + span.SetStatus(codes.Error, stage) + c.errors.Add(ctx, 1, metric.WithAttributes(otelAttrs...)) + } + span.End() + }() + + stage = "BuildURL" + u := uri.Clone(c.requestURL(ctx)) + var pathParts [1]string + pathParts[0] = "/thumbnails/assets" + uri.AddPathParts(u, pathParts[:]...) + + stage = "EncodeRequest" + r, err := ht.NewRequest(ctx, "POST", u) + if err != nil { + return res, errors.Wrap(err, "create request") + } + if err := encodeBatchAssetThumbnailsRequest(request, r); err != nil { + return res, errors.Wrap(err, "encode request") + } + + stage = "SendRequest" + resp, err := c.cfg.Client.Do(r) + if err != nil { + return res, errors.Wrap(err, "do request") + } + defer resp.Body.Close() + + stage = "DecodeResponse" + result, err := decodeBatchAssetThumbnailsResponse(resp) + if err != nil { + return res, errors.Wrap(err, "decode response") + } + + return result, nil +} + +// BatchUserThumbnails invokes batchUserThumbnails operation. +// +// Batch fetch user avatar thumbnails. +// +// POST /thumbnails/users +func (c *Client) BatchUserThumbnails(ctx context.Context, request *BatchUserThumbnailsReq) (*BatchUserThumbnailsOK, error) { + res, err := c.sendBatchUserThumbnails(ctx, request) + return res, err +} + +func (c *Client) sendBatchUserThumbnails(ctx context.Context, request *BatchUserThumbnailsReq) (res *BatchUserThumbnailsOK, err error) { + otelAttrs := []attribute.KeyValue{ + otelogen.OperationID("batchUserThumbnails"), + semconv.HTTPRequestMethodKey.String("POST"), + semconv.URLTemplateKey.String("/thumbnails/users"), + } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) + + // Run stopwatch. + startTime := time.Now() + defer func() { + // Use floating point division here for higher precision (instead of Millisecond method). + elapsedDuration := time.Since(startTime) + c.duration.Record(ctx, float64(elapsedDuration)/float64(time.Millisecond), metric.WithAttributes(otelAttrs...)) + }() + + // Increment request counter. + c.requests.Add(ctx, 1, metric.WithAttributes(otelAttrs...)) + + // Start a span for this request. + ctx, span := c.cfg.Tracer.Start(ctx, BatchUserThumbnailsOperation, + trace.WithAttributes(otelAttrs...), + clientSpanKind, + ) + // Track stage for error reporting. + var stage string + defer func() { + if err != nil { + span.RecordError(err) + span.SetStatus(codes.Error, stage) + c.errors.Add(ctx, 1, metric.WithAttributes(otelAttrs...)) + } + span.End() + }() + + stage = "BuildURL" + u := uri.Clone(c.requestURL(ctx)) + var pathParts [1]string + pathParts[0] = "/thumbnails/users" + uri.AddPathParts(u, pathParts[:]...) + + stage = "EncodeRequest" + r, err := ht.NewRequest(ctx, "POST", u) + if err != nil { + return res, errors.Wrap(err, "create request") + } + if err := encodeBatchUserThumbnailsRequest(request, r); err != nil { + return res, errors.Wrap(err, "encode request") + } + + stage = "SendRequest" + resp, err := c.cfg.Client.Do(r) + if err != nil { + return res, errors.Wrap(err, "do request") + } + defer resp.Body.Close() + + stage = "DecodeResponse" + result, err := decodeBatchUserThumbnailsResponse(resp) + if err != nil { + return res, errors.Wrap(err, "decode response") + } + + return result, nil +} + // CreateMapfix invokes createMapfix operation. // // Trigger the validator to create a mapfix. @@ -3418,8 +3617,9 @@ func (c *Client) sendCreateMapfix(ctx context.Context, request *MapfixTriggerCre otelAttrs := []attribute.KeyValue{ otelogen.OperationID("createMapfix"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes"), + semconv.URLTemplateKey.String("/mapfixes"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -3526,8 +3726,9 @@ func (c *Client) sendCreateMapfixAuditComment(ctx context.Context, request Creat otelAttrs := []attribute.KeyValue{ otelogen.OperationID("createMapfixAuditComment"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/comment"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/comment"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -3653,8 +3854,9 @@ func (c *Client) sendCreateScript(ctx context.Context, request *ScriptCreate) (r otelAttrs := []attribute.KeyValue{ otelogen.OperationID("createScript"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/scripts"), + semconv.URLTemplateKey.String("/scripts"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -3761,8 +3963,9 @@ func (c *Client) sendCreateScriptPolicy(ctx context.Context, request *ScriptPoli otelAttrs := []attribute.KeyValue{ otelogen.OperationID("createScriptPolicy"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/script-policy"), + semconv.URLTemplateKey.String("/script-policy"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -3869,8 +4072,9 @@ func (c *Client) sendCreateSubmission(ctx context.Context, request *SubmissionTr otelAttrs := []attribute.KeyValue{ otelogen.OperationID("createSubmission"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions"), + semconv.URLTemplateKey.String("/submissions"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -3977,8 +4181,9 @@ func (c *Client) sendCreateSubmissionAdmin(ctx context.Context, request *Submiss otelAttrs := []attribute.KeyValue{ otelogen.OperationID("createSubmissionAdmin"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions-admin"), + semconv.URLTemplateKey.String("/submissions-admin"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -4085,8 +4290,9 @@ func (c *Client) sendCreateSubmissionAuditComment(ctx context.Context, request C otelAttrs := []attribute.KeyValue{ otelogen.OperationID("createSubmissionAuditComment"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/comment"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/comment"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -4212,8 +4418,9 @@ func (c *Client) sendDeleteScript(ctx context.Context, params DeleteScriptParams otelAttrs := []attribute.KeyValue{ otelogen.OperationID("deleteScript"), semconv.HTTPRequestMethodKey.String("DELETE"), - semconv.HTTPRouteKey.String("/scripts/{ScriptID}"), + semconv.URLTemplateKey.String("/scripts/{ScriptID}"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -4335,8 +4542,9 @@ func (c *Client) sendDeleteScriptPolicy(ctx context.Context, params DeleteScript otelAttrs := []attribute.KeyValue{ otelogen.OperationID("deleteScriptPolicy"), semconv.HTTPRequestMethodKey.String("DELETE"), - semconv.HTTPRouteKey.String("/script-policy/{ScriptPolicyID}"), + semconv.URLTemplateKey.String("/script-policy/{ScriptPolicyID}"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -4458,8 +4666,9 @@ func (c *Client) sendDownloadMapAsset(ctx context.Context, params DownloadMapAss otelAttrs := []attribute.KeyValue{ otelogen.OperationID("downloadMapAsset"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/maps/{MapID}/download"), + semconv.URLTemplateKey.String("/maps/{MapID}/download"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -4568,6 +4777,118 @@ func (c *Client) sendDownloadMapAsset(ctx context.Context, params DownloadMapAss return result, nil } +// GetAssetThumbnail invokes getAssetThumbnail operation. +// +// Get single asset thumbnail. +// +// GET /thumbnails/asset/{AssetID} +func (c *Client) GetAssetThumbnail(ctx context.Context, params GetAssetThumbnailParams) (*GetAssetThumbnailFound, error) { + res, err := c.sendGetAssetThumbnail(ctx, params) + return res, err +} + +func (c *Client) sendGetAssetThumbnail(ctx context.Context, params GetAssetThumbnailParams) (res *GetAssetThumbnailFound, err error) { + otelAttrs := []attribute.KeyValue{ + otelogen.OperationID("getAssetThumbnail"), + semconv.HTTPRequestMethodKey.String("GET"), + semconv.URLTemplateKey.String("/thumbnails/asset/{AssetID}"), + } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) + + // Run stopwatch. + startTime := time.Now() + defer func() { + // Use floating point division here for higher precision (instead of Millisecond method). + elapsedDuration := time.Since(startTime) + c.duration.Record(ctx, float64(elapsedDuration)/float64(time.Millisecond), metric.WithAttributes(otelAttrs...)) + }() + + // Increment request counter. + c.requests.Add(ctx, 1, metric.WithAttributes(otelAttrs...)) + + // Start a span for this request. + ctx, span := c.cfg.Tracer.Start(ctx, GetAssetThumbnailOperation, + trace.WithAttributes(otelAttrs...), + clientSpanKind, + ) + // Track stage for error reporting. + var stage string + defer func() { + if err != nil { + span.RecordError(err) + span.SetStatus(codes.Error, stage) + c.errors.Add(ctx, 1, metric.WithAttributes(otelAttrs...)) + } + span.End() + }() + + stage = "BuildURL" + u := uri.Clone(c.requestURL(ctx)) + var pathParts [2]string + pathParts[0] = "/thumbnails/asset/" + { + // Encode "AssetID" parameter. + e := uri.NewPathEncoder(uri.PathEncoderConfig{ + Param: "AssetID", + Style: uri.PathStyleSimple, + Explode: false, + }) + if err := func() error { + return e.EncodeValue(conv.Uint64ToString(params.AssetID)) + }(); err != nil { + return res, errors.Wrap(err, "encode path") + } + encoded, err := e.Result() + if err != nil { + return res, errors.Wrap(err, "encode path") + } + pathParts[1] = encoded + } + uri.AddPathParts(u, pathParts[:]...) + + stage = "EncodeQueryParams" + q := uri.NewQueryEncoder() + { + // Encode "size" parameter. + cfg := uri.QueryParameterEncodingConfig{ + Name: "size", + Style: uri.QueryStyleForm, + Explode: true, + } + + if err := q.EncodeParam(cfg, func(e uri.Encoder) error { + if val, ok := params.Size.Get(); ok { + return e.EncodeValue(conv.StringToString(string(val))) + } + return nil + }); err != nil { + return res, errors.Wrap(err, "encode query") + } + } + u.RawQuery = q.Values().Encode() + + stage = "EncodeRequest" + r, err := ht.NewRequest(ctx, "GET", u) + if err != nil { + return res, errors.Wrap(err, "create request") + } + + stage = "SendRequest" + resp, err := c.cfg.Client.Do(r) + if err != nil { + return res, errors.Wrap(err, "do request") + } + defer resp.Body.Close() + + stage = "DecodeResponse" + result, err := decodeGetAssetThumbnailResponse(resp) + if err != nil { + return res, errors.Wrap(err, "decode response") + } + + return result, nil +} + // GetMap invokes getMap operation. // // Retrieve map with ID. @@ -4582,8 +4903,9 @@ func (c *Client) sendGetMap(ctx context.Context, params GetMapParams) (res *Map, otelAttrs := []attribute.KeyValue{ otelogen.OperationID("getMap"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/maps/{MapID}"), + semconv.URLTemplateKey.String("/maps/{MapID}"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -4672,8 +4994,9 @@ func (c *Client) sendGetMapfix(ctx context.Context, params GetMapfixParams) (res otelAttrs := []attribute.KeyValue{ otelogen.OperationID("getMapfix"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -4762,8 +5085,9 @@ func (c *Client) sendGetOperation(ctx context.Context, params GetOperationParams otelAttrs := []attribute.KeyValue{ otelogen.OperationID("getOperation"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/operations/{OperationID}"), + semconv.URLTemplateKey.String("/operations/{OperationID}"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -4885,8 +5209,9 @@ func (c *Client) sendGetScript(ctx context.Context, params GetScriptParams) (res otelAttrs := []attribute.KeyValue{ otelogen.OperationID("getScript"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/scripts/{ScriptID}"), + semconv.URLTemplateKey.String("/scripts/{ScriptID}"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -4975,8 +5300,9 @@ func (c *Client) sendGetScriptPolicy(ctx context.Context, params GetScriptPolicy otelAttrs := []attribute.KeyValue{ otelogen.OperationID("getScriptPolicy"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/script-policy/{ScriptPolicyID}"), + semconv.URLTemplateKey.String("/script-policy/{ScriptPolicyID}"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -5065,8 +5391,9 @@ func (c *Client) sendGetSubmission(ctx context.Context, params GetSubmissionPara otelAttrs := []attribute.KeyValue{ otelogen.OperationID("getSubmission"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -5141,6 +5468,118 @@ func (c *Client) sendGetSubmission(ctx context.Context, params GetSubmissionPara return result, nil } +// GetUserThumbnail invokes getUserThumbnail operation. +// +// Get single user avatar thumbnail. +// +// GET /thumbnails/user/{UserID} +func (c *Client) GetUserThumbnail(ctx context.Context, params GetUserThumbnailParams) (*GetUserThumbnailFound, error) { + res, err := c.sendGetUserThumbnail(ctx, params) + return res, err +} + +func (c *Client) sendGetUserThumbnail(ctx context.Context, params GetUserThumbnailParams) (res *GetUserThumbnailFound, err error) { + otelAttrs := []attribute.KeyValue{ + otelogen.OperationID("getUserThumbnail"), + semconv.HTTPRequestMethodKey.String("GET"), + semconv.URLTemplateKey.String("/thumbnails/user/{UserID}"), + } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) + + // Run stopwatch. + startTime := time.Now() + defer func() { + // Use floating point division here for higher precision (instead of Millisecond method). + elapsedDuration := time.Since(startTime) + c.duration.Record(ctx, float64(elapsedDuration)/float64(time.Millisecond), metric.WithAttributes(otelAttrs...)) + }() + + // Increment request counter. + c.requests.Add(ctx, 1, metric.WithAttributes(otelAttrs...)) + + // Start a span for this request. + ctx, span := c.cfg.Tracer.Start(ctx, GetUserThumbnailOperation, + trace.WithAttributes(otelAttrs...), + clientSpanKind, + ) + // Track stage for error reporting. + var stage string + defer func() { + if err != nil { + span.RecordError(err) + span.SetStatus(codes.Error, stage) + c.errors.Add(ctx, 1, metric.WithAttributes(otelAttrs...)) + } + span.End() + }() + + stage = "BuildURL" + u := uri.Clone(c.requestURL(ctx)) + var pathParts [2]string + pathParts[0] = "/thumbnails/user/" + { + // Encode "UserID" parameter. + e := uri.NewPathEncoder(uri.PathEncoderConfig{ + Param: "UserID", + Style: uri.PathStyleSimple, + Explode: false, + }) + if err := func() error { + return e.EncodeValue(conv.Uint64ToString(params.UserID)) + }(); err != nil { + return res, errors.Wrap(err, "encode path") + } + encoded, err := e.Result() + if err != nil { + return res, errors.Wrap(err, "encode path") + } + pathParts[1] = encoded + } + uri.AddPathParts(u, pathParts[:]...) + + stage = "EncodeQueryParams" + q := uri.NewQueryEncoder() + { + // Encode "size" parameter. + cfg := uri.QueryParameterEncodingConfig{ + Name: "size", + Style: uri.QueryStyleForm, + Explode: true, + } + + if err := q.EncodeParam(cfg, func(e uri.Encoder) error { + if val, ok := params.Size.Get(); ok { + return e.EncodeValue(conv.StringToString(string(val))) + } + return nil + }); err != nil { + return res, errors.Wrap(err, "encode query") + } + } + u.RawQuery = q.Values().Encode() + + stage = "EncodeRequest" + r, err := ht.NewRequest(ctx, "GET", u) + if err != nil { + return res, errors.Wrap(err, "create request") + } + + stage = "SendRequest" + resp, err := c.cfg.Client.Do(r) + if err != nil { + return res, errors.Wrap(err, "do request") + } + defer resp.Body.Close() + + stage = "DecodeResponse" + result, err := decodeGetUserThumbnailResponse(resp) + if err != nil { + return res, errors.Wrap(err, "decode response") + } + + return result, nil +} + // ListMapfixAuditEvents invokes listMapfixAuditEvents operation. // // Retrieve a list of audit events. @@ -5155,8 +5594,9 @@ func (c *Client) sendListMapfixAuditEvents(ctx context.Context, params ListMapfi otelAttrs := []attribute.KeyValue{ otelogen.OperationID("listMapfixAuditEvents"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/audit-events"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/audit-events"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -5278,8 +5718,9 @@ func (c *Client) sendListMapfixes(ctx context.Context, params ListMapfixesParams otelAttrs := []attribute.KeyValue{ otelogen.OperationID("listMapfixes"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/mapfixes"), + semconv.URLTemplateKey.String("/mapfixes"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -5535,8 +5976,9 @@ func (c *Client) sendListMaps(ctx context.Context, params ListMapsParams) (res [ otelAttrs := []attribute.KeyValue{ otelogen.OperationID("listMaps"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/maps"), + semconv.URLTemplateKey.String("/maps"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -5707,8 +6149,9 @@ func (c *Client) sendListScriptPolicy(ctx context.Context, params ListScriptPoli otelAttrs := []attribute.KeyValue{ otelogen.OperationID("listScriptPolicy"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/script-policy"), + semconv.URLTemplateKey.String("/script-policy"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -5862,8 +6305,9 @@ func (c *Client) sendListScripts(ctx context.Context, params ListScriptsParams) otelAttrs := []attribute.KeyValue{ otelogen.OperationID("listScripts"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/scripts"), + semconv.URLTemplateKey.String("/scripts"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -6051,8 +6495,9 @@ func (c *Client) sendListSubmissionAuditEvents(ctx context.Context, params ListS otelAttrs := []attribute.KeyValue{ otelogen.OperationID("listSubmissionAuditEvents"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/audit-events"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/audit-events"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -6174,8 +6619,9 @@ func (c *Client) sendListSubmissions(ctx context.Context, params ListSubmissions otelAttrs := []attribute.KeyValue{ otelogen.OperationID("listSubmissions"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/submissions"), + semconv.URLTemplateKey.String("/submissions"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -6431,8 +6877,9 @@ func (c *Client) sendReleaseSubmissions(ctx context.Context, request []ReleaseIn otelAttrs := []attribute.KeyValue{ otelogen.OperationID("releaseSubmissions"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/release-submissions"), + semconv.URLTemplateKey.String("/release-submissions"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -6539,8 +6986,9 @@ func (c *Client) sendSessionRoles(ctx context.Context) (res *Roles, err error) { otelAttrs := []attribute.KeyValue{ otelogen.OperationID("sessionRoles"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/session/roles"), + semconv.URLTemplateKey.String("/session/roles"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -6644,8 +7092,9 @@ func (c *Client) sendSessionUser(ctx context.Context) (res *User, err error) { otelAttrs := []attribute.KeyValue{ otelogen.OperationID("sessionUser"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/session/user"), + semconv.URLTemplateKey.String("/session/user"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -6749,8 +7198,9 @@ func (c *Client) sendSessionValidate(ctx context.Context) (res bool, err error) otelAttrs := []attribute.KeyValue{ otelogen.OperationID("sessionValidate"), semconv.HTTPRequestMethodKey.String("GET"), - semconv.HTTPRouteKey.String("/session/validate"), + semconv.URLTemplateKey.String("/session/validate"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -6854,8 +7304,9 @@ func (c *Client) sendSetMapfixCompleted(ctx context.Context, params SetMapfixCom otelAttrs := []attribute.KeyValue{ otelogen.OperationID("setMapfixCompleted"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/completed"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/completed"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -6978,8 +7429,9 @@ func (c *Client) sendSetSubmissionCompleted(ctx context.Context, params SetSubmi otelAttrs := []attribute.KeyValue{ otelogen.OperationID("setSubmissionCompleted"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/completed"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/completed"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -7102,8 +7554,9 @@ func (c *Client) sendUpdateMapfixModel(ctx context.Context, params UpdateMapfixM otelAttrs := []attribute.KeyValue{ otelogen.OperationID("updateMapfixModel"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/mapfixes/{MapfixID}/model"), + semconv.URLTemplateKey.String("/mapfixes/{MapfixID}/model"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -7258,8 +7711,9 @@ func (c *Client) sendUpdateScript(ctx context.Context, request *ScriptUpdate, pa otelAttrs := []attribute.KeyValue{ otelogen.OperationID("updateScript"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/scripts/{ScriptID}"), + semconv.URLTemplateKey.String("/scripts/{ScriptID}"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -7384,8 +7838,9 @@ func (c *Client) sendUpdateScriptPolicy(ctx context.Context, request *ScriptPoli otelAttrs := []attribute.KeyValue{ otelogen.OperationID("updateScriptPolicy"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/script-policy/{ScriptPolicyID}"), + semconv.URLTemplateKey.String("/script-policy/{ScriptPolicyID}"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() @@ -7510,8 +7965,9 @@ func (c *Client) sendUpdateSubmissionModel(ctx context.Context, params UpdateSub otelAttrs := []attribute.KeyValue{ otelogen.OperationID("updateSubmissionModel"), semconv.HTTPRequestMethodKey.String("POST"), - semconv.HTTPRouteKey.String("/submissions/{SubmissionID}/model"), + semconv.URLTemplateKey.String("/submissions/{SubmissionID}/model"), } + otelAttrs = append(otelAttrs, c.cfg.Attributes...) // Run stopwatch. startTime := time.Now() diff --git a/pkg/api/oas_defaults_gen.go b/pkg/api/oas_defaults_gen.go new file mode 100644 index 0000000..da8b721 --- /dev/null +++ b/pkg/api/oas_defaults_gen.go @@ -0,0 +1,19 @@ +// Code generated by ogen, DO NOT EDIT. + +package api + +// setDefaults set default value of fields. +func (s *BatchAssetThumbnailsReq) setDefaults() { + { + val := BatchAssetThumbnailsReqSize("420x420") + s.Size.SetTo(val) + } +} + +// setDefaults set default value of fields. +func (s *BatchUserThumbnailsReq) setDefaults() { + { + val := BatchUserThumbnailsReqSize("150x150") + s.Size.SetTo(val) + } +} diff --git a/pkg/api/oas_handlers_gen.go b/pkg/api/oas_handlers_gen.go index 2d9f21e..00ea170 100644 --- a/pkg/api/oas_handlers_gen.go +++ b/pkg/api/oas_handlers_gen.go @@ -8,16 +8,15 @@ import ( "time" "github.com/go-faster/errors" - "go.opentelemetry.io/otel/attribute" - "go.opentelemetry.io/otel/codes" - "go.opentelemetry.io/otel/metric" - semconv "go.opentelemetry.io/otel/semconv/v1.26.0" - "go.opentelemetry.io/otel/trace" - ht "github.com/ogen-go/ogen/http" "github.com/ogen-go/ogen/middleware" "github.com/ogen-go/ogen/ogenerrors" "github.com/ogen-go/ogen/otelogen" + "go.opentelemetry.io/otel/attribute" + "go.opentelemetry.io/otel/codes" + "go.opentelemetry.io/otel/metric" + semconv "go.opentelemetry.io/otel/semconv/v1.37.0" + "go.opentelemetry.io/otel/trace" ) type codeRecorder struct { @@ -30,6 +29,10 @@ func (c *codeRecorder) WriteHeader(status int) { c.ResponseWriter.WriteHeader(status) } +func (c *codeRecorder) Unwrap() http.ResponseWriter { + return c.ResponseWriter +} + // handleActionMapfixAcceptedRequest handles actionMapfixAccepted operation. // // Role Reviewer manually resets validating softlock and changes status from Validating -> Accepted. @@ -86,7 +89,7 @@ func (s *Server) handleActionMapfixAcceptedRequest(args [1]string, argsEscaped b // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -161,6 +164,8 @@ func (s *Server) handleActionMapfixAcceptedRequest(args [1]string, argsEscaped b return } + var rawBody []byte + var response *ActionMapfixAcceptedNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -169,6 +174,7 @@ func (s *Server) handleActionMapfixAcceptedRequest(args [1]string, argsEscaped b OperationSummary: "Role Reviewer manually resets validating softlock and changes status from Validating -> Accepted", OperationID: "actionMapfixAccepted", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -281,7 +287,7 @@ func (s *Server) handleActionMapfixRejectRequest(args [1]string, argsEscaped boo // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -356,6 +362,8 @@ func (s *Server) handleActionMapfixRejectRequest(args [1]string, argsEscaped boo return } + var rawBody []byte + var response *ActionMapfixRejectNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -364,6 +372,7 @@ func (s *Server) handleActionMapfixRejectRequest(args [1]string, argsEscaped boo OperationSummary: "Role Reviewer changes status from Submitted -> Rejected", OperationID: "actionMapfixReject", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -476,7 +485,7 @@ func (s *Server) handleActionMapfixRequestChangesRequest(args [1]string, argsEsc // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -551,6 +560,8 @@ func (s *Server) handleActionMapfixRequestChangesRequest(args [1]string, argsEsc return } + var rawBody []byte + var response *ActionMapfixRequestChangesNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -559,6 +570,7 @@ func (s *Server) handleActionMapfixRequestChangesRequest(args [1]string, argsEsc OperationSummary: "Role Reviewer changes status from Validated|Accepted|Submitted -> ChangesRequested", OperationID: "actionMapfixRequestChanges", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -672,7 +684,7 @@ func (s *Server) handleActionMapfixResetSubmittingRequest(args [1]string, argsEs // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -747,6 +759,8 @@ func (s *Server) handleActionMapfixResetSubmittingRequest(args [1]string, argsEs return } + var rawBody []byte + var response *ActionMapfixResetSubmittingNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -755,6 +769,7 @@ func (s *Server) handleActionMapfixResetSubmittingRequest(args [1]string, argsEs OperationSummary: "Role Submitter manually resets submitting softlock and changes status from Submitting -> UnderConstruction", OperationID: "actionMapfixResetSubmitting", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -867,7 +882,7 @@ func (s *Server) handleActionMapfixRetryValidateRequest(args [1]string, argsEsca // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -942,6 +957,8 @@ func (s *Server) handleActionMapfixRetryValidateRequest(args [1]string, argsEsca return } + var rawBody []byte + var response *ActionMapfixRetryValidateNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -950,6 +967,7 @@ func (s *Server) handleActionMapfixRetryValidateRequest(args [1]string, argsEsca OperationSummary: "Role Reviewer re-runs validation and changes status from Accepted -> Validating", OperationID: "actionMapfixRetryValidate", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -1062,7 +1080,7 @@ func (s *Server) handleActionMapfixRevokeRequest(args [1]string, argsEscaped boo // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -1137,6 +1155,8 @@ func (s *Server) handleActionMapfixRevokeRequest(args [1]string, argsEscaped boo return } + var rawBody []byte + var response *ActionMapfixRevokeNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -1145,6 +1165,7 @@ func (s *Server) handleActionMapfixRevokeRequest(args [1]string, argsEscaped boo OperationSummary: "Role Submitter changes status from Submitted|ChangesRequested -> UnderConstruction", OperationID: "actionMapfixRevoke", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -1257,7 +1278,7 @@ func (s *Server) handleActionMapfixTriggerReleaseRequest(args [1]string, argsEsc // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -1332,6 +1353,8 @@ func (s *Server) handleActionMapfixTriggerReleaseRequest(args [1]string, argsEsc return } + var rawBody []byte + var response *ActionMapfixTriggerReleaseNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -1340,6 +1363,7 @@ func (s *Server) handleActionMapfixTriggerReleaseRequest(args [1]string, argsEsc OperationSummary: "Role MapfixUpload changes status from Uploaded -> Releasing", OperationID: "actionMapfixTriggerRelease", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -1452,7 +1476,7 @@ func (s *Server) handleActionMapfixTriggerSubmitRequest(args [1]string, argsEsca // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -1527,6 +1551,8 @@ func (s *Server) handleActionMapfixTriggerSubmitRequest(args [1]string, argsEsca return } + var rawBody []byte + var response *ActionMapfixTriggerSubmitNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -1535,6 +1561,7 @@ func (s *Server) handleActionMapfixTriggerSubmitRequest(args [1]string, argsEsca OperationSummary: "Role Submitter changes status from UnderConstruction|ChangesRequested -> Submitting", OperationID: "actionMapfixTriggerSubmit", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -1647,7 +1674,7 @@ func (s *Server) handleActionMapfixTriggerSubmitUncheckedRequest(args [1]string, // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -1722,6 +1749,8 @@ func (s *Server) handleActionMapfixTriggerSubmitUncheckedRequest(args [1]string, return } + var rawBody []byte + var response *ActionMapfixTriggerSubmitUncheckedNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -1730,6 +1759,7 @@ func (s *Server) handleActionMapfixTriggerSubmitUncheckedRequest(args [1]string, OperationSummary: "Role Reviewer changes status from ChangesRequested -> Submitting", OperationID: "actionMapfixTriggerSubmitUnchecked", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -1842,7 +1872,7 @@ func (s *Server) handleActionMapfixTriggerUploadRequest(args [1]string, argsEsca // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -1917,6 +1947,8 @@ func (s *Server) handleActionMapfixTriggerUploadRequest(args [1]string, argsEsca return } + var rawBody []byte + var response *ActionMapfixTriggerUploadNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -1925,6 +1957,7 @@ func (s *Server) handleActionMapfixTriggerUploadRequest(args [1]string, argsEsca OperationSummary: "Role MapfixUpload changes status from Validated -> Uploading", OperationID: "actionMapfixTriggerUpload", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -2037,7 +2070,7 @@ func (s *Server) handleActionMapfixTriggerValidateRequest(args [1]string, argsEs // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -2112,6 +2145,8 @@ func (s *Server) handleActionMapfixTriggerValidateRequest(args [1]string, argsEs return } + var rawBody []byte + var response *ActionMapfixTriggerValidateNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -2120,6 +2155,7 @@ func (s *Server) handleActionMapfixTriggerValidateRequest(args [1]string, argsEs OperationSummary: "Role Reviewer triggers validation and changes status from Submitted -> Validating", OperationID: "actionMapfixTriggerValidate", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -2232,7 +2268,7 @@ func (s *Server) handleActionMapfixUploadedRequest(args [1]string, argsEscaped b // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -2307,6 +2343,8 @@ func (s *Server) handleActionMapfixUploadedRequest(args [1]string, argsEscaped b return } + var rawBody []byte + var response *ActionMapfixUploadedNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -2315,6 +2353,7 @@ func (s *Server) handleActionMapfixUploadedRequest(args [1]string, argsEscaped b OperationSummary: "Role MapfixUpload manually resets releasing softlock and changes status from Releasing -> Uploaded", OperationID: "actionMapfixUploaded", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -2427,7 +2466,7 @@ func (s *Server) handleActionMapfixValidatedRequest(args [1]string, argsEscaped // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -2502,6 +2541,8 @@ func (s *Server) handleActionMapfixValidatedRequest(args [1]string, argsEscaped return } + var rawBody []byte + var response *ActionMapfixValidatedNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -2510,6 +2551,7 @@ func (s *Server) handleActionMapfixValidatedRequest(args [1]string, argsEscaped OperationSummary: "Role MapfixUpload manually resets uploading softlock and changes status from Uploading -> Validated", OperationID: "actionMapfixValidated", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -2622,7 +2664,7 @@ func (s *Server) handleActionSubmissionAcceptedRequest(args [1]string, argsEscap // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -2697,6 +2739,8 @@ func (s *Server) handleActionSubmissionAcceptedRequest(args [1]string, argsEscap return } + var rawBody []byte + var response *ActionSubmissionAcceptedNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -2705,6 +2749,7 @@ func (s *Server) handleActionSubmissionAcceptedRequest(args [1]string, argsEscap OperationSummary: "Role Reviewer manually resets validating softlock and changes status from Validating -> Accepted", OperationID: "actionSubmissionAccepted", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -2817,7 +2862,7 @@ func (s *Server) handleActionSubmissionRejectRequest(args [1]string, argsEscaped // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -2892,6 +2937,8 @@ func (s *Server) handleActionSubmissionRejectRequest(args [1]string, argsEscaped return } + var rawBody []byte + var response *ActionSubmissionRejectNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -2900,6 +2947,7 @@ func (s *Server) handleActionSubmissionRejectRequest(args [1]string, argsEscaped OperationSummary: "Role Reviewer changes status from Submitted -> Rejected", OperationID: "actionSubmissionReject", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -3012,7 +3060,7 @@ func (s *Server) handleActionSubmissionRequestChangesRequest(args [1]string, arg // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -3087,6 +3135,8 @@ func (s *Server) handleActionSubmissionRequestChangesRequest(args [1]string, arg return } + var rawBody []byte + var response *ActionSubmissionRequestChangesNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -3095,6 +3145,7 @@ func (s *Server) handleActionSubmissionRequestChangesRequest(args [1]string, arg OperationSummary: "Role Reviewer changes status from Validated|Accepted|Submitted -> ChangesRequested", OperationID: "actionSubmissionRequestChanges", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -3208,7 +3259,7 @@ func (s *Server) handleActionSubmissionResetSubmittingRequest(args [1]string, ar // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -3283,6 +3334,8 @@ func (s *Server) handleActionSubmissionResetSubmittingRequest(args [1]string, ar return } + var rawBody []byte + var response *ActionSubmissionResetSubmittingNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -3291,6 +3344,7 @@ func (s *Server) handleActionSubmissionResetSubmittingRequest(args [1]string, ar OperationSummary: "Role Submitter manually resets submitting softlock and changes status from Submitting -> UnderConstruction", OperationID: "actionSubmissionResetSubmitting", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -3403,7 +3457,7 @@ func (s *Server) handleActionSubmissionRetryValidateRequest(args [1]string, args // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -3478,6 +3532,8 @@ func (s *Server) handleActionSubmissionRetryValidateRequest(args [1]string, args return } + var rawBody []byte + var response *ActionSubmissionRetryValidateNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -3486,6 +3542,7 @@ func (s *Server) handleActionSubmissionRetryValidateRequest(args [1]string, args OperationSummary: "Role Reviewer re-runs validation and changes status from Accepted -> Validating", OperationID: "actionSubmissionRetryValidate", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -3598,7 +3655,7 @@ func (s *Server) handleActionSubmissionRevokeRequest(args [1]string, argsEscaped // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -3673,6 +3730,8 @@ func (s *Server) handleActionSubmissionRevokeRequest(args [1]string, argsEscaped return } + var rawBody []byte + var response *ActionSubmissionRevokeNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -3681,6 +3740,7 @@ func (s *Server) handleActionSubmissionRevokeRequest(args [1]string, argsEscaped OperationSummary: "Role Submitter changes status from Submitted|ChangesRequested -> UnderConstruction", OperationID: "actionSubmissionRevoke", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -3793,7 +3853,7 @@ func (s *Server) handleActionSubmissionTriggerSubmitRequest(args [1]string, args // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -3868,6 +3928,8 @@ func (s *Server) handleActionSubmissionTriggerSubmitRequest(args [1]string, args return } + var rawBody []byte + var response *ActionSubmissionTriggerSubmitNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -3876,6 +3938,7 @@ func (s *Server) handleActionSubmissionTriggerSubmitRequest(args [1]string, args OperationSummary: "Role Submitter changes status from UnderConstruction|ChangesRequested -> Submitting", OperationID: "actionSubmissionTriggerSubmit", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -3988,7 +4051,7 @@ func (s *Server) handleActionSubmissionTriggerSubmitUncheckedRequest(args [1]str // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -4063,6 +4126,8 @@ func (s *Server) handleActionSubmissionTriggerSubmitUncheckedRequest(args [1]str return } + var rawBody []byte + var response *ActionSubmissionTriggerSubmitUncheckedNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -4071,6 +4136,7 @@ func (s *Server) handleActionSubmissionTriggerSubmitUncheckedRequest(args [1]str OperationSummary: "Role Reviewer changes status from ChangesRequested -> Submitting", OperationID: "actionSubmissionTriggerSubmitUnchecked", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -4183,7 +4249,7 @@ func (s *Server) handleActionSubmissionTriggerUploadRequest(args [1]string, args // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -4258,6 +4324,8 @@ func (s *Server) handleActionSubmissionTriggerUploadRequest(args [1]string, args return } + var rawBody []byte + var response *ActionSubmissionTriggerUploadNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -4266,6 +4334,7 @@ func (s *Server) handleActionSubmissionTriggerUploadRequest(args [1]string, args OperationSummary: "Role SubmissionUpload changes status from Validated -> Uploading", OperationID: "actionSubmissionTriggerUpload", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -4378,7 +4447,7 @@ func (s *Server) handleActionSubmissionTriggerValidateRequest(args [1]string, ar // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -4453,6 +4522,8 @@ func (s *Server) handleActionSubmissionTriggerValidateRequest(args [1]string, ar return } + var rawBody []byte + var response *ActionSubmissionTriggerValidateNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -4461,6 +4532,7 @@ func (s *Server) handleActionSubmissionTriggerValidateRequest(args [1]string, ar OperationSummary: "Role Reviewer triggers validation and changes status from Submitted -> Validating", OperationID: "actionSubmissionTriggerValidate", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -4574,7 +4646,7 @@ func (s *Server) handleActionSubmissionValidatedRequest(args [1]string, argsEsca // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -4649,6 +4721,8 @@ func (s *Server) handleActionSubmissionValidatedRequest(args [1]string, argsEsca return } + var rawBody []byte + var response *ActionSubmissionValidatedNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -4657,6 +4731,7 @@ func (s *Server) handleActionSubmissionValidatedRequest(args [1]string, argsEsca OperationSummary: "Role SubmissionUpload manually resets uploading softlock and changes status from Uploading -> Validated", OperationID: "actionSubmissionValidated", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -4713,6 +4788,310 @@ func (s *Server) handleActionSubmissionValidatedRequest(args [1]string, argsEsca } } +// handleBatchAssetThumbnailsRequest handles batchAssetThumbnails operation. +// +// Batch fetch asset thumbnails. +// +// POST /thumbnails/assets +func (s *Server) handleBatchAssetThumbnailsRequest(args [0]string, argsEscaped bool, w http.ResponseWriter, r *http.Request) { + statusWriter := &codeRecorder{ResponseWriter: w} + w = statusWriter + otelAttrs := []attribute.KeyValue{ + otelogen.OperationID("batchAssetThumbnails"), + semconv.HTTPRequestMethodKey.String("POST"), + semconv.HTTPRouteKey.String("/thumbnails/assets"), + } + + // Start a span for this request. + ctx, span := s.cfg.Tracer.Start(r.Context(), BatchAssetThumbnailsOperation, + trace.WithAttributes(otelAttrs...), + serverSpanKind, + ) + defer span.End() + + // Add Labeler to context. + labeler := &Labeler{attrs: otelAttrs} + ctx = contextWithLabeler(ctx, labeler) + + // Run stopwatch. + startTime := time.Now() + defer func() { + elapsedDuration := time.Since(startTime) + + attrSet := labeler.AttributeSet() + attrs := attrSet.ToSlice() + code := statusWriter.status + if code != 0 { + codeAttr := semconv.HTTPResponseStatusCode(code) + attrs = append(attrs, codeAttr) + span.SetAttributes(codeAttr) + } + attrOpt := metric.WithAttributes(attrs...) + + // Increment request counter. + s.requests.Add(ctx, 1, attrOpt) + + // Use floating point division here for higher precision (instead of Millisecond method). + s.duration.Record(ctx, float64(elapsedDuration)/float64(time.Millisecond), attrOpt) + }() + + var ( + recordError = func(stage string, err error) { + span.RecordError(err) + + // https://opentelemetry.io/docs/specs/semconv/http/http-spans/#status + // Span Status MUST be left unset if HTTP status code was in the 1xx, 2xx or 3xx ranges, + // unless there was another error (e.g., network error receiving the response body; or 3xx codes with + // max redirects exceeded), in which case status MUST be set to Error. + code := statusWriter.status + if code < 100 || code >= 500 { + span.SetStatus(codes.Error, stage) + } + + attrSet := labeler.AttributeSet() + attrs := attrSet.ToSlice() + if code != 0 { + attrs = append(attrs, semconv.HTTPResponseStatusCode(code)) + } + + s.errors.Add(ctx, 1, metric.WithAttributes(attrs...)) + } + err error + opErrContext = ogenerrors.OperationContext{ + Name: BatchAssetThumbnailsOperation, + ID: "batchAssetThumbnails", + } + ) + + var rawBody []byte + request, rawBody, close, err := s.decodeBatchAssetThumbnailsRequest(r) + if err != nil { + err = &ogenerrors.DecodeRequestError{ + OperationContext: opErrContext, + Err: err, + } + defer recordError("DecodeRequest", err) + s.cfg.ErrorHandler(ctx, w, r, err) + return + } + defer func() { + if err := close(); err != nil { + recordError("CloseRequest", err) + } + }() + + var response *BatchAssetThumbnailsOK + if m := s.cfg.Middleware; m != nil { + mreq := middleware.Request{ + Context: ctx, + OperationName: BatchAssetThumbnailsOperation, + OperationSummary: "Batch fetch asset thumbnails", + OperationID: "batchAssetThumbnails", + Body: request, + RawBody: rawBody, + Params: middleware.Parameters{}, + Raw: r, + } + + type ( + Request = *BatchAssetThumbnailsReq + Params = struct{} + Response = *BatchAssetThumbnailsOK + ) + response, err = middleware.HookMiddleware[ + Request, + Params, + Response, + ]( + m, + mreq, + nil, + func(ctx context.Context, request Request, params Params) (response Response, err error) { + response, err = s.h.BatchAssetThumbnails(ctx, request) + return response, err + }, + ) + } else { + response, err = s.h.BatchAssetThumbnails(ctx, request) + } + if err != nil { + if errRes, ok := errors.Into[*ErrorStatusCode](err); ok { + if err := encodeErrorResponse(errRes, w, span); err != nil { + defer recordError("Internal", err) + } + return + } + if errors.Is(err, ht.ErrNotImplemented) { + s.cfg.ErrorHandler(ctx, w, r, err) + return + } + if err := encodeErrorResponse(s.h.NewError(ctx, err), w, span); err != nil { + defer recordError("Internal", err) + } + return + } + + if err := encodeBatchAssetThumbnailsResponse(response, w, span); err != nil { + defer recordError("EncodeResponse", err) + if !errors.Is(err, ht.ErrInternalServerErrorResponse) { + s.cfg.ErrorHandler(ctx, w, r, err) + } + return + } +} + +// handleBatchUserThumbnailsRequest handles batchUserThumbnails operation. +// +// Batch fetch user avatar thumbnails. +// +// POST /thumbnails/users +func (s *Server) handleBatchUserThumbnailsRequest(args [0]string, argsEscaped bool, w http.ResponseWriter, r *http.Request) { + statusWriter := &codeRecorder{ResponseWriter: w} + w = statusWriter + otelAttrs := []attribute.KeyValue{ + otelogen.OperationID("batchUserThumbnails"), + semconv.HTTPRequestMethodKey.String("POST"), + semconv.HTTPRouteKey.String("/thumbnails/users"), + } + + // Start a span for this request. + ctx, span := s.cfg.Tracer.Start(r.Context(), BatchUserThumbnailsOperation, + trace.WithAttributes(otelAttrs...), + serverSpanKind, + ) + defer span.End() + + // Add Labeler to context. + labeler := &Labeler{attrs: otelAttrs} + ctx = contextWithLabeler(ctx, labeler) + + // Run stopwatch. + startTime := time.Now() + defer func() { + elapsedDuration := time.Since(startTime) + + attrSet := labeler.AttributeSet() + attrs := attrSet.ToSlice() + code := statusWriter.status + if code != 0 { + codeAttr := semconv.HTTPResponseStatusCode(code) + attrs = append(attrs, codeAttr) + span.SetAttributes(codeAttr) + } + attrOpt := metric.WithAttributes(attrs...) + + // Increment request counter. + s.requests.Add(ctx, 1, attrOpt) + + // Use floating point division here for higher precision (instead of Millisecond method). + s.duration.Record(ctx, float64(elapsedDuration)/float64(time.Millisecond), attrOpt) + }() + + var ( + recordError = func(stage string, err error) { + span.RecordError(err) + + // https://opentelemetry.io/docs/specs/semconv/http/http-spans/#status + // Span Status MUST be left unset if HTTP status code was in the 1xx, 2xx or 3xx ranges, + // unless there was another error (e.g., network error receiving the response body; or 3xx codes with + // max redirects exceeded), in which case status MUST be set to Error. + code := statusWriter.status + if code < 100 || code >= 500 { + span.SetStatus(codes.Error, stage) + } + + attrSet := labeler.AttributeSet() + attrs := attrSet.ToSlice() + if code != 0 { + attrs = append(attrs, semconv.HTTPResponseStatusCode(code)) + } + + s.errors.Add(ctx, 1, metric.WithAttributes(attrs...)) + } + err error + opErrContext = ogenerrors.OperationContext{ + Name: BatchUserThumbnailsOperation, + ID: "batchUserThumbnails", + } + ) + + var rawBody []byte + request, rawBody, close, err := s.decodeBatchUserThumbnailsRequest(r) + if err != nil { + err = &ogenerrors.DecodeRequestError{ + OperationContext: opErrContext, + Err: err, + } + defer recordError("DecodeRequest", err) + s.cfg.ErrorHandler(ctx, w, r, err) + return + } + defer func() { + if err := close(); err != nil { + recordError("CloseRequest", err) + } + }() + + var response *BatchUserThumbnailsOK + if m := s.cfg.Middleware; m != nil { + mreq := middleware.Request{ + Context: ctx, + OperationName: BatchUserThumbnailsOperation, + OperationSummary: "Batch fetch user avatar thumbnails", + OperationID: "batchUserThumbnails", + Body: request, + RawBody: rawBody, + Params: middleware.Parameters{}, + Raw: r, + } + + type ( + Request = *BatchUserThumbnailsReq + Params = struct{} + Response = *BatchUserThumbnailsOK + ) + response, err = middleware.HookMiddleware[ + Request, + Params, + Response, + ]( + m, + mreq, + nil, + func(ctx context.Context, request Request, params Params) (response Response, err error) { + response, err = s.h.BatchUserThumbnails(ctx, request) + return response, err + }, + ) + } else { + response, err = s.h.BatchUserThumbnails(ctx, request) + } + if err != nil { + if errRes, ok := errors.Into[*ErrorStatusCode](err); ok { + if err := encodeErrorResponse(errRes, w, span); err != nil { + defer recordError("Internal", err) + } + return + } + if errors.Is(err, ht.ErrNotImplemented) { + s.cfg.ErrorHandler(ctx, w, r, err) + return + } + if err := encodeErrorResponse(s.h.NewError(ctx, err), w, span); err != nil { + defer recordError("Internal", err) + } + return + } + + if err := encodeBatchUserThumbnailsResponse(response, w, span); err != nil { + defer recordError("EncodeResponse", err) + if !errors.Is(err, ht.ErrInternalServerErrorResponse) { + s.cfg.ErrorHandler(ctx, w, r, err) + } + return + } +} + // handleCreateMapfixRequest handles createMapfix operation. // // Trigger the validator to create a mapfix. @@ -4769,7 +5148,7 @@ func (s *Server) handleCreateMapfixRequest(args [0]string, argsEscaped bool, w h // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -4833,7 +5212,9 @@ func (s *Server) handleCreateMapfixRequest(args [0]string, argsEscaped bool, w h return } } - request, close, err := s.decodeCreateMapfixRequest(r) + + var rawBody []byte + request, rawBody, close, err := s.decodeCreateMapfixRequest(r) if err != nil { err = &ogenerrors.DecodeRequestError{ OperationContext: opErrContext, @@ -4857,6 +5238,7 @@ func (s *Server) handleCreateMapfixRequest(args [0]string, argsEscaped bool, w h OperationSummary: "Trigger the validator to create a mapfix", OperationID: "createMapfix", Body: request, + RawBody: rawBody, Params: middleware.Parameters{}, Raw: r, } @@ -4964,7 +5346,7 @@ func (s *Server) handleCreateMapfixAuditCommentRequest(args [1]string, argsEscap // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -5038,7 +5420,9 @@ func (s *Server) handleCreateMapfixAuditCommentRequest(args [1]string, argsEscap s.cfg.ErrorHandler(ctx, w, r, err) return } - request, close, err := s.decodeCreateMapfixAuditCommentRequest(r) + + var rawBody []byte + request, rawBody, close, err := s.decodeCreateMapfixAuditCommentRequest(r) if err != nil { err = &ogenerrors.DecodeRequestError{ OperationContext: opErrContext, @@ -5062,6 +5446,7 @@ func (s *Server) handleCreateMapfixAuditCommentRequest(args [1]string, argsEscap OperationSummary: "Post a comment to the audit log", OperationID: "createMapfixAuditComment", Body: request, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -5174,7 +5559,7 @@ func (s *Server) handleCreateScriptRequest(args [0]string, argsEscaped bool, w h // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -5238,7 +5623,9 @@ func (s *Server) handleCreateScriptRequest(args [0]string, argsEscaped bool, w h return } } - request, close, err := s.decodeCreateScriptRequest(r) + + var rawBody []byte + request, rawBody, close, err := s.decodeCreateScriptRequest(r) if err != nil { err = &ogenerrors.DecodeRequestError{ OperationContext: opErrContext, @@ -5262,6 +5649,7 @@ func (s *Server) handleCreateScriptRequest(args [0]string, argsEscaped bool, w h OperationSummary: "Create a new script", OperationID: "createScript", Body: request, + RawBody: rawBody, Params: middleware.Parameters{}, Raw: r, } @@ -5369,7 +5757,7 @@ func (s *Server) handleCreateScriptPolicyRequest(args [0]string, argsEscaped boo // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -5433,7 +5821,9 @@ func (s *Server) handleCreateScriptPolicyRequest(args [0]string, argsEscaped boo return } } - request, close, err := s.decodeCreateScriptPolicyRequest(r) + + var rawBody []byte + request, rawBody, close, err := s.decodeCreateScriptPolicyRequest(r) if err != nil { err = &ogenerrors.DecodeRequestError{ OperationContext: opErrContext, @@ -5457,6 +5847,7 @@ func (s *Server) handleCreateScriptPolicyRequest(args [0]string, argsEscaped boo OperationSummary: "Create a new script policy", OperationID: "createScriptPolicy", Body: request, + RawBody: rawBody, Params: middleware.Parameters{}, Raw: r, } @@ -5564,7 +5955,7 @@ func (s *Server) handleCreateSubmissionRequest(args [0]string, argsEscaped bool, // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -5628,7 +6019,9 @@ func (s *Server) handleCreateSubmissionRequest(args [0]string, argsEscaped bool, return } } - request, close, err := s.decodeCreateSubmissionRequest(r) + + var rawBody []byte + request, rawBody, close, err := s.decodeCreateSubmissionRequest(r) if err != nil { err = &ogenerrors.DecodeRequestError{ OperationContext: opErrContext, @@ -5652,6 +6045,7 @@ func (s *Server) handleCreateSubmissionRequest(args [0]string, argsEscaped bool, OperationSummary: "Trigger the validator to create a new submission", OperationID: "createSubmission", Body: request, + RawBody: rawBody, Params: middleware.Parameters{}, Raw: r, } @@ -5759,7 +6153,7 @@ func (s *Server) handleCreateSubmissionAdminRequest(args [0]string, argsEscaped // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -5823,7 +6217,9 @@ func (s *Server) handleCreateSubmissionAdminRequest(args [0]string, argsEscaped return } } - request, close, err := s.decodeCreateSubmissionAdminRequest(r) + + var rawBody []byte + request, rawBody, close, err := s.decodeCreateSubmissionAdminRequest(r) if err != nil { err = &ogenerrors.DecodeRequestError{ OperationContext: opErrContext, @@ -5847,6 +6243,7 @@ func (s *Server) handleCreateSubmissionAdminRequest(args [0]string, argsEscaped OperationSummary: "Trigger the validator to create a new submission", OperationID: "createSubmissionAdmin", Body: request, + RawBody: rawBody, Params: middleware.Parameters{}, Raw: r, } @@ -5954,7 +6351,7 @@ func (s *Server) handleCreateSubmissionAuditCommentRequest(args [1]string, argsE // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -6028,7 +6425,9 @@ func (s *Server) handleCreateSubmissionAuditCommentRequest(args [1]string, argsE s.cfg.ErrorHandler(ctx, w, r, err) return } - request, close, err := s.decodeCreateSubmissionAuditCommentRequest(r) + + var rawBody []byte + request, rawBody, close, err := s.decodeCreateSubmissionAuditCommentRequest(r) if err != nil { err = &ogenerrors.DecodeRequestError{ OperationContext: opErrContext, @@ -6052,6 +6451,7 @@ func (s *Server) handleCreateSubmissionAuditCommentRequest(args [1]string, argsE OperationSummary: "Post a comment to the audit log", OperationID: "createSubmissionAuditComment", Body: request, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -6164,7 +6564,7 @@ func (s *Server) handleDeleteScriptRequest(args [1]string, argsEscaped bool, w h // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -6239,6 +6639,8 @@ func (s *Server) handleDeleteScriptRequest(args [1]string, argsEscaped bool, w h return } + var rawBody []byte + var response *DeleteScriptNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -6247,6 +6649,7 @@ func (s *Server) handleDeleteScriptRequest(args [1]string, argsEscaped bool, w h OperationSummary: "Delete the specified script by ID", OperationID: "deleteScript", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "ScriptID", @@ -6359,7 +6762,7 @@ func (s *Server) handleDeleteScriptPolicyRequest(args [1]string, argsEscaped boo // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -6434,6 +6837,8 @@ func (s *Server) handleDeleteScriptPolicyRequest(args [1]string, argsEscaped boo return } + var rawBody []byte + var response *DeleteScriptPolicyNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -6442,6 +6847,7 @@ func (s *Server) handleDeleteScriptPolicyRequest(args [1]string, argsEscaped boo OperationSummary: "Delete the specified script policy by ID", OperationID: "deleteScriptPolicy", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "ScriptPolicyID", @@ -6554,7 +6960,7 @@ func (s *Server) handleDownloadMapAssetRequest(args [1]string, argsEscaped bool, // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -6629,6 +7035,8 @@ func (s *Server) handleDownloadMapAssetRequest(args [1]string, argsEscaped bool, return } + var rawBody []byte + var response DownloadMapAssetOK if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -6637,6 +7045,7 @@ func (s *Server) handleDownloadMapAssetRequest(args [1]string, argsEscaped bool, OperationSummary: "Download the map asset", OperationID: "downloadMapAsset", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapID", @@ -6693,6 +7102,162 @@ func (s *Server) handleDownloadMapAssetRequest(args [1]string, argsEscaped bool, } } +// handleGetAssetThumbnailRequest handles getAssetThumbnail operation. +// +// Get single asset thumbnail. +// +// GET /thumbnails/asset/{AssetID} +func (s *Server) handleGetAssetThumbnailRequest(args [1]string, argsEscaped bool, w http.ResponseWriter, r *http.Request) { + statusWriter := &codeRecorder{ResponseWriter: w} + w = statusWriter + otelAttrs := []attribute.KeyValue{ + otelogen.OperationID("getAssetThumbnail"), + semconv.HTTPRequestMethodKey.String("GET"), + semconv.HTTPRouteKey.String("/thumbnails/asset/{AssetID}"), + } + + // Start a span for this request. + ctx, span := s.cfg.Tracer.Start(r.Context(), GetAssetThumbnailOperation, + trace.WithAttributes(otelAttrs...), + serverSpanKind, + ) + defer span.End() + + // Add Labeler to context. + labeler := &Labeler{attrs: otelAttrs} + ctx = contextWithLabeler(ctx, labeler) + + // Run stopwatch. + startTime := time.Now() + defer func() { + elapsedDuration := time.Since(startTime) + + attrSet := labeler.AttributeSet() + attrs := attrSet.ToSlice() + code := statusWriter.status + if code != 0 { + codeAttr := semconv.HTTPResponseStatusCode(code) + attrs = append(attrs, codeAttr) + span.SetAttributes(codeAttr) + } + attrOpt := metric.WithAttributes(attrs...) + + // Increment request counter. + s.requests.Add(ctx, 1, attrOpt) + + // Use floating point division here for higher precision (instead of Millisecond method). + s.duration.Record(ctx, float64(elapsedDuration)/float64(time.Millisecond), attrOpt) + }() + + var ( + recordError = func(stage string, err error) { + span.RecordError(err) + + // https://opentelemetry.io/docs/specs/semconv/http/http-spans/#status + // Span Status MUST be left unset if HTTP status code was in the 1xx, 2xx or 3xx ranges, + // unless there was another error (e.g., network error receiving the response body; or 3xx codes with + // max redirects exceeded), in which case status MUST be set to Error. + code := statusWriter.status + if code < 100 || code >= 500 { + span.SetStatus(codes.Error, stage) + } + + attrSet := labeler.AttributeSet() + attrs := attrSet.ToSlice() + if code != 0 { + attrs = append(attrs, semconv.HTTPResponseStatusCode(code)) + } + + s.errors.Add(ctx, 1, metric.WithAttributes(attrs...)) + } + err error + opErrContext = ogenerrors.OperationContext{ + Name: GetAssetThumbnailOperation, + ID: "getAssetThumbnail", + } + ) + params, err := decodeGetAssetThumbnailParams(args, argsEscaped, r) + if err != nil { + err = &ogenerrors.DecodeParamsError{ + OperationContext: opErrContext, + Err: err, + } + defer recordError("DecodeParams", err) + s.cfg.ErrorHandler(ctx, w, r, err) + return + } + + var rawBody []byte + + var response *GetAssetThumbnailFound + if m := s.cfg.Middleware; m != nil { + mreq := middleware.Request{ + Context: ctx, + OperationName: GetAssetThumbnailOperation, + OperationSummary: "Get single asset thumbnail", + OperationID: "getAssetThumbnail", + Body: nil, + RawBody: rawBody, + Params: middleware.Parameters{ + { + Name: "AssetID", + In: "path", + }: params.AssetID, + { + Name: "size", + In: "query", + }: params.Size, + }, + Raw: r, + } + + type ( + Request = struct{} + Params = GetAssetThumbnailParams + Response = *GetAssetThumbnailFound + ) + response, err = middleware.HookMiddleware[ + Request, + Params, + Response, + ]( + m, + mreq, + unpackGetAssetThumbnailParams, + func(ctx context.Context, request Request, params Params) (response Response, err error) { + response, err = s.h.GetAssetThumbnail(ctx, params) + return response, err + }, + ) + } else { + response, err = s.h.GetAssetThumbnail(ctx, params) + } + if err != nil { + if errRes, ok := errors.Into[*ErrorStatusCode](err); ok { + if err := encodeErrorResponse(errRes, w, span); err != nil { + defer recordError("Internal", err) + } + return + } + if errors.Is(err, ht.ErrNotImplemented) { + s.cfg.ErrorHandler(ctx, w, r, err) + return + } + if err := encodeErrorResponse(s.h.NewError(ctx, err), w, span); err != nil { + defer recordError("Internal", err) + } + return + } + + if err := encodeGetAssetThumbnailResponse(response, w, span); err != nil { + defer recordError("EncodeResponse", err) + if !errors.Is(err, ht.ErrInternalServerErrorResponse) { + s.cfg.ErrorHandler(ctx, w, r, err) + } + return + } +} + // handleGetMapRequest handles getMap operation. // // Retrieve map with ID. @@ -6749,7 +7314,7 @@ func (s *Server) handleGetMapRequest(args [1]string, argsEscaped bool, w http.Re // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -6778,6 +7343,8 @@ func (s *Server) handleGetMapRequest(args [1]string, argsEscaped bool, w http.Re return } + var rawBody []byte + var response *Map if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -6786,6 +7353,7 @@ func (s *Server) handleGetMapRequest(args [1]string, argsEscaped bool, w http.Re OperationSummary: "Retrieve map with ID", OperationID: "getMap", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapID", @@ -6898,7 +7466,7 @@ func (s *Server) handleGetMapfixRequest(args [1]string, argsEscaped bool, w http // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -6927,6 +7495,8 @@ func (s *Server) handleGetMapfixRequest(args [1]string, argsEscaped bool, w http return } + var rawBody []byte + var response *Mapfix if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -6935,6 +7505,7 @@ func (s *Server) handleGetMapfixRequest(args [1]string, argsEscaped bool, w http OperationSummary: "Retrieve map with ID", OperationID: "getMapfix", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -7047,7 +7618,7 @@ func (s *Server) handleGetOperationRequest(args [1]string, argsEscaped bool, w h // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -7122,6 +7693,8 @@ func (s *Server) handleGetOperationRequest(args [1]string, argsEscaped bool, w h return } + var rawBody []byte + var response *Operation if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -7130,6 +7703,7 @@ func (s *Server) handleGetOperationRequest(args [1]string, argsEscaped bool, w h OperationSummary: "Retrieve operation with ID", OperationID: "getOperation", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "OperationID", @@ -7242,7 +7816,7 @@ func (s *Server) handleGetScriptRequest(args [1]string, argsEscaped bool, w http // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -7271,6 +7845,8 @@ func (s *Server) handleGetScriptRequest(args [1]string, argsEscaped bool, w http return } + var rawBody []byte + var response *Script if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -7279,6 +7855,7 @@ func (s *Server) handleGetScriptRequest(args [1]string, argsEscaped bool, w http OperationSummary: "Get the specified script by ID", OperationID: "getScript", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "ScriptID", @@ -7391,7 +7968,7 @@ func (s *Server) handleGetScriptPolicyRequest(args [1]string, argsEscaped bool, // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -7420,6 +7997,8 @@ func (s *Server) handleGetScriptPolicyRequest(args [1]string, argsEscaped bool, return } + var rawBody []byte + var response *ScriptPolicy if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -7428,6 +8007,7 @@ func (s *Server) handleGetScriptPolicyRequest(args [1]string, argsEscaped bool, OperationSummary: "Get the specified script policy by ID", OperationID: "getScriptPolicy", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "ScriptPolicyID", @@ -7540,7 +8120,7 @@ func (s *Server) handleGetSubmissionRequest(args [1]string, argsEscaped bool, w // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -7569,6 +8149,8 @@ func (s *Server) handleGetSubmissionRequest(args [1]string, argsEscaped bool, w return } + var rawBody []byte + var response *Submission if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -7577,6 +8159,7 @@ func (s *Server) handleGetSubmissionRequest(args [1]string, argsEscaped bool, w OperationSummary: "Retrieve map with ID", OperationID: "getSubmission", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -7633,6 +8216,162 @@ func (s *Server) handleGetSubmissionRequest(args [1]string, argsEscaped bool, w } } +// handleGetUserThumbnailRequest handles getUserThumbnail operation. +// +// Get single user avatar thumbnail. +// +// GET /thumbnails/user/{UserID} +func (s *Server) handleGetUserThumbnailRequest(args [1]string, argsEscaped bool, w http.ResponseWriter, r *http.Request) { + statusWriter := &codeRecorder{ResponseWriter: w} + w = statusWriter + otelAttrs := []attribute.KeyValue{ + otelogen.OperationID("getUserThumbnail"), + semconv.HTTPRequestMethodKey.String("GET"), + semconv.HTTPRouteKey.String("/thumbnails/user/{UserID}"), + } + + // Start a span for this request. + ctx, span := s.cfg.Tracer.Start(r.Context(), GetUserThumbnailOperation, + trace.WithAttributes(otelAttrs...), + serverSpanKind, + ) + defer span.End() + + // Add Labeler to context. + labeler := &Labeler{attrs: otelAttrs} + ctx = contextWithLabeler(ctx, labeler) + + // Run stopwatch. + startTime := time.Now() + defer func() { + elapsedDuration := time.Since(startTime) + + attrSet := labeler.AttributeSet() + attrs := attrSet.ToSlice() + code := statusWriter.status + if code != 0 { + codeAttr := semconv.HTTPResponseStatusCode(code) + attrs = append(attrs, codeAttr) + span.SetAttributes(codeAttr) + } + attrOpt := metric.WithAttributes(attrs...) + + // Increment request counter. + s.requests.Add(ctx, 1, attrOpt) + + // Use floating point division here for higher precision (instead of Millisecond method). + s.duration.Record(ctx, float64(elapsedDuration)/float64(time.Millisecond), attrOpt) + }() + + var ( + recordError = func(stage string, err error) { + span.RecordError(err) + + // https://opentelemetry.io/docs/specs/semconv/http/http-spans/#status + // Span Status MUST be left unset if HTTP status code was in the 1xx, 2xx or 3xx ranges, + // unless there was another error (e.g., network error receiving the response body; or 3xx codes with + // max redirects exceeded), in which case status MUST be set to Error. + code := statusWriter.status + if code < 100 || code >= 500 { + span.SetStatus(codes.Error, stage) + } + + attrSet := labeler.AttributeSet() + attrs := attrSet.ToSlice() + if code != 0 { + attrs = append(attrs, semconv.HTTPResponseStatusCode(code)) + } + + s.errors.Add(ctx, 1, metric.WithAttributes(attrs...)) + } + err error + opErrContext = ogenerrors.OperationContext{ + Name: GetUserThumbnailOperation, + ID: "getUserThumbnail", + } + ) + params, err := decodeGetUserThumbnailParams(args, argsEscaped, r) + if err != nil { + err = &ogenerrors.DecodeParamsError{ + OperationContext: opErrContext, + Err: err, + } + defer recordError("DecodeParams", err) + s.cfg.ErrorHandler(ctx, w, r, err) + return + } + + var rawBody []byte + + var response *GetUserThumbnailFound + if m := s.cfg.Middleware; m != nil { + mreq := middleware.Request{ + Context: ctx, + OperationName: GetUserThumbnailOperation, + OperationSummary: "Get single user avatar thumbnail", + OperationID: "getUserThumbnail", + Body: nil, + RawBody: rawBody, + Params: middleware.Parameters{ + { + Name: "UserID", + In: "path", + }: params.UserID, + { + Name: "size", + In: "query", + }: params.Size, + }, + Raw: r, + } + + type ( + Request = struct{} + Params = GetUserThumbnailParams + Response = *GetUserThumbnailFound + ) + response, err = middleware.HookMiddleware[ + Request, + Params, + Response, + ]( + m, + mreq, + unpackGetUserThumbnailParams, + func(ctx context.Context, request Request, params Params) (response Response, err error) { + response, err = s.h.GetUserThumbnail(ctx, params) + return response, err + }, + ) + } else { + response, err = s.h.GetUserThumbnail(ctx, params) + } + if err != nil { + if errRes, ok := errors.Into[*ErrorStatusCode](err); ok { + if err := encodeErrorResponse(errRes, w, span); err != nil { + defer recordError("Internal", err) + } + return + } + if errors.Is(err, ht.ErrNotImplemented) { + s.cfg.ErrorHandler(ctx, w, r, err) + return + } + if err := encodeErrorResponse(s.h.NewError(ctx, err), w, span); err != nil { + defer recordError("Internal", err) + } + return + } + + if err := encodeGetUserThumbnailResponse(response, w, span); err != nil { + defer recordError("EncodeResponse", err) + if !errors.Is(err, ht.ErrInternalServerErrorResponse) { + s.cfg.ErrorHandler(ctx, w, r, err) + } + return + } +} + // handleListMapfixAuditEventsRequest handles listMapfixAuditEvents operation. // // Retrieve a list of audit events. @@ -7689,7 +8428,7 @@ func (s *Server) handleListMapfixAuditEventsRequest(args [1]string, argsEscaped // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -7718,6 +8457,8 @@ func (s *Server) handleListMapfixAuditEventsRequest(args [1]string, argsEscaped return } + var rawBody []byte + var response []AuditEvent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -7726,6 +8467,7 @@ func (s *Server) handleListMapfixAuditEventsRequest(args [1]string, argsEscaped OperationSummary: "Retrieve a list of audit events", OperationID: "listMapfixAuditEvents", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -7846,7 +8588,7 @@ func (s *Server) handleListMapfixesRequest(args [0]string, argsEscaped bool, w h // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -7875,6 +8617,8 @@ func (s *Server) handleListMapfixesRequest(args [0]string, argsEscaped bool, w h return } + var rawBody []byte + var response *Mapfixes if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -7883,6 +8627,7 @@ func (s *Server) handleListMapfixesRequest(args [0]string, argsEscaped bool, w h OperationSummary: "Get list of mapfixes", OperationID: "listMapfixes", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "Page", @@ -8035,7 +8780,7 @@ func (s *Server) handleListMapsRequest(args [0]string, argsEscaped bool, w http. // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -8064,6 +8809,8 @@ func (s *Server) handleListMapsRequest(args [0]string, argsEscaped bool, w http. return } + var rawBody []byte + var response []Map if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -8072,6 +8819,7 @@ func (s *Server) handleListMapsRequest(args [0]string, argsEscaped bool, w http. OperationSummary: "Get list of maps", OperationID: "listMaps", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "Page", @@ -8204,7 +8952,7 @@ func (s *Server) handleListScriptPolicyRequest(args [0]string, argsEscaped bool, // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -8233,6 +8981,8 @@ func (s *Server) handleListScriptPolicyRequest(args [0]string, argsEscaped bool, return } + var rawBody []byte + var response []ScriptPolicy if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -8241,6 +8991,7 @@ func (s *Server) handleListScriptPolicyRequest(args [0]string, argsEscaped bool, OperationSummary: "Get list of script policies", OperationID: "listScriptPolicy", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "Page", @@ -8369,7 +9120,7 @@ func (s *Server) handleListScriptsRequest(args [0]string, argsEscaped bool, w ht // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -8398,6 +9149,8 @@ func (s *Server) handleListScriptsRequest(args [0]string, argsEscaped bool, w ht return } + var rawBody []byte + var response []Script if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -8406,6 +9159,7 @@ func (s *Server) handleListScriptsRequest(args [0]string, argsEscaped bool, w ht OperationSummary: "Get list of scripts", OperationID: "listScripts", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "Page", @@ -8542,7 +9296,7 @@ func (s *Server) handleListSubmissionAuditEventsRequest(args [1]string, argsEsca // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -8571,6 +9325,8 @@ func (s *Server) handleListSubmissionAuditEventsRequest(args [1]string, argsEsca return } + var rawBody []byte + var response []AuditEvent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -8579,6 +9335,7 @@ func (s *Server) handleListSubmissionAuditEventsRequest(args [1]string, argsEsca OperationSummary: "Retrieve a list of audit events", OperationID: "listSubmissionAuditEvents", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -8699,7 +9456,7 @@ func (s *Server) handleListSubmissionsRequest(args [0]string, argsEscaped bool, // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -8728,6 +9485,8 @@ func (s *Server) handleListSubmissionsRequest(args [0]string, argsEscaped bool, return } + var rawBody []byte + var response *Submissions if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -8736,6 +9495,7 @@ func (s *Server) handleListSubmissionsRequest(args [0]string, argsEscaped bool, OperationSummary: "Get list of submissions", OperationID: "listSubmissions", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "Page", @@ -8888,7 +9648,7 @@ func (s *Server) handleReleaseSubmissionsRequest(args [0]string, argsEscaped boo // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -8952,7 +9712,9 @@ func (s *Server) handleReleaseSubmissionsRequest(args [0]string, argsEscaped boo return } } - request, close, err := s.decodeReleaseSubmissionsRequest(r) + + var rawBody []byte + request, rawBody, close, err := s.decodeReleaseSubmissionsRequest(r) if err != nil { err = &ogenerrors.DecodeRequestError{ OperationContext: opErrContext, @@ -8976,6 +9738,7 @@ func (s *Server) handleReleaseSubmissionsRequest(args [0]string, argsEscaped boo OperationSummary: "Release a set of uploaded maps. Role SubmissionRelease", OperationID: "releaseSubmissions", Body: request, + RawBody: rawBody, Params: middleware.Parameters{}, Raw: r, } @@ -9083,7 +9846,7 @@ func (s *Server) handleSessionRolesRequest(args [0]string, argsEscaped bool, w h // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -9148,6 +9911,8 @@ func (s *Server) handleSessionRolesRequest(args [0]string, argsEscaped bool, w h } } + var rawBody []byte + var response *Roles if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -9156,6 +9921,7 @@ func (s *Server) handleSessionRolesRequest(args [0]string, argsEscaped bool, w h OperationSummary: "Get list of roles for the current session", OperationID: "sessionRoles", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{}, Raw: r, } @@ -9263,7 +10029,7 @@ func (s *Server) handleSessionUserRequest(args [0]string, argsEscaped bool, w ht // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -9328,6 +10094,8 @@ func (s *Server) handleSessionUserRequest(args [0]string, argsEscaped bool, w ht } } + var rawBody []byte + var response *User if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -9336,6 +10104,7 @@ func (s *Server) handleSessionUserRequest(args [0]string, argsEscaped bool, w ht OperationSummary: "Get information about the currently logged in user", OperationID: "sessionUser", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{}, Raw: r, } @@ -9443,7 +10212,7 @@ func (s *Server) handleSessionValidateRequest(args [0]string, argsEscaped bool, // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -9508,6 +10277,8 @@ func (s *Server) handleSessionValidateRequest(args [0]string, argsEscaped bool, } } + var rawBody []byte + var response bool if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -9516,6 +10287,7 @@ func (s *Server) handleSessionValidateRequest(args [0]string, argsEscaped bool, OperationSummary: "Ask if the current session is valid", OperationID: "sessionValidate", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{}, Raw: r, } @@ -9623,7 +10395,7 @@ func (s *Server) handleSetMapfixCompletedRequest(args [1]string, argsEscaped boo // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -9698,6 +10470,8 @@ func (s *Server) handleSetMapfixCompletedRequest(args [1]string, argsEscaped boo return } + var rawBody []byte + var response *SetMapfixCompletedNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -9706,6 +10480,7 @@ func (s *Server) handleSetMapfixCompletedRequest(args [1]string, argsEscaped boo OperationSummary: "Called by maptest when a player completes the map", OperationID: "setMapfixCompleted", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -9818,7 +10593,7 @@ func (s *Server) handleSetSubmissionCompletedRequest(args [1]string, argsEscaped // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -9893,6 +10668,8 @@ func (s *Server) handleSetSubmissionCompletedRequest(args [1]string, argsEscaped return } + var rawBody []byte + var response *SetSubmissionCompletedNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -9901,6 +10678,7 @@ func (s *Server) handleSetSubmissionCompletedRequest(args [1]string, argsEscaped OperationSummary: "Called by maptest when a player completes the map", OperationID: "setSubmissionCompleted", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", @@ -10013,7 +10791,7 @@ func (s *Server) handleUpdateMapfixModelRequest(args [1]string, argsEscaped bool // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -10088,6 +10866,8 @@ func (s *Server) handleUpdateMapfixModelRequest(args [1]string, argsEscaped bool return } + var rawBody []byte + var response *UpdateMapfixModelNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -10096,6 +10876,7 @@ func (s *Server) handleUpdateMapfixModelRequest(args [1]string, argsEscaped bool OperationSummary: "Update model following role restrictions", OperationID: "updateMapfixModel", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "MapfixID", @@ -10216,7 +10997,7 @@ func (s *Server) handleUpdateScriptRequest(args [1]string, argsEscaped bool, w h // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -10290,7 +11071,9 @@ func (s *Server) handleUpdateScriptRequest(args [1]string, argsEscaped bool, w h s.cfg.ErrorHandler(ctx, w, r, err) return } - request, close, err := s.decodeUpdateScriptRequest(r) + + var rawBody []byte + request, rawBody, close, err := s.decodeUpdateScriptRequest(r) if err != nil { err = &ogenerrors.DecodeRequestError{ OperationContext: opErrContext, @@ -10314,6 +11097,7 @@ func (s *Server) handleUpdateScriptRequest(args [1]string, argsEscaped bool, w h OperationSummary: "Update the specified script by ID", OperationID: "updateScript", Body: request, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "ScriptID", @@ -10426,7 +11210,7 @@ func (s *Server) handleUpdateScriptPolicyRequest(args [1]string, argsEscaped boo // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -10500,7 +11284,9 @@ func (s *Server) handleUpdateScriptPolicyRequest(args [1]string, argsEscaped boo s.cfg.ErrorHandler(ctx, w, r, err) return } - request, close, err := s.decodeUpdateScriptPolicyRequest(r) + + var rawBody []byte + request, rawBody, close, err := s.decodeUpdateScriptPolicyRequest(r) if err != nil { err = &ogenerrors.DecodeRequestError{ OperationContext: opErrContext, @@ -10524,6 +11310,7 @@ func (s *Server) handleUpdateScriptPolicyRequest(args [1]string, argsEscaped boo OperationSummary: "Update the specified script policy by ID", OperationID: "updateScriptPolicy", Body: request, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "ScriptPolicyID", @@ -10636,7 +11423,7 @@ func (s *Server) handleUpdateSubmissionModelRequest(args [1]string, argsEscaped // unless there was another error (e.g., network error receiving the response body; or 3xx codes with // max redirects exceeded), in which case status MUST be set to Error. code := statusWriter.status - if code >= 100 && code < 500 { + if code < 100 || code >= 500 { span.SetStatus(codes.Error, stage) } @@ -10711,6 +11498,8 @@ func (s *Server) handleUpdateSubmissionModelRequest(args [1]string, argsEscaped return } + var rawBody []byte + var response *UpdateSubmissionModelNoContent if m := s.cfg.Middleware; m != nil { mreq := middleware.Request{ @@ -10719,6 +11508,7 @@ func (s *Server) handleUpdateSubmissionModelRequest(args [1]string, argsEscaped OperationSummary: "Update model following role restrictions", OperationID: "updateSubmissionModel", Body: nil, + RawBody: rawBody, Params: middleware.Parameters{ { Name: "SubmissionID", diff --git a/pkg/api/oas_json_gen.go b/pkg/api/oas_json_gen.go index 7ee6f05..7456cf8 100644 --- a/pkg/api/oas_json_gen.go +++ b/pkg/api/oas_json_gen.go @@ -8,7 +8,6 @@ import ( "github.com/go-faster/errors" "github.com/go-faster/jx" - "github.com/ogen-go/ogen/json" "github.com/ogen-go/ogen/validate" ) @@ -284,6 +283,580 @@ func (s *AuditEventEventData) UnmarshalJSON(data []byte) error { return s.Decode(d) } +// Encode implements json.Marshaler. +func (s *BatchAssetThumbnailsOK) Encode(e *jx.Encoder) { + e.ObjStart() + s.encodeFields(e) + e.ObjEnd() +} + +// encodeFields encodes fields. +func (s *BatchAssetThumbnailsOK) encodeFields(e *jx.Encoder) { + { + if s.Thumbnails.Set { + e.FieldStart("thumbnails") + s.Thumbnails.Encode(e) + } + } +} + +var jsonFieldsNameOfBatchAssetThumbnailsOK = [1]string{ + 0: "thumbnails", +} + +// Decode decodes BatchAssetThumbnailsOK from json. +func (s *BatchAssetThumbnailsOK) Decode(d *jx.Decoder) error { + if s == nil { + return errors.New("invalid: unable to decode BatchAssetThumbnailsOK to nil") + } + + if err := d.ObjBytes(func(d *jx.Decoder, k []byte) error { + switch string(k) { + case "thumbnails": + if err := func() error { + s.Thumbnails.Reset() + if err := s.Thumbnails.Decode(d); err != nil { + return err + } + return nil + }(); err != nil { + return errors.Wrap(err, "decode field \"thumbnails\"") + } + default: + return d.Skip() + } + return nil + }); err != nil { + return errors.Wrap(err, "decode BatchAssetThumbnailsOK") + } + + return nil +} + +// MarshalJSON implements stdjson.Marshaler. +func (s *BatchAssetThumbnailsOK) MarshalJSON() ([]byte, error) { + e := jx.Encoder{} + s.Encode(&e) + return e.Bytes(), nil +} + +// UnmarshalJSON implements stdjson.Unmarshaler. +func (s *BatchAssetThumbnailsOK) UnmarshalJSON(data []byte) error { + d := jx.DecodeBytes(data) + return s.Decode(d) +} + +// Encode implements json.Marshaler. +func (s BatchAssetThumbnailsOKThumbnails) Encode(e *jx.Encoder) { + e.ObjStart() + s.encodeFields(e) + e.ObjEnd() +} + +// encodeFields implements json.Marshaler. +func (s BatchAssetThumbnailsOKThumbnails) encodeFields(e *jx.Encoder) { + for k, elem := range s { + e.FieldStart(k) + + e.Str(elem) + } +} + +// Decode decodes BatchAssetThumbnailsOKThumbnails from json. +func (s *BatchAssetThumbnailsOKThumbnails) Decode(d *jx.Decoder) error { + if s == nil { + return errors.New("invalid: unable to decode BatchAssetThumbnailsOKThumbnails to nil") + } + m := s.init() + if err := d.ObjBytes(func(d *jx.Decoder, k []byte) error { + var elem string + if err := func() error { + v, err := d.Str() + elem = string(v) + if err != nil { + return err + } + return nil + }(); err != nil { + return errors.Wrapf(err, "decode field %q", k) + } + m[string(k)] = elem + return nil + }); err != nil { + return errors.Wrap(err, "decode BatchAssetThumbnailsOKThumbnails") + } + + return nil +} + +// MarshalJSON implements stdjson.Marshaler. +func (s BatchAssetThumbnailsOKThumbnails) MarshalJSON() ([]byte, error) { + e := jx.Encoder{} + s.Encode(&e) + return e.Bytes(), nil +} + +// UnmarshalJSON implements stdjson.Unmarshaler. +func (s *BatchAssetThumbnailsOKThumbnails) UnmarshalJSON(data []byte) error { + d := jx.DecodeBytes(data) + return s.Decode(d) +} + +// Encode implements json.Marshaler. +func (s *BatchAssetThumbnailsReq) Encode(e *jx.Encoder) { + e.ObjStart() + s.encodeFields(e) + e.ObjEnd() +} + +// encodeFields encodes fields. +func (s *BatchAssetThumbnailsReq) encodeFields(e *jx.Encoder) { + { + e.FieldStart("assetIds") + e.ArrStart() + for _, elem := range s.AssetIds { + e.UInt64(elem) + } + e.ArrEnd() + } + { + if s.Size.Set { + e.FieldStart("size") + s.Size.Encode(e) + } + } +} + +var jsonFieldsNameOfBatchAssetThumbnailsReq = [2]string{ + 0: "assetIds", + 1: "size", +} + +// Decode decodes BatchAssetThumbnailsReq from json. +func (s *BatchAssetThumbnailsReq) Decode(d *jx.Decoder) error { + if s == nil { + return errors.New("invalid: unable to decode BatchAssetThumbnailsReq to nil") + } + var requiredBitSet [1]uint8 + s.setDefaults() + + if err := d.ObjBytes(func(d *jx.Decoder, k []byte) error { + switch string(k) { + case "assetIds": + requiredBitSet[0] |= 1 << 0 + if err := func() error { + s.AssetIds = make([]uint64, 0) + if err := d.Arr(func(d *jx.Decoder) error { + var elem uint64 + v, err := d.UInt64() + elem = uint64(v) + if err != nil { + return err + } + s.AssetIds = append(s.AssetIds, elem) + return nil + }); err != nil { + return err + } + return nil + }(); err != nil { + return errors.Wrap(err, "decode field \"assetIds\"") + } + case "size": + if err := func() error { + s.Size.Reset() + if err := s.Size.Decode(d); err != nil { + return err + } + return nil + }(); err != nil { + return errors.Wrap(err, "decode field \"size\"") + } + default: + return d.Skip() + } + return nil + }); err != nil { + return errors.Wrap(err, "decode BatchAssetThumbnailsReq") + } + // Validate required fields. + var failures []validate.FieldError + for i, mask := range [1]uint8{ + 0b00000001, + } { + if result := (requiredBitSet[i] & mask) ^ mask; result != 0 { + // Mask only required fields and check equality to mask using XOR. + // + // If XOR result is not zero, result is not equal to expected, so some fields are missed. + // Bits of fields which would be set are actually bits of missed fields. + missed := bits.OnesCount8(result) + for bitN := 0; bitN < missed; bitN++ { + bitIdx := bits.TrailingZeros8(result) + fieldIdx := i*8 + bitIdx + var name string + if fieldIdx < len(jsonFieldsNameOfBatchAssetThumbnailsReq) { + name = jsonFieldsNameOfBatchAssetThumbnailsReq[fieldIdx] + } else { + name = strconv.Itoa(fieldIdx) + } + failures = append(failures, validate.FieldError{ + Name: name, + Error: validate.ErrFieldRequired, + }) + // Reset bit. + result &^= 1 << bitIdx + } + } + } + if len(failures) > 0 { + return &validate.Error{Fields: failures} + } + + return nil +} + +// MarshalJSON implements stdjson.Marshaler. +func (s *BatchAssetThumbnailsReq) MarshalJSON() ([]byte, error) { + e := jx.Encoder{} + s.Encode(&e) + return e.Bytes(), nil +} + +// UnmarshalJSON implements stdjson.Unmarshaler. +func (s *BatchAssetThumbnailsReq) UnmarshalJSON(data []byte) error { + d := jx.DecodeBytes(data) + return s.Decode(d) +} + +// Encode encodes BatchAssetThumbnailsReqSize as json. +func (s BatchAssetThumbnailsReqSize) Encode(e *jx.Encoder) { + e.Str(string(s)) +} + +// Decode decodes BatchAssetThumbnailsReqSize from json. +func (s *BatchAssetThumbnailsReqSize) Decode(d *jx.Decoder) error { + if s == nil { + return errors.New("invalid: unable to decode BatchAssetThumbnailsReqSize to nil") + } + v, err := d.StrBytes() + if err != nil { + return err + } + // Try to use constant string. + switch BatchAssetThumbnailsReqSize(v) { + case BatchAssetThumbnailsReqSize150x150: + *s = BatchAssetThumbnailsReqSize150x150 + case BatchAssetThumbnailsReqSize420x420: + *s = BatchAssetThumbnailsReqSize420x420 + case BatchAssetThumbnailsReqSize768x432: + *s = BatchAssetThumbnailsReqSize768x432 + default: + *s = BatchAssetThumbnailsReqSize(v) + } + + return nil +} + +// MarshalJSON implements stdjson.Marshaler. +func (s BatchAssetThumbnailsReqSize) MarshalJSON() ([]byte, error) { + e := jx.Encoder{} + s.Encode(&e) + return e.Bytes(), nil +} + +// UnmarshalJSON implements stdjson.Unmarshaler. +func (s *BatchAssetThumbnailsReqSize) UnmarshalJSON(data []byte) error { + d := jx.DecodeBytes(data) + return s.Decode(d) +} + +// Encode implements json.Marshaler. +func (s *BatchUserThumbnailsOK) Encode(e *jx.Encoder) { + e.ObjStart() + s.encodeFields(e) + e.ObjEnd() +} + +// encodeFields encodes fields. +func (s *BatchUserThumbnailsOK) encodeFields(e *jx.Encoder) { + { + if s.Thumbnails.Set { + e.FieldStart("thumbnails") + s.Thumbnails.Encode(e) + } + } +} + +var jsonFieldsNameOfBatchUserThumbnailsOK = [1]string{ + 0: "thumbnails", +} + +// Decode decodes BatchUserThumbnailsOK from json. +func (s *BatchUserThumbnailsOK) Decode(d *jx.Decoder) error { + if s == nil { + return errors.New("invalid: unable to decode BatchUserThumbnailsOK to nil") + } + + if err := d.ObjBytes(func(d *jx.Decoder, k []byte) error { + switch string(k) { + case "thumbnails": + if err := func() error { + s.Thumbnails.Reset() + if err := s.Thumbnails.Decode(d); err != nil { + return err + } + return nil + }(); err != nil { + return errors.Wrap(err, "decode field \"thumbnails\"") + } + default: + return d.Skip() + } + return nil + }); err != nil { + return errors.Wrap(err, "decode BatchUserThumbnailsOK") + } + + return nil +} + +// MarshalJSON implements stdjson.Marshaler. +func (s *BatchUserThumbnailsOK) MarshalJSON() ([]byte, error) { + e := jx.Encoder{} + s.Encode(&e) + return e.Bytes(), nil +} + +// UnmarshalJSON implements stdjson.Unmarshaler. +func (s *BatchUserThumbnailsOK) UnmarshalJSON(data []byte) error { + d := jx.DecodeBytes(data) + return s.Decode(d) +} + +// Encode implements json.Marshaler. +func (s BatchUserThumbnailsOKThumbnails) Encode(e *jx.Encoder) { + e.ObjStart() + s.encodeFields(e) + e.ObjEnd() +} + +// encodeFields implements json.Marshaler. +func (s BatchUserThumbnailsOKThumbnails) encodeFields(e *jx.Encoder) { + for k, elem := range s { + e.FieldStart(k) + + e.Str(elem) + } +} + +// Decode decodes BatchUserThumbnailsOKThumbnails from json. +func (s *BatchUserThumbnailsOKThumbnails) Decode(d *jx.Decoder) error { + if s == nil { + return errors.New("invalid: unable to decode BatchUserThumbnailsOKThumbnails to nil") + } + m := s.init() + if err := d.ObjBytes(func(d *jx.Decoder, k []byte) error { + var elem string + if err := func() error { + v, err := d.Str() + elem = string(v) + if err != nil { + return err + } + return nil + }(); err != nil { + return errors.Wrapf(err, "decode field %q", k) + } + m[string(k)] = elem + return nil + }); err != nil { + return errors.Wrap(err, "decode BatchUserThumbnailsOKThumbnails") + } + + return nil +} + +// MarshalJSON implements stdjson.Marshaler. +func (s BatchUserThumbnailsOKThumbnails) MarshalJSON() ([]byte, error) { + e := jx.Encoder{} + s.Encode(&e) + return e.Bytes(), nil +} + +// UnmarshalJSON implements stdjson.Unmarshaler. +func (s *BatchUserThumbnailsOKThumbnails) UnmarshalJSON(data []byte) error { + d := jx.DecodeBytes(data) + return s.Decode(d) +} + +// Encode implements json.Marshaler. +func (s *BatchUserThumbnailsReq) Encode(e *jx.Encoder) { + e.ObjStart() + s.encodeFields(e) + e.ObjEnd() +} + +// encodeFields encodes fields. +func (s *BatchUserThumbnailsReq) encodeFields(e *jx.Encoder) { + { + e.FieldStart("userIds") + e.ArrStart() + for _, elem := range s.UserIds { + e.UInt64(elem) + } + e.ArrEnd() + } + { + if s.Size.Set { + e.FieldStart("size") + s.Size.Encode(e) + } + } +} + +var jsonFieldsNameOfBatchUserThumbnailsReq = [2]string{ + 0: "userIds", + 1: "size", +} + +// Decode decodes BatchUserThumbnailsReq from json. +func (s *BatchUserThumbnailsReq) Decode(d *jx.Decoder) error { + if s == nil { + return errors.New("invalid: unable to decode BatchUserThumbnailsReq to nil") + } + var requiredBitSet [1]uint8 + s.setDefaults() + + if err := d.ObjBytes(func(d *jx.Decoder, k []byte) error { + switch string(k) { + case "userIds": + requiredBitSet[0] |= 1 << 0 + if err := func() error { + s.UserIds = make([]uint64, 0) + if err := d.Arr(func(d *jx.Decoder) error { + var elem uint64 + v, err := d.UInt64() + elem = uint64(v) + if err != nil { + return err + } + s.UserIds = append(s.UserIds, elem) + return nil + }); err != nil { + return err + } + return nil + }(); err != nil { + return errors.Wrap(err, "decode field \"userIds\"") + } + case "size": + if err := func() error { + s.Size.Reset() + if err := s.Size.Decode(d); err != nil { + return err + } + return nil + }(); err != nil { + return errors.Wrap(err, "decode field \"size\"") + } + default: + return d.Skip() + } + return nil + }); err != nil { + return errors.Wrap(err, "decode BatchUserThumbnailsReq") + } + // Validate required fields. + var failures []validate.FieldError + for i, mask := range [1]uint8{ + 0b00000001, + } { + if result := (requiredBitSet[i] & mask) ^ mask; result != 0 { + // Mask only required fields and check equality to mask using XOR. + // + // If XOR result is not zero, result is not equal to expected, so some fields are missed. + // Bits of fields which would be set are actually bits of missed fields. + missed := bits.OnesCount8(result) + for bitN := 0; bitN < missed; bitN++ { + bitIdx := bits.TrailingZeros8(result) + fieldIdx := i*8 + bitIdx + var name string + if fieldIdx < len(jsonFieldsNameOfBatchUserThumbnailsReq) { + name = jsonFieldsNameOfBatchUserThumbnailsReq[fieldIdx] + } else { + name = strconv.Itoa(fieldIdx) + } + failures = append(failures, validate.FieldError{ + Name: name, + Error: validate.ErrFieldRequired, + }) + // Reset bit. + result &^= 1 << bitIdx + } + } + } + if len(failures) > 0 { + return &validate.Error{Fields: failures} + } + + return nil +} + +// MarshalJSON implements stdjson.Marshaler. +func (s *BatchUserThumbnailsReq) MarshalJSON() ([]byte, error) { + e := jx.Encoder{} + s.Encode(&e) + return e.Bytes(), nil +} + +// UnmarshalJSON implements stdjson.Unmarshaler. +func (s *BatchUserThumbnailsReq) UnmarshalJSON(data []byte) error { + d := jx.DecodeBytes(data) + return s.Decode(d) +} + +// Encode encodes BatchUserThumbnailsReqSize as json. +func (s BatchUserThumbnailsReqSize) Encode(e *jx.Encoder) { + e.Str(string(s)) +} + +// Decode decodes BatchUserThumbnailsReqSize from json. +func (s *BatchUserThumbnailsReqSize) Decode(d *jx.Decoder) error { + if s == nil { + return errors.New("invalid: unable to decode BatchUserThumbnailsReqSize to nil") + } + v, err := d.StrBytes() + if err != nil { + return err + } + // Try to use constant string. + switch BatchUserThumbnailsReqSize(v) { + case BatchUserThumbnailsReqSize150x150: + *s = BatchUserThumbnailsReqSize150x150 + case BatchUserThumbnailsReqSize420x420: + *s = BatchUserThumbnailsReqSize420x420 + case BatchUserThumbnailsReqSize768x432: + *s = BatchUserThumbnailsReqSize768x432 + default: + *s = BatchUserThumbnailsReqSize(v) + } + + return nil +} + +// MarshalJSON implements stdjson.Marshaler. +func (s BatchUserThumbnailsReqSize) MarshalJSON() ([]byte, error) { + e := jx.Encoder{} + s.Encode(&e) + return e.Bytes(), nil +} + +// UnmarshalJSON implements stdjson.Unmarshaler. +func (s *BatchUserThumbnailsReqSize) UnmarshalJSON(data []byte) error { + d := jx.DecodeBytes(data) + return s.Decode(d) +} + // Encode implements json.Marshaler. func (s *Error) Encode(e *jx.Encoder) { e.ObjStart() @@ -1546,6 +2119,140 @@ func (s *OperationID) UnmarshalJSON(data []byte) error { return s.Decode(d) } +// Encode encodes BatchAssetThumbnailsOKThumbnails as json. +func (o OptBatchAssetThumbnailsOKThumbnails) Encode(e *jx.Encoder) { + if !o.Set { + return + } + o.Value.Encode(e) +} + +// Decode decodes BatchAssetThumbnailsOKThumbnails from json. +func (o *OptBatchAssetThumbnailsOKThumbnails) Decode(d *jx.Decoder) error { + if o == nil { + return errors.New("invalid: unable to decode OptBatchAssetThumbnailsOKThumbnails to nil") + } + o.Set = true + o.Value = make(BatchAssetThumbnailsOKThumbnails) + if err := o.Value.Decode(d); err != nil { + return err + } + return nil +} + +// MarshalJSON implements stdjson.Marshaler. +func (s OptBatchAssetThumbnailsOKThumbnails) MarshalJSON() ([]byte, error) { + e := jx.Encoder{} + s.Encode(&e) + return e.Bytes(), nil +} + +// UnmarshalJSON implements stdjson.Unmarshaler. +func (s *OptBatchAssetThumbnailsOKThumbnails) UnmarshalJSON(data []byte) error { + d := jx.DecodeBytes(data) + return s.Decode(d) +} + +// Encode encodes BatchAssetThumbnailsReqSize as json. +func (o OptBatchAssetThumbnailsReqSize) Encode(e *jx.Encoder) { + if !o.Set { + return + } + e.Str(string(o.Value)) +} + +// Decode decodes BatchAssetThumbnailsReqSize from json. +func (o *OptBatchAssetThumbnailsReqSize) Decode(d *jx.Decoder) error { + if o == nil { + return errors.New("invalid: unable to decode OptBatchAssetThumbnailsReqSize to nil") + } + o.Set = true + if err := o.Value.Decode(d); err != nil { + return err + } + return nil +} + +// MarshalJSON implements stdjson.Marshaler. +func (s OptBatchAssetThumbnailsReqSize) MarshalJSON() ([]byte, error) { + e := jx.Encoder{} + s.Encode(&e) + return e.Bytes(), nil +} + +// UnmarshalJSON implements stdjson.Unmarshaler. +func (s *OptBatchAssetThumbnailsReqSize) UnmarshalJSON(data []byte) error { + d := jx.DecodeBytes(data) + return s.Decode(d) +} + +// Encode encodes BatchUserThumbnailsOKThumbnails as json. +func (o OptBatchUserThumbnailsOKThumbnails) Encode(e *jx.Encoder) { + if !o.Set { + return + } + o.Value.Encode(e) +} + +// Decode decodes BatchUserThumbnailsOKThumbnails from json. +func (o *OptBatchUserThumbnailsOKThumbnails) Decode(d *jx.Decoder) error { + if o == nil { + return errors.New("invalid: unable to decode OptBatchUserThumbnailsOKThumbnails to nil") + } + o.Set = true + o.Value = make(BatchUserThumbnailsOKThumbnails) + if err := o.Value.Decode(d); err != nil { + return err + } + return nil +} + +// MarshalJSON implements stdjson.Marshaler. +func (s OptBatchUserThumbnailsOKThumbnails) MarshalJSON() ([]byte, error) { + e := jx.Encoder{} + s.Encode(&e) + return e.Bytes(), nil +} + +// UnmarshalJSON implements stdjson.Unmarshaler. +func (s *OptBatchUserThumbnailsOKThumbnails) UnmarshalJSON(data []byte) error { + d := jx.DecodeBytes(data) + return s.Decode(d) +} + +// Encode encodes BatchUserThumbnailsReqSize as json. +func (o OptBatchUserThumbnailsReqSize) Encode(e *jx.Encoder) { + if !o.Set { + return + } + e.Str(string(o.Value)) +} + +// Decode decodes BatchUserThumbnailsReqSize from json. +func (o *OptBatchUserThumbnailsReqSize) Decode(d *jx.Decoder) error { + if o == nil { + return errors.New("invalid: unable to decode OptBatchUserThumbnailsReqSize to nil") + } + o.Set = true + if err := o.Value.Decode(d); err != nil { + return err + } + return nil +} + +// MarshalJSON implements stdjson.Marshaler. +func (s OptBatchUserThumbnailsReqSize) MarshalJSON() ([]byte, error) { + e := jx.Encoder{} + s.Encode(&e) + return e.Bytes(), nil +} + +// UnmarshalJSON implements stdjson.Unmarshaler. +func (s *OptBatchUserThumbnailsReqSize) UnmarshalJSON(data []byte) error { + d := jx.DecodeBytes(data) + return s.Decode(d) +} + // Encode encodes int32 as json. func (o OptInt32) Encode(e *jx.Encoder) { if !o.Set { diff --git a/pkg/api/oas_operations_gen.go b/pkg/api/oas_operations_gen.go index fa2d75d..b251bf1 100644 --- a/pkg/api/oas_operations_gen.go +++ b/pkg/api/oas_operations_gen.go @@ -30,6 +30,8 @@ const ( ActionSubmissionTriggerUploadOperation OperationName = "ActionSubmissionTriggerUpload" ActionSubmissionTriggerValidateOperation OperationName = "ActionSubmissionTriggerValidate" ActionSubmissionValidatedOperation OperationName = "ActionSubmissionValidated" + BatchAssetThumbnailsOperation OperationName = "BatchAssetThumbnails" + BatchUserThumbnailsOperation OperationName = "BatchUserThumbnails" CreateMapfixOperation OperationName = "CreateMapfix" CreateMapfixAuditCommentOperation OperationName = "CreateMapfixAuditComment" CreateScriptOperation OperationName = "CreateScript" @@ -40,12 +42,14 @@ const ( DeleteScriptOperation OperationName = "DeleteScript" DeleteScriptPolicyOperation OperationName = "DeleteScriptPolicy" DownloadMapAssetOperation OperationName = "DownloadMapAsset" + GetAssetThumbnailOperation OperationName = "GetAssetThumbnail" GetMapOperation OperationName = "GetMap" GetMapfixOperation OperationName = "GetMapfix" GetOperationOperation OperationName = "GetOperation" GetScriptOperation OperationName = "GetScript" GetScriptPolicyOperation OperationName = "GetScriptPolicy" GetSubmissionOperation OperationName = "GetSubmission" + GetUserThumbnailOperation OperationName = "GetUserThumbnail" ListMapfixAuditEventsOperation OperationName = "ListMapfixAuditEvents" ListMapfixesOperation OperationName = "ListMapfixes" ListMapsOperation OperationName = "ListMaps" diff --git a/pkg/api/oas_parameters_gen.go b/pkg/api/oas_parameters_gen.go index 5107683..b6b84b5 100644 --- a/pkg/api/oas_parameters_gen.go +++ b/pkg/api/oas_parameters_gen.go @@ -7,7 +7,6 @@ import ( "net/url" "github.com/go-faster/errors" - "github.com/ogen-go/ogen/conv" "github.com/ogen-go/ogen/middleware" "github.com/ogen-go/ogen/ogenerrors" @@ -77,6 +76,7 @@ func decodeActionMapfixAcceptedParams(args [1]string, argsEscaped bool, r *http. MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -160,6 +160,7 @@ func decodeActionMapfixRejectParams(args [1]string, argsEscaped bool, r *http.Re MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -243,6 +244,7 @@ func decodeActionMapfixRequestChangesParams(args [1]string, argsEscaped bool, r MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -326,6 +328,7 @@ func decodeActionMapfixResetSubmittingParams(args [1]string, argsEscaped bool, r MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -409,6 +412,7 @@ func decodeActionMapfixRetryValidateParams(args [1]string, argsEscaped bool, r * MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -492,6 +496,7 @@ func decodeActionMapfixRevokeParams(args [1]string, argsEscaped bool, r *http.Re MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -575,6 +580,7 @@ func decodeActionMapfixTriggerReleaseParams(args [1]string, argsEscaped bool, r MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -658,6 +664,7 @@ func decodeActionMapfixTriggerSubmitParams(args [1]string, argsEscaped bool, r * MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -741,6 +748,7 @@ func decodeActionMapfixTriggerSubmitUncheckedParams(args [1]string, argsEscaped MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -824,6 +832,7 @@ func decodeActionMapfixTriggerUploadParams(args [1]string, argsEscaped bool, r * MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -907,6 +916,7 @@ func decodeActionMapfixTriggerValidateParams(args [1]string, argsEscaped bool, r MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -990,6 +1000,7 @@ func decodeActionMapfixUploadedParams(args [1]string, argsEscaped bool, r *http. MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -1073,6 +1084,7 @@ func decodeActionMapfixValidatedParams(args [1]string, argsEscaped bool, r *http MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -1156,6 +1168,7 @@ func decodeActionSubmissionAcceptedParams(args [1]string, argsEscaped bool, r *h MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -1239,6 +1252,7 @@ func decodeActionSubmissionRejectParams(args [1]string, argsEscaped bool, r *htt MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -1322,6 +1336,7 @@ func decodeActionSubmissionRequestChangesParams(args [1]string, argsEscaped bool MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -1405,6 +1420,7 @@ func decodeActionSubmissionResetSubmittingParams(args [1]string, argsEscaped boo MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -1488,6 +1504,7 @@ func decodeActionSubmissionRetryValidateParams(args [1]string, argsEscaped bool, MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -1571,6 +1588,7 @@ func decodeActionSubmissionRevokeParams(args [1]string, argsEscaped bool, r *htt MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -1654,6 +1672,7 @@ func decodeActionSubmissionTriggerSubmitParams(args [1]string, argsEscaped bool, MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -1737,6 +1756,7 @@ func decodeActionSubmissionTriggerSubmitUncheckedParams(args [1]string, argsEsca MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -1820,6 +1840,7 @@ func decodeActionSubmissionTriggerUploadParams(args [1]string, argsEscaped bool, MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -1903,6 +1924,7 @@ func decodeActionSubmissionTriggerValidateParams(args [1]string, argsEscaped boo MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -1986,6 +2008,7 @@ func decodeActionSubmissionValidatedParams(args [1]string, argsEscaped bool, r * MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -2069,6 +2092,7 @@ func decodeCreateMapfixAuditCommentParams(args [1]string, argsEscaped bool, r *h MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -2152,6 +2176,7 @@ func decodeCreateSubmissionAuditCommentParams(args [1]string, argsEscaped bool, MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -2235,6 +2260,7 @@ func decodeDeleteScriptParams(args [1]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.ScriptID)); err != nil { return errors.Wrap(err, "int") } @@ -2318,6 +2344,7 @@ func decodeDeleteScriptPolicyParams(args [1]string, argsEscaped bool, r *http.Re MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.ScriptPolicyID)); err != nil { return errors.Wrap(err, "int") } @@ -2400,6 +2427,7 @@ func decodeDownloadMapAssetParams(args [1]string, argsEscaped bool, r *http.Requ MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapID)); err != nil { return errors.Wrap(err, "int") } @@ -2421,6 +2449,143 @@ func decodeDownloadMapAssetParams(args [1]string, argsEscaped bool, r *http.Requ return params, nil } +// GetAssetThumbnailParams is parameters of getAssetThumbnail operation. +type GetAssetThumbnailParams struct { + AssetID uint64 + Size OptGetAssetThumbnailSize `json:",omitempty,omitzero"` +} + +func unpackGetAssetThumbnailParams(packed middleware.Parameters) (params GetAssetThumbnailParams) { + { + key := middleware.ParameterKey{ + Name: "AssetID", + In: "path", + } + params.AssetID = packed[key].(uint64) + } + { + key := middleware.ParameterKey{ + Name: "size", + In: "query", + } + if v, ok := packed[key]; ok { + params.Size = v.(OptGetAssetThumbnailSize) + } + } + return params +} + +func decodeGetAssetThumbnailParams(args [1]string, argsEscaped bool, r *http.Request) (params GetAssetThumbnailParams, _ error) { + q := uri.NewQueryDecoder(r.URL.Query()) + // Decode path: AssetID. + if err := func() error { + param := args[0] + if argsEscaped { + unescaped, err := url.PathUnescape(args[0]) + if err != nil { + return errors.Wrap(err, "unescape path") + } + param = unescaped + } + if len(param) > 0 { + d := uri.NewPathDecoder(uri.PathDecoderConfig{ + Param: "AssetID", + Value: param, + Style: uri.PathStyleSimple, + Explode: false, + }) + + if err := func() error { + val, err := d.DecodeValue() + if err != nil { + return err + } + + c, err := conv.ToUint64(val) + if err != nil { + return err + } + + params.AssetID = c + return nil + }(); err != nil { + return err + } + } else { + return validate.ErrFieldRequired + } + return nil + }(); err != nil { + return params, &ogenerrors.DecodeParamError{ + Name: "AssetID", + In: "path", + Err: err, + } + } + // Set default value for query: size. + { + val := GetAssetThumbnailSize("420x420") + params.Size.SetTo(val) + } + // Decode query: size. + if err := func() error { + cfg := uri.QueryParameterDecodingConfig{ + Name: "size", + Style: uri.QueryStyleForm, + Explode: true, + } + + if err := q.HasParam(cfg); err == nil { + if err := q.DecodeParam(cfg, func(d uri.Decoder) error { + var paramsDotSizeVal GetAssetThumbnailSize + if err := func() error { + val, err := d.DecodeValue() + if err != nil { + return err + } + + c, err := conv.ToString(val) + if err != nil { + return err + } + + paramsDotSizeVal = GetAssetThumbnailSize(c) + return nil + }(); err != nil { + return err + } + params.Size.SetTo(paramsDotSizeVal) + return nil + }); err != nil { + return err + } + if err := func() error { + if value, ok := params.Size.Get(); ok { + if err := func() error { + if err := value.Validate(); err != nil { + return err + } + return nil + }(); err != nil { + return err + } + } + return nil + }(); err != nil { + return err + } + } + return nil + }(); err != nil { + return params, &ogenerrors.DecodeParamError{ + Name: "size", + In: "query", + Err: err, + } + } + return params, nil +} + // GetMapParams is parameters of getMap operation. type GetMapParams struct { // The unique identifier for a map. @@ -2483,6 +2648,7 @@ func decodeGetMapParams(args [1]string, argsEscaped bool, r *http.Request) (para MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapID)); err != nil { return errors.Wrap(err, "int") } @@ -2566,6 +2732,7 @@ func decodeGetMapfixParams(args [1]string, argsEscaped bool, r *http.Request) (p MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -2649,6 +2816,7 @@ func decodeGetOperationParams(args [1]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.OperationID)); err != nil { return errors.Wrap(err, "int") } @@ -2732,6 +2900,7 @@ func decodeGetScriptParams(args [1]string, argsEscaped bool, r *http.Request) (p MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.ScriptID)); err != nil { return errors.Wrap(err, "int") } @@ -2815,6 +2984,7 @@ func decodeGetScriptPolicyParams(args [1]string, argsEscaped bool, r *http.Reque MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.ScriptPolicyID)); err != nil { return errors.Wrap(err, "int") } @@ -2898,6 +3068,7 @@ func decodeGetSubmissionParams(args [1]string, argsEscaped bool, r *http.Request MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -2919,6 +3090,143 @@ func decodeGetSubmissionParams(args [1]string, argsEscaped bool, r *http.Request return params, nil } +// GetUserThumbnailParams is parameters of getUserThumbnail operation. +type GetUserThumbnailParams struct { + UserID uint64 + Size OptGetUserThumbnailSize `json:",omitempty,omitzero"` +} + +func unpackGetUserThumbnailParams(packed middleware.Parameters) (params GetUserThumbnailParams) { + { + key := middleware.ParameterKey{ + Name: "UserID", + In: "path", + } + params.UserID = packed[key].(uint64) + } + { + key := middleware.ParameterKey{ + Name: "size", + In: "query", + } + if v, ok := packed[key]; ok { + params.Size = v.(OptGetUserThumbnailSize) + } + } + return params +} + +func decodeGetUserThumbnailParams(args [1]string, argsEscaped bool, r *http.Request) (params GetUserThumbnailParams, _ error) { + q := uri.NewQueryDecoder(r.URL.Query()) + // Decode path: UserID. + if err := func() error { + param := args[0] + if argsEscaped { + unescaped, err := url.PathUnescape(args[0]) + if err != nil { + return errors.Wrap(err, "unescape path") + } + param = unescaped + } + if len(param) > 0 { + d := uri.NewPathDecoder(uri.PathDecoderConfig{ + Param: "UserID", + Value: param, + Style: uri.PathStyleSimple, + Explode: false, + }) + + if err := func() error { + val, err := d.DecodeValue() + if err != nil { + return err + } + + c, err := conv.ToUint64(val) + if err != nil { + return err + } + + params.UserID = c + return nil + }(); err != nil { + return err + } + } else { + return validate.ErrFieldRequired + } + return nil + }(); err != nil { + return params, &ogenerrors.DecodeParamError{ + Name: "UserID", + In: "path", + Err: err, + } + } + // Set default value for query: size. + { + val := GetUserThumbnailSize("150x150") + params.Size.SetTo(val) + } + // Decode query: size. + if err := func() error { + cfg := uri.QueryParameterDecodingConfig{ + Name: "size", + Style: uri.QueryStyleForm, + Explode: true, + } + + if err := q.HasParam(cfg); err == nil { + if err := q.DecodeParam(cfg, func(d uri.Decoder) error { + var paramsDotSizeVal GetUserThumbnailSize + if err := func() error { + val, err := d.DecodeValue() + if err != nil { + return err + } + + c, err := conv.ToString(val) + if err != nil { + return err + } + + paramsDotSizeVal = GetUserThumbnailSize(c) + return nil + }(); err != nil { + return err + } + params.Size.SetTo(paramsDotSizeVal) + return nil + }); err != nil { + return err + } + if err := func() error { + if value, ok := params.Size.Get(); ok { + if err := func() error { + if err := value.Validate(); err != nil { + return err + } + return nil + }(); err != nil { + return err + } + } + return nil + }(); err != nil { + return err + } + } + return nil + }(); err != nil { + return params, &ogenerrors.DecodeParamError{ + Name: "size", + In: "query", + Err: err, + } + } + return params, nil +} + // ListMapfixAuditEventsParams is parameters of listMapfixAuditEvents operation. type ListMapfixAuditEventsParams struct { // The unique identifier for a mapfix. @@ -2998,6 +3306,7 @@ func decodeListMapfixAuditEventsParams(args [1]string, argsEscaped bool, r *http MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -3051,6 +3360,7 @@ func decodeListMapfixAuditEventsParams(args [1]string, argsEscaped bool, r *http MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Page)); err != nil { return errors.Wrap(err, "int") } @@ -3104,6 +3414,7 @@ func decodeListMapfixAuditEventsParams(args [1]string, argsEscaped bool, r *http MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Limit)); err != nil { return errors.Wrap(err, "int") } @@ -3129,24 +3440,24 @@ func decodeListMapfixAuditEventsParams(args [1]string, argsEscaped bool, r *http type ListMapfixesParams struct { Page int32 Limit int32 - DisplayName OptString - Creator OptString + DisplayName OptString `json:",omitempty,omitzero"` + Creator OptString `json:",omitempty,omitzero"` // Game ID: * `1` - Bhop * `2` - Surf * `5` - FlyTrials. - GameID OptInt32 + GameID OptInt32 `json:",omitempty,omitzero"` // Sort order: * `0` - Disabled * `1` - DisplayNameAscending * `2` - DisplayNameDescending * `3` - // DateAscending * `4` - DateDescending. - Sort OptInt32 - Submitter OptInt64 - AssetID OptInt64 - AssetVersion OptInt64 - TargetAssetID OptInt64 + Sort OptInt32 `json:",omitempty,omitzero"` + Submitter OptInt64 `json:",omitempty,omitzero"` + AssetID OptInt64 `json:",omitempty,omitzero"` + AssetVersion OptInt64 `json:",omitempty,omitzero"` + TargetAssetID OptInt64 `json:",omitempty,omitzero"` // // Phase: Creation * `0` - UnderConstruction * `1` - ChangesRequested // // Phase: Review * `2` - Submitting * `3` - Submitted // // Phase: Testing * `4` - AcceptedUnvalidated // pending script review, can re-trigger validation // * `5` - Validating * `6` - Validated * `7` - Uploading // // Phase: Final MapfixStatus * `8` - Uploaded // uploaded to the group, but pending release * `9` // - Rejected. - StatusID OptInt32 + StatusID OptInt32 `json:",omitempty,omitzero"` } func unpackListMapfixesParams(packed middleware.Parameters) (params ListMapfixesParams) { @@ -3285,6 +3596,7 @@ func decodeListMapfixesParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Page)); err != nil { return errors.Wrap(err, "int") } @@ -3338,6 +3650,7 @@ func decodeListMapfixesParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Limit)); err != nil { return errors.Wrap(err, "int") } @@ -3392,13 +3705,17 @@ func decodeListMapfixesParams(args [0]string, argsEscaped bool, r *http.Request) if value, ok := params.DisplayName.Get(); ok { if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(value)); err != nil { return errors.Wrap(err, "string") } @@ -3456,13 +3773,17 @@ func decodeListMapfixesParams(args [0]string, argsEscaped bool, r *http.Request) if value, ok := params.Creator.Get(); ok { if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(value)); err != nil { return errors.Wrap(err, "string") } @@ -3528,6 +3849,7 @@ func decodeListMapfixesParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -3593,6 +3915,7 @@ func decodeListMapfixesParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -3658,6 +3981,7 @@ func decodeListMapfixesParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -3723,6 +4047,7 @@ func decodeListMapfixesParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -3788,6 +4113,7 @@ func decodeListMapfixesParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -3853,6 +4179,7 @@ func decodeListMapfixesParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -3918,6 +4245,7 @@ func decodeListMapfixesParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -3946,12 +4274,12 @@ func decodeListMapfixesParams(args [0]string, argsEscaped bool, r *http.Request) type ListMapsParams struct { Page int32 Limit int32 - DisplayName OptString - Creator OptString - GameID OptInt32 + DisplayName OptString `json:",omitempty,omitzero"` + Creator OptString `json:",omitempty,omitzero"` + GameID OptInt32 `json:",omitempty,omitzero"` // Sort order: * `0` - Disabled * `1` - DisplayNameAscending * `2` - DisplayNameDescending * `3` - // DateAscending * `4` - DateDescending. - Sort OptInt32 + Sort OptInt32 `json:",omitempty,omitzero"` } func unpackListMapsParams(packed middleware.Parameters) (params ListMapsParams) { @@ -4045,6 +4373,7 @@ func decodeListMapsParams(args [0]string, argsEscaped bool, r *http.Request) (pa MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Page)); err != nil { return errors.Wrap(err, "int") } @@ -4098,6 +4427,7 @@ func decodeListMapsParams(args [0]string, argsEscaped bool, r *http.Request) (pa MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Limit)); err != nil { return errors.Wrap(err, "int") } @@ -4152,13 +4482,17 @@ func decodeListMapsParams(args [0]string, argsEscaped bool, r *http.Request) (pa if value, ok := params.DisplayName.Get(); ok { if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(value)); err != nil { return errors.Wrap(err, "string") } @@ -4216,13 +4550,17 @@ func decodeListMapsParams(args [0]string, argsEscaped bool, r *http.Request) (pa if value, ok := params.Creator.Get(); ok { if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(value)); err != nil { return errors.Wrap(err, "string") } @@ -4288,6 +4626,7 @@ func decodeListMapsParams(args [0]string, argsEscaped bool, r *http.Request) (pa MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -4353,6 +4692,7 @@ func decodeListMapsParams(args [0]string, argsEscaped bool, r *http.Request) (pa MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -4381,9 +4721,9 @@ func decodeListMapsParams(args [0]string, argsEscaped bool, r *http.Request) (pa type ListScriptPolicyParams struct { Page int32 Limit int32 - FromScriptHash OptString - ToScriptID OptInt64 - Policy OptInt32 + FromScriptHash OptString `json:",omitempty,omitzero"` + ToScriptID OptInt64 `json:",omitempty,omitzero"` + Policy OptInt32 `json:",omitempty,omitzero"` } func unpackListScriptPolicyParams(packed middleware.Parameters) (params ListScriptPolicyParams) { @@ -4468,6 +4808,7 @@ func decodeListScriptPolicyParams(args [0]string, argsEscaped bool, r *http.Requ MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Page)); err != nil { return errors.Wrap(err, "int") } @@ -4521,6 +4862,7 @@ func decodeListScriptPolicyParams(args [0]string, argsEscaped bool, r *http.Requ MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Limit)); err != nil { return errors.Wrap(err, "int") } @@ -4575,13 +4917,17 @@ func decodeListScriptPolicyParams(args [0]string, argsEscaped bool, r *http.Requ if value, ok := params.FromScriptHash.Get(); ok { if err := func() error { if err := (validate.String{ - MinLength: 16, - MinLengthSet: true, - MaxLength: 16, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 16, + MinLengthSet: true, + MaxLength: 16, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(value)); err != nil { return errors.Wrap(err, "string") } @@ -4647,6 +4993,7 @@ func decodeListScriptPolicyParams(args [0]string, argsEscaped bool, r *http.Requ MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -4712,6 +5059,7 @@ func decodeListScriptPolicyParams(args [0]string, argsEscaped bool, r *http.Requ MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -4740,11 +5088,11 @@ func decodeListScriptPolicyParams(args [0]string, argsEscaped bool, r *http.Requ type ListScriptsParams struct { Page int32 Limit int32 - Hash OptString - Name OptString - Source OptString - ResourceType OptInt32 - ResourceID OptInt64 + Hash OptString `json:",omitempty,omitzero"` + Name OptString `json:",omitempty,omitzero"` + Source OptString `json:",omitempty,omitzero"` + ResourceType OptInt32 `json:",omitempty,omitzero"` + ResourceID OptInt64 `json:",omitempty,omitzero"` } func unpackListScriptsParams(packed middleware.Parameters) (params ListScriptsParams) { @@ -4847,6 +5195,7 @@ func decodeListScriptsParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Page)); err != nil { return errors.Wrap(err, "int") } @@ -4900,6 +5249,7 @@ func decodeListScriptsParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Limit)); err != nil { return errors.Wrap(err, "int") } @@ -4954,13 +5304,17 @@ func decodeListScriptsParams(args [0]string, argsEscaped bool, r *http.Request) if value, ok := params.Hash.Get(); ok { if err := func() error { if err := (validate.String{ - MinLength: 16, - MinLengthSet: true, - MaxLength: 16, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 16, + MinLengthSet: true, + MaxLength: 16, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(value)); err != nil { return errors.Wrap(err, "string") } @@ -5018,13 +5372,17 @@ func decodeListScriptsParams(args [0]string, argsEscaped bool, r *http.Request) if value, ok := params.Name.Get(); ok { if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(value)); err != nil { return errors.Wrap(err, "string") } @@ -5082,13 +5440,17 @@ func decodeListScriptsParams(args [0]string, argsEscaped bool, r *http.Request) if value, ok := params.Source.Get(); ok { if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 1048576, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 1048576, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(value)); err != nil { return errors.Wrap(err, "string") } @@ -5154,6 +5516,7 @@ func decodeListScriptsParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -5219,6 +5582,7 @@ func decodeListScriptsParams(args [0]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -5322,6 +5686,7 @@ func decodeListSubmissionAuditEventsParams(args [1]string, argsEscaped bool, r * MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -5375,6 +5740,7 @@ func decodeListSubmissionAuditEventsParams(args [1]string, argsEscaped bool, r * MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Page)); err != nil { return errors.Wrap(err, "int") } @@ -5428,6 +5794,7 @@ func decodeListSubmissionAuditEventsParams(args [1]string, argsEscaped bool, r * MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Limit)); err != nil { return errors.Wrap(err, "int") } @@ -5453,24 +5820,24 @@ func decodeListSubmissionAuditEventsParams(args [1]string, argsEscaped bool, r * type ListSubmissionsParams struct { Page int32 Limit int32 - DisplayName OptString - Creator OptString + DisplayName OptString `json:",omitempty,omitzero"` + Creator OptString `json:",omitempty,omitzero"` // Game ID: * `1` - Bhop * `2` - Surf * `5` - FlyTrials. - GameID OptInt32 + GameID OptInt32 `json:",omitempty,omitzero"` // Sort order: * `0` - Disabled * `1` - DisplayNameAscending * `2` - DisplayNameDescending * `3` - // DateAscending * `4` - DateDescending. - Sort OptInt32 - Submitter OptInt64 - AssetID OptInt64 - AssetVersion OptInt64 - UploadedAssetID OptInt64 + Sort OptInt32 `json:",omitempty,omitzero"` + Submitter OptInt64 `json:",omitempty,omitzero"` + AssetID OptInt64 `json:",omitempty,omitzero"` + AssetVersion OptInt64 `json:",omitempty,omitzero"` + UploadedAssetID OptInt64 `json:",omitempty,omitzero"` // // Phase: Creation * `0` - UnderConstruction * `1` - ChangesRequested // // Phase: Review * `2` - Submitting * `3` - Submitted // // Phase: Testing * `4` - AcceptedUnvalidated // pending script review, can re-trigger validation // * `5` - Validating * `6` - Validated * `7` - Uploading * `8` - Uploaded // uploaded to the group, // but pending release // // Phase: Final SubmissionStatus * `9` - Rejected * `10` - Released. - StatusID OptInt32 + StatusID OptInt32 `json:",omitempty,omitzero"` } func unpackListSubmissionsParams(packed middleware.Parameters) (params ListSubmissionsParams) { @@ -5609,6 +5976,7 @@ func decodeListSubmissionsParams(args [0]string, argsEscaped bool, r *http.Reque MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Page)); err != nil { return errors.Wrap(err, "int") } @@ -5662,6 +6030,7 @@ func decodeListSubmissionsParams(args [0]string, argsEscaped bool, r *http.Reque MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.Limit)); err != nil { return errors.Wrap(err, "int") } @@ -5716,13 +6085,17 @@ func decodeListSubmissionsParams(args [0]string, argsEscaped bool, r *http.Reque if value, ok := params.DisplayName.Get(); ok { if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(value)); err != nil { return errors.Wrap(err, "string") } @@ -5780,13 +6153,17 @@ func decodeListSubmissionsParams(args [0]string, argsEscaped bool, r *http.Reque if value, ok := params.Creator.Get(); ok { if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(value)); err != nil { return errors.Wrap(err, "string") } @@ -5852,6 +6229,7 @@ func decodeListSubmissionsParams(args [0]string, argsEscaped bool, r *http.Reque MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -5917,6 +6295,7 @@ func decodeListSubmissionsParams(args [0]string, argsEscaped bool, r *http.Reque MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -5982,6 +6361,7 @@ func decodeListSubmissionsParams(args [0]string, argsEscaped bool, r *http.Reque MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -6047,6 +6427,7 @@ func decodeListSubmissionsParams(args [0]string, argsEscaped bool, r *http.Reque MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -6112,6 +6493,7 @@ func decodeListSubmissionsParams(args [0]string, argsEscaped bool, r *http.Reque MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -6177,6 +6559,7 @@ func decodeListSubmissionsParams(args [0]string, argsEscaped bool, r *http.Reque MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -6242,6 +6625,7 @@ func decodeListSubmissionsParams(args [0]string, argsEscaped bool, r *http.Reque MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -6328,6 +6712,7 @@ func decodeSetMapfixCompletedParams(args [1]string, argsEscaped bool, r *http.Re MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -6411,6 +6796,7 @@ func decodeSetSubmissionCompletedParams(args [1]string, argsEscaped bool, r *htt MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -6511,6 +6897,7 @@ func decodeUpdateMapfixModelParams(args [1]string, argsEscaped bool, r *http.Req MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.MapfixID)); err != nil { return errors.Wrap(err, "int") } @@ -6564,6 +6951,7 @@ func decodeUpdateMapfixModelParams(args [1]string, argsEscaped bool, r *http.Req MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.ModelID)); err != nil { return errors.Wrap(err, "int") } @@ -6617,6 +7005,7 @@ func decodeUpdateMapfixModelParams(args [1]string, argsEscaped bool, r *http.Req MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.ModelVersion)); err != nil { return errors.Wrap(err, "int") } @@ -6700,6 +7089,7 @@ func decodeUpdateScriptParams(args [1]string, argsEscaped bool, r *http.Request) MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.ScriptID)); err != nil { return errors.Wrap(err, "int") } @@ -6783,6 +7173,7 @@ func decodeUpdateScriptPolicyParams(args [1]string, argsEscaped bool, r *http.Re MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.ScriptPolicyID)); err != nil { return errors.Wrap(err, "int") } @@ -6883,6 +7274,7 @@ func decodeUpdateSubmissionModelParams(args [1]string, argsEscaped bool, r *http MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -6936,6 +7328,7 @@ func decodeUpdateSubmissionModelParams(args [1]string, argsEscaped bool, r *http MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.ModelID)); err != nil { return errors.Wrap(err, "int") } @@ -6989,6 +7382,7 @@ func decodeUpdateSubmissionModelParams(args [1]string, argsEscaped bool, r *http MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(params.ModelVersion)); err != nil { return errors.Wrap(err, "int") } diff --git a/pkg/api/oas_request_decoders_gen.go b/pkg/api/oas_request_decoders_gen.go index 24ca5bf..8e8cbb3 100644 --- a/pkg/api/oas_request_decoders_gen.go +++ b/pkg/api/oas_request_decoders_gen.go @@ -3,6 +3,7 @@ package api import ( + "bytes" "fmt" "io" "mime" @@ -10,13 +11,13 @@ import ( "github.com/go-faster/errors" "github.com/go-faster/jx" - "github.com/ogen-go/ogen/ogenerrors" "github.com/ogen-go/ogen/validate" ) -func (s *Server) decodeCreateMapfixRequest(r *http.Request) ( - req *MapfixTriggerCreate, +func (s *Server) decodeBatchAssetThumbnailsRequest(r *http.Request) ( + req *BatchAssetThumbnailsReq, + rawBody []byte, close func() error, rerr error, ) { @@ -37,22 +38,187 @@ func (s *Server) decodeCreateMapfixRequest(r *http.Request) ( }() ct, _, err := mime.ParseMediaType(r.Header.Get("Content-Type")) if err != nil { - return req, close, errors.Wrap(err, "parse media type") + return req, rawBody, close, errors.Wrap(err, "parse media type") } switch { case ct == "application/json": if r.ContentLength == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } buf, err := io.ReadAll(r.Body) + defer func() { + _ = r.Body.Close() + }() if err != nil { - return req, close, err + return req, rawBody, close, err } + // Reset the body to allow for downstream reading. + r.Body = io.NopCloser(bytes.NewBuffer(buf)) + if len(buf) == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } + rawBody = append(rawBody, buf...) + d := jx.DecodeBytes(buf) + + var request BatchAssetThumbnailsReq + if err := func() error { + if err := request.Decode(d); err != nil { + return err + } + if err := d.Skip(); err != io.EOF { + return errors.New("unexpected trailing data") + } + return nil + }(); err != nil { + err = &ogenerrors.DecodeBodyError{ + ContentType: ct, + Body: buf, + Err: err, + } + return req, rawBody, close, err + } + if err := func() error { + if err := request.Validate(); err != nil { + return err + } + return nil + }(); err != nil { + return req, rawBody, close, errors.Wrap(err, "validate") + } + return &request, rawBody, close, nil + default: + return req, rawBody, close, validate.InvalidContentType(ct) + } +} + +func (s *Server) decodeBatchUserThumbnailsRequest(r *http.Request) ( + req *BatchUserThumbnailsReq, + rawBody []byte, + close func() error, + rerr error, +) { + var closers []func() error + close = func() error { + var merr error + // Close in reverse order, to match defer behavior. + for i := len(closers) - 1; i >= 0; i-- { + c := closers[i] + merr = errors.Join(merr, c()) + } + return merr + } + defer func() { + if rerr != nil { + rerr = errors.Join(rerr, close()) + } + }() + ct, _, err := mime.ParseMediaType(r.Header.Get("Content-Type")) + if err != nil { + return req, rawBody, close, errors.Wrap(err, "parse media type") + } + switch { + case ct == "application/json": + if r.ContentLength == 0 { + return req, rawBody, close, validate.ErrBodyRequired + } + buf, err := io.ReadAll(r.Body) + defer func() { + _ = r.Body.Close() + }() + if err != nil { + return req, rawBody, close, err + } + + // Reset the body to allow for downstream reading. + r.Body = io.NopCloser(bytes.NewBuffer(buf)) + + if len(buf) == 0 { + return req, rawBody, close, validate.ErrBodyRequired + } + + rawBody = append(rawBody, buf...) + d := jx.DecodeBytes(buf) + + var request BatchUserThumbnailsReq + if err := func() error { + if err := request.Decode(d); err != nil { + return err + } + if err := d.Skip(); err != io.EOF { + return errors.New("unexpected trailing data") + } + return nil + }(); err != nil { + err = &ogenerrors.DecodeBodyError{ + ContentType: ct, + Body: buf, + Err: err, + } + return req, rawBody, close, err + } + if err := func() error { + if err := request.Validate(); err != nil { + return err + } + return nil + }(); err != nil { + return req, rawBody, close, errors.Wrap(err, "validate") + } + return &request, rawBody, close, nil + default: + return req, rawBody, close, validate.InvalidContentType(ct) + } +} + +func (s *Server) decodeCreateMapfixRequest(r *http.Request) ( + req *MapfixTriggerCreate, + rawBody []byte, + close func() error, + rerr error, +) { + var closers []func() error + close = func() error { + var merr error + // Close in reverse order, to match defer behavior. + for i := len(closers) - 1; i >= 0; i-- { + c := closers[i] + merr = errors.Join(merr, c()) + } + return merr + } + defer func() { + if rerr != nil { + rerr = errors.Join(rerr, close()) + } + }() + ct, _, err := mime.ParseMediaType(r.Header.Get("Content-Type")) + if err != nil { + return req, rawBody, close, errors.Wrap(err, "parse media type") + } + switch { + case ct == "application/json": + if r.ContentLength == 0 { + return req, rawBody, close, validate.ErrBodyRequired + } + buf, err := io.ReadAll(r.Body) + defer func() { + _ = r.Body.Close() + }() + if err != nil { + return req, rawBody, close, err + } + + // Reset the body to allow for downstream reading. + r.Body = io.NopCloser(bytes.NewBuffer(buf)) + + if len(buf) == 0 { + return req, rawBody, close, validate.ErrBodyRequired + } + + rawBody = append(rawBody, buf...) d := jx.DecodeBytes(buf) var request MapfixTriggerCreate @@ -70,7 +236,7 @@ func (s *Server) decodeCreateMapfixRequest(r *http.Request) ( Body: buf, Err: err, } - return req, close, err + return req, rawBody, close, err } if err := func() error { if err := request.Validate(); err != nil { @@ -78,16 +244,17 @@ func (s *Server) decodeCreateMapfixRequest(r *http.Request) ( } return nil }(); err != nil { - return req, close, errors.Wrap(err, "validate") + return req, rawBody, close, errors.Wrap(err, "validate") } - return &request, close, nil + return &request, rawBody, close, nil default: - return req, close, validate.InvalidContentType(ct) + return req, rawBody, close, validate.InvalidContentType(ct) } } func (s *Server) decodeCreateMapfixAuditCommentRequest(r *http.Request) ( req CreateMapfixAuditCommentReq, + rawBody []byte, close func() error, rerr error, ) { @@ -108,20 +275,21 @@ func (s *Server) decodeCreateMapfixAuditCommentRequest(r *http.Request) ( }() ct, _, err := mime.ParseMediaType(r.Header.Get("Content-Type")) if err != nil { - return req, close, errors.Wrap(err, "parse media type") + return req, rawBody, close, errors.Wrap(err, "parse media type") } switch { case ct == "text/plain": reader := r.Body request := CreateMapfixAuditCommentReq{Data: reader} - return request, close, nil + return request, rawBody, close, nil default: - return req, close, validate.InvalidContentType(ct) + return req, rawBody, close, validate.InvalidContentType(ct) } } func (s *Server) decodeCreateScriptRequest(r *http.Request) ( req *ScriptCreate, + rawBody []byte, close func() error, rerr error, ) { @@ -142,22 +310,29 @@ func (s *Server) decodeCreateScriptRequest(r *http.Request) ( }() ct, _, err := mime.ParseMediaType(r.Header.Get("Content-Type")) if err != nil { - return req, close, errors.Wrap(err, "parse media type") + return req, rawBody, close, errors.Wrap(err, "parse media type") } switch { case ct == "application/json": if r.ContentLength == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } buf, err := io.ReadAll(r.Body) + defer func() { + _ = r.Body.Close() + }() if err != nil { - return req, close, err + return req, rawBody, close, err } + // Reset the body to allow for downstream reading. + r.Body = io.NopCloser(bytes.NewBuffer(buf)) + if len(buf) == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } + rawBody = append(rawBody, buf...) d := jx.DecodeBytes(buf) var request ScriptCreate @@ -175,7 +350,7 @@ func (s *Server) decodeCreateScriptRequest(r *http.Request) ( Body: buf, Err: err, } - return req, close, err + return req, rawBody, close, err } if err := func() error { if err := request.Validate(); err != nil { @@ -183,16 +358,17 @@ func (s *Server) decodeCreateScriptRequest(r *http.Request) ( } return nil }(); err != nil { - return req, close, errors.Wrap(err, "validate") + return req, rawBody, close, errors.Wrap(err, "validate") } - return &request, close, nil + return &request, rawBody, close, nil default: - return req, close, validate.InvalidContentType(ct) + return req, rawBody, close, validate.InvalidContentType(ct) } } func (s *Server) decodeCreateScriptPolicyRequest(r *http.Request) ( req *ScriptPolicyCreate, + rawBody []byte, close func() error, rerr error, ) { @@ -213,22 +389,29 @@ func (s *Server) decodeCreateScriptPolicyRequest(r *http.Request) ( }() ct, _, err := mime.ParseMediaType(r.Header.Get("Content-Type")) if err != nil { - return req, close, errors.Wrap(err, "parse media type") + return req, rawBody, close, errors.Wrap(err, "parse media type") } switch { case ct == "application/json": if r.ContentLength == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } buf, err := io.ReadAll(r.Body) + defer func() { + _ = r.Body.Close() + }() if err != nil { - return req, close, err + return req, rawBody, close, err } + // Reset the body to allow for downstream reading. + r.Body = io.NopCloser(bytes.NewBuffer(buf)) + if len(buf) == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } + rawBody = append(rawBody, buf...) d := jx.DecodeBytes(buf) var request ScriptPolicyCreate @@ -246,7 +429,7 @@ func (s *Server) decodeCreateScriptPolicyRequest(r *http.Request) ( Body: buf, Err: err, } - return req, close, err + return req, rawBody, close, err } if err := func() error { if err := request.Validate(); err != nil { @@ -254,16 +437,17 @@ func (s *Server) decodeCreateScriptPolicyRequest(r *http.Request) ( } return nil }(); err != nil { - return req, close, errors.Wrap(err, "validate") + return req, rawBody, close, errors.Wrap(err, "validate") } - return &request, close, nil + return &request, rawBody, close, nil default: - return req, close, validate.InvalidContentType(ct) + return req, rawBody, close, validate.InvalidContentType(ct) } } func (s *Server) decodeCreateSubmissionRequest(r *http.Request) ( req *SubmissionTriggerCreate, + rawBody []byte, close func() error, rerr error, ) { @@ -284,22 +468,29 @@ func (s *Server) decodeCreateSubmissionRequest(r *http.Request) ( }() ct, _, err := mime.ParseMediaType(r.Header.Get("Content-Type")) if err != nil { - return req, close, errors.Wrap(err, "parse media type") + return req, rawBody, close, errors.Wrap(err, "parse media type") } switch { case ct == "application/json": if r.ContentLength == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } buf, err := io.ReadAll(r.Body) + defer func() { + _ = r.Body.Close() + }() if err != nil { - return req, close, err + return req, rawBody, close, err } + // Reset the body to allow for downstream reading. + r.Body = io.NopCloser(bytes.NewBuffer(buf)) + if len(buf) == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } + rawBody = append(rawBody, buf...) d := jx.DecodeBytes(buf) var request SubmissionTriggerCreate @@ -317,7 +508,7 @@ func (s *Server) decodeCreateSubmissionRequest(r *http.Request) ( Body: buf, Err: err, } - return req, close, err + return req, rawBody, close, err } if err := func() error { if err := request.Validate(); err != nil { @@ -325,16 +516,17 @@ func (s *Server) decodeCreateSubmissionRequest(r *http.Request) ( } return nil }(); err != nil { - return req, close, errors.Wrap(err, "validate") + return req, rawBody, close, errors.Wrap(err, "validate") } - return &request, close, nil + return &request, rawBody, close, nil default: - return req, close, validate.InvalidContentType(ct) + return req, rawBody, close, validate.InvalidContentType(ct) } } func (s *Server) decodeCreateSubmissionAdminRequest(r *http.Request) ( req *SubmissionTriggerCreate, + rawBody []byte, close func() error, rerr error, ) { @@ -355,22 +547,29 @@ func (s *Server) decodeCreateSubmissionAdminRequest(r *http.Request) ( }() ct, _, err := mime.ParseMediaType(r.Header.Get("Content-Type")) if err != nil { - return req, close, errors.Wrap(err, "parse media type") + return req, rawBody, close, errors.Wrap(err, "parse media type") } switch { case ct == "application/json": if r.ContentLength == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } buf, err := io.ReadAll(r.Body) + defer func() { + _ = r.Body.Close() + }() if err != nil { - return req, close, err + return req, rawBody, close, err } + // Reset the body to allow for downstream reading. + r.Body = io.NopCloser(bytes.NewBuffer(buf)) + if len(buf) == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } + rawBody = append(rawBody, buf...) d := jx.DecodeBytes(buf) var request SubmissionTriggerCreate @@ -388,7 +587,7 @@ func (s *Server) decodeCreateSubmissionAdminRequest(r *http.Request) ( Body: buf, Err: err, } - return req, close, err + return req, rawBody, close, err } if err := func() error { if err := request.Validate(); err != nil { @@ -396,16 +595,17 @@ func (s *Server) decodeCreateSubmissionAdminRequest(r *http.Request) ( } return nil }(); err != nil { - return req, close, errors.Wrap(err, "validate") + return req, rawBody, close, errors.Wrap(err, "validate") } - return &request, close, nil + return &request, rawBody, close, nil default: - return req, close, validate.InvalidContentType(ct) + return req, rawBody, close, validate.InvalidContentType(ct) } } func (s *Server) decodeCreateSubmissionAuditCommentRequest(r *http.Request) ( req CreateSubmissionAuditCommentReq, + rawBody []byte, close func() error, rerr error, ) { @@ -426,20 +626,21 @@ func (s *Server) decodeCreateSubmissionAuditCommentRequest(r *http.Request) ( }() ct, _, err := mime.ParseMediaType(r.Header.Get("Content-Type")) if err != nil { - return req, close, errors.Wrap(err, "parse media type") + return req, rawBody, close, errors.Wrap(err, "parse media type") } switch { case ct == "text/plain": reader := r.Body request := CreateSubmissionAuditCommentReq{Data: reader} - return request, close, nil + return request, rawBody, close, nil default: - return req, close, validate.InvalidContentType(ct) + return req, rawBody, close, validate.InvalidContentType(ct) } } func (s *Server) decodeReleaseSubmissionsRequest(r *http.Request) ( req []ReleaseInfo, + rawBody []byte, close func() error, rerr error, ) { @@ -460,22 +661,29 @@ func (s *Server) decodeReleaseSubmissionsRequest(r *http.Request) ( }() ct, _, err := mime.ParseMediaType(r.Header.Get("Content-Type")) if err != nil { - return req, close, errors.Wrap(err, "parse media type") + return req, rawBody, close, errors.Wrap(err, "parse media type") } switch { case ct == "application/json": if r.ContentLength == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } buf, err := io.ReadAll(r.Body) + defer func() { + _ = r.Body.Close() + }() if err != nil { - return req, close, err + return req, rawBody, close, err } + // Reset the body to allow for downstream reading. + r.Body = io.NopCloser(bytes.NewBuffer(buf)) + if len(buf) == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } + rawBody = append(rawBody, buf...) d := jx.DecodeBytes(buf) var request []ReleaseInfo @@ -501,7 +709,7 @@ func (s *Server) decodeReleaseSubmissionsRequest(r *http.Request) ( Body: buf, Err: err, } - return req, close, err + return req, rawBody, close, err } if err := func() error { if request == nil { @@ -534,16 +742,17 @@ func (s *Server) decodeReleaseSubmissionsRequest(r *http.Request) ( } return nil }(); err != nil { - return req, close, errors.Wrap(err, "validate") + return req, rawBody, close, errors.Wrap(err, "validate") } - return request, close, nil + return request, rawBody, close, nil default: - return req, close, validate.InvalidContentType(ct) + return req, rawBody, close, validate.InvalidContentType(ct) } } func (s *Server) decodeUpdateScriptRequest(r *http.Request) ( req *ScriptUpdate, + rawBody []byte, close func() error, rerr error, ) { @@ -564,22 +773,29 @@ func (s *Server) decodeUpdateScriptRequest(r *http.Request) ( }() ct, _, err := mime.ParseMediaType(r.Header.Get("Content-Type")) if err != nil { - return req, close, errors.Wrap(err, "parse media type") + return req, rawBody, close, errors.Wrap(err, "parse media type") } switch { case ct == "application/json": if r.ContentLength == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } buf, err := io.ReadAll(r.Body) + defer func() { + _ = r.Body.Close() + }() if err != nil { - return req, close, err + return req, rawBody, close, err } + // Reset the body to allow for downstream reading. + r.Body = io.NopCloser(bytes.NewBuffer(buf)) + if len(buf) == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } + rawBody = append(rawBody, buf...) d := jx.DecodeBytes(buf) var request ScriptUpdate @@ -597,7 +813,7 @@ func (s *Server) decodeUpdateScriptRequest(r *http.Request) ( Body: buf, Err: err, } - return req, close, err + return req, rawBody, close, err } if err := func() error { if err := request.Validate(); err != nil { @@ -605,16 +821,17 @@ func (s *Server) decodeUpdateScriptRequest(r *http.Request) ( } return nil }(); err != nil { - return req, close, errors.Wrap(err, "validate") + return req, rawBody, close, errors.Wrap(err, "validate") } - return &request, close, nil + return &request, rawBody, close, nil default: - return req, close, validate.InvalidContentType(ct) + return req, rawBody, close, validate.InvalidContentType(ct) } } func (s *Server) decodeUpdateScriptPolicyRequest(r *http.Request) ( req *ScriptPolicyUpdate, + rawBody []byte, close func() error, rerr error, ) { @@ -635,22 +852,29 @@ func (s *Server) decodeUpdateScriptPolicyRequest(r *http.Request) ( }() ct, _, err := mime.ParseMediaType(r.Header.Get("Content-Type")) if err != nil { - return req, close, errors.Wrap(err, "parse media type") + return req, rawBody, close, errors.Wrap(err, "parse media type") } switch { case ct == "application/json": if r.ContentLength == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } buf, err := io.ReadAll(r.Body) + defer func() { + _ = r.Body.Close() + }() if err != nil { - return req, close, err + return req, rawBody, close, err } + // Reset the body to allow for downstream reading. + r.Body = io.NopCloser(bytes.NewBuffer(buf)) + if len(buf) == 0 { - return req, close, validate.ErrBodyRequired + return req, rawBody, close, validate.ErrBodyRequired } + rawBody = append(rawBody, buf...) d := jx.DecodeBytes(buf) var request ScriptPolicyUpdate @@ -668,7 +892,7 @@ func (s *Server) decodeUpdateScriptPolicyRequest(r *http.Request) ( Body: buf, Err: err, } - return req, close, err + return req, rawBody, close, err } if err := func() error { if err := request.Validate(); err != nil { @@ -676,10 +900,10 @@ func (s *Server) decodeUpdateScriptPolicyRequest(r *http.Request) ( } return nil }(); err != nil { - return req, close, errors.Wrap(err, "validate") + return req, rawBody, close, errors.Wrap(err, "validate") } - return &request, close, nil + return &request, rawBody, close, nil default: - return req, close, validate.InvalidContentType(ct) + return req, rawBody, close, validate.InvalidContentType(ct) } } diff --git a/pkg/api/oas_request_encoders_gen.go b/pkg/api/oas_request_encoders_gen.go index 09c700c..6520bb4 100644 --- a/pkg/api/oas_request_encoders_gen.go +++ b/pkg/api/oas_request_encoders_gen.go @@ -7,10 +7,37 @@ import ( "net/http" "github.com/go-faster/jx" - ht "github.com/ogen-go/ogen/http" ) +func encodeBatchAssetThumbnailsRequest( + req *BatchAssetThumbnailsReq, + r *http.Request, +) error { + const contentType = "application/json" + e := new(jx.Encoder) + { + req.Encode(e) + } + encoded := e.Bytes() + ht.SetBody(r, bytes.NewReader(encoded), contentType) + return nil +} + +func encodeBatchUserThumbnailsRequest( + req *BatchUserThumbnailsReq, + r *http.Request, +) error { + const contentType = "application/json" + e := new(jx.Encoder) + { + req.Encode(e) + } + encoded := e.Bytes() + ht.SetBody(r, bytes.NewReader(encoded), contentType) + return nil +} + func encodeCreateMapfixRequest( req *MapfixTriggerCreate, r *http.Request, diff --git a/pkg/api/oas_response_decoders_gen.go b/pkg/api/oas_response_decoders_gen.go index 25ecc22..c5de549 100644 --- a/pkg/api/oas_response_decoders_gen.go +++ b/pkg/api/oas_response_decoders_gen.go @@ -11,8 +11,9 @@ import ( "github.com/go-faster/errors" "github.com/go-faster/jx" - + "github.com/ogen-go/ogen/conv" "github.com/ogen-go/ogen/ogenerrors" + "github.com/ogen-go/ogen/uri" "github.com/ogen-go/ogen/validate" ) @@ -1456,6 +1457,190 @@ func decodeActionSubmissionValidatedResponse(resp *http.Response) (res *ActionSu return res, errors.Wrap(defRes, "error") } +func decodeBatchAssetThumbnailsResponse(resp *http.Response) (res *BatchAssetThumbnailsOK, _ error) { + switch resp.StatusCode { + case 200: + // Code 200. + ct, _, err := mime.ParseMediaType(resp.Header.Get("Content-Type")) + if err != nil { + return res, errors.Wrap(err, "parse media type") + } + switch { + case ct == "application/json": + buf, err := io.ReadAll(resp.Body) + if err != nil { + return res, err + } + d := jx.DecodeBytes(buf) + + var response BatchAssetThumbnailsOK + if err := func() error { + if err := response.Decode(d); err != nil { + return err + } + if err := d.Skip(); err != io.EOF { + return errors.New("unexpected trailing data") + } + return nil + }(); err != nil { + err = &ogenerrors.DecodeBodyError{ + ContentType: ct, + Body: buf, + Err: err, + } + return res, err + } + return &response, nil + default: + return res, validate.InvalidContentType(ct) + } + } + // Convenient error response. + defRes, err := func() (res *ErrorStatusCode, err error) { + ct, _, err := mime.ParseMediaType(resp.Header.Get("Content-Type")) + if err != nil { + return res, errors.Wrap(err, "parse media type") + } + switch { + case ct == "application/json": + buf, err := io.ReadAll(resp.Body) + if err != nil { + return res, err + } + d := jx.DecodeBytes(buf) + + var response Error + if err := func() error { + if err := response.Decode(d); err != nil { + return err + } + if err := d.Skip(); err != io.EOF { + return errors.New("unexpected trailing data") + } + return nil + }(); err != nil { + err = &ogenerrors.DecodeBodyError{ + ContentType: ct, + Body: buf, + Err: err, + } + return res, err + } + // Validate response. + if err := func() error { + if err := response.Validate(); err != nil { + return err + } + return nil + }(); err != nil { + return res, errors.Wrap(err, "validate") + } + return &ErrorStatusCode{ + StatusCode: resp.StatusCode, + Response: response, + }, nil + default: + return res, validate.InvalidContentType(ct) + } + }() + if err != nil { + return res, errors.Wrapf(err, "default (code %d)", resp.StatusCode) + } + return res, errors.Wrap(defRes, "error") +} + +func decodeBatchUserThumbnailsResponse(resp *http.Response) (res *BatchUserThumbnailsOK, _ error) { + switch resp.StatusCode { + case 200: + // Code 200. + ct, _, err := mime.ParseMediaType(resp.Header.Get("Content-Type")) + if err != nil { + return res, errors.Wrap(err, "parse media type") + } + switch { + case ct == "application/json": + buf, err := io.ReadAll(resp.Body) + if err != nil { + return res, err + } + d := jx.DecodeBytes(buf) + + var response BatchUserThumbnailsOK + if err := func() error { + if err := response.Decode(d); err != nil { + return err + } + if err := d.Skip(); err != io.EOF { + return errors.New("unexpected trailing data") + } + return nil + }(); err != nil { + err = &ogenerrors.DecodeBodyError{ + ContentType: ct, + Body: buf, + Err: err, + } + return res, err + } + return &response, nil + default: + return res, validate.InvalidContentType(ct) + } + } + // Convenient error response. + defRes, err := func() (res *ErrorStatusCode, err error) { + ct, _, err := mime.ParseMediaType(resp.Header.Get("Content-Type")) + if err != nil { + return res, errors.Wrap(err, "parse media type") + } + switch { + case ct == "application/json": + buf, err := io.ReadAll(resp.Body) + if err != nil { + return res, err + } + d := jx.DecodeBytes(buf) + + var response Error + if err := func() error { + if err := response.Decode(d); err != nil { + return err + } + if err := d.Skip(); err != io.EOF { + return errors.New("unexpected trailing data") + } + return nil + }(); err != nil { + err = &ogenerrors.DecodeBodyError{ + ContentType: ct, + Body: buf, + Err: err, + } + return res, err + } + // Validate response. + if err := func() error { + if err := response.Validate(); err != nil { + return err + } + return nil + }(); err != nil { + return res, errors.Wrap(err, "validate") + } + return &ErrorStatusCode{ + StatusCode: resp.StatusCode, + Response: response, + }, nil + default: + return res, validate.InvalidContentType(ct) + } + }() + if err != nil { + return res, errors.Wrapf(err, "default (code %d)", resp.StatusCode) + } + return res, errors.Wrap(defRes, "error") +} + func decodeCreateMapfixResponse(resp *http.Response) (res *OperationID, _ error) { switch resp.StatusCode { case 201: @@ -2277,6 +2462,105 @@ func decodeDownloadMapAssetResponse(resp *http.Response) (res DownloadMapAssetOK return res, errors.Wrap(defRes, "error") } +func decodeGetAssetThumbnailResponse(resp *http.Response) (res *GetAssetThumbnailFound, _ error) { + switch resp.StatusCode { + case 302: + // Code 302. + var wrapper GetAssetThumbnailFound + h := uri.NewHeaderDecoder(resp.Header) + // Parse "Location" header. + { + cfg := uri.HeaderParameterDecodingConfig{ + Name: "Location", + Explode: false, + } + if err := func() error { + if err := h.HasParam(cfg); err == nil { + if err := h.DecodeParam(cfg, func(d uri.Decoder) error { + var wrapperDotLocationVal string + if err := func() error { + val, err := d.DecodeValue() + if err != nil { + return err + } + + c, err := conv.ToString(val) + if err != nil { + return err + } + + wrapperDotLocationVal = c + return nil + }(); err != nil { + return err + } + wrapper.Location.SetTo(wrapperDotLocationVal) + return nil + }); err != nil { + return err + } + } + return nil + }(); err != nil { + return res, errors.Wrap(err, "parse Location header") + } + } + return &wrapper, nil + } + // Convenient error response. + defRes, err := func() (res *ErrorStatusCode, err error) { + ct, _, err := mime.ParseMediaType(resp.Header.Get("Content-Type")) + if err != nil { + return res, errors.Wrap(err, "parse media type") + } + switch { + case ct == "application/json": + buf, err := io.ReadAll(resp.Body) + if err != nil { + return res, err + } + d := jx.DecodeBytes(buf) + + var response Error + if err := func() error { + if err := response.Decode(d); err != nil { + return err + } + if err := d.Skip(); err != io.EOF { + return errors.New("unexpected trailing data") + } + return nil + }(); err != nil { + err = &ogenerrors.DecodeBodyError{ + ContentType: ct, + Body: buf, + Err: err, + } + return res, err + } + // Validate response. + if err := func() error { + if err := response.Validate(); err != nil { + return err + } + return nil + }(); err != nil { + return res, errors.Wrap(err, "validate") + } + return &ErrorStatusCode{ + StatusCode: resp.StatusCode, + Response: response, + }, nil + default: + return res, validate.InvalidContentType(ct) + } + }() + if err != nil { + return res, errors.Wrapf(err, "default (code %d)", resp.StatusCode) + } + return res, errors.Wrap(defRes, "error") +} + func decodeGetMapResponse(resp *http.Response) (res *Map, _ error) { switch resp.StatusCode { case 200: @@ -2883,6 +3167,105 @@ func decodeGetSubmissionResponse(resp *http.Response) (res *Submission, _ error) return res, errors.Wrap(defRes, "error") } +func decodeGetUserThumbnailResponse(resp *http.Response) (res *GetUserThumbnailFound, _ error) { + switch resp.StatusCode { + case 302: + // Code 302. + var wrapper GetUserThumbnailFound + h := uri.NewHeaderDecoder(resp.Header) + // Parse "Location" header. + { + cfg := uri.HeaderParameterDecodingConfig{ + Name: "Location", + Explode: false, + } + if err := func() error { + if err := h.HasParam(cfg); err == nil { + if err := h.DecodeParam(cfg, func(d uri.Decoder) error { + var wrapperDotLocationVal string + if err := func() error { + val, err := d.DecodeValue() + if err != nil { + return err + } + + c, err := conv.ToString(val) + if err != nil { + return err + } + + wrapperDotLocationVal = c + return nil + }(); err != nil { + return err + } + wrapper.Location.SetTo(wrapperDotLocationVal) + return nil + }); err != nil { + return err + } + } + return nil + }(); err != nil { + return res, errors.Wrap(err, "parse Location header") + } + } + return &wrapper, nil + } + // Convenient error response. + defRes, err := func() (res *ErrorStatusCode, err error) { + ct, _, err := mime.ParseMediaType(resp.Header.Get("Content-Type")) + if err != nil { + return res, errors.Wrap(err, "parse media type") + } + switch { + case ct == "application/json": + buf, err := io.ReadAll(resp.Body) + if err != nil { + return res, err + } + d := jx.DecodeBytes(buf) + + var response Error + if err := func() error { + if err := response.Decode(d); err != nil { + return err + } + if err := d.Skip(); err != io.EOF { + return errors.New("unexpected trailing data") + } + return nil + }(); err != nil { + err = &ogenerrors.DecodeBodyError{ + ContentType: ct, + Body: buf, + Err: err, + } + return res, err + } + // Validate response. + if err := func() error { + if err := response.Validate(); err != nil { + return err + } + return nil + }(); err != nil { + return res, errors.Wrap(err, "validate") + } + return &ErrorStatusCode{ + StatusCode: resp.StatusCode, + Response: response, + }, nil + default: + return res, validate.InvalidContentType(ct) + } + }() + if err != nil { + return res, errors.Wrapf(err, "default (code %d)", resp.StatusCode) + } + return res, errors.Wrap(defRes, "error") +} + func decodeListMapfixAuditEventsResponse(resp *http.Response) (res []AuditEvent, _ error) { switch resp.StatusCode { case 200: diff --git a/pkg/api/oas_response_encoders_gen.go b/pkg/api/oas_response_encoders_gen.go index abd0578..483cfe6 100644 --- a/pkg/api/oas_response_encoders_gen.go +++ b/pkg/api/oas_response_encoders_gen.go @@ -8,10 +8,11 @@ import ( "github.com/go-faster/errors" "github.com/go-faster/jx" + "github.com/ogen-go/ogen/conv" + ht "github.com/ogen-go/ogen/http" + "github.com/ogen-go/ogen/uri" "go.opentelemetry.io/otel/codes" "go.opentelemetry.io/otel/trace" - - ht "github.com/ogen-go/ogen/http" ) func encodeActionMapfixAcceptedResponse(response *ActionMapfixAcceptedNoContent, w http.ResponseWriter, span trace.Span) error { @@ -182,6 +183,34 @@ func encodeActionSubmissionValidatedResponse(response *ActionSubmissionValidated return nil } +func encodeBatchAssetThumbnailsResponse(response *BatchAssetThumbnailsOK, w http.ResponseWriter, span trace.Span) error { + w.Header().Set("Content-Type", "application/json; charset=utf-8") + w.WriteHeader(200) + span.SetStatus(codes.Ok, http.StatusText(200)) + + e := new(jx.Encoder) + response.Encode(e) + if _, err := e.WriteTo(w); err != nil { + return errors.Wrap(err, "write") + } + + return nil +} + +func encodeBatchUserThumbnailsResponse(response *BatchUserThumbnailsOK, w http.ResponseWriter, span trace.Span) error { + w.Header().Set("Content-Type", "application/json; charset=utf-8") + w.WriteHeader(200) + span.SetStatus(codes.Ok, http.StatusText(200)) + + e := new(jx.Encoder) + response.Encode(e) + if _, err := e.WriteTo(w); err != nil { + return errors.Wrap(err, "write") + } + + return nil +} + func encodeCreateMapfixResponse(response *OperationID, w http.ResponseWriter, span trace.Span) error { w.Header().Set("Content-Type", "application/json; charset=utf-8") w.WriteHeader(201) @@ -296,6 +325,32 @@ func encodeDownloadMapAssetResponse(response DownloadMapAssetOK, w http.Response return nil } +func encodeGetAssetThumbnailResponse(response *GetAssetThumbnailFound, w http.ResponseWriter, span trace.Span) error { + // Encoding response headers. + { + h := uri.NewHeaderEncoder(w.Header()) + // Encode "Location" header. + { + cfg := uri.HeaderParameterEncodingConfig{ + Name: "Location", + Explode: false, + } + if err := h.EncodeParam(cfg, func(e uri.Encoder) error { + if val, ok := response.Location.Get(); ok { + return e.EncodeValue(conv.StringToString(val)) + } + return nil + }); err != nil { + return errors.Wrap(err, "encode Location header") + } + } + } + w.WriteHeader(302) + span.SetStatus(codes.Ok, http.StatusText(302)) + + return nil +} + func encodeGetMapResponse(response *Map, w http.ResponseWriter, span trace.Span) error { w.Header().Set("Content-Type", "application/json; charset=utf-8") w.WriteHeader(200) @@ -380,6 +435,32 @@ func encodeGetSubmissionResponse(response *Submission, w http.ResponseWriter, sp return nil } +func encodeGetUserThumbnailResponse(response *GetUserThumbnailFound, w http.ResponseWriter, span trace.Span) error { + // Encoding response headers. + { + h := uri.NewHeaderEncoder(w.Header()) + // Encode "Location" header. + { + cfg := uri.HeaderParameterEncodingConfig{ + Name: "Location", + Explode: false, + } + if err := h.EncodeParam(cfg, func(e uri.Encoder) error { + if val, ok := response.Location.Get(); ok { + return e.EncodeValue(conv.StringToString(val)) + } + return nil + }); err != nil { + return errors.Wrap(err, "encode Location header") + } + } + } + w.WriteHeader(302) + span.SetStatus(codes.Ok, http.StatusText(302)) + + return nil +} + func encodeListMapfixAuditEventsResponse(response []AuditEvent, w http.ResponseWriter, span trace.Span) error { w.Header().Set("Content-Type", "application/json; charset=utf-8") w.WriteHeader(200) diff --git a/pkg/api/oas_router_gen.go b/pkg/api/oas_router_gen.go index 50cc71f..cbba73d 100644 --- a/pkg/api/oas_router_gen.go +++ b/pkg/api/oas_router_gen.go @@ -1431,6 +1431,150 @@ func (s *Server) ServeHTTP(w http.ResponseWriter, r *http.Request) { } + case 't': // Prefix: "thumbnails/" + + if l := len("thumbnails/"); len(elem) >= l && elem[0:l] == "thumbnails/" { + elem = elem[l:] + } else { + break + } + + if len(elem) == 0 { + break + } + switch elem[0] { + case 'a': // Prefix: "asset" + + if l := len("asset"); len(elem) >= l && elem[0:l] == "asset" { + elem = elem[l:] + } else { + break + } + + if len(elem) == 0 { + break + } + switch elem[0] { + case '/': // Prefix: "/" + + if l := len("/"); len(elem) >= l && elem[0:l] == "/" { + elem = elem[l:] + } else { + break + } + + // Param: "AssetID" + // Leaf parameter, slashes are prohibited + idx := strings.IndexByte(elem, '/') + if idx >= 0 { + break + } + args[0] = elem + elem = "" + + if len(elem) == 0 { + // Leaf node. + switch r.Method { + case "GET": + s.handleGetAssetThumbnailRequest([1]string{ + args[0], + }, elemIsEscaped, w, r) + default: + s.notAllowed(w, r, "GET") + } + + return + } + + case 's': // Prefix: "s" + + if l := len("s"); len(elem) >= l && elem[0:l] == "s" { + elem = elem[l:] + } else { + break + } + + if len(elem) == 0 { + // Leaf node. + switch r.Method { + case "POST": + s.handleBatchAssetThumbnailsRequest([0]string{}, elemIsEscaped, w, r) + default: + s.notAllowed(w, r, "POST") + } + + return + } + + } + + case 'u': // Prefix: "user" + + if l := len("user"); len(elem) >= l && elem[0:l] == "user" { + elem = elem[l:] + } else { + break + } + + if len(elem) == 0 { + break + } + switch elem[0] { + case '/': // Prefix: "/" + + if l := len("/"); len(elem) >= l && elem[0:l] == "/" { + elem = elem[l:] + } else { + break + } + + // Param: "UserID" + // Leaf parameter, slashes are prohibited + idx := strings.IndexByte(elem, '/') + if idx >= 0 { + break + } + args[0] = elem + elem = "" + + if len(elem) == 0 { + // Leaf node. + switch r.Method { + case "GET": + s.handleGetUserThumbnailRequest([1]string{ + args[0], + }, elemIsEscaped, w, r) + default: + s.notAllowed(w, r, "GET") + } + + return + } + + case 's': // Prefix: "s" + + if l := len("s"); len(elem) >= l && elem[0:l] == "s" { + elem = elem[l:] + } else { + break + } + + if len(elem) == 0 { + // Leaf node. + switch r.Method { + case "POST": + s.handleBatchUserThumbnailsRequest([0]string{}, elemIsEscaped, w, r) + default: + s.notAllowed(w, r, "POST") + } + + return + } + + } + + } + } } @@ -1440,12 +1584,13 @@ func (s *Server) ServeHTTP(w http.ResponseWriter, r *http.Request) { // Route is route object. type Route struct { - name string - summary string - operationID string - pathPattern string - count int - args [1]string + name string + summary string + operationID string + operationGroup string + pathPattern string + count int + args [1]string } // Name returns ogen operation name. @@ -1465,6 +1610,11 @@ func (r Route) OperationID() string { return r.operationID } +// OperationGroup returns the x-ogen-operation-group value. +func (r Route) OperationGroup() string { + return r.operationGroup +} + // PathPattern returns OpenAPI path. func (r Route) PathPattern() string { return r.pathPattern @@ -1551,6 +1701,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ListMapfixesOperation r.summary = "Get list of mapfixes" r.operationID = "listMapfixes" + r.operationGroup = "" r.pathPattern = "/mapfixes" r.args = args r.count = 0 @@ -1559,6 +1710,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = CreateMapfixOperation r.summary = "Trigger the validator to create a mapfix" r.operationID = "createMapfix" + r.operationGroup = "" r.pathPattern = "/mapfixes" r.args = args r.count = 0 @@ -1591,6 +1743,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = GetMapfixOperation r.summary = "Retrieve map with ID" r.operationID = "getMapfix" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}" r.args = args r.count = 1 @@ -1627,6 +1780,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ListMapfixAuditEventsOperation r.summary = "Retrieve a list of audit events" r.operationID = "listMapfixAuditEvents" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/audit-events" r.args = args r.count = 1 @@ -1663,6 +1817,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = CreateMapfixAuditCommentOperation r.summary = "Post a comment to the audit log" r.operationID = "createMapfixAuditComment" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/comment" r.args = args r.count = 1 @@ -1687,6 +1842,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = SetMapfixCompletedOperation r.summary = "Called by maptest when a player completes the map" r.operationID = "setMapfixCompleted" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/completed" r.args = args r.count = 1 @@ -1713,6 +1869,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = UpdateMapfixModelOperation r.summary = "Update model following role restrictions" r.operationID = "updateMapfixModel" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/model" r.args = args r.count = 1 @@ -1761,6 +1918,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixRejectOperation r.summary = "Role Reviewer changes status from Submitted -> Rejected" r.operationID = "actionMapfixReject" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/reject" r.args = args r.count = 1 @@ -1785,6 +1943,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixRequestChangesOperation r.summary = "Role Reviewer changes status from Validated|Accepted|Submitted -> ChangesRequested" r.operationID = "actionMapfixRequestChanges" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/request-changes" r.args = args r.count = 1 @@ -1821,6 +1980,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixUploadedOperation r.summary = "Role MapfixUpload manually resets releasing softlock and changes status from Releasing -> Uploaded" r.operationID = "actionMapfixUploaded" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/reset-releasing" r.args = args r.count = 1 @@ -1845,6 +2005,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixResetSubmittingOperation r.summary = "Role Submitter manually resets submitting softlock and changes status from Submitting -> UnderConstruction" r.operationID = "actionMapfixResetSubmitting" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/reset-submitting" r.args = args r.count = 1 @@ -1869,6 +2030,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixValidatedOperation r.summary = "Role MapfixUpload manually resets uploading softlock and changes status from Uploading -> Validated" r.operationID = "actionMapfixValidated" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/reset-uploading" r.args = args r.count = 1 @@ -1893,6 +2055,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixAcceptedOperation r.summary = "Role Reviewer manually resets validating softlock and changes status from Validating -> Accepted" r.operationID = "actionMapfixAccepted" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/reset-validating" r.args = args r.count = 1 @@ -1919,6 +2082,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixRetryValidateOperation r.summary = "Role Reviewer re-runs validation and changes status from Accepted -> Validating" r.operationID = "actionMapfixRetryValidate" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/retry-validate" r.args = args r.count = 1 @@ -1943,6 +2107,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixRevokeOperation r.summary = "Role Submitter changes status from Submitted|ChangesRequested -> UnderConstruction" r.operationID = "actionMapfixRevoke" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/revoke" r.args = args r.count = 1 @@ -1981,6 +2146,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixTriggerReleaseOperation r.summary = "Role MapfixUpload changes status from Uploaded -> Releasing" r.operationID = "actionMapfixTriggerRelease" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/trigger-release" r.args = args r.count = 1 @@ -2004,6 +2170,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixTriggerSubmitOperation r.summary = "Role Submitter changes status from UnderConstruction|ChangesRequested -> Submitting" r.operationID = "actionMapfixTriggerSubmit" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/trigger-submit" r.args = args r.count = 1 @@ -2028,6 +2195,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixTriggerSubmitUncheckedOperation r.summary = "Role Reviewer changes status from ChangesRequested -> Submitting" r.operationID = "actionMapfixTriggerSubmitUnchecked" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/trigger-submit-unchecked" r.args = args r.count = 1 @@ -2054,6 +2222,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixTriggerUploadOperation r.summary = "Role MapfixUpload changes status from Validated -> Uploading" r.operationID = "actionMapfixTriggerUpload" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/trigger-upload" r.args = args r.count = 1 @@ -2078,6 +2247,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionMapfixTriggerValidateOperation r.summary = "Role Reviewer triggers validation and changes status from Submitted -> Validating" r.operationID = "actionMapfixTriggerValidate" + r.operationGroup = "" r.pathPattern = "/mapfixes/{MapfixID}/status/trigger-validate" r.args = args r.count = 1 @@ -2111,6 +2281,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ListMapsOperation r.summary = "Get list of maps" r.operationID = "listMaps" + r.operationGroup = "" r.pathPattern = "/maps" r.args = args r.count = 0 @@ -2143,6 +2314,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = GetMapOperation r.summary = "Retrieve map with ID" r.operationID = "getMap" + r.operationGroup = "" r.pathPattern = "/maps/{MapID}" r.args = args r.count = 1 @@ -2167,6 +2339,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = DownloadMapAssetOperation r.summary = "Download the map asset" r.operationID = "downloadMapAsset" + r.operationGroup = "" r.pathPattern = "/maps/{MapID}/download" r.args = args r.count = 1 @@ -2206,6 +2379,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = GetOperationOperation r.summary = "Retrieve operation with ID" r.operationID = "getOperation" + r.operationGroup = "" r.pathPattern = "/operations/{OperationID}" r.args = args r.count = 1 @@ -2230,6 +2404,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ReleaseSubmissionsOperation r.summary = "Release a set of uploaded maps. Role SubmissionRelease" r.operationID = "releaseSubmissions" + r.operationGroup = "" r.pathPattern = "/release-submissions" r.args = args r.count = 0 @@ -2277,6 +2452,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ListScriptPolicyOperation r.summary = "Get list of script policies" r.operationID = "listScriptPolicy" + r.operationGroup = "" r.pathPattern = "/script-policy" r.args = args r.count = 0 @@ -2285,6 +2461,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = CreateScriptPolicyOperation r.summary = "Create a new script policy" r.operationID = "createScriptPolicy" + r.operationGroup = "" r.pathPattern = "/script-policy" r.args = args r.count = 0 @@ -2318,6 +2495,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = DeleteScriptPolicyOperation r.summary = "Delete the specified script policy by ID" r.operationID = "deleteScriptPolicy" + r.operationGroup = "" r.pathPattern = "/script-policy/{ScriptPolicyID}" r.args = args r.count = 1 @@ -2326,6 +2504,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = GetScriptPolicyOperation r.summary = "Get the specified script policy by ID" r.operationID = "getScriptPolicy" + r.operationGroup = "" r.pathPattern = "/script-policy/{ScriptPolicyID}" r.args = args r.count = 1 @@ -2334,6 +2513,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = UpdateScriptPolicyOperation r.summary = "Update the specified script policy by ID" r.operationID = "updateScriptPolicy" + r.operationGroup = "" r.pathPattern = "/script-policy/{ScriptPolicyID}" r.args = args r.count = 1 @@ -2359,6 +2539,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ListScriptsOperation r.summary = "Get list of scripts" r.operationID = "listScripts" + r.operationGroup = "" r.pathPattern = "/scripts" r.args = args r.count = 0 @@ -2367,6 +2548,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = CreateScriptOperation r.summary = "Create a new script" r.operationID = "createScript" + r.operationGroup = "" r.pathPattern = "/scripts" r.args = args r.count = 0 @@ -2400,6 +2582,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = DeleteScriptOperation r.summary = "Delete the specified script by ID" r.operationID = "deleteScript" + r.operationGroup = "" r.pathPattern = "/scripts/{ScriptID}" r.args = args r.count = 1 @@ -2408,6 +2591,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = GetScriptOperation r.summary = "Get the specified script by ID" r.operationID = "getScript" + r.operationGroup = "" r.pathPattern = "/scripts/{ScriptID}" r.args = args r.count = 1 @@ -2416,6 +2600,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = UpdateScriptOperation r.summary = "Update the specified script by ID" r.operationID = "updateScript" + r.operationGroup = "" r.pathPattern = "/scripts/{ScriptID}" r.args = args r.count = 1 @@ -2456,6 +2641,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = SessionRolesOperation r.summary = "Get list of roles for the current session" r.operationID = "sessionRoles" + r.operationGroup = "" r.pathPattern = "/session/roles" r.args = args r.count = 0 @@ -2480,6 +2666,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = SessionUserOperation r.summary = "Get information about the currently logged in user" r.operationID = "sessionUser" + r.operationGroup = "" r.pathPattern = "/session/user" r.args = args r.count = 0 @@ -2504,6 +2691,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = SessionValidateOperation r.summary = "Ask if the current session is valid" r.operationID = "sessionValidate" + r.operationGroup = "" r.pathPattern = "/session/validate" r.args = args r.count = 0 @@ -2529,6 +2717,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ListSubmissionsOperation r.summary = "Get list of submissions" r.operationID = "listSubmissions" + r.operationGroup = "" r.pathPattern = "/submissions" r.args = args r.count = 0 @@ -2537,6 +2726,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = CreateSubmissionOperation r.summary = "Trigger the validator to create a new submission" r.operationID = "createSubmission" + r.operationGroup = "" r.pathPattern = "/submissions" r.args = args r.count = 0 @@ -2561,6 +2751,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = CreateSubmissionAdminOperation r.summary = "Trigger the validator to create a new submission" r.operationID = "createSubmissionAdmin" + r.operationGroup = "" r.pathPattern = "/submissions-admin" r.args = args r.count = 0 @@ -2593,6 +2784,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = GetSubmissionOperation r.summary = "Retrieve map with ID" r.operationID = "getSubmission" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}" r.args = args r.count = 1 @@ -2629,6 +2821,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ListSubmissionAuditEventsOperation r.summary = "Retrieve a list of audit events" r.operationID = "listSubmissionAuditEvents" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/audit-events" r.args = args r.count = 1 @@ -2665,6 +2858,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = CreateSubmissionAuditCommentOperation r.summary = "Post a comment to the audit log" r.operationID = "createSubmissionAuditComment" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/comment" r.args = args r.count = 1 @@ -2689,6 +2883,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = SetSubmissionCompletedOperation r.summary = "Called by maptest when a player completes the map" r.operationID = "setSubmissionCompleted" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/completed" r.args = args r.count = 1 @@ -2715,6 +2910,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = UpdateSubmissionModelOperation r.summary = "Update model following role restrictions" r.operationID = "updateSubmissionModel" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/model" r.args = args r.count = 1 @@ -2763,6 +2959,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionSubmissionRejectOperation r.summary = "Role Reviewer changes status from Submitted -> Rejected" r.operationID = "actionSubmissionReject" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/status/reject" r.args = args r.count = 1 @@ -2787,6 +2984,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionSubmissionRequestChangesOperation r.summary = "Role Reviewer changes status from Validated|Accepted|Submitted -> ChangesRequested" r.operationID = "actionSubmissionRequestChanges" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/status/request-changes" r.args = args r.count = 1 @@ -2823,6 +3021,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionSubmissionResetSubmittingOperation r.summary = "Role Submitter manually resets submitting softlock and changes status from Submitting -> UnderConstruction" r.operationID = "actionSubmissionResetSubmitting" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/status/reset-submitting" r.args = args r.count = 1 @@ -2847,6 +3046,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionSubmissionValidatedOperation r.summary = "Role SubmissionUpload manually resets uploading softlock and changes status from Uploading -> Validated" r.operationID = "actionSubmissionValidated" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/status/reset-uploading" r.args = args r.count = 1 @@ -2871,6 +3071,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionSubmissionAcceptedOperation r.summary = "Role Reviewer manually resets validating softlock and changes status from Validating -> Accepted" r.operationID = "actionSubmissionAccepted" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/status/reset-validating" r.args = args r.count = 1 @@ -2897,6 +3098,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionSubmissionRetryValidateOperation r.summary = "Role Reviewer re-runs validation and changes status from Accepted -> Validating" r.operationID = "actionSubmissionRetryValidate" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/status/retry-validate" r.args = args r.count = 1 @@ -2921,6 +3123,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionSubmissionRevokeOperation r.summary = "Role Submitter changes status from Submitted|ChangesRequested -> UnderConstruction" r.operationID = "actionSubmissionRevoke" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/status/revoke" r.args = args r.count = 1 @@ -2958,6 +3161,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionSubmissionTriggerSubmitOperation r.summary = "Role Submitter changes status from UnderConstruction|ChangesRequested -> Submitting" r.operationID = "actionSubmissionTriggerSubmit" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/status/trigger-submit" r.args = args r.count = 1 @@ -2982,6 +3186,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionSubmissionTriggerSubmitUncheckedOperation r.summary = "Role Reviewer changes status from ChangesRequested -> Submitting" r.operationID = "actionSubmissionTriggerSubmitUnchecked" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/status/trigger-submit-unchecked" r.args = args r.count = 1 @@ -3008,6 +3213,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionSubmissionTriggerUploadOperation r.summary = "Role SubmissionUpload changes status from Validated -> Uploading" r.operationID = "actionSubmissionTriggerUpload" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/status/trigger-upload" r.args = args r.count = 1 @@ -3032,6 +3238,7 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { r.name = ActionSubmissionTriggerValidateOperation r.summary = "Role Reviewer triggers validation and changes status from Submitted -> Validating" r.operationID = "actionSubmissionTriggerValidate" + r.operationGroup = "" r.pathPattern = "/submissions/{SubmissionID}/status/trigger-validate" r.args = args r.count = 1 @@ -3053,6 +3260,166 @@ func (s *Server) FindPath(method string, u *url.URL) (r Route, _ bool) { } + case 't': // Prefix: "thumbnails/" + + if l := len("thumbnails/"); len(elem) >= l && elem[0:l] == "thumbnails/" { + elem = elem[l:] + } else { + break + } + + if len(elem) == 0 { + break + } + switch elem[0] { + case 'a': // Prefix: "asset" + + if l := len("asset"); len(elem) >= l && elem[0:l] == "asset" { + elem = elem[l:] + } else { + break + } + + if len(elem) == 0 { + break + } + switch elem[0] { + case '/': // Prefix: "/" + + if l := len("/"); len(elem) >= l && elem[0:l] == "/" { + elem = elem[l:] + } else { + break + } + + // Param: "AssetID" + // Leaf parameter, slashes are prohibited + idx := strings.IndexByte(elem, '/') + if idx >= 0 { + break + } + args[0] = elem + elem = "" + + if len(elem) == 0 { + // Leaf node. + switch method { + case "GET": + r.name = GetAssetThumbnailOperation + r.summary = "Get single asset thumbnail" + r.operationID = "getAssetThumbnail" + r.operationGroup = "" + r.pathPattern = "/thumbnails/asset/{AssetID}" + r.args = args + r.count = 1 + return r, true + default: + return + } + } + + case 's': // Prefix: "s" + + if l := len("s"); len(elem) >= l && elem[0:l] == "s" { + elem = elem[l:] + } else { + break + } + + if len(elem) == 0 { + // Leaf node. + switch method { + case "POST": + r.name = BatchAssetThumbnailsOperation + r.summary = "Batch fetch asset thumbnails" + r.operationID = "batchAssetThumbnails" + r.operationGroup = "" + r.pathPattern = "/thumbnails/assets" + r.args = args + r.count = 0 + return r, true + default: + return + } + } + + } + + case 'u': // Prefix: "user" + + if l := len("user"); len(elem) >= l && elem[0:l] == "user" { + elem = elem[l:] + } else { + break + } + + if len(elem) == 0 { + break + } + switch elem[0] { + case '/': // Prefix: "/" + + if l := len("/"); len(elem) >= l && elem[0:l] == "/" { + elem = elem[l:] + } else { + break + } + + // Param: "UserID" + // Leaf parameter, slashes are prohibited + idx := strings.IndexByte(elem, '/') + if idx >= 0 { + break + } + args[0] = elem + elem = "" + + if len(elem) == 0 { + // Leaf node. + switch method { + case "GET": + r.name = GetUserThumbnailOperation + r.summary = "Get single user avatar thumbnail" + r.operationID = "getUserThumbnail" + r.operationGroup = "" + r.pathPattern = "/thumbnails/user/{UserID}" + r.args = args + r.count = 1 + return r, true + default: + return + } + } + + case 's': // Prefix: "s" + + if l := len("s"); len(elem) >= l && elem[0:l] == "s" { + elem = elem[l:] + } else { + break + } + + if len(elem) == 0 { + // Leaf node. + switch method { + case "POST": + r.name = BatchUserThumbnailsOperation + r.summary = "Batch fetch user avatar thumbnails" + r.operationID = "batchUserThumbnails" + r.operationGroup = "" + r.pathPattern = "/thumbnails/users" + r.args = args + r.count = 0 + return r, true + default: + return + } + } + + } + + } + } } diff --git a/pkg/api/oas_schemas_gen.go b/pkg/api/oas_schemas_gen.go index 26e9c6d..8a5bb50 100644 --- a/pkg/api/oas_schemas_gen.go +++ b/pkg/api/oas_schemas_gen.go @@ -7,6 +7,7 @@ import ( "io" "time" + "github.com/go-faster/errors" "github.com/go-faster/jx" ) @@ -192,6 +193,212 @@ func (s *AuditEventEventData) init() AuditEventEventData { return m } +type BatchAssetThumbnailsOK struct { + // Map of asset ID to thumbnail URL. + Thumbnails OptBatchAssetThumbnailsOKThumbnails `json:"thumbnails"` +} + +// GetThumbnails returns the value of Thumbnails. +func (s *BatchAssetThumbnailsOK) GetThumbnails() OptBatchAssetThumbnailsOKThumbnails { + return s.Thumbnails +} + +// SetThumbnails sets the value of Thumbnails. +func (s *BatchAssetThumbnailsOK) SetThumbnails(val OptBatchAssetThumbnailsOKThumbnails) { + s.Thumbnails = val +} + +// Map of asset ID to thumbnail URL. +type BatchAssetThumbnailsOKThumbnails map[string]string + +func (s *BatchAssetThumbnailsOKThumbnails) init() BatchAssetThumbnailsOKThumbnails { + m := *s + if m == nil { + m = map[string]string{} + *s = m + } + return m +} + +type BatchAssetThumbnailsReq struct { + // Array of asset IDs (max 100). + AssetIds []uint64 `json:"assetIds"` + // Thumbnail size. + Size OptBatchAssetThumbnailsReqSize `json:"size"` +} + +// GetAssetIds returns the value of AssetIds. +func (s *BatchAssetThumbnailsReq) GetAssetIds() []uint64 { + return s.AssetIds +} + +// GetSize returns the value of Size. +func (s *BatchAssetThumbnailsReq) GetSize() OptBatchAssetThumbnailsReqSize { + return s.Size +} + +// SetAssetIds sets the value of AssetIds. +func (s *BatchAssetThumbnailsReq) SetAssetIds(val []uint64) { + s.AssetIds = val +} + +// SetSize sets the value of Size. +func (s *BatchAssetThumbnailsReq) SetSize(val OptBatchAssetThumbnailsReqSize) { + s.Size = val +} + +// Thumbnail size. +type BatchAssetThumbnailsReqSize string + +const ( + BatchAssetThumbnailsReqSize150x150 BatchAssetThumbnailsReqSize = "150x150" + BatchAssetThumbnailsReqSize420x420 BatchAssetThumbnailsReqSize = "420x420" + BatchAssetThumbnailsReqSize768x432 BatchAssetThumbnailsReqSize = "768x432" +) + +// AllValues returns all BatchAssetThumbnailsReqSize values. +func (BatchAssetThumbnailsReqSize) AllValues() []BatchAssetThumbnailsReqSize { + return []BatchAssetThumbnailsReqSize{ + BatchAssetThumbnailsReqSize150x150, + BatchAssetThumbnailsReqSize420x420, + BatchAssetThumbnailsReqSize768x432, + } +} + +// MarshalText implements encoding.TextMarshaler. +func (s BatchAssetThumbnailsReqSize) MarshalText() ([]byte, error) { + switch s { + case BatchAssetThumbnailsReqSize150x150: + return []byte(s), nil + case BatchAssetThumbnailsReqSize420x420: + return []byte(s), nil + case BatchAssetThumbnailsReqSize768x432: + return []byte(s), nil + default: + return nil, errors.Errorf("invalid value: %q", s) + } +} + +// UnmarshalText implements encoding.TextUnmarshaler. +func (s *BatchAssetThumbnailsReqSize) UnmarshalText(data []byte) error { + switch BatchAssetThumbnailsReqSize(data) { + case BatchAssetThumbnailsReqSize150x150: + *s = BatchAssetThumbnailsReqSize150x150 + return nil + case BatchAssetThumbnailsReqSize420x420: + *s = BatchAssetThumbnailsReqSize420x420 + return nil + case BatchAssetThumbnailsReqSize768x432: + *s = BatchAssetThumbnailsReqSize768x432 + return nil + default: + return errors.Errorf("invalid value: %q", data) + } +} + +type BatchUserThumbnailsOK struct { + // Map of user ID to thumbnail URL. + Thumbnails OptBatchUserThumbnailsOKThumbnails `json:"thumbnails"` +} + +// GetThumbnails returns the value of Thumbnails. +func (s *BatchUserThumbnailsOK) GetThumbnails() OptBatchUserThumbnailsOKThumbnails { + return s.Thumbnails +} + +// SetThumbnails sets the value of Thumbnails. +func (s *BatchUserThumbnailsOK) SetThumbnails(val OptBatchUserThumbnailsOKThumbnails) { + s.Thumbnails = val +} + +// Map of user ID to thumbnail URL. +type BatchUserThumbnailsOKThumbnails map[string]string + +func (s *BatchUserThumbnailsOKThumbnails) init() BatchUserThumbnailsOKThumbnails { + m := *s + if m == nil { + m = map[string]string{} + *s = m + } + return m +} + +type BatchUserThumbnailsReq struct { + // Array of user IDs (max 100). + UserIds []uint64 `json:"userIds"` + // Thumbnail size. + Size OptBatchUserThumbnailsReqSize `json:"size"` +} + +// GetUserIds returns the value of UserIds. +func (s *BatchUserThumbnailsReq) GetUserIds() []uint64 { + return s.UserIds +} + +// GetSize returns the value of Size. +func (s *BatchUserThumbnailsReq) GetSize() OptBatchUserThumbnailsReqSize { + return s.Size +} + +// SetUserIds sets the value of UserIds. +func (s *BatchUserThumbnailsReq) SetUserIds(val []uint64) { + s.UserIds = val +} + +// SetSize sets the value of Size. +func (s *BatchUserThumbnailsReq) SetSize(val OptBatchUserThumbnailsReqSize) { + s.Size = val +} + +// Thumbnail size. +type BatchUserThumbnailsReqSize string + +const ( + BatchUserThumbnailsReqSize150x150 BatchUserThumbnailsReqSize = "150x150" + BatchUserThumbnailsReqSize420x420 BatchUserThumbnailsReqSize = "420x420" + BatchUserThumbnailsReqSize768x432 BatchUserThumbnailsReqSize = "768x432" +) + +// AllValues returns all BatchUserThumbnailsReqSize values. +func (BatchUserThumbnailsReqSize) AllValues() []BatchUserThumbnailsReqSize { + return []BatchUserThumbnailsReqSize{ + BatchUserThumbnailsReqSize150x150, + BatchUserThumbnailsReqSize420x420, + BatchUserThumbnailsReqSize768x432, + } +} + +// MarshalText implements encoding.TextMarshaler. +func (s BatchUserThumbnailsReqSize) MarshalText() ([]byte, error) { + switch s { + case BatchUserThumbnailsReqSize150x150: + return []byte(s), nil + case BatchUserThumbnailsReqSize420x420: + return []byte(s), nil + case BatchUserThumbnailsReqSize768x432: + return []byte(s), nil + default: + return nil, errors.Errorf("invalid value: %q", s) + } +} + +// UnmarshalText implements encoding.TextUnmarshaler. +func (s *BatchUserThumbnailsReqSize) UnmarshalText(data []byte) error { + switch BatchUserThumbnailsReqSize(data) { + case BatchUserThumbnailsReqSize150x150: + *s = BatchUserThumbnailsReqSize150x150 + return nil + case BatchUserThumbnailsReqSize420x420: + *s = BatchUserThumbnailsReqSize420x420 + return nil + case BatchUserThumbnailsReqSize768x432: + *s = BatchUserThumbnailsReqSize768x432 + return nil + default: + return errors.Errorf("invalid value: %q", data) + } +} + type CookieAuth struct { APIKey string Roles []string @@ -324,6 +531,132 @@ func (s *ErrorStatusCode) SetResponse(val Error) { s.Response = val } +// GetAssetThumbnailFound is response for GetAssetThumbnail operation. +type GetAssetThumbnailFound struct { + Location OptString +} + +// GetLocation returns the value of Location. +func (s *GetAssetThumbnailFound) GetLocation() OptString { + return s.Location +} + +// SetLocation sets the value of Location. +func (s *GetAssetThumbnailFound) SetLocation(val OptString) { + s.Location = val +} + +type GetAssetThumbnailSize string + +const ( + GetAssetThumbnailSize150x150 GetAssetThumbnailSize = "150x150" + GetAssetThumbnailSize420x420 GetAssetThumbnailSize = "420x420" + GetAssetThumbnailSize768x432 GetAssetThumbnailSize = "768x432" +) + +// AllValues returns all GetAssetThumbnailSize values. +func (GetAssetThumbnailSize) AllValues() []GetAssetThumbnailSize { + return []GetAssetThumbnailSize{ + GetAssetThumbnailSize150x150, + GetAssetThumbnailSize420x420, + GetAssetThumbnailSize768x432, + } +} + +// MarshalText implements encoding.TextMarshaler. +func (s GetAssetThumbnailSize) MarshalText() ([]byte, error) { + switch s { + case GetAssetThumbnailSize150x150: + return []byte(s), nil + case GetAssetThumbnailSize420x420: + return []byte(s), nil + case GetAssetThumbnailSize768x432: + return []byte(s), nil + default: + return nil, errors.Errorf("invalid value: %q", s) + } +} + +// UnmarshalText implements encoding.TextUnmarshaler. +func (s *GetAssetThumbnailSize) UnmarshalText(data []byte) error { + switch GetAssetThumbnailSize(data) { + case GetAssetThumbnailSize150x150: + *s = GetAssetThumbnailSize150x150 + return nil + case GetAssetThumbnailSize420x420: + *s = GetAssetThumbnailSize420x420 + return nil + case GetAssetThumbnailSize768x432: + *s = GetAssetThumbnailSize768x432 + return nil + default: + return errors.Errorf("invalid value: %q", data) + } +} + +// GetUserThumbnailFound is response for GetUserThumbnail operation. +type GetUserThumbnailFound struct { + Location OptString +} + +// GetLocation returns the value of Location. +func (s *GetUserThumbnailFound) GetLocation() OptString { + return s.Location +} + +// SetLocation sets the value of Location. +func (s *GetUserThumbnailFound) SetLocation(val OptString) { + s.Location = val +} + +type GetUserThumbnailSize string + +const ( + GetUserThumbnailSize150x150 GetUserThumbnailSize = "150x150" + GetUserThumbnailSize420x420 GetUserThumbnailSize = "420x420" + GetUserThumbnailSize768x432 GetUserThumbnailSize = "768x432" +) + +// AllValues returns all GetUserThumbnailSize values. +func (GetUserThumbnailSize) AllValues() []GetUserThumbnailSize { + return []GetUserThumbnailSize{ + GetUserThumbnailSize150x150, + GetUserThumbnailSize420x420, + GetUserThumbnailSize768x432, + } +} + +// MarshalText implements encoding.TextMarshaler. +func (s GetUserThumbnailSize) MarshalText() ([]byte, error) { + switch s { + case GetUserThumbnailSize150x150: + return []byte(s), nil + case GetUserThumbnailSize420x420: + return []byte(s), nil + case GetUserThumbnailSize768x432: + return []byte(s), nil + default: + return nil, errors.Errorf("invalid value: %q", s) + } +} + +// UnmarshalText implements encoding.TextUnmarshaler. +func (s *GetUserThumbnailSize) UnmarshalText(data []byte) error { + switch GetUserThumbnailSize(data) { + case GetUserThumbnailSize150x150: + *s = GetUserThumbnailSize150x150 + return nil + case GetUserThumbnailSize420x420: + *s = GetUserThumbnailSize420x420 + return nil + case GetUserThumbnailSize768x432: + *s = GetUserThumbnailSize768x432 + return nil + default: + return errors.Errorf("invalid value: %q", data) + } +} + // Ref: #/components/schemas/Map type Map struct { ID int64 `json:"ID"` @@ -777,6 +1110,282 @@ func (s *OperationID) SetOperationID(val int32) { s.OperationID = val } +// NewOptBatchAssetThumbnailsOKThumbnails returns new OptBatchAssetThumbnailsOKThumbnails with value set to v. +func NewOptBatchAssetThumbnailsOKThumbnails(v BatchAssetThumbnailsOKThumbnails) OptBatchAssetThumbnailsOKThumbnails { + return OptBatchAssetThumbnailsOKThumbnails{ + Value: v, + Set: true, + } +} + +// OptBatchAssetThumbnailsOKThumbnails is optional BatchAssetThumbnailsOKThumbnails. +type OptBatchAssetThumbnailsOKThumbnails struct { + Value BatchAssetThumbnailsOKThumbnails + Set bool +} + +// IsSet returns true if OptBatchAssetThumbnailsOKThumbnails was set. +func (o OptBatchAssetThumbnailsOKThumbnails) IsSet() bool { return o.Set } + +// Reset unsets value. +func (o *OptBatchAssetThumbnailsOKThumbnails) Reset() { + var v BatchAssetThumbnailsOKThumbnails + o.Value = v + o.Set = false +} + +// SetTo sets value to v. +func (o *OptBatchAssetThumbnailsOKThumbnails) SetTo(v BatchAssetThumbnailsOKThumbnails) { + o.Set = true + o.Value = v +} + +// Get returns value and boolean that denotes whether value was set. +func (o OptBatchAssetThumbnailsOKThumbnails) Get() (v BatchAssetThumbnailsOKThumbnails, ok bool) { + if !o.Set { + return v, false + } + return o.Value, true +} + +// Or returns value if set, or given parameter if does not. +func (o OptBatchAssetThumbnailsOKThumbnails) Or(d BatchAssetThumbnailsOKThumbnails) BatchAssetThumbnailsOKThumbnails { + if v, ok := o.Get(); ok { + return v + } + return d +} + +// NewOptBatchAssetThumbnailsReqSize returns new OptBatchAssetThumbnailsReqSize with value set to v. +func NewOptBatchAssetThumbnailsReqSize(v BatchAssetThumbnailsReqSize) OptBatchAssetThumbnailsReqSize { + return OptBatchAssetThumbnailsReqSize{ + Value: v, + Set: true, + } +} + +// OptBatchAssetThumbnailsReqSize is optional BatchAssetThumbnailsReqSize. +type OptBatchAssetThumbnailsReqSize struct { + Value BatchAssetThumbnailsReqSize + Set bool +} + +// IsSet returns true if OptBatchAssetThumbnailsReqSize was set. +func (o OptBatchAssetThumbnailsReqSize) IsSet() bool { return o.Set } + +// Reset unsets value. +func (o *OptBatchAssetThumbnailsReqSize) Reset() { + var v BatchAssetThumbnailsReqSize + o.Value = v + o.Set = false +} + +// SetTo sets value to v. +func (o *OptBatchAssetThumbnailsReqSize) SetTo(v BatchAssetThumbnailsReqSize) { + o.Set = true + o.Value = v +} + +// Get returns value and boolean that denotes whether value was set. +func (o OptBatchAssetThumbnailsReqSize) Get() (v BatchAssetThumbnailsReqSize, ok bool) { + if !o.Set { + return v, false + } + return o.Value, true +} + +// Or returns value if set, or given parameter if does not. +func (o OptBatchAssetThumbnailsReqSize) Or(d BatchAssetThumbnailsReqSize) BatchAssetThumbnailsReqSize { + if v, ok := o.Get(); ok { + return v + } + return d +} + +// NewOptBatchUserThumbnailsOKThumbnails returns new OptBatchUserThumbnailsOKThumbnails with value set to v. +func NewOptBatchUserThumbnailsOKThumbnails(v BatchUserThumbnailsOKThumbnails) OptBatchUserThumbnailsOKThumbnails { + return OptBatchUserThumbnailsOKThumbnails{ + Value: v, + Set: true, + } +} + +// OptBatchUserThumbnailsOKThumbnails is optional BatchUserThumbnailsOKThumbnails. +type OptBatchUserThumbnailsOKThumbnails struct { + Value BatchUserThumbnailsOKThumbnails + Set bool +} + +// IsSet returns true if OptBatchUserThumbnailsOKThumbnails was set. +func (o OptBatchUserThumbnailsOKThumbnails) IsSet() bool { return o.Set } + +// Reset unsets value. +func (o *OptBatchUserThumbnailsOKThumbnails) Reset() { + var v BatchUserThumbnailsOKThumbnails + o.Value = v + o.Set = false +} + +// SetTo sets value to v. +func (o *OptBatchUserThumbnailsOKThumbnails) SetTo(v BatchUserThumbnailsOKThumbnails) { + o.Set = true + o.Value = v +} + +// Get returns value and boolean that denotes whether value was set. +func (o OptBatchUserThumbnailsOKThumbnails) Get() (v BatchUserThumbnailsOKThumbnails, ok bool) { + if !o.Set { + return v, false + } + return o.Value, true +} + +// Or returns value if set, or given parameter if does not. +func (o OptBatchUserThumbnailsOKThumbnails) Or(d BatchUserThumbnailsOKThumbnails) BatchUserThumbnailsOKThumbnails { + if v, ok := o.Get(); ok { + return v + } + return d +} + +// NewOptBatchUserThumbnailsReqSize returns new OptBatchUserThumbnailsReqSize with value set to v. +func NewOptBatchUserThumbnailsReqSize(v BatchUserThumbnailsReqSize) OptBatchUserThumbnailsReqSize { + return OptBatchUserThumbnailsReqSize{ + Value: v, + Set: true, + } +} + +// OptBatchUserThumbnailsReqSize is optional BatchUserThumbnailsReqSize. +type OptBatchUserThumbnailsReqSize struct { + Value BatchUserThumbnailsReqSize + Set bool +} + +// IsSet returns true if OptBatchUserThumbnailsReqSize was set. +func (o OptBatchUserThumbnailsReqSize) IsSet() bool { return o.Set } + +// Reset unsets value. +func (o *OptBatchUserThumbnailsReqSize) Reset() { + var v BatchUserThumbnailsReqSize + o.Value = v + o.Set = false +} + +// SetTo sets value to v. +func (o *OptBatchUserThumbnailsReqSize) SetTo(v BatchUserThumbnailsReqSize) { + o.Set = true + o.Value = v +} + +// Get returns value and boolean that denotes whether value was set. +func (o OptBatchUserThumbnailsReqSize) Get() (v BatchUserThumbnailsReqSize, ok bool) { + if !o.Set { + return v, false + } + return o.Value, true +} + +// Or returns value if set, or given parameter if does not. +func (o OptBatchUserThumbnailsReqSize) Or(d BatchUserThumbnailsReqSize) BatchUserThumbnailsReqSize { + if v, ok := o.Get(); ok { + return v + } + return d +} + +// NewOptGetAssetThumbnailSize returns new OptGetAssetThumbnailSize with value set to v. +func NewOptGetAssetThumbnailSize(v GetAssetThumbnailSize) OptGetAssetThumbnailSize { + return OptGetAssetThumbnailSize{ + Value: v, + Set: true, + } +} + +// OptGetAssetThumbnailSize is optional GetAssetThumbnailSize. +type OptGetAssetThumbnailSize struct { + Value GetAssetThumbnailSize + Set bool +} + +// IsSet returns true if OptGetAssetThumbnailSize was set. +func (o OptGetAssetThumbnailSize) IsSet() bool { return o.Set } + +// Reset unsets value. +func (o *OptGetAssetThumbnailSize) Reset() { + var v GetAssetThumbnailSize + o.Value = v + o.Set = false +} + +// SetTo sets value to v. +func (o *OptGetAssetThumbnailSize) SetTo(v GetAssetThumbnailSize) { + o.Set = true + o.Value = v +} + +// Get returns value and boolean that denotes whether value was set. +func (o OptGetAssetThumbnailSize) Get() (v GetAssetThumbnailSize, ok bool) { + if !o.Set { + return v, false + } + return o.Value, true +} + +// Or returns value if set, or given parameter if does not. +func (o OptGetAssetThumbnailSize) Or(d GetAssetThumbnailSize) GetAssetThumbnailSize { + if v, ok := o.Get(); ok { + return v + } + return d +} + +// NewOptGetUserThumbnailSize returns new OptGetUserThumbnailSize with value set to v. +func NewOptGetUserThumbnailSize(v GetUserThumbnailSize) OptGetUserThumbnailSize { + return OptGetUserThumbnailSize{ + Value: v, + Set: true, + } +} + +// OptGetUserThumbnailSize is optional GetUserThumbnailSize. +type OptGetUserThumbnailSize struct { + Value GetUserThumbnailSize + Set bool +} + +// IsSet returns true if OptGetUserThumbnailSize was set. +func (o OptGetUserThumbnailSize) IsSet() bool { return o.Set } + +// Reset unsets value. +func (o *OptGetUserThumbnailSize) Reset() { + var v GetUserThumbnailSize + o.Value = v + o.Set = false +} + +// SetTo sets value to v. +func (o *OptGetUserThumbnailSize) SetTo(v GetUserThumbnailSize) { + o.Set = true + o.Value = v +} + +// Get returns value and boolean that denotes whether value was set. +func (o OptGetUserThumbnailSize) Get() (v GetUserThumbnailSize, ok bool) { + if !o.Set { + return v, false + } + return o.Value, true +} + +// Or returns value if set, or given parameter if does not. +func (o OptGetUserThumbnailSize) Or(d GetUserThumbnailSize) GetUserThumbnailSize { + if v, ok := o.Get(); ok { + return v + } + return d +} + // NewOptInt32 returns new OptInt32 with value set to v. func NewOptInt32(v int32) OptInt32 { return OptInt32{ diff --git a/pkg/api/oas_security_gen.go b/pkg/api/oas_security_gen.go index ddc2925..86db301 100644 --- a/pkg/api/oas_security_gen.go +++ b/pkg/api/oas_security_gen.go @@ -8,7 +8,6 @@ import ( "strings" "github.com/go-faster/errors" - "github.com/ogen-go/ogen/ogenerrors" ) diff --git a/pkg/api/oas_server_gen.go b/pkg/api/oas_server_gen.go index 88cc775..5e955fd 100644 --- a/pkg/api/oas_server_gen.go +++ b/pkg/api/oas_server_gen.go @@ -155,6 +155,18 @@ type Handler interface { // // POST /submissions/{SubmissionID}/status/reset-uploading ActionSubmissionValidated(ctx context.Context, params ActionSubmissionValidatedParams) error + // BatchAssetThumbnails implements batchAssetThumbnails operation. + // + // Batch fetch asset thumbnails. + // + // POST /thumbnails/assets + BatchAssetThumbnails(ctx context.Context, req *BatchAssetThumbnailsReq) (*BatchAssetThumbnailsOK, error) + // BatchUserThumbnails implements batchUserThumbnails operation. + // + // Batch fetch user avatar thumbnails. + // + // POST /thumbnails/users + BatchUserThumbnails(ctx context.Context, req *BatchUserThumbnailsReq) (*BatchUserThumbnailsOK, error) // CreateMapfix implements createMapfix operation. // // Trigger the validator to create a mapfix. @@ -215,6 +227,12 @@ type Handler interface { // // GET /maps/{MapID}/download DownloadMapAsset(ctx context.Context, params DownloadMapAssetParams) (DownloadMapAssetOK, error) + // GetAssetThumbnail implements getAssetThumbnail operation. + // + // Get single asset thumbnail. + // + // GET /thumbnails/asset/{AssetID} + GetAssetThumbnail(ctx context.Context, params GetAssetThumbnailParams) (*GetAssetThumbnailFound, error) // GetMap implements getMap operation. // // Retrieve map with ID. @@ -251,6 +269,12 @@ type Handler interface { // // GET /submissions/{SubmissionID} GetSubmission(ctx context.Context, params GetSubmissionParams) (*Submission, error) + // GetUserThumbnail implements getUserThumbnail operation. + // + // Get single user avatar thumbnail. + // + // GET /thumbnails/user/{UserID} + GetUserThumbnail(ctx context.Context, params GetUserThumbnailParams) (*GetUserThumbnailFound, error) // ListMapfixAuditEvents implements listMapfixAuditEvents operation. // // Retrieve a list of audit events. diff --git a/pkg/api/oas_unimplemented_gen.go b/pkg/api/oas_unimplemented_gen.go index 5321159..d27f4a3 100644 --- a/pkg/api/oas_unimplemented_gen.go +++ b/pkg/api/oas_unimplemented_gen.go @@ -232,6 +232,24 @@ func (UnimplementedHandler) ActionSubmissionValidated(ctx context.Context, param return ht.ErrNotImplemented } +// BatchAssetThumbnails implements batchAssetThumbnails operation. +// +// Batch fetch asset thumbnails. +// +// POST /thumbnails/assets +func (UnimplementedHandler) BatchAssetThumbnails(ctx context.Context, req *BatchAssetThumbnailsReq) (r *BatchAssetThumbnailsOK, _ error) { + return r, ht.ErrNotImplemented +} + +// BatchUserThumbnails implements batchUserThumbnails operation. +// +// Batch fetch user avatar thumbnails. +// +// POST /thumbnails/users +func (UnimplementedHandler) BatchUserThumbnails(ctx context.Context, req *BatchUserThumbnailsReq) (r *BatchUserThumbnailsOK, _ error) { + return r, ht.ErrNotImplemented +} + // CreateMapfix implements createMapfix operation. // // Trigger the validator to create a mapfix. @@ -322,6 +340,15 @@ func (UnimplementedHandler) DownloadMapAsset(ctx context.Context, params Downloa return r, ht.ErrNotImplemented } +// GetAssetThumbnail implements getAssetThumbnail operation. +// +// Get single asset thumbnail. +// +// GET /thumbnails/asset/{AssetID} +func (UnimplementedHandler) GetAssetThumbnail(ctx context.Context, params GetAssetThumbnailParams) (r *GetAssetThumbnailFound, _ error) { + return r, ht.ErrNotImplemented +} + // GetMap implements getMap operation. // // Retrieve map with ID. @@ -376,6 +403,15 @@ func (UnimplementedHandler) GetSubmission(ctx context.Context, params GetSubmiss return r, ht.ErrNotImplemented } +// GetUserThumbnail implements getUserThumbnail operation. +// +// Get single user avatar thumbnail. +// +// GET /thumbnails/user/{UserID} +func (UnimplementedHandler) GetUserThumbnail(ctx context.Context, params GetUserThumbnailParams) (r *GetUserThumbnailFound, _ error) { + return r, ht.ErrNotImplemented +} + // ListMapfixAuditEvents implements listMapfixAuditEvents operation. // // Retrieve a list of audit events. diff --git a/pkg/api/oas_validators_gen.go b/pkg/api/oas_validators_gen.go index 6e768bc..8f40139 100644 --- a/pkg/api/oas_validators_gen.go +++ b/pkg/api/oas_validators_gen.go @@ -6,7 +6,6 @@ import ( "fmt" "github.com/go-faster/errors" - "github.com/ogen-go/ogen/validate" ) @@ -18,13 +17,17 @@ func (s *AuditEvent) Validate() error { var failures []validate.FieldError if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 64, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 64, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Username)); err != nil { return errors.Wrap(err, "string") } @@ -41,6 +44,130 @@ func (s *AuditEvent) Validate() error { return nil } +func (s *BatchAssetThumbnailsReq) Validate() error { + if s == nil { + return validate.ErrNilPointer + } + + var failures []validate.FieldError + if err := func() error { + if s.AssetIds == nil { + return errors.New("nil is invalid value") + } + if err := (validate.Array{ + MinLength: 0, + MinLengthSet: false, + MaxLength: 100, + MaxLengthSet: true, + }).ValidateLength(len(s.AssetIds)); err != nil { + return errors.Wrap(err, "array") + } + return nil + }(); err != nil { + failures = append(failures, validate.FieldError{ + Name: "assetIds", + Error: err, + }) + } + if err := func() error { + if value, ok := s.Size.Get(); ok { + if err := func() error { + if err := value.Validate(); err != nil { + return err + } + return nil + }(); err != nil { + return err + } + } + return nil + }(); err != nil { + failures = append(failures, validate.FieldError{ + Name: "size", + Error: err, + }) + } + if len(failures) > 0 { + return &validate.Error{Fields: failures} + } + return nil +} + +func (s BatchAssetThumbnailsReqSize) Validate() error { + switch s { + case "150x150": + return nil + case "420x420": + return nil + case "768x432": + return nil + default: + return errors.Errorf("invalid value: %v", s) + } +} + +func (s *BatchUserThumbnailsReq) Validate() error { + if s == nil { + return validate.ErrNilPointer + } + + var failures []validate.FieldError + if err := func() error { + if s.UserIds == nil { + return errors.New("nil is invalid value") + } + if err := (validate.Array{ + MinLength: 0, + MinLengthSet: false, + MaxLength: 100, + MaxLengthSet: true, + }).ValidateLength(len(s.UserIds)); err != nil { + return errors.Wrap(err, "array") + } + return nil + }(); err != nil { + failures = append(failures, validate.FieldError{ + Name: "userIds", + Error: err, + }) + } + if err := func() error { + if value, ok := s.Size.Get(); ok { + if err := func() error { + if err := value.Validate(); err != nil { + return err + } + return nil + }(); err != nil { + return err + } + } + return nil + }(); err != nil { + failures = append(failures, validate.FieldError{ + Name: "size", + Error: err, + }) + } + if len(failures) > 0 { + return &validate.Error{Fields: failures} + } + return nil +} + +func (s BatchUserThumbnailsReqSize) Validate() error { + switch s { + case "150x150": + return nil + case "420x420": + return nil + case "768x432": + return nil + default: + return errors.Errorf("invalid value: %v", s) + } +} + func (s *Error) Validate() error { if s == nil { return validate.ErrNilPointer @@ -57,6 +184,7 @@ func (s *Error) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.Code)); err != nil { return errors.Wrap(err, "int") } @@ -96,6 +224,32 @@ func (s *ErrorStatusCode) Validate() error { return nil } +func (s GetAssetThumbnailSize) Validate() error { + switch s { + case "150x150": + return nil + case "420x420": + return nil + case "768x432": + return nil + default: + return errors.Errorf("invalid value: %v", s) + } +} + +func (s GetUserThumbnailSize) Validate() error { + switch s { + case "150x150": + return nil + case "420x420": + return nil + case "768x432": + return nil + default: + return errors.Errorf("invalid value: %v", s) + } +} + func (s *Map) Validate() error { if s == nil { return validate.ErrNilPointer @@ -112,6 +266,7 @@ func (s *Map) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ID)); err != nil { return errors.Wrap(err, "int") } @@ -124,13 +279,17 @@ func (s *Map) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.DisplayName)); err != nil { return errors.Wrap(err, "string") } @@ -143,13 +302,17 @@ func (s *Map) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Creator)); err != nil { return errors.Wrap(err, "string") } @@ -170,6 +333,7 @@ func (s *Map) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.GameID)); err != nil { return errors.Wrap(err, "int") } @@ -190,6 +354,7 @@ func (s *Map) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.Date)); err != nil { return errors.Wrap(err, "int") } @@ -222,6 +387,7 @@ func (s *Mapfix) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ID)); err != nil { return errors.Wrap(err, "int") } @@ -234,13 +400,17 @@ func (s *Mapfix) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.DisplayName)); err != nil { return errors.Wrap(err, "string") } @@ -253,13 +423,17 @@ func (s *Mapfix) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Creator)); err != nil { return errors.Wrap(err, "string") } @@ -280,6 +454,7 @@ func (s *Mapfix) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.GameID)); err != nil { return errors.Wrap(err, "int") } @@ -300,6 +475,7 @@ func (s *Mapfix) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.CreatedAt)); err != nil { return errors.Wrap(err, "int") } @@ -320,6 +496,7 @@ func (s *Mapfix) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.UpdatedAt)); err != nil { return errors.Wrap(err, "int") } @@ -340,6 +517,7 @@ func (s *Mapfix) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.Submitter)); err != nil { return errors.Wrap(err, "int") } @@ -360,6 +538,7 @@ func (s *Mapfix) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.AssetID)); err != nil { return errors.Wrap(err, "int") } @@ -380,6 +559,7 @@ func (s *Mapfix) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.AssetVersion)); err != nil { return errors.Wrap(err, "int") } @@ -402,6 +582,7 @@ func (s *Mapfix) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -429,6 +610,7 @@ func (s *Mapfix) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -454,6 +636,7 @@ func (s *Mapfix) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.TargetAssetID)); err != nil { return errors.Wrap(err, "int") } @@ -474,6 +657,7 @@ func (s *Mapfix) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.StatusID)); err != nil { return errors.Wrap(err, "int") } @@ -486,13 +670,17 @@ func (s *Mapfix) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 256, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 256, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Description)); err != nil { return errors.Wrap(err, "string") } @@ -525,6 +713,7 @@ func (s *MapfixTriggerCreate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.AssetID)); err != nil { return errors.Wrap(err, "int") } @@ -545,6 +734,7 @@ func (s *MapfixTriggerCreate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.TargetAssetID)); err != nil { return errors.Wrap(err, "int") } @@ -557,13 +747,17 @@ func (s *MapfixTriggerCreate) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 256, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 256, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Description)); err != nil { return errors.Wrap(err, "string") } @@ -596,6 +790,7 @@ func (s *Mapfixes) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.Total)); err != nil { return errors.Wrap(err, "int") } @@ -656,6 +851,7 @@ func (s *Operation) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.OperationID)); err != nil { return errors.Wrap(err, "int") } @@ -676,6 +872,7 @@ func (s *Operation) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.Date)); err != nil { return errors.Wrap(err, "int") } @@ -696,6 +893,7 @@ func (s *Operation) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.Owner)); err != nil { return errors.Wrap(err, "int") } @@ -716,6 +914,7 @@ func (s *Operation) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.Status)); err != nil { return errors.Wrap(err, "int") } @@ -728,13 +927,17 @@ func (s *Operation) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 256, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 256, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.StatusMessage)); err != nil { return errors.Wrap(err, "string") } @@ -747,13 +950,17 @@ func (s *Operation) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Path)); err != nil { return errors.Wrap(err, "string") } @@ -786,6 +993,7 @@ func (s *OperationID) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.OperationID)); err != nil { return errors.Wrap(err, "int") } @@ -818,6 +1026,7 @@ func (s *ReleaseInfo) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.SubmissionID)); err != nil { return errors.Wrap(err, "int") } @@ -850,6 +1059,7 @@ func (s *Roles) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.Roles)); err != nil { return errors.Wrap(err, "int") } @@ -882,6 +1092,7 @@ func (s *Script) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ID)); err != nil { return errors.Wrap(err, "int") } @@ -894,13 +1105,17 @@ func (s *Script) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Name)); err != nil { return errors.Wrap(err, "string") } @@ -913,13 +1128,17 @@ func (s *Script) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 16, - MinLengthSet: true, - MaxLength: 16, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 16, + MinLengthSet: true, + MaxLength: 16, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Hash)); err != nil { return errors.Wrap(err, "string") } @@ -932,13 +1151,17 @@ func (s *Script) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 1048576, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 1048576, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Source)); err != nil { return errors.Wrap(err, "string") } @@ -959,6 +1182,7 @@ func (s *Script) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ResourceType)); err != nil { return errors.Wrap(err, "int") } @@ -979,6 +1203,7 @@ func (s *Script) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ResourceID)); err != nil { return errors.Wrap(err, "int") } @@ -1003,13 +1228,17 @@ func (s *ScriptCreate) Validate() error { var failures []validate.FieldError if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 256, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 256, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Name)); err != nil { return errors.Wrap(err, "string") } @@ -1022,13 +1251,17 @@ func (s *ScriptCreate) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 1048576, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 1048576, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Source)); err != nil { return errors.Wrap(err, "string") } @@ -1049,6 +1282,7 @@ func (s *ScriptCreate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ResourceType)); err != nil { return errors.Wrap(err, "int") } @@ -1071,6 +1305,7 @@ func (s *ScriptCreate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -1108,6 +1343,7 @@ func (s *ScriptID) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ScriptID)); err != nil { return errors.Wrap(err, "int") } @@ -1140,6 +1376,7 @@ func (s *ScriptPolicy) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ID)); err != nil { return errors.Wrap(err, "int") } @@ -1152,13 +1389,17 @@ func (s *ScriptPolicy) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 16, - MinLengthSet: true, - MaxLength: 16, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 16, + MinLengthSet: true, + MaxLength: 16, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.FromScriptHash)); err != nil { return errors.Wrap(err, "string") } @@ -1179,6 +1420,7 @@ func (s *ScriptPolicy) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ToScriptID)); err != nil { return errors.Wrap(err, "int") } @@ -1199,6 +1441,7 @@ func (s *ScriptPolicy) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.Policy)); err != nil { return errors.Wrap(err, "int") } @@ -1231,6 +1474,7 @@ func (s *ScriptPolicyCreate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.FromScriptID)); err != nil { return errors.Wrap(err, "int") } @@ -1251,6 +1495,7 @@ func (s *ScriptPolicyCreate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ToScriptID)); err != nil { return errors.Wrap(err, "int") } @@ -1271,6 +1516,7 @@ func (s *ScriptPolicyCreate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.Policy)); err != nil { return errors.Wrap(err, "int") } @@ -1303,6 +1549,7 @@ func (s *ScriptPolicyID) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ScriptPolicyID)); err != nil { return errors.Wrap(err, "int") } @@ -1335,6 +1582,7 @@ func (s *ScriptPolicyUpdate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ID)); err != nil { return errors.Wrap(err, "int") } @@ -1357,6 +1605,7 @@ func (s *ScriptPolicyUpdate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -1384,6 +1633,7 @@ func (s *ScriptPolicyUpdate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -1411,6 +1661,7 @@ func (s *ScriptPolicyUpdate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -1448,6 +1699,7 @@ func (s *ScriptUpdate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ID)); err != nil { return errors.Wrap(err, "int") } @@ -1462,13 +1714,17 @@ func (s *ScriptUpdate) Validate() error { if value, ok := s.Name.Get(); ok { if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(value)); err != nil { return errors.Wrap(err, "string") } @@ -1488,13 +1744,17 @@ func (s *ScriptUpdate) Validate() error { if value, ok := s.Source.Get(); ok { if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 1048576, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 1048576, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(value)); err != nil { return errors.Wrap(err, "string") } @@ -1522,6 +1782,7 @@ func (s *ScriptUpdate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -1549,6 +1810,7 @@ func (s *ScriptUpdate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -1586,6 +1848,7 @@ func (s *Submission) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.ID)); err != nil { return errors.Wrap(err, "int") } @@ -1598,13 +1861,17 @@ func (s *Submission) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.DisplayName)); err != nil { return errors.Wrap(err, "string") } @@ -1617,13 +1884,17 @@ func (s *Submission) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Creator)); err != nil { return errors.Wrap(err, "string") } @@ -1644,6 +1915,7 @@ func (s *Submission) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.GameID)); err != nil { return errors.Wrap(err, "int") } @@ -1664,6 +1936,7 @@ func (s *Submission) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.CreatedAt)); err != nil { return errors.Wrap(err, "int") } @@ -1684,6 +1957,7 @@ func (s *Submission) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.UpdatedAt)); err != nil { return errors.Wrap(err, "int") } @@ -1704,6 +1978,7 @@ func (s *Submission) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.Submitter)); err != nil { return errors.Wrap(err, "int") } @@ -1724,6 +1999,7 @@ func (s *Submission) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.AssetID)); err != nil { return errors.Wrap(err, "int") } @@ -1744,6 +2020,7 @@ func (s *Submission) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.AssetVersion)); err != nil { return errors.Wrap(err, "int") } @@ -1766,6 +2043,7 @@ func (s *Submission) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -1793,6 +2071,7 @@ func (s *Submission) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -1820,6 +2099,7 @@ func (s *Submission) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(value)); err != nil { return errors.Wrap(err, "int") } @@ -1845,6 +2125,7 @@ func (s *Submission) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.StatusID)); err != nil { return errors.Wrap(err, "int") } @@ -1877,6 +2158,7 @@ func (s *SubmissionTriggerCreate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.AssetID)); err != nil { return errors.Wrap(err, "int") } @@ -1889,13 +2171,17 @@ func (s *SubmissionTriggerCreate) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.DisplayName)); err != nil { return errors.Wrap(err, "string") } @@ -1908,13 +2194,17 @@ func (s *SubmissionTriggerCreate) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Creator)); err != nil { return errors.Wrap(err, "string") } @@ -1935,6 +2225,7 @@ func (s *SubmissionTriggerCreate) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.GameID)); err != nil { return errors.Wrap(err, "int") } @@ -1967,6 +2258,7 @@ func (s *Submissions) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.Total)); err != nil { return errors.Wrap(err, "int") } @@ -2027,6 +2319,7 @@ func (s *User) Validate() error { MaxExclusive: false, MultipleOfSet: false, MultipleOf: 0, + Pattern: nil, }).Validate(int64(s.UserID)); err != nil { return errors.Wrap(err, "int") } @@ -2039,13 +2332,17 @@ func (s *User) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 128, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 128, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.Username)); err != nil { return errors.Wrap(err, "string") } @@ -2058,13 +2355,17 @@ func (s *User) Validate() error { } if err := func() error { if err := (validate.String{ - MinLength: 0, - MinLengthSet: false, - MaxLength: 256, - MaxLengthSet: true, - Email: false, - Hostname: false, - Regex: nil, + MinLength: 0, + MinLengthSet: false, + MaxLength: 256, + MaxLengthSet: true, + Email: false, + Hostname: false, + Regex: nil, + MinNumeric: 0, + MinNumericSet: false, + MaxNumeric: 0, + MaxNumericSet: false, }).Validate(string(s.AvatarURL)); err != nil { return errors.Wrap(err, "string") } diff --git a/pkg/cmds/serve.go b/pkg/cmds/serve.go index c01b503..24b151e 100644 --- a/pkg/cmds/serve.go +++ b/pkg/cmds/serve.go @@ -18,6 +18,7 @@ import ( "git.itzana.me/strafesnet/maps-service/pkg/validator_controller" "git.itzana.me/strafesnet/maps-service/pkg/web_api" "github.com/nats-io/nats.go" + "github.com/redis/go-redis/v9" log "github.com/sirupsen/logrus" "github.com/urfave/cli/v2" "google.golang.org/grpc" @@ -102,6 +103,24 @@ func NewServeCommand() *cli.Command { EnvVars: []string{"RBX_API_KEY"}, Required: true, }, + &cli.StringFlag{ + Name: "redis-host", + Usage: "Host of Redis cache", + EnvVars: []string{"REDIS_HOST"}, + Value: "localhost:6379", + }, + &cli.StringFlag{ + Name: "redis-password", + Usage: "Password for Redis", + EnvVars: []string{"REDIS_PASSWORD"}, + Value: "", + }, + &cli.IntFlag{ + Name: "redis-db", + Usage: "Redis database number", + EnvVars: []string{"REDIS_DB"}, + Value: 0, + }, }, } } @@ -129,6 +148,24 @@ func serve(ctx *cli.Context) error { log.WithError(err).Fatal("failed to add stream") } + // Initialize Redis client + redisClient := redis.NewClient(&redis.Options{ + Addr: ctx.String("redis-host"), + Password: ctx.String("redis-password"), + DB: ctx.Int("redis-db"), + }) + + // Test Redis connection + if err := redisClient.Ping(ctx.Context).Err(); err != nil { + log.WithError(err).Warn("failed to connect to Redis - thumbnails will not be cached") + } + + // Initialize Roblox client + robloxClient := &roblox.Client{ + HttpClient: http.DefaultClient, + ApiKey: ctx.String("rbx-api-key"), + } + // connect to main game database conn, err := grpc.Dial(ctx.String("data-rpc-host"), grpc.WithTransportCredentials(insecure.NewCredentials())) if err != nil { @@ -139,13 +176,15 @@ func serve(ctx *cli.Context) error { js, maps.NewMapsServiceClient(conn), users.NewUsersServiceClient(conn), + robloxClient, + redisClient, ) svc_external := web_api.NewService( &svc_inner, roblox.Client{ HttpClient: http.DefaultClient, - ApiKey: ctx.String("rbx-api-key"), + ApiKey: ctx.String("rbx-api-key"), }, ) diff --git a/pkg/roblox/thumbnails.go b/pkg/roblox/thumbnails.go new file mode 100644 index 0000000..2d5e6be --- /dev/null +++ b/pkg/roblox/thumbnails.go @@ -0,0 +1,160 @@ +package roblox + +import ( + "bytes" + "encoding/json" + "fmt" + "io" + "net/http" +) + +// ThumbnailSize represents valid Roblox thumbnail sizes +type ThumbnailSize string + +const ( + Size150x150 ThumbnailSize = "150x150" + Size420x420 ThumbnailSize = "420x420" + Size768x432 ThumbnailSize = "768x432" +) + +// ThumbnailFormat represents the image format +type ThumbnailFormat string + +const ( + FormatPng ThumbnailFormat = "Png" + FormatJpeg ThumbnailFormat = "Jpeg" +) + +// ThumbnailRequest represents a single thumbnail request +type ThumbnailRequest struct { + RequestID string `json:"requestId,omitempty"` + Type string `json:"type"` + TargetID uint64 `json:"targetId"` + Size string `json:"size,omitempty"` + Format string `json:"format,omitempty"` +} + +// ThumbnailData represents a single thumbnail response +type ThumbnailData struct { + TargetID uint64 `json:"targetId"` + State string `json:"state"` // "Completed", "Error", "Pending" + ImageURL string `json:"imageUrl"` +} + +// BatchThumbnailsResponse represents the API response +type BatchThumbnailsResponse struct { + Data []ThumbnailData `json:"data"` +} + +// GetAssetThumbnails fetches thumbnails for multiple assets in a single batch request +// Roblox allows up to 100 assets per batch +func (c *Client) GetAssetThumbnails(assetIDs []uint64, size ThumbnailSize, format ThumbnailFormat) ([]ThumbnailData, error) { + if len(assetIDs) == 0 { + return []ThumbnailData{}, nil + } + if len(assetIDs) > 100 { + return nil, GetError("batch size cannot exceed 100 assets") + } + + // Build request payload - the API expects an array directly, not wrapped in an object + requests := make([]ThumbnailRequest, len(assetIDs)) + for i, assetID := range assetIDs { + requests[i] = ThumbnailRequest{ + Type: "Asset", + TargetID: assetID, + Size: string(size), + Format: string(format), + } + } + + jsonData, err := json.Marshal(requests) + if err != nil { + return nil, GetError("JSONMarshalError: " + err.Error()) + } + + req, err := http.NewRequest("POST", "https://thumbnails.roblox.com/v1/batch", bytes.NewBuffer(jsonData)) + if err != nil { + return nil, GetError("RequestCreationError: " + err.Error()) + } + + req.Header.Set("Content-Type", "application/json") + + resp, err := c.HttpClient.Do(req) + if err != nil { + return nil, GetError("RequestError: " + err.Error()) + } + defer resp.Body.Close() + + if resp.StatusCode != http.StatusOK { + body, _ := io.ReadAll(resp.Body) + return nil, GetError(fmt.Sprintf("ResponseError: status code %d, body: %s", resp.StatusCode, string(body))) + } + + body, err := io.ReadAll(resp.Body) + if err != nil { + return nil, GetError("ReadBodyError: " + err.Error()) + } + + var response BatchThumbnailsResponse + if err := json.Unmarshal(body, &response); err != nil { + return nil, GetError("JSONUnmarshalError: " + err.Error()) + } + + return response.Data, nil +} + +// GetUserAvatarThumbnails fetches avatar thumbnails for multiple users in a single batch request +func (c *Client) GetUserAvatarThumbnails(userIDs []uint64, size ThumbnailSize, format ThumbnailFormat) ([]ThumbnailData, error) { + if len(userIDs) == 0 { + return []ThumbnailData{}, nil + } + if len(userIDs) > 100 { + return nil, GetError("batch size cannot exceed 100 users") + } + + // Build request payload - the API expects an array directly, not wrapped in an object + requests := make([]ThumbnailRequest, len(userIDs)) + for i, userID := range userIDs { + requests[i] = ThumbnailRequest{ + Type: "AvatarHeadShot", + TargetID: userID, + Size: string(size), + Format: string(format), + } + } + + jsonData, err := json.Marshal(requests) + if err != nil { + return nil, GetError("JSONMarshalError: " + err.Error()) + } + + req, err := http.NewRequest("POST", "https://thumbnails.roblox.com/v1/batch", bytes.NewBuffer(jsonData)) + if err != nil { + return nil, GetError("RequestCreationError: " + err.Error()) + } + + req.Header.Set("Content-Type", "application/json") + + resp, err := c.HttpClient.Do(req) + if err != nil { + return nil, GetError("RequestError: " + err.Error()) + } + defer resp.Body.Close() + + if resp.StatusCode != http.StatusOK { + body, _ := io.ReadAll(resp.Body) + return nil, GetError(fmt.Sprintf("ResponseError: status code %d, body: %s", resp.StatusCode, string(body))) + } + + body, err := io.ReadAll(resp.Body) + if err != nil { + return nil, GetError("ReadBodyError: " + err.Error()) + } + + var response BatchThumbnailsResponse + if err := json.Unmarshal(body, &response); err != nil { + return nil, GetError("JSONUnmarshalError: " + err.Error()) + } + + return response.Data, nil +} diff --git a/pkg/service/service.go b/pkg/service/service.go index 31198a5..4395fc9 100644 --- a/pkg/service/service.go +++ b/pkg/service/service.go @@ -1,17 +1,22 @@ package service import ( + "context" + "git.itzana.me/strafesnet/go-grpc/maps" "git.itzana.me/strafesnet/go-grpc/users" "git.itzana.me/strafesnet/maps-service/pkg/datastore" + "git.itzana.me/strafesnet/maps-service/pkg/roblox" "github.com/nats-io/nats.go" + "github.com/redis/go-redis/v9" ) type Service struct { - db datastore.Datastore - nats nats.JetStreamContext - maps maps.MapsServiceClient - users users.UsersServiceClient + db datastore.Datastore + nats nats.JetStreamContext + maps maps.MapsServiceClient + users users.UsersServiceClient + thumbnailService *ThumbnailService } func NewService( @@ -19,11 +24,34 @@ func NewService( nats nats.JetStreamContext, maps maps.MapsServiceClient, users users.UsersServiceClient, + robloxClient *roblox.Client, + redisClient *redis.Client, ) Service { return Service{ - db: db, - nats: nats, - maps: maps, - users: users, + db: db, + nats: nats, + maps: maps, + users: users, + thumbnailService: NewThumbnailService(robloxClient, redisClient), } } + +// GetAssetThumbnails proxies to the thumbnail service +func (s *Service) GetAssetThumbnails(ctx context.Context, assetIDs []uint64, size roblox.ThumbnailSize) (map[uint64]string, error) { + return s.thumbnailService.GetAssetThumbnails(ctx, assetIDs, size) +} + +// GetUserAvatarThumbnails proxies to the thumbnail service +func (s *Service) GetUserAvatarThumbnails(ctx context.Context, userIDs []uint64, size roblox.ThumbnailSize) (map[uint64]string, error) { + return s.thumbnailService.GetUserAvatarThumbnails(ctx, userIDs, size) +} + +// GetSingleAssetThumbnail proxies to the thumbnail service +func (s *Service) GetSingleAssetThumbnail(ctx context.Context, assetID uint64, size roblox.ThumbnailSize) (string, error) { + return s.thumbnailService.GetSingleAssetThumbnail(ctx, assetID, size) +} + +// GetSingleUserAvatarThumbnail proxies to the thumbnail service +func (s *Service) GetSingleUserAvatarThumbnail(ctx context.Context, userID uint64, size roblox.ThumbnailSize) (string, error) { + return s.thumbnailService.GetSingleUserAvatarThumbnail(ctx, userID, size) +} diff --git a/pkg/service/thumbnails.go b/pkg/service/thumbnails.go new file mode 100644 index 0000000..bb90d43 --- /dev/null +++ b/pkg/service/thumbnails.go @@ -0,0 +1,218 @@ +package service + +import ( + "context" + "encoding/json" + "fmt" + "time" + + "git.itzana.me/strafesnet/maps-service/pkg/roblox" + "github.com/redis/go-redis/v9" +) + +type ThumbnailService struct { + robloxClient *roblox.Client + redisClient *redis.Client + cacheTTL time.Duration +} + +func NewThumbnailService(robloxClient *roblox.Client, redisClient *redis.Client) *ThumbnailService { + return &ThumbnailService{ + robloxClient: robloxClient, + redisClient: redisClient, + cacheTTL: 24 * time.Hour, // Cache thumbnails for 24 hours + } +} + +// CachedThumbnail represents a cached thumbnail entry +type CachedThumbnail struct { + ImageURL string `json:"imageUrl"` + State string `json:"state"` + CachedAt time.Time `json:"cachedAt"` +} + +// GetAssetThumbnails fetches thumbnails with Redis caching and batching +func (s *ThumbnailService) GetAssetThumbnails(ctx context.Context, assetIDs []uint64, size roblox.ThumbnailSize) (map[uint64]string, error) { + if len(assetIDs) == 0 { + return map[uint64]string{}, nil + } + + result := make(map[uint64]string) + var missingIDs []uint64 + + // Try to get from cache first + for _, assetID := range assetIDs { + cacheKey := fmt.Sprintf("thumbnail:asset:%d:%s", assetID, size) + cached, err := s.redisClient.Get(ctx, cacheKey).Result() + + if err == redis.Nil { + // Cache miss + missingIDs = append(missingIDs, assetID) + } else if err != nil { + // Redis error - treat as cache miss + missingIDs = append(missingIDs, assetID) + } else { + // Cache hit + var thumbnail CachedThumbnail + if err := json.Unmarshal([]byte(cached), &thumbnail); err == nil && thumbnail.State == "Completed" { + result[assetID] = thumbnail.ImageURL + } else { + missingIDs = append(missingIDs, assetID) + } + } + } + + // If all were cached, return early + if len(missingIDs) == 0 { + return result, nil + } + + // Batch fetch missing thumbnails from Roblox API + // Split into batches of 100 (Roblox API limit) + for i := 0; i < len(missingIDs); i += 100 { + end := i + 100 + if end > len(missingIDs) { + end = len(missingIDs) + } + batch := missingIDs[i:end] + + thumbnails, err := s.robloxClient.GetAssetThumbnails(batch, size, roblox.FormatPng) + if err != nil { + return nil, fmt.Errorf("failed to fetch thumbnails: %w", err) + } + + // Process results and cache them + for _, thumb := range thumbnails { + cached := CachedThumbnail{ + ImageURL: thumb.ImageURL, + State: thumb.State, + CachedAt: time.Now(), + } + + if thumb.State == "Completed" && thumb.ImageURL != "" { + result[thumb.TargetID] = thumb.ImageURL + } + + // Cache the result (even if incomplete, to avoid repeated API calls) + cacheKey := fmt.Sprintf("thumbnail:asset:%d:%s", thumb.TargetID, size) + cachedJSON, _ := json.Marshal(cached) + + // Use shorter TTL for incomplete thumbnails + ttl := s.cacheTTL + if thumb.State != "Completed" { + ttl = 5 * time.Minute + } + + s.redisClient.Set(ctx, cacheKey, cachedJSON, ttl) + } + } + + return result, nil +} + +// GetUserAvatarThumbnails fetches user avatar thumbnails with Redis caching and batching +func (s *ThumbnailService) GetUserAvatarThumbnails(ctx context.Context, userIDs []uint64, size roblox.ThumbnailSize) (map[uint64]string, error) { + if len(userIDs) == 0 { + return map[uint64]string{}, nil + } + + result := make(map[uint64]string) + var missingIDs []uint64 + + // Try to get from cache first + for _, userID := range userIDs { + cacheKey := fmt.Sprintf("thumbnail:user:%d:%s", userID, size) + cached, err := s.redisClient.Get(ctx, cacheKey).Result() + + if err == redis.Nil { + // Cache miss + missingIDs = append(missingIDs, userID) + } else if err != nil { + // Redis error - treat as cache miss + missingIDs = append(missingIDs, userID) + } else { + // Cache hit + var thumbnail CachedThumbnail + if err := json.Unmarshal([]byte(cached), &thumbnail); err == nil && thumbnail.State == "Completed" { + result[userID] = thumbnail.ImageURL + } else { + missingIDs = append(missingIDs, userID) + } + } + } + + // If all were cached, return early + if len(missingIDs) == 0 { + return result, nil + } + + // Batch fetch missing thumbnails from Roblox API + // Split into batches of 100 (Roblox API limit) + for i := 0; i < len(missingIDs); i += 100 { + end := i + 100 + if end > len(missingIDs) { + end = len(missingIDs) + } + batch := missingIDs[i:end] + + thumbnails, err := s.robloxClient.GetUserAvatarThumbnails(batch, size, roblox.FormatPng) + if err != nil { + return nil, fmt.Errorf("failed to fetch user thumbnails: %w", err) + } + + // Process results and cache them + for _, thumb := range thumbnails { + cached := CachedThumbnail{ + ImageURL: thumb.ImageURL, + State: thumb.State, + CachedAt: time.Now(), + } + + if thumb.State == "Completed" && thumb.ImageURL != "" { + result[thumb.TargetID] = thumb.ImageURL + } + + // Cache the result + cacheKey := fmt.Sprintf("thumbnail:user:%d:%s", thumb.TargetID, size) + cachedJSON, _ := json.Marshal(cached) + + // Use shorter TTL for incomplete thumbnails + ttl := s.cacheTTL + if thumb.State != "Completed" { + ttl = 5 * time.Minute + } + + s.redisClient.Set(ctx, cacheKey, cachedJSON, ttl) + } + } + + return result, nil +} + +// GetSingleAssetThumbnail is a convenience method for fetching a single asset thumbnail +func (s *ThumbnailService) GetSingleAssetThumbnail(ctx context.Context, assetID uint64, size roblox.ThumbnailSize) (string, error) { + results, err := s.GetAssetThumbnails(ctx, []uint64{assetID}, size) + if err != nil { + return "", err + } + + if url, ok := results[assetID]; ok { + return url, nil + } + + return "", fmt.Errorf("thumbnail not available for asset %d", assetID) +} + +// GetSingleUserAvatarThumbnail is a convenience method for fetching a single user avatar thumbnail +func (s *ThumbnailService) GetSingleUserAvatarThumbnail(ctx context.Context, userID uint64, size roblox.ThumbnailSize) (string, error) { + results, err := s.GetUserAvatarThumbnails(ctx, []uint64{userID}, size) + if err != nil { + return "", err + } + + if url, ok := results[userID]; ok { + return url, nil + } + + return "", fmt.Errorf("thumbnail not available for user %d", userID) +} diff --git a/pkg/web_api/thumbnails.go b/pkg/web_api/thumbnails.go new file mode 100644 index 0000000..a8c54f5 --- /dev/null +++ b/pkg/web_api/thumbnails.go @@ -0,0 +1,135 @@ +package web_api + +import ( + "context" + "strconv" + + "git.itzana.me/strafesnet/maps-service/pkg/api" + "git.itzana.me/strafesnet/maps-service/pkg/roblox" +) + +// BatchAssetThumbnails handles batch fetching of asset thumbnails +func (svc *Service) BatchAssetThumbnails(ctx context.Context, req *api.BatchAssetThumbnailsReq) (*api.BatchAssetThumbnailsOK, error) { + if len(req.AssetIds) == 0 { + return &api.BatchAssetThumbnailsOK{ + Thumbnails: api.NewOptBatchAssetThumbnailsOKThumbnails(map[string]string{}), + }, nil + } + + // Convert size string to enum + size := roblox.Size420x420 + if req.Size.IsSet() { + sizeStr := req.Size.Value + switch api.BatchAssetThumbnailsReqSize(sizeStr) { + case api.BatchAssetThumbnailsReqSize150x150: + size = roblox.Size150x150 + case api.BatchAssetThumbnailsReqSize768x432: + size = roblox.Size768x432 + } + } + + // Fetch thumbnails from service + thumbnails, err := svc.inner.GetAssetThumbnails(ctx, req.AssetIds, size) + if err != nil { + return nil, err + } + + // Convert map[uint64]string to map[string]string for JSON + result := make(map[string]string, len(thumbnails)) + for assetID, url := range thumbnails { + result[strconv.FormatUint(assetID, 10)] = url + } + + return &api.BatchAssetThumbnailsOK{ + Thumbnails: api.NewOptBatchAssetThumbnailsOKThumbnails(result), + }, nil +} + +// GetAssetThumbnail handles single asset thumbnail fetch (with redirect) +func (svc *Service) GetAssetThumbnail(ctx context.Context, params api.GetAssetThumbnailParams) (*api.GetAssetThumbnailFound, error) { + // Convert size string to enum + size := roblox.Size420x420 + if params.Size.IsSet() { + sizeStr := params.Size.Value + switch api.GetAssetThumbnailSize(sizeStr) { + case api.GetAssetThumbnailSize150x150: + size = roblox.Size150x150 + case api.GetAssetThumbnailSize768x432: + size = roblox.Size768x432 + } + } + + // Fetch thumbnail + thumbnailURL, err := svc.inner.GetSingleAssetThumbnail(ctx, params.AssetID, size) + if err != nil { + return nil, err + } + + // Return redirect response + return &api.GetAssetThumbnailFound{ + Location: api.NewOptString(thumbnailURL), + }, nil +} + +// BatchUserThumbnails handles batch fetching of user avatar thumbnails +func (svc *Service) BatchUserThumbnails(ctx context.Context, req *api.BatchUserThumbnailsReq) (*api.BatchUserThumbnailsOK, error) { + if len(req.UserIds) == 0 { + return &api.BatchUserThumbnailsOK{ + Thumbnails: api.NewOptBatchUserThumbnailsOKThumbnails(map[string]string{}), + }, nil + } + + // Convert size string to enum + size := roblox.Size150x150 + if req.Size.IsSet() { + sizeStr := req.Size.Value + switch api.BatchUserThumbnailsReqSize(sizeStr) { + case api.BatchUserThumbnailsReqSize420x420: + size = roblox.Size420x420 + case api.BatchUserThumbnailsReqSize768x432: + size = roblox.Size768x432 + } + } + + // Fetch thumbnails from service + thumbnails, err := svc.inner.GetUserAvatarThumbnails(ctx, req.UserIds, size) + if err != nil { + return nil, err + } + + // Convert map[uint64]string to map[string]string for JSON + result := make(map[string]string, len(thumbnails)) + for userID, url := range thumbnails { + result[strconv.FormatUint(userID, 10)] = url + } + + return &api.BatchUserThumbnailsOK{ + Thumbnails: api.NewOptBatchUserThumbnailsOKThumbnails(result), + }, nil +} + +// GetUserThumbnail handles single user avatar thumbnail fetch (with redirect) +func (svc *Service) GetUserThumbnail(ctx context.Context, params api.GetUserThumbnailParams) (*api.GetUserThumbnailFound, error) { + // Convert size string to enum + size := roblox.Size150x150 + if params.Size.IsSet() { + sizeStr := params.Size.Value + switch api.GetUserThumbnailSize(sizeStr) { + case api.GetUserThumbnailSize420x420: + size = roblox.Size420x420 + case api.GetUserThumbnailSize768x432: + size = roblox.Size768x432 + } + } + + // Fetch thumbnail + thumbnailURL, err := svc.inner.GetSingleUserAvatarThumbnail(ctx, params.UserID, size) + if err != nil { + return nil, err + } + + // Return redirect response + return &api.GetUserThumbnailFound{ + Location: api.NewOptString(thumbnailURL), + }, nil +}