From 8280426cea12fa9e72a82de0ce61d64055c6209e Mon Sep 17 00:00:00 2001 From: Konstantin Demin Date: Mon, 20 May 2024 16:40:03 +0300 Subject: [PATCH] quay: improvements --- njs/quay.js | 7 + site.avail/http-quay.krd.sh.conf | 263 ++++++++++++++++++++----------- 2 files changed, 178 insertions(+), 92 deletions(-) create mode 100644 njs/quay.js diff --git a/njs/quay.js b/njs/quay.js new file mode 100644 index 0000000..8ceb099 --- /dev/null +++ b/njs/quay.js @@ -0,0 +1,7 @@ +function route_ui(r) +{ + r.internalRedirect("@" + r.variables.krdsh_quay_ui_njs + "_ui"); +} + + +export default { route_ui }; diff --git a/site.avail/http-quay.krd.sh.conf b/site.avail/http-quay.krd.sh.conf index c380e57..8179ba1 100644 --- a/site.avail/http-quay.krd.sh.conf +++ b/site.avail/http-quay.krd.sh.conf @@ -8,6 +8,11 @@ upstream krdsh_quay_secscan { server unix:/home/user/quay-run/gunicorn_secscan.sock fail_timeout=0; } +proxy_cache_path + /var/cache/angie/proxy/krdsh-quay + keys_zone=krdsh_cache_quay:10m + levels=1:2; + map $http2:$http3 $krdsh_quay_http1_bucket { @@ -16,6 +21,7 @@ map $http2:$http3 ## current instanse is not behind LB/ingress, ## so $proxy_protocol_addr is meaningless # ":" $proxy_protocol_addr; + ":" $remote_addr; } @@ -40,41 +46,62 @@ map $uri { default ""; + ## ~*^/v2/([^/]+)(?:/[^/]+)+/blobs/ $1; + ## ~*^/v2/([^/]+)/[^/]+/tags/ $1; + ## ~*^/v2/([^/]+)/[^/]+/manifests/ $1; ~*^/v2/([^/]+)/.+/(?:blobs|manifests|tags)/ $1; } ## use $request_id to remove (tight) request limit -map $krdsh_quay_namespace +map $krdsh_quay_namespace:$krdsh_remote_type $krdsh_quay_http1_ns_bucket { default $krdsh_quay_http1_bucket; - ~*^(?:k2|krd)$ $request_id; + ~*^(?:k2|krd): $request_id; + + ## remove limits for internal usage + ~^[^:]+:internal$ $request_id; } -map $krdsh_quay_namespace +map $krdsh_quay_namespace:$krdsh_remote_type $krdsh_quay_http2_ns_bucket { default $krdsh_quay_http2_bucket; - ~*^(?:k2|krd)$ $request_id; + ~*^(?:k2|krd): $request_id; + + ## remove limits for internal usage + ~^[^:]+:internal$ $request_id; } -map $krdsh_quay_namespace +map $krdsh_quay_namespace:$krdsh_remote_type $krdsh_quay_http3_ns_bucket { default $krdsh_quay_http3_bucket; - ~*^(?:k2|krd)$ $request_id; + ~*^(?:k2|krd): $request_id; + + ## remove limits for internal usage + ~^[^:]+:internal$ $request_id; } map $cookie_patternfly $krdsh_quay_ui { - volatile; - default old; true new; } +map $request_method:$uri + $krdsh_quay_nocache +{ + default 1; + + ## cache requests: + ## - ^/api/v1/repository/.+/tag/$ + ## - ^/api/v1/repository/.+/manifest/.+$ + ~*^(?:GET|HEAD):/api/v1/repository/(?:krd|k2|library|docker_io|quay_io|gcr_io|ghcr_io|registry_k8s_io)/.+/(?:tag/|manifest/.+)$ ""; +} + limit_req_zone $http_authorization zone=krdsh_quay_staticauth:10m rate=30r/s; limit_req_zone $krdsh_quay_http1_bucket zone=krdsh_quay_http1_light:10m rate=60r/s; @@ -115,7 +142,8 @@ server { include snip.d/empty-favicon; - location / { + location / + { return 301 https://$host$uri$is_args$args; } } @@ -144,7 +172,13 @@ server { error_page 502 /home/user/quay-run-static/static/502.html; - location /static/ { + limit_req_status 429; + limit_req_log_level warn; + + js_import njs/quay.js; + + location /static/ + { root /home/user/quay-run-static; expires 1d; @@ -156,7 +190,12 @@ server { error_page 404 /404; } - location / { + location @old_ui + { + proxy_pass http://krdsh_quay_web; + } + location @new_ui + { root /home/user/quay-run-static/static/patternfly; index index.html; @@ -164,86 +203,123 @@ server { brotli_static on; zstd_static on; - if ($krdsh_quay_ui = "old") { - proxy_pass http://krdsh_quay_web; - } - if ($krdsh_quay_ui = "new") { - rewrite - ^/(?:overview|organization|repository|tag) - /index.html - break; - } + rewrite + ^/(?:overview|organization|repository|tag) + /index.html + break; + } + location / + { + js_content quay.route_ui; + + js_var $krdsh_quay_ui_njs "$krdsh_quay_ui"; } - location /angular { + location /angular + { # Expire cookie and switch to old UI add_header Set-Cookie "patternfly=deleted; path=/; Expires=Thu, Jan 01 1970 00:00:00 UTC"; return 302 /$is_args$args; } - location /react { + location /react + { # Set cookie and witch to new UI add_header Set-Cookie "patternfly=true; path=/; SameSite=Lax; HttpOnly;" always; return 302 /$is_args$args; } - limit_req_status 429; - limit_req_log_level warn; - # Temporarily force signin for old and new UI to route to web app - location /signin { + location /signin + { proxy_pass http://krdsh_quay_web/; } # Capture traffic that needs to go to web_app, see /web.py - location ~* ^/(?:config|csrf_token|oauth1|oauth2|webhooks|keys|.well-known|customtrigger|userfiles/) { + location ~* ^/(?:config|csrf_token|oauth1|oauth2|webhooks|keys|.well-known|customtrigger|userfiles/) + { proxy_pass http://krdsh_quay_web; } # Capture old UI paths that aren't present in new UI - location ~* ^/(?:user/|search) { + location ~* ^/(?:user/|search) + { proxy_pass http://krdsh_quay_web; } - location /push { + location /push + { proxy_pass http://krdsh_quay_web; client_max_body_size 5M; } - location /realtime { + location /realtime + { proxy_pass http://krdsh_quay_web; proxy_buffering off; proxy_request_buffering off; } - location /secscan/ { + location /secscan/ + { proxy_pass http://krdsh_quay_secscan; } # location ~ ^/v2/.+/_trust/tuf/ { # proxy_pass https://tuf.krd.sh$uri; - # + # include snip.d/proxy-common-headers; # include snip.d/proxy-accept-encoding; # include snip.d/proxy-connection-close; # include snip.d/proxy-early-data; - # - # proxy_set_header Host tuf.krd.sh; + + # proxy_set_header Host $host; # } - location /api/ { + location ~* ^/api/v1/repository(?:/.+/tag/|/.+/manifest/.+)$ + { + limit_req zone=krdsh_quay_http1_medium burst=50 nodelay; + limit_req zone=krdsh_quay_http2_medium burst=100 nodelay; + limit_req zone=krdsh_quay_http3_medium burst=100 nodelay; + proxy_pass http://krdsh_quay_web; + keepalive_timeout 0; + + proxy_cache krdsh_cache_quay; + proxy_cache_key $uri$is_args$args; + proxy_cache_bypass $http_pragma $http_authorization $krdsh_quay_nocache; + proxy_no_cache $http_pragma $http_authorization $krdsh_quay_nocache; + + expires 30s; + proxy_cache_valid 200 1m; + proxy_cache_valid 10s; + proxy_ignore_client_abort on; + + proxy_ignore_headers Cache-Control Expires Set-Cookie Vary; + proxy_hide_header Cache-Control; + proxy_hide_header Expires; + proxy_hide_header Set-Cookie; + proxy_hide_header Vary; + + ## quirks + proxy_temp_file_write_size 4m; + } + location /api/ + { limit_req zone=krdsh_quay_http1_heavy burst=25 nodelay; limit_req zone=krdsh_quay_http2_heavy burst=100 nodelay; limit_req zone=krdsh_quay_http3_heavy burst=100 nodelay; + proxy_pass http://krdsh_quay_web; + keepalive_timeout 0; } - location /api/suconfig { + location /api/suconfig + { proxy_pass http://krdsh_quay_web; proxy_read_timeout 2000; @@ -251,33 +327,36 @@ server { ## Docker Registry V2 - location = /v2/auth { - proxy_pass http://krdsh_quay_registry; - + location = /v2/auth + { limit_req zone=krdsh_quay_staticauth burst=10 nodelay; + proxy_pass http://krdsh_quay_registry; + keepalive_timeout 0; } - location ~* ^/v2/_catalog { - proxy_pass http://krdsh_quay_registry; - - proxy_read_timeout 10; - keepalive_timeout 0; - + location ~* ^/v2/_catalog + { limit_req zone=krdsh_quay_http1_heavy burst=1 nodelay; limit_req zone=krdsh_quay_http2_heavy burst=5 nodelay; limit_req zone=krdsh_quay_http3_heavy burst=5 nodelay; - } - location ~* ^/v2/.+/blobs/ { proxy_pass http://krdsh_quay_registry; - # if ($request_method = HEAD) { - # gzip off; - # brotli off; - # zstd off; - # } + keepalive_timeout 0; + proxy_read_timeout 10; + } + + location ~* ^/v2/.+/blobs/ + { + limit_req zone=krdsh_quay_http1_ns_medium burst=50 nodelay; + limit_req zone=krdsh_quay_http2_ns_medium burst=100 nodelay; + limit_req zone=krdsh_quay_http3_ns_medium burst=100 nodelay; + + proxy_pass http://krdsh_quay_registry; + + keepalive_timeout 0; proxy_buffering off; proxy_request_buffering off; @@ -285,76 +364,76 @@ server { proxy_read_timeout 2000; proxy_send_timeout 2000; - client_max_body_size 10240M; + client_max_body_size 10G; http2_chunk_size 32k; - limit_req zone=krdsh_quay_http1_ns_medium burst=50 nodelay; - limit_req zone=krdsh_quay_http2_ns_medium burst=100 nodelay; - limit_req zone=krdsh_quay_http3_ns_medium burst=100 nodelay; - - keepalive_timeout 0; + include snip.d/disable-comp; } - location ~* ^/v2/.+/tags/ { - proxy_pass http://krdsh_quay_registry; - + location ~* ^/v2/.+/tags/ + { limit_req zone=krdsh_quay_http1_ns_heavy burst=2 nodelay; limit_req zone=krdsh_quay_http2_ns_heavy burst=2 nodelay; limit_req zone=krdsh_quay_http3_ns_heavy burst=2 nodelay; + proxy_pass http://krdsh_quay_registry; + keepalive_timeout 0; } - location ~* ^/v2/.+/manifests/ { - proxy_pass http://krdsh_quay_registry; - + location ~* ^/v2/.+/manifests/ + { limit_req zone=krdsh_quay_http1_ns_medium burst=10 nodelay; limit_req zone=krdsh_quay_http2_ns_medium burst=50 nodelay; limit_req zone=krdsh_quay_http3_ns_medium burst=50 nodelay; + proxy_pass http://krdsh_quay_registry; + keepalive_timeout 0; } - location /v2/ { - proxy_pass http://krdsh_quay_registry; - - # if ($request_method = HEAD) { - # gzip off; - # brotli off; - # zstd off; - # } - + location /v2/ + { limit_req zone=krdsh_quay_http1_light burst=20 nodelay; limit_req zone=krdsh_quay_http2_light burst=80 nodelay; limit_req zone=krdsh_quay_http3_light burst=80 nodelay; + proxy_pass http://krdsh_quay_registry; + keepalive_timeout 0; } ## Docker Registry V1 ## KrD: seems to be legacy - location /v1/ { - proxy_pass http://krdsh_quay_registry; - - proxy_buffering off; - proxy_request_buffering off; - - client_max_body_size 10240M; - - limit_req zone=krdsh_quay_http1_heavy burst=5 nodelay; - limit_req zone=krdsh_quay_http2_heavy burst=25 nodelay; - limit_req zone=krdsh_quay_http3_heavy burst=25 nodelay; - - keepalive_timeout 0; + location /v1/ + { + return 444; } - location = /v1/_ping { - default_type text/plain; + # location /v1/ + # { + # limit_req zone=krdsh_quay_http1_heavy burst=5 nodelay; + # limit_req zone=krdsh_quay_http2_heavy burst=25 nodelay; + # limit_req zone=krdsh_quay_http3_heavy burst=25 nodelay; - add_header X-Docker-Registry-Version 0.6.0; - add_header X-Docker-Registry-Standalone 0; + # proxy_pass http://krdsh_quay_registry; - return 200 "true"; - } + # proxy_buffering off; + # proxy_request_buffering off; + + # client_max_body_size 10G; + + # keepalive_timeout 0; + # } + + # location = /v1/_ping + # { + # default_type text/plain; + + # add_header X-Docker-Registry-Version 0.6.0; + # add_header X-Docker-Registry-Standalone 0; + + # return 200 "true"; + # } }