From 4d622837a8a2d85db334fab5291f166b417f15f6 Mon Sep 17 00:00:00 2001 From: Carl George Date: Tue, 24 Jan 2023 14:25:58 -0600 Subject: [PATCH 01/10] Rebuild for CVE-2022-41717 in golang --- caddy.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/caddy.spec b/caddy.spec index b416b09..c369ec2 100644 --- a/caddy.spec +++ b/caddy.spec @@ -17,7 +17,7 @@ Version: %{basever}%{?prerel:~%{prerel}%{prerelnum}} Caddy is the web server with automatic HTTPS.} Name: caddy -Release: 4%{?dist} +Release: 5%{?dist} Summary: Web server with automatic HTTPS %if %{with vendor} # github.com/caddyserver/caddy ASL 2.0 @@ -295,6 +295,9 @@ fi %changelog +* Tue Jan 24 2023 Carl George - 2.4.6-5 +- Rebuild for CVE-2022-41717 in golang + * Tue Jul 19 2022 Maxwell G - 2.4.6-4 - Rebuild for CVE-2022-{1705,32148,30631,30633,28131,30635,30632,30630,1962} in golang From bf2cf07ee493b86377099ad90f6b9f6745c71c93 Mon Sep 17 00:00:00 2001 From: Carl George Date: Tue, 28 Feb 2023 20:10:34 -0600 Subject: [PATCH 02/10] Backport of upstream fix for CVE-2022-29718 --- ...e-commands-that-can-alter-the-binary.patch | 4 +- ...dyhttp-Fix-MatchPath-sanitizing-4499.patch | 43 +++++++++++++++++++ caddy.spec | 8 +++- 3 files changed, 52 insertions(+), 3 deletions(-) create mode 100644 0002-caddyhttp-Fix-MatchPath-sanitizing-4499.patch diff --git a/0001-Disable-commands-that-can-alter-the-binary.patch b/0001-Disable-commands-that-can-alter-the-binary.patch index 3b48ffb..aa32bf5 100644 --- a/0001-Disable-commands-that-can-alter-the-binary.patch +++ b/0001-Disable-commands-that-can-alter-the-binary.patch @@ -1,7 +1,7 @@ From 7bf03a1414b1ebc1a9ef573369fe8e7ee9956a33 Mon Sep 17 00:00:00 2001 From: Carl George Date: Wed, 16 Feb 2022 11:45:03 -0600 -Subject: [PATCH] Disable commands that can alter the binary +Subject: [PATCH 1/2] Disable commands that can alter the binary --- cmd/commands.go | 48 ------------------------------------------------ @@ -67,5 +67,5 @@ index 1e2c40de..cc091bce 100644 // RegisterCommand registers the command cmd. -- -2.35.1 +2.39.2 diff --git a/0002-caddyhttp-Fix-MatchPath-sanitizing-4499.patch b/0002-caddyhttp-Fix-MatchPath-sanitizing-4499.patch new file mode 100644 index 0000000..2209c5a --- /dev/null +++ b/0002-caddyhttp-Fix-MatchPath-sanitizing-4499.patch @@ -0,0 +1,43 @@ +From 7681fd2370d3b36e2839717fce59e6e6a9d5d00a Mon Sep 17 00:00:00 2001 +From: Francis Lavoie +Date: Thu, 30 Dec 2021 04:15:48 -0500 +Subject: [PATCH 2/2] caddyhttp: Fix `MatchPath` sanitizing (#4499) + +This is a followup to #4407, in response to a report on the forums: https://caddy.community/t/php-fastcgi-phishing-redirection/14542 + +Turns out that doing `TrimRight` to remove trailing dots, _before_ cleaning the path, will cause double-dots at the end of the path to not be cleaned away as they should. We should instead remove the dots _after_ cleaning. +--- + modules/caddyhttp/matchers.go | 10 +++++----- + 1 file changed, 5 insertions(+), 5 deletions(-) + +diff --git a/modules/caddyhttp/matchers.go b/modules/caddyhttp/matchers.go +index 439c4073..272c9242 100644 +--- a/modules/caddyhttp/matchers.go ++++ b/modules/caddyhttp/matchers.go +@@ -325,6 +325,11 @@ func (m MatchPath) Match(r *http.Request) bool { + + lowerPath := strings.ToLower(unescapedPath) + ++ // Clean the path, merges doubled slashes, etc. ++ // This ensures maliciously crafted requests can't bypass ++ // the path matcher. See #4407 ++ lowerPath = path.Clean(lowerPath) ++ + // see #2917; Windows ignores trailing dots and spaces + // when accessing files (sigh), potentially causing a + // security risk (cry) if PHP files end up being served +@@ -332,11 +337,6 @@ func (m MatchPath) Match(r *http.Request) bool { + // being matched by *.php to be treated as PHP scripts + lowerPath = strings.TrimRight(lowerPath, ". ") + +- // Clean the path, merges doubled slashes, etc. +- // This ensures maliciously crafted requests can't bypass +- // the path matcher. See #4407 +- lowerPath = path.Clean(lowerPath) +- + // Cleaning may remove the trailing slash, but we want to keep it + if lowerPath != "/" && strings.HasSuffix(r.URL.Path, "/") { + lowerPath = lowerPath + "/" +-- +2.39.2 + diff --git a/caddy.spec b/caddy.spec index c369ec2..8bc6986 100644 --- a/caddy.spec +++ b/caddy.spec @@ -17,7 +17,7 @@ Version: %{basever}%{?prerel:~%{prerel}%{prerelnum}} Caddy is the web server with automatic HTTPS.} Name: caddy -Release: 5%{?dist} +Release: 6%{?dist} Summary: Web server with automatic HTTPS %if %{with vendor} # github.com/caddyserver/caddy ASL 2.0 @@ -80,6 +80,9 @@ Source7: zsh-completion # downstream only patch to disable commands that can alter the binary Patch: 0001-Disable-commands-that-can-alter-the-binary.patch +# backport of upstream fix for CVE-2022-29718 +# https://github.com/caddyserver/caddy/pull/4499 +Patch: 0002-caddyhttp-Fix-MatchPath-sanitizing-4499.patch # https://github.com/caddyserver/caddy/commit/6bc87ea2ff50a962f16dfafeb125f0f947c1a885 BuildRequires: golang >= 1.16 @@ -295,6 +298,9 @@ fi %changelog +* Wed Mar 01 2023 Carl George - 2.4.6-6 +- Backport of upstream fix for CVE-2022-29718 + * Tue Jan 24 2023 Carl George - 2.4.6-5 - Rebuild for CVE-2022-41717 in golang From 8648d6338a6b6e8b4b3b188d260f08739dc35ee2 Mon Sep 17 00:00:00 2001 From: Carl George Date: Wed, 26 Jul 2023 22:50:39 -0500 Subject: [PATCH 03/10] Remove vendor conditionals The caddy upstream adds and removes dependencies too often to keep up with. I doubt that I will ever have the time to package all of the dependencies as system packages. --- caddy.spec | 71 ++-------------------------------------- create-vendor-tarball.sh | 38 +++++++++++++++++++++ 2 files changed, 40 insertions(+), 69 deletions(-) create mode 100755 create-vendor-tarball.sh diff --git a/caddy.spec b/caddy.spec index 8bc6986..db462ef 100644 --- a/caddy.spec +++ b/caddy.spec @@ -1,9 +1,3 @@ -%bcond_without vendor - -%if %{without vendor} -%bcond_without check -%endif - # https://github.com/caddyserver/caddy %global goipath github.com/caddyserver/caddy %global basever 2.4.6 @@ -19,7 +13,6 @@ Caddy is the web server with automatic HTTPS.} Name: caddy Release: 6%{?dist} Summary: Web server with automatic HTTPS -%if %{with vendor} # github.com/caddyserver/caddy ASL 2.0 # github.com/Masterminds/sprig/v3 MIT # github.com/alecthomas/chroma MIT @@ -51,22 +44,10 @@ Summary: Web server with automatic HTTPS # gopkg.in/natefinch/lumberjack.v2 MIT # gopkg.in/yaml.v2 ASL 2.0 and MIT License: ASL 2.0 and MIT and BSD -%else -License: ASL 2.0 -%endif URL: https://caddyserver.com -%if %{with vendor} -# git clone https://github.com/caddyserver/caddy.git caddy-%%{version} -# cd caddy-%%{version} -# git checkout v%%{version} -# go mod vendor -# cd .. -# tar --exclude .git -czf caddy-%%{version}-vendored.tar.gz caddy-%%{version} +# see create-vendor-tarball.sh in this distgit repo Source0: caddy-%{version}-vendored.tar.gz -%else -Source0: %{gosource} -%endif # based on reference files upstream # https://github.com/caddyserver/dist @@ -87,7 +68,6 @@ Patch: 0002-caddyhttp-Fix-MatchPath-sanitizing-4499.patch # https://github.com/caddyserver/caddy/commit/6bc87ea2ff50a962f16dfafeb125f0f947c1a885 BuildRequires: golang >= 1.16 -%if %{with vendor} Provides: bundled(golang(github.com/Masterminds/sprig/v3)) Provides: bundled(golang(github.com/alecthomas/chroma)) Provides: bundled(golang(github.com/aryann/difflib)) @@ -117,37 +97,6 @@ Provides: bundled(golang(google.golang.org/genproto)) Provides: bundled(golang(google.golang.org/protobuf)) Provides: bundled(golang(gopkg.in/natefinch/lumberjack.v2)) Provides: bundled(golang(gopkg.in/yaml.v2)) -%else -BuildRequires: golang(github.com/Masterminds/sprig/v3) -BuildRequires: golang(github.com/alecthomas/chroma) -BuildRequires: golang(github.com/aryann/difflib) -BuildRequires: golang(github.com/caddyserver/certmagic) -BuildRequires: golang(github.com/dustin/go-humanize) -BuildRequires: golang(github.com/go-chi/chi) -BuildRequires: golang(github.com/google/cel-go) -BuildRequires: golang(github.com/google/uuid) -BuildRequires: golang(github.com/klauspost/compress) -BuildRequires: golang(github.com/klauspost/cpuid/v2) -BuildRequires: golang(github.com/lucas-clemente/quic-go) -BuildRequires: golang(github.com/mholt/acmez) -BuildRequires: golang(github.com/naoina/go-stringutil) -BuildRequires: golang(github.com/naoina/toml) -BuildRequires: golang(github.com/prometheus/client_golang) -BuildRequires: golang(github.com/smallstep/certificates) -BuildRequires: golang(github.com/smallstep/cli) -BuildRequires: golang(github.com/smallstep/nosql) -BuildRequires: golang(github.com/smallstep/truststore) -BuildRequires: golang(github.com/yuin/goldmark) -BuildRequires: golang(github.com/yuin/goldmark-highlighting) -BuildRequires: golang(go.uber.org/zap) -BuildRequires: golang(golang.org/x/crypto) -BuildRequires: golang(golang.org/x/net) -BuildRequires: golang(golang.org/x/term) -BuildRequires: golang(google.golang.org/genproto) -BuildRequires: golang(google.golang.org/protobuf) -BuildRequires: golang(gopkg.in/natefinch/lumberjack.v2) -BuildRequires: golang(gopkg.in/yaml.v2) -%endif BuildRequires: systemd-rpm-macros %{?systemd_requires} @@ -158,13 +107,8 @@ Provides: webserver %description %{common_description} -%if %{without vendor} -%gopkg -%endif - - %prep -%goprep %{?with_vendor:-k} +%goprep -k %autopatch -p 1 sed -e '/mod.Version/ s/unknown/%{version}-%{release}/' -i caddy.go @@ -175,10 +119,6 @@ sed -e '/mod.Version/ s/unknown/%{version}-%{release}/' -i caddy.go %install -%if %{without vendor} -%gopkginstall -%endif - # command install -D -p -m 0755 %{gobuilddir}/bin/caddy %{buildroot}%{_bindir}/caddy @@ -208,10 +148,8 @@ install -D -p -m 0644 %{S:6} %{buildroot}%{_datadir}/bash-completion/completions install -D -p -m 0644 %{S:7} %{buildroot}%{_datadir}/zsh/site-functions/_caddy -%if %{with check} %check %gocheck -%endif %pre @@ -292,11 +230,6 @@ fi %{_datadir}/zsh/site-functions/_caddy -%if %{without vendor} -%gopkgfiles -%endif - - %changelog * Wed Mar 01 2023 Carl George - 2.4.6-6 - Backport of upstream fix for CVE-2022-29718 diff --git a/create-vendor-tarball.sh b/create-vendor-tarball.sh new file mode 100755 index 0000000..cf2a545 --- /dev/null +++ b/create-vendor-tarball.sh @@ -0,0 +1,38 @@ +#!/usr/bin/bash + +tag=$1 + +if [[ -z $tag ]]; then + echo "This script requires the tag as an argument." + exit 1 +fi + +set -euo pipefail + +# transform tag into version +case $tag in + *beta*) + # v2.0.0-beta.1 -> 2.0.0~beta1 + temp=${tag#v} + version=${temp/-beta./~beta} + ;; + *rc*) + # v2.0.0-rc.1 -> 2.0.0~rc1 + temp=${tag#v} + version=${temp/-rc./~rc} + ;; + *) + # v2.0.0 -> 2.0.0 + version=${tag#v} + ;; +esac + +echo "Using tag: $tag" +echo "Using version: $version" + +git -c advice.detachedHead=false clone --branch $tag --depth 1 https://github.com/caddyserver/caddy.git caddy-$version +pushd caddy-$version +GOPROXY='https://proxy.golang.org,direct' go mod vendor +popd +tar --exclude .git -czf caddy-$version-vendored.tar.gz caddy-$version +rm -r caddy-$version From 75c9917645beffb8b31df2284933525be761b68b Mon Sep 17 00:00:00 2001 From: Carl George Date: Wed, 26 Jul 2023 23:25:16 -0500 Subject: [PATCH 04/10] Re-number sources --- caddy.spec | 28 ++++++++++++++-------------- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/caddy.spec b/caddy.spec index db462ef..84ba1d5 100644 --- a/caddy.spec +++ b/caddy.spec @@ -51,13 +51,13 @@ Source0: caddy-%{version}-vendored.tar.gz # based on reference files upstream # https://github.com/caddyserver/dist -Source1: Caddyfile -Source2: caddy.service -Source3: caddy-api.service -Source4: poweredby-white.png -Source5: poweredby-black.png -Source6: bash-completion -Source7: zsh-completion +Source10: Caddyfile +Source20: caddy.service +Source21: caddy-api.service +Source30: poweredby-white.png +Source31: poweredby-black.png +Source40: bash-completion +Source41: zsh-completion # downstream only patch to disable commands that can alter the binary Patch: 0001-Disable-commands-that-can-alter-the-binary.patch @@ -123,29 +123,29 @@ sed -e '/mod.Version/ s/unknown/%{version}-%{release}/' -i caddy.go install -D -p -m 0755 %{gobuilddir}/bin/caddy %{buildroot}%{_bindir}/caddy # config -install -D -p -m 0644 %{S:1} %{buildroot}%{_sysconfdir}/caddy/Caddyfile +install -D -p -m 0644 %{S:10} %{buildroot}%{_sysconfdir}/caddy/Caddyfile install -d -m 0755 %{buildroot}%{_sysconfdir}/caddy/Caddyfile.d # systemd units -install -D -p -m 0644 %{S:2} %{buildroot}%{_unitdir}/caddy.service -install -D -p -m 0644 %{S:3} %{buildroot}%{_unitdir}/caddy-api.service +install -D -p -m 0644 %{S:20} %{buildroot}%{_unitdir}/caddy.service +install -D -p -m 0644 %{S:21} %{buildroot}%{_unitdir}/caddy-api.service # data directory install -d -m 0750 %{buildroot}%{_sharedstatedir}/caddy # welcome page %if %{defined fedora} -install -D -p -m 0644 %{S:4} %{buildroot}%{_datadir}/caddy/poweredby.png +install -D -p -m 0644 %{S:30} %{buildroot}%{_datadir}/caddy/poweredby.png %else -install -D -p -m 0644 %{S:5} %{buildroot}%{_datadir}/caddy/poweredby.png +install -D -p -m 0644 %{S:31} %{buildroot}%{_datadir}/caddy/poweredby.png %endif ln -s ../testpage/index.html %{buildroot}%{_datadir}/caddy/index.html install -d -m 0755 %{buildroot}%{_datadir}/caddy/icons ln -s ../../pixmaps/poweredby.png %{buildroot}%{_datadir}/caddy/icons/poweredby.png # shell completion -install -D -p -m 0644 %{S:6} %{buildroot}%{_datadir}/bash-completion/completions/caddy -install -D -p -m 0644 %{S:7} %{buildroot}%{_datadir}/zsh/site-functions/_caddy +install -D -p -m 0644 %{S:40} %{buildroot}%{_datadir}/bash-completion/completions/caddy +install -D -p -m 0644 %{S:41} %{buildroot}%{_datadir}/zsh/site-functions/_caddy %check From 7abb762bb5274eb842d301705b832a24f12f627e Mon Sep 17 00:00:00 2001 From: Carl George Date: Tue, 15 Aug 2023 16:14:40 -0500 Subject: [PATCH 05/10] Remove usage of %gometa, %goprep, %gobuilddir, and %gocheck These macros are inconsistent across EPEL branches. --- caddy.spec | 40 ++++++++++++++++++++++++---------------- 1 file changed, 24 insertions(+), 16 deletions(-) diff --git a/caddy.spec b/caddy.spec index 84ba1d5..2707532 100644 --- a/caddy.spec +++ b/caddy.spec @@ -1,16 +1,7 @@ -# https://github.com/caddyserver/caddy %global goipath github.com/caddyserver/caddy -%global basever 2.4.6 -#global prerel rc -#global prerelnum 3 -Version: %{basever}%{?prerel:~%{prerel}%{prerelnum}} - -%gometa - -%global common_description %{expand: -Caddy is the web server with automatic HTTPS.} Name: caddy +Version: 2.4.6 Release: 6%{?dist} Summary: Web server with automatic HTTPS # github.com/caddyserver/caddy ASL 2.0 @@ -46,6 +37,16 @@ Summary: Web server with automatic HTTPS License: ASL 2.0 and MIT and BSD URL: https://caddyserver.com +%if %{defined fedora} +ExclusiveArch: %{golang_arches_future} +%else +ExclusiveArch: %{golang_arches} +%endif + +%if %{undefined el8} +BuildRequires: go-rpm-macros +%endif + # see create-vendor-tarball.sh in this distgit repo Source0: caddy-%{version}-vendored.tar.gz @@ -104,23 +105,27 @@ Requires: system-logos-httpd Provides: webserver -%description %{common_description} +%description +Caddy is the web server with automatic HTTPS. %prep -%goprep -k -%autopatch -p 1 +%autosetup -p 1 +mkdir -p src/$(dirname %{goipath}) +ln -s $PWD src/%{goipath} sed -e '/mod.Version/ s/unknown/%{version}-%{release}/' -i caddy.go %build -%gobuild -o %{gobuilddir}/bin/caddy %{goipath}/cmd/caddy +export GO111MODULE=off +export GOPATH=$PWD +%gobuild -o bin/caddy %{goipath}/cmd/caddy %install # command -install -D -p -m 0755 %{gobuilddir}/bin/caddy %{buildroot}%{_bindir}/caddy +install -D -p -m 0755 bin/caddy %{buildroot}%{_bindir}/caddy # config install -D -p -m 0644 %{S:10} %{buildroot}%{_sysconfdir}/caddy/Caddyfile @@ -149,7 +154,10 @@ install -D -p -m 0644 %{S:41} %{buildroot}%{_datadir}/zsh/site-functions/_caddy %check -%gocheck +export GO111MODULE=off +export GOPATH=$PWD +cd src/%{goipath} +%gotest ./... %pre From 187cdb9a730f878d6aeebec295b87810573b5509 Mon Sep 17 00:00:00 2001 From: Carl George Date: Tue, 15 Aug 2023 17:07:33 -0500 Subject: [PATCH 06/10] Update to version 2.6.4 I'm targeting this version specifically for EPEL 9, because RHEL 9 currently has golang 1.19, and 2.6.4 is the newest version of caddy that doesn't require a higher golang version. --- ...e-commands-that-can-alter-the-binary.patch | 16 +- ...dyhttp-Fix-MatchPath-sanitizing-4499.patch | 43 --- caddy.spec | 340 ++++++++++++++---- sources | 2 +- 4 files changed, 280 insertions(+), 121 deletions(-) delete mode 100644 0002-caddyhttp-Fix-MatchPath-sanitizing-4499.patch diff --git a/0001-Disable-commands-that-can-alter-the-binary.patch b/0001-Disable-commands-that-can-alter-the-binary.patch index aa32bf5..c2899c9 100644 --- a/0001-Disable-commands-that-can-alter-the-binary.patch +++ b/0001-Disable-commands-that-can-alter-the-binary.patch @@ -1,17 +1,17 @@ -From 7bf03a1414b1ebc1a9ef573369fe8e7ee9956a33 Mon Sep 17 00:00:00 2001 +From 08a40c6b09cf5e649c82829724b858b385b3cd66 Mon Sep 17 00:00:00 2001 From: Carl George Date: Wed, 16 Feb 2022 11:45:03 -0600 -Subject: [PATCH 1/2] Disable commands that can alter the binary +Subject: [PATCH] Disable commands that can alter the binary --- cmd/commands.go | 48 ------------------------------------------------ 1 file changed, 48 deletions(-) diff --git a/cmd/commands.go b/cmd/commands.go -index 1e2c40de..cc091bce 100644 +index 9216b898..85f7bc7d 100644 --- a/cmd/commands.go +++ b/cmd/commands.go -@@ -289,54 +289,6 @@ is always printed to stdout.`, +@@ -333,54 +333,6 @@ is always printed to stdout.`, }(), }) @@ -63,9 +63,9 @@ index 1e2c40de..cc091bce 100644 - }(), - }) - - } - - // RegisterCommand registers the command cmd. + RegisterCommand(Command{ + Name: "manpage", + Func: func(fl Flags) (int, error) { -- -2.39.2 +2.41.0 diff --git a/0002-caddyhttp-Fix-MatchPath-sanitizing-4499.patch b/0002-caddyhttp-Fix-MatchPath-sanitizing-4499.patch deleted file mode 100644 index 2209c5a..0000000 --- a/0002-caddyhttp-Fix-MatchPath-sanitizing-4499.patch +++ /dev/null @@ -1,43 +0,0 @@ -From 7681fd2370d3b36e2839717fce59e6e6a9d5d00a Mon Sep 17 00:00:00 2001 -From: Francis Lavoie -Date: Thu, 30 Dec 2021 04:15:48 -0500 -Subject: [PATCH 2/2] caddyhttp: Fix `MatchPath` sanitizing (#4499) - -This is a followup to #4407, in response to a report on the forums: https://caddy.community/t/php-fastcgi-phishing-redirection/14542 - -Turns out that doing `TrimRight` to remove trailing dots, _before_ cleaning the path, will cause double-dots at the end of the path to not be cleaned away as they should. We should instead remove the dots _after_ cleaning. ---- - modules/caddyhttp/matchers.go | 10 +++++----- - 1 file changed, 5 insertions(+), 5 deletions(-) - -diff --git a/modules/caddyhttp/matchers.go b/modules/caddyhttp/matchers.go -index 439c4073..272c9242 100644 ---- a/modules/caddyhttp/matchers.go -+++ b/modules/caddyhttp/matchers.go -@@ -325,6 +325,11 @@ func (m MatchPath) Match(r *http.Request) bool { - - lowerPath := strings.ToLower(unescapedPath) - -+ // Clean the path, merges doubled slashes, etc. -+ // This ensures maliciously crafted requests can't bypass -+ // the path matcher. See #4407 -+ lowerPath = path.Clean(lowerPath) -+ - // see #2917; Windows ignores trailing dots and spaces - // when accessing files (sigh), potentially causing a - // security risk (cry) if PHP files end up being served -@@ -332,11 +337,6 @@ func (m MatchPath) Match(r *http.Request) bool { - // being matched by *.php to be treated as PHP scripts - lowerPath = strings.TrimRight(lowerPath, ". ") - -- // Clean the path, merges doubled slashes, etc. -- // This ensures maliciously crafted requests can't bypass -- // the path matcher. See #4407 -- lowerPath = path.Clean(lowerPath) -- - // Cleaning may remove the trailing slash, but we want to keep it - if lowerPath != "/" && strings.HasSuffix(r.URL.Path, "/") { - lowerPath = lowerPath + "/" --- -2.39.2 - diff --git a/caddy.spec b/caddy.spec index 2707532..fc71be0 100644 --- a/caddy.spec +++ b/caddy.spec @@ -1,40 +1,12 @@ %global goipath github.com/caddyserver/caddy Name: caddy -Version: 2.4.6 -Release: 6%{?dist} +Version: 2.6.4 +Release: 1%{?dist} Summary: Web server with automatic HTTPS -# github.com/caddyserver/caddy ASL 2.0 -# github.com/Masterminds/sprig/v3 MIT -# github.com/alecthomas/chroma MIT -# github.com/aryann/difflib MIT -# github.com/caddyserver/certmagic ASL 2.0 -# github.com/dustin/go-humanize MIT -# github.com/go-chi/chi MIT -# github.com/google/cel-go ASL 2.0 -# github.com/google/uuid BSD -# github.com/klauspost/compress BSD and ASL 2.0 -# github.com/klauspost/cpuid/v2 MIT -# github.com/lucas-clemente/quic-go MIT -# github.com/mholt/acmez ASL 2.0 -# github.com/naoina/go-stringutil MIT -# github.com/naoina/toml MIT -# github.com/prometheus/client_golang ASL 2.0 -# github.com/smallstep/certificates ASL 2.0 -# github.com/smallstep/cli ASL 2.0 -# github.com/smallstep/nosql ASL 2.0 -# github.com/smallstep/truststore ASL 2.0 -# github.com/yuin/goldmark MIT -# github.com/yuin/goldmark-highlighting MIT -# go.uber.org/zap MIT -# golang.org/x/crypto BSD -# golang.org/x/net BSD -# golang.org/x/term BSD -# google.golang.org/genproto ASL 2.0 -# google.golang.org/protobuf BSD -# gopkg.in/natefinch/lumberjack.v2 MIT -# gopkg.in/yaml.v2 ASL 2.0 and MIT -License: ASL 2.0 and MIT and BSD +# main source code is Apache-2.0 +# see comments above provides tags for bundled license breakdown +License: Apache-2.0 AND BSD-2-Clause AND BSD-3-Clause AND MIT AND BSD-2-Clause-Views AND ISC AND CC0-1.0 AND MPL-2.0 URL: https://caddyserver.com %if %{defined fedora} @@ -62,42 +34,266 @@ Source41: zsh-completion # downstream only patch to disable commands that can alter the binary Patch: 0001-Disable-commands-that-can-alter-the-binary.patch -# backport of upstream fix for CVE-2022-29718 -# https://github.com/caddyserver/caddy/pull/4499 -Patch: 0002-caddyhttp-Fix-MatchPath-sanitizing-4499.patch -# https://github.com/caddyserver/caddy/commit/6bc87ea2ff50a962f16dfafeb125f0f947c1a885 -BuildRequires: golang >= 1.16 +# https://github.com/caddyserver/caddy/commit/141872ed80d6323505e7543628c259fdae8506d3 +BuildRequires: golang >= 1.18 -Provides: bundled(golang(github.com/Masterminds/sprig/v3)) -Provides: bundled(golang(github.com/alecthomas/chroma)) -Provides: bundled(golang(github.com/aryann/difflib)) -Provides: bundled(golang(github.com/caddyserver/certmagic)) -Provides: bundled(golang(github.com/dustin/go-humanize)) -Provides: bundled(golang(github.com/go-chi/chi)) -Provides: bundled(golang(github.com/google/cel-go)) -Provides: bundled(golang(github.com/google/uuid)) -Provides: bundled(golang(github.com/klauspost/compress)) -Provides: bundled(golang(github.com/klauspost/cpuid/v2)) -Provides: bundled(golang(github.com/lucas-clemente/quic-go)) -Provides: bundled(golang(github.com/mholt/acmez)) -Provides: bundled(golang(github.com/naoina/go-stringutil)) -Provides: bundled(golang(github.com/naoina/toml)) -Provides: bundled(golang(github.com/prometheus/client_golang)) -Provides: bundled(golang(github.com/smallstep/certificates)) -Provides: bundled(golang(github.com/smallstep/cli)) -Provides: bundled(golang(github.com/smallstep/nosql)) -Provides: bundled(golang(github.com/smallstep/truststore)) -Provides: bundled(golang(github.com/yuin/goldmark)) -Provides: bundled(golang(github.com/yuin/goldmark-highlighting)) -Provides: bundled(golang(go.uber.org/zap)) -Provides: bundled(golang(golang.org/x/crypto)) -Provides: bundled(golang(golang.org/x/net)) -Provides: bundled(golang(golang.org/x/term)) -Provides: bundled(golang(google.golang.org/genproto)) -Provides: bundled(golang(google.golang.org/protobuf)) -Provides: bundled(golang(gopkg.in/natefinch/lumberjack.v2)) -Provides: bundled(golang(gopkg.in/yaml.v2)) +# BSD-3-Clause +Provides: bundled(golang(filippo.io/edwards25519)) = 1.0.0 +# MIT AND CC0-1.0 +Provides: bundled(golang(github.com/AndreasBriese/bbloom)) = 46b345b +# MIT +Provides: bundled(golang(github.com/BurntSushi/toml)) = 1.2.1 +# Apache-2.0 +Provides: bundled(golang(github.com/Masterminds/goutils)) = 1.1.1 +# MIT +Provides: bundled(golang(github.com/Masterminds/semver/v3)) = 3.2.0 +# MIT +Provides: bundled(golang(github.com/Masterminds/sprig/v3)) = 3.2.3 +# MIT +Provides: bundled(golang(github.com/Microsoft/go-winio)) = 0.6.0 +# MIT +Provides: bundled(golang(github.com/alecthomas/chroma/v2)) = 2.5.0 +# BSD-3-Clause +Provides: bundled(golang(github.com/antlr/antlr4/runtime/Go/antlr)) = 1.4.10 +# MIT +Provides: bundled(golang(github.com/aryann/difflib)) = ff5ff6d +# MIT +Provides: bundled(golang(github.com/beorn7/perks)) = 1.0.1 +# Apache-2.0 +Provides: bundled(golang(github.com/caddyserver/certmagic)) = 0.17.2 +# MIT +Provides: bundled(golang(github.com/cenkalti/backoff/v4)) = 4.1.2 +# MIT +Provides: bundled(golang(github.com/cespare/xxhash)) = 1.1.0 +# MIT +Provides: bundled(golang(github.com/cespare/xxhash/v2)) = 2.1.2 +# MIT +Provides: bundled(golang(github.com/chzyer/readline)) = 2972be2 +# MIT +Provides: bundled(golang(github.com/cpuguy83/go-md2man/v2)) = 2.0.2 +# ISC +Provides: bundled(golang(github.com/davecgh/go-spew)) = 1.1.1 +# Apache-2.0 +Provides: bundled(golang(github.com/dgraph-io/badger)) = 1.6.2 +# Apache-2.0 +Provides: bundled(golang(github.com/dgraph-io/badger/v2)) = 2.2007.4 +# Apache-2.0 AND MIT +Provides: bundled(golang(github.com/dgraph-io/ristretto)) = 0.1.0 +# MIT +Provides: bundled(golang(github.com/dgryski/go-farm)) = a6ae236 +# MIT +Provides: bundled(golang(github.com/dlclark/regexp2)) = 1.7.0 +# MIT +Provides: bundled(golang(github.com/dustin/go-humanize)) = 1.0.1 +# MIT +Provides: bundled(golang(github.com/felixge/httpsnoop)) = 1.0.3 +# MIT +Provides: bundled(golang(github.com/fxamacker/cbor/v2)) = 2.4.0 +# MIT +Provides: bundled(golang(github.com/go-chi/chi)) = 4.1.2+incompatible +# MIT +Provides: bundled(golang(github.com/go-kit/kit)) = 0.10.0 +# MIT +Provides: bundled(golang(github.com/go-logfmt/logfmt)) = 0.5.1 +# Apache-2.0 +Provides: bundled(golang(github.com/go-logr/logr)) = 1.2.3 +# Apache-2.0 +Provides: bundled(golang(github.com/go-logr/stdr)) = 1.2.2 +# MPL-2.0 +Provides: bundled(golang(github.com/go-sql-driver/mysql)) = 1.6.0 +# MIT +Provides: bundled(golang(github.com/go-task/slim-sprig)) = 348f09d +# Apache-2.0 +Provides: bundled(golang(github.com/golang/glog)) = 1.0.0 +# Apache-2.0 +Provides: bundled(golang(github.com/golang/mock)) = 1.6.0 +# BSD-3-Clause +Provides: bundled(golang(github.com/golang/protobuf)) = 1.5.2 +# BSD-3-Clause +Provides: bundled(golang(github.com/golang/snappy)) = 0.0.4 +# Apache-2.0 +Provides: bundled(golang(github.com/google/cel-go)) = 0.13.0 +# Apache-2.0 +Provides: bundled(golang(github.com/google/pprof)) = 94a9f03 +# BSD-3-Clause +Provides: bundled(golang(github.com/google/uuid)) = 1.3.0 +# BSD-3-Clause +Provides: bundled(golang(github.com/grpc-ecosystem/grpc-gateway)) = 1.16.0 +# MIT +Provides: bundled(golang(github.com/huandu/xstrings)) = 1.3.3 +# BSD-3-Clause +Provides: bundled(golang(github.com/imdario/mergo)) = 0.3.12 +# Apache-2.0 +Provides: bundled(golang(github.com/inconshreveable/mousetrap)) = 1.0.1 +# MIT +Provides: bundled(golang(github.com/jackc/chunkreader/v2)) = 2.0.1 +# MIT +Provides: bundled(golang(github.com/jackc/pgconn)) = 1.13.0 +# MIT +Provides: bundled(golang(github.com/jackc/pgio)) = 1.0.0 +# MIT +Provides: bundled(golang(github.com/jackc/pgpassfile)) = 1.0.0 +# MIT +Provides: bundled(golang(github.com/jackc/pgproto3/v2)) = 2.3.1 +# MIT +Provides: bundled(golang(github.com/jackc/pgservicefile)) = 2b9c447 +# MIT +Provides: bundled(golang(github.com/jackc/pgtype)) = 1.12.0 +# MIT +Provides: bundled(golang(github.com/jackc/pgx/v4)) = 4.17.2 +# BSD-3-Clause AND Apache-2.0 AND MIT +Provides: bundled(golang(github.com/klauspost/compress)) = 1.15.15 +# MIT +Provides: bundled(golang(github.com/klauspost/cpuid/v2)) = 2.2.3 +# MIT +Provides: bundled(golang(github.com/libdns/libdns)) = 0.2.1 +# BSD-3-Clause +Provides: bundled(golang(github.com/manifoldco/promptui)) = 0.9.0 +# MIT +Provides: bundled(golang(github.com/mattn/go-colorable)) = 0.1.8 +# MIT +Provides: bundled(golang(github.com/mattn/go-isatty)) = 0.0.13 +# Apache-2.0 +Provides: bundled(golang(github.com/matttproud/golang_protobuf_extensions)) = 1.0.1 +# MIT +Provides: bundled(golang(github.com/mgutz/ansi)) = d51e80e +# Apache-2.0 +Provides: bundled(golang(github.com/mholt/acmez)) = 1.1.0 +# MIT +Provides: bundled(golang(github.com/micromdm/scep/v2)) = 2.1.0 +# BSD-3-Clause +Provides: bundled(golang(github.com/miekg/dns)) = 1.1.50 +# MIT +Provides: bundled(golang(github.com/mitchellh/copystructure)) = 1.2.0 +# MIT +Provides: bundled(golang(github.com/mitchellh/go-ps)) = 1.0.0 +# MIT +Provides: bundled(golang(github.com/mitchellh/reflectwalk)) = 1.0.2 +# MIT +Provides: bundled(golang(github.com/onsi/ginkgo/v2)) = 2.2.0 +# BSD-2-Clause +Provides: bundled(golang(github.com/pkg/errors)) = 0.9.1 +# Apache-2.0 +Provides: bundled(golang(github.com/prometheus/client_golang)) = 1.14.0 +# Apache-2.0 +Provides: bundled(golang(github.com/prometheus/client_model)) = 0.3.0 +# Apache-2.0 +Provides: bundled(golang(github.com/prometheus/common)) = 0.37.0 +# Apache-2.0 +Provides: bundled(golang(github.com/prometheus/procfs)) = 0.8.0 +# MIT +Provides: bundled(golang(github.com/quic-go/qpack)) = 0.4.0 +# BSD-3-Clause +Provides: bundled(golang(github.com/quic-go/qtls-go1-18)) = 0.2.0 +# BSD-3-Clause +Provides: bundled(golang(github.com/quic-go/qtls-go1-19)) = 0.2.0 +# BSD-3-Clause +Provides: bundled(golang(github.com/quic-go/qtls-go1-20)) = 0.1.0 +# MIT +Provides: bundled(golang(github.com/quic-go/quic-go)) = 0.32.0 +# MIT +Provides: bundled(golang(github.com/rs/xid)) = 1.4.0 +# BSD-2-Clause +Provides: bundled(golang(github.com/russross/blackfriday/v2)) = 2.1.0 +# MIT +Provides: bundled(golang(github.com/shopspring/decimal)) = 1.2.0 +# MIT +Provides: bundled(golang(github.com/shurcooL/sanitized_anchor_name)) = 1.0.0 +# MIT +Provides: bundled(golang(github.com/sirupsen/logrus)) = 1.9.0 +# MIT +Provides: bundled(golang(github.com/slackhq/nebula)) = 1.6.1 +# Apache-2.0 +Provides: bundled(golang(github.com/smallstep/certificates)) = 0.23.2 +# Apache-2.0 +Provides: bundled(golang(github.com/smallstep/nosql)) = 0.5.0 +# Apache-2.0 +Provides: bundled(golang(github.com/smallstep/truststore)) = 0.12.1 +# MIT +Provides: bundled(golang(github.com/spf13/cast)) = 1.4.1 +# Apache-2.0 +Provides: bundled(golang(github.com/spf13/cobra)) = 1.6.1 +# BSD-3-Clause +Provides: bundled(golang(github.com/spf13/pflag)) = 1.0.5 +# MIT +Provides: bundled(golang(github.com/stoewer/go-strcase)) = 1.2.0 +# BSD-3-Clause +Provides: bundled(golang(github.com/tailscale/tscert)) = c6dc1f4 +# MIT +Provides: bundled(golang(github.com/urfave/cli)) = 1.22.12 +# MIT +Provides: bundled(golang(github.com/x448/float16)) = 0.8.4 +# MIT +Provides: bundled(golang(github.com/yuin/goldmark)) = 1.5.4 +# MIT +Provides: bundled(golang(github.com/yuin/goldmark-highlighting/v2)) = 1513624 +# MIT +Provides: bundled(golang(go.etcd.io/bbolt)) = 1.3.6 +# MIT +Provides: bundled(golang(go.mozilla.org/pkcs7)) = 33d0574 +# Apache-2.0 +Provides: bundled(golang(go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp)) = 0.39.0 +# Apache-2.0 +Provides: bundled(golang(go.opentelemetry.io/otel)) = 1.13.0 +# Apache-2.0 +Provides: bundled(golang(go.opentelemetry.io/otel/exporters/otlp/internal/retry)) = 1.4.0 +# Apache-2.0 +Provides: bundled(golang(go.opentelemetry.io/otel/exporters/otlp/otlptrace)) = 1.4.0 +# Apache-2.0 +Provides: bundled(golang(go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc)) = 1.4.0 +# Apache-2.0 +Provides: bundled(golang(go.opentelemetry.io/otel/metric)) = 0.36.0 +# Apache-2.0 +Provides: bundled(golang(go.opentelemetry.io/otel/sdk)) = 1.13.0 +# Apache-2.0 +Provides: bundled(golang(go.opentelemetry.io/otel/trace)) = 1.13.0 +# Apache-2.0 +Provides: bundled(golang(go.opentelemetry.io/proto/otlp)) = 0.12.0 +# Apache-2.0 AND BSD-2-Clause +Provides: bundled(golang(go.step.sm/cli-utils)) = 0.7.5 +# Apache-2.0 AND BSD-2-Clause +Provides: bundled(golang(go.step.sm/crypto)) = 0.23.2 +# Apache-2.0 +Provides: bundled(golang(go.step.sm/linkedca)) = 0.19.0 +# MIT +Provides: bundled(golang(go.uber.org/atomic)) = 1.9.0 +# MIT +Provides: bundled(golang(go.uber.org/multierr)) = 1.6.0 +# MIT +Provides: bundled(golang(go.uber.org/zap)) = 1.24.0 +# BSD-3-Clause +Provides: bundled(golang(golang.org/x/crypto)) = 0.5.0 +# BSD-3-Clause +Provides: bundled(golang(golang.org/x/exp)) = 47842c8 +# BSD-3-Clause +Provides: bundled(golang(golang.org/x/mod)) = 0.6.0 +# BSD-3-Clause +Provides: bundled(golang(golang.org/x/net)) = 0.7.0 +# BSD-3-Clause +Provides: bundled(golang(golang.org/x/sync)) = 0.1.0 +# BSD-3-Clause +Provides: bundled(golang(golang.org/x/sys)) = 0.5.0 +# BSD-3-Clause +Provides: bundled(golang(golang.org/x/term)) = 0.5.0 +# BSD-3-Clause +Provides: bundled(golang(golang.org/x/text)) = 0.7.0 +# BSD-3-Clause +Provides: bundled(golang(golang.org/x/tools)) = 0.2.0 +# Apache-2.0 +Provides: bundled(golang(google.golang.org/genproto)) = 008b390 +# Apache-2.0 +Provides: bundled(golang(google.golang.org/grpc)) = 1.52.3 +# BSD-3-Clause +Provides: bundled(golang(google.golang.org/protobuf)) = 1.28.1 +# MIT +Provides: bundled(golang(gopkg.in/natefinch/lumberjack.v2)) = 2.2.1 +# Apache-2.0 AND BSD-3-Clause +Provides: bundled(golang(gopkg.in/square/go-jose.v2)) = 2.6.0 +# Apache-2.0 AND MIT +Provides: bundled(golang(gopkg.in/yaml.v3)) = 3.0.1 +# BSD-2-Clause-Views AND BSD-3-Clause +Provides: bundled(golang(howett.net/plist)) = 1.0.0 BuildRequires: systemd-rpm-macros %{?systemd_requires} @@ -114,12 +310,11 @@ Caddy is the web server with automatic HTTPS. mkdir -p src/$(dirname %{goipath}) ln -s $PWD src/%{goipath} -sed -e '/mod.Version/ s/unknown/%{version}-%{release}/' -i caddy.go - %build export GO111MODULE=off export GOPATH=$PWD +export LDFLAGS="-X %{goipath}.CustomVersion=v%{version}" %gobuild -o bin/caddy %{goipath}/cmd/caddy @@ -154,6 +349,10 @@ install -D -p -m 0644 %{S:41} %{buildroot}%{_datadir}/zsh/site-functions/_caddy %check +# ensure that the version was embedded correctly +[[ "$(./bin/caddy version)" == "v%{version}" ]] || exit 1 + +# run the upstream tests export GO111MODULE=off export GOPATH=$PWD cd src/%{goipath} @@ -239,6 +438,9 @@ fi %changelog +* Thu Aug 24 2023 Carl George - 2.6.4-1 +- Update to version 2.6.4 + * Wed Mar 01 2023 Carl George - 2.4.6-6 - Backport of upstream fix for CVE-2022-29718 diff --git a/sources b/sources index be5b56a..c0c8b0b 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (caddy-2.4.6-vendored.tar.gz) = d2a3d98f831f153dc408c6793331e16649fd0e543e4be8ec0cf8b4d3918d1e11f6e57a9459bb3ac2d7c3345e036252f7666c4b7535ced5d7b6f3f52162e850ea +SHA512 (caddy-2.6.4-vendored.tar.gz) = 877e5975eab7315f3327fa381f2361563b3e8711f66240029768a9d0b4b7d0b961973a7a67e5baf4ba8039659bc708a408482442b3dba9b51822bb196f3cf2e0 From 0817b8e9466479664d173ab0b35ff0e65a1f1745 Mon Sep 17 00:00:00 2001 From: Carl George Date: Tue, 15 Aug 2023 18:02:11 -0500 Subject: [PATCH 07/10] Add man pages --- caddy.spec | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/caddy.spec b/caddy.spec index fc71be0..95d8355 100644 --- a/caddy.spec +++ b/caddy.spec @@ -322,6 +322,9 @@ export LDFLAGS="-X %{goipath}.CustomVersion=v%{version}" # command install -D -p -m 0755 bin/caddy %{buildroot}%{_bindir}/caddy +# man pages +./bin/caddy manpage --directory %{buildroot}%{_mandir}/man8 + # config install -D -p -m 0644 %{S:10} %{buildroot}%{_sysconfdir}/caddy/Caddyfile install -d -m 0755 %{buildroot}%{_sysconfdir}/caddy/Caddyfile.d @@ -422,6 +425,7 @@ fi %license LICENSE %doc README.md AUTHORS %{_bindir}/caddy +%{_mandir}/man8/caddy*.8* %{_datadir}/caddy %{_unitdir}/caddy.service %{_unitdir}/caddy-api.service @@ -440,6 +444,7 @@ fi %changelog * Thu Aug 24 2023 Carl George - 2.6.4-1 - Update to version 2.6.4 +- Add man pages * Wed Mar 01 2023 Carl George - 2.4.6-6 - Backport of upstream fix for CVE-2022-29718 From a7bfd48390516817f2ac14c5f12f3f1280397987 Mon Sep 17 00:00:00 2001 From: Carl George Date: Tue, 15 Aug 2023 18:03:01 -0500 Subject: [PATCH 08/10] Use generated shell completion files instead of static ones --- bash-completion | 1210 ----------------------------------------------- caddy.spec | 11 +- zsh-completion | 166 ------- 3 files changed, 6 insertions(+), 1381 deletions(-) delete mode 100644 bash-completion delete mode 100644 zsh-completion diff --git a/bash-completion b/bash-completion deleted file mode 100644 index 1da7f36..0000000 --- a/bash-completion +++ /dev/null @@ -1,1210 +0,0 @@ -#!/usr/bin/env bash - -# helper method -declare -f _contains_element > /dev/null || _contains_element() { - local e match="$1" - shift - for e; do [[ "$e" == "$match" ]] && return 0; done - return 1 -} - -_caddy_completions() -{ - # get current word, words array, current word index, and previous word, ignoring ":" as a wordbreak - local cur cword words - _get_comp_words_by_ref -n ":" cur words cword prev - - # complete subcommands list - if [ "$cword" -eq "1" ] && [ "adapt build-info environ file-server fmt hash-password help list-modules reload reverse-proxy run start stop trust untrust validate version" != "" ]; then - COMPREPLY=($(compgen -W "adapt build-info environ file-server fmt hash-password help list-modules reload reverse-proxy run start stop trust untrust validate version" -- "$cur")) - __ltrim_colon_completions "$cur" - return - fi - - local subcommand="${words[1]}" - - local args used_flags used_args index - - # register completions for each subcommand - if [ "${subcommand}" == "adapt" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - if [ "${args[0]}" == "--pretty" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - if [ "${args[0]}" == "--validate" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - if [ "${args[0]}" == "--adapter" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--config" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - if [[ "$prev" == "--adapter" ]]; then - COMPREPLY=() - if command -v grep > /dev/null && command -v sed > /dev/null && command -v tr > /dev/null; then - COMPREPLY=($(compgen -W "$(caddy list-modules | grep adapters | sed s/caddy.adapters.// | tr ' -' ' ')" -- "$cur")) - fi - return - fi - if [[ "$prev" == "--config" ]]; then - COMPREPLY=() - COMPREPLY=($(compgen -f -- "$cur")) - return - fi - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - if ! _contains_element "--pretty" "${used_flags[@]}"; then - completion+=("--pretty") - fi - if ! _contains_element "--validate" "${used_flags[@]}"; then - completion+=("--validate") - fi - if ! _contains_element "--adapter" "${used_flags[@]}"; then - completion+=("--adapter") - fi - if ! _contains_element "--config" "${used_flags[@]}"; then - completion+=("--config") - fi - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "build-info" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "environ" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "file-server" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - if [ "${args[0]}" == "--browse" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - if [ "${args[0]}" == "--templates" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - if [ "${args[0]}" == "--domain" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--listen" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--root" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - if [[ "$prev" == "--domain" ]]; then - COMPREPLY=() - return - fi - if [[ "$prev" == "--listen" ]]; then - COMPREPLY=() - return - fi - if [[ "$prev" == "--root" ]]; then - COMPREPLY=() - COMPREPLY=($(compgen -d -- "$cur")) - return - fi - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - if ! _contains_element "--browse" "${used_flags[@]}"; then - completion+=("--browse") - fi - if ! _contains_element "--templates" "${used_flags[@]}"; then - completion+=("--templates") - fi - if ! _contains_element "--domain" "${used_flags[@]}"; then - completion+=("--domain") - fi - if ! _contains_element "--listen" "${used_flags[@]}"; then - completion+=("--listen") - fi - if ! _contains_element "--root" "${used_flags[@]}"; then - completion+=("--root") - fi - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "fmt" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - if [ "${args[0]}" == "--overwrite" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - if ! _contains_element "--overwrite" "${used_flags[@]}"; then - completion+=("--overwrite") - fi - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - if [[ "${#used_args[@]}" -eq "0" ]]; then - COMPREPLY=() - COMPREPLY=($(compgen -f -- "$cur")) - return - fi - - return - fi - if [ "${subcommand}" == "hash-password" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - - if [ "${args[0]}" == "--algorithm" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--plaintext" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--salt" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - if [[ "$prev" == "--algorithm" ]]; then - COMPREPLY=() - return - fi - if [[ "$prev" == "--plaintext" ]]; then - COMPREPLY=() - return - fi - if [[ "$prev" == "--salt" ]]; then - COMPREPLY=() - return - fi - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - if ! _contains_element "--algorithm" "${used_flags[@]}"; then - completion+=("--algorithm") - fi - if ! _contains_element "--plaintext" "${used_flags[@]}"; then - completion+=("--plaintext") - fi - if ! _contains_element "--salt" "${used_flags[@]}"; then - completion+=("--salt") - fi - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "help" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - if [[ "${#used_args[@]}" -eq "0" ]]; then - COMPREPLY=() - COMPREPLY=($(compgen -W "adapt build-info environ file-server fmt hash-password help list-modules reload reverse-proxy run stop trust untrust validate" -- "$cur")) - return - fi - - return - fi - if [ "${subcommand}" == "list-modules" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - if [ "${args[0]}" == "--versions" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - if ! _contains_element "--versions" "${used_flags[@]}"; then - completion+=("--versions") - fi - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "reload" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - - if [ "${args[0]}" == "--adapter" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--config" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--address" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - if [[ "$prev" == "--adapter" ]]; then - COMPREPLY=() - if command -v grep > /dev/null && command -v sed > /dev/null && command -v tr > /dev/null; then - COMPREPLY=($(compgen -W "$(caddy list-modules | grep adapters | sed s/caddy.adapters.// | tr ' -' ' ')" -- "$cur")) - fi - return - fi - if [[ "$prev" == "--config" ]]; then - COMPREPLY=() - COMPREPLY=($(compgen -f -- "$cur")) - return - fi - if [[ "$prev" == "--address" ]]; then - COMPREPLY=() - return - fi - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - if ! _contains_element "--adapter" "${used_flags[@]}"; then - completion+=("--adapter") - fi - if ! _contains_element "--config" "${used_flags[@]}"; then - completion+=("--config") - fi - if ! _contains_element "--address" "${used_flags[@]}"; then - completion+=("--address") - fi - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "reverse-proxy" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - if [ "${args[0]}" == "--change-host-header" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - if [ "${args[0]}" == "--from" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--to" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - if [[ "$prev" == "--from" ]]; then - COMPREPLY=() - return - fi - if [[ "$prev" == "--to" ]]; then - COMPREPLY=() - return - fi - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - if ! _contains_element "--change-host-header" "${used_flags[@]}"; then - completion+=("--change-host-header") - fi - if ! _contains_element "--from" "${used_flags[@]}"; then - completion+=("--from") - fi - if ! _contains_element "--to" "${used_flags[@]}"; then - completion+=("--to") - fi - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "run" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - if [ "${args[0]}" == "--environ" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - if [ "${args[0]}" == "--resume" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - if [ "${args[0]}" == "--watch" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - if [ "${args[0]}" == "--adapter" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--config" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--pingback" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--pidfile" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - if [[ "$prev" == "--adapter" ]]; then - COMPREPLY=() - if command -v grep > /dev/null && command -v sed > /dev/null && command -v tr > /dev/null; then - COMPREPLY=($(compgen -W "$(caddy list-modules | grep adapters | sed s/caddy.adapters.// | tr ' -' ' ')" -- "$cur")) - fi - return - fi - if [[ "$prev" == "--config" ]]; then - COMPREPLY=() - COMPREPLY=($(compgen -f -- "$cur")) - return - fi - if [[ "$prev" == "--pingback" ]]; then - COMPREPLY=() - return - fi - if [[ "$prev" == "--pidfile" ]]; then - COMPREPLY=() - COMPREPLY=($(compgen -f -- "$cur")) - return - fi - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - if ! _contains_element "--environ" "${used_flags[@]}"; then - completion+=("--environ") - fi - if ! _contains_element "--resume" "${used_flags[@]}"; then - completion+=("--resume") - fi - if ! _contains_element "--watch" "${used_flags[@]}"; then - completion+=("--watch") - fi - if ! _contains_element "--adapter" "${used_flags[@]}"; then - completion+=("--adapter") - fi - if ! _contains_element "--config" "${used_flags[@]}"; then - completion+=("--config") - fi - if ! _contains_element "--pingback" "${used_flags[@]}"; then - completion+=("--pingback") - fi - if ! _contains_element "--pidfile" "${used_flags[@]}"; then - completion+=("--pidfile") - fi - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "start" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - if [ "${args[0]}" == "--watch" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - if [ "${args[0]}" == "--adapter" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--config" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--pidfile" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - if [[ "$prev" == "--adapter" ]]; then - COMPREPLY=() - if command -v grep > /dev/null && command -v sed > /dev/null && command -v tr > /dev/null; then - COMPREPLY=($(compgen -W "$(caddy list-modules | grep adapters | sed s/caddy.adapters.// | tr ' -' ' ')" -- "$cur")) - fi - return - fi - if [[ "$prev" == "--config" ]]; then - COMPREPLY=() - COMPREPLY=($(compgen -f -- "$cur")) - return - fi - if [[ "$prev" == "--pidfile" ]]; then - COMPREPLY=() - COMPREPLY=($(compgen -f -- "$cur")) - return - fi - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - if ! _contains_element "--watch" "${used_flags[@]}"; then - completion+=("--watch") - fi - if ! _contains_element "--adapter" "${used_flags[@]}"; then - completion+=("--adapter") - fi - if ! _contains_element "--config" "${used_flags[@]}"; then - completion+=("--config") - fi - if ! _contains_element "--pidfile" "${used_flags[@]}"; then - completion+=("--pidfile") - fi - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "stop" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - - if [ "${args[0]}" == "--address" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - if [[ "$prev" == "--address" ]]; then - COMPREPLY=() - return - fi - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - if ! _contains_element "--address" "${used_flags[@]}"; then - completion+=("--address") - fi - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "trust" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "untrust" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - - if [ "${args[0]}" == "--ca" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--cert" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - if [[ "$prev" == "--ca" ]]; then - COMPREPLY=() - return - fi - if [[ "$prev" == "--cert" ]]; then - COMPREPLY=() - COMPREPLY=($(compgen -f -- "$cur")) - return - fi - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - if ! _contains_element "--ca" "${used_flags[@]}"; then - completion+=("--ca") - fi - if ! _contains_element "--cert" "${used_flags[@]}"; then - completion+=("--cert") - fi - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "validate" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - - if [ "${args[0]}" == "--config" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - if [ "${args[0]}" == "--adapter" ]; then - used_flags+=("${args[0]}") - args=("${args[@]:2}") - index=$((index+2)) - continue - fi - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - if [[ "$prev" == "--config" ]]; then - COMPREPLY=() - COMPREPLY=($(compgen -f -- "$cur")) - return - fi - if [[ "$prev" == "--adapter" ]]; then - COMPREPLY=() - if command -v grep > /dev/null && command -v sed > /dev/null && command -v tr > /dev/null; then - COMPREPLY=($(compgen -W "$(caddy list-modules | grep adapters | sed s/caddy.adapters.// | tr ' -' ' ')" -- "$cur")) - fi - return - fi - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - if ! _contains_element "--config" "${used_flags[@]}"; then - completion+=("--config") - fi - if ! _contains_element "--adapter" "${used_flags[@]}"; then - completion+=("--adapter") - fi - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi - if [ "${subcommand}" == "version" ]; then - local args_shift=2 - # get the list of already used flags and args, ignoring the current word - args=("${words[@]:args_shift}") # args without command and subcommand - used_flags=() - used_args=() - index=0 - - while [ "${#args[@]}" -gt 0 ]; do - if [ "${index}" -eq "$((cword-args_shift))" ]; then - # ignore current word - args=("${args[@]:1}") - index=$((index+1)) - continue - fi - - - - if [[ "${args[0]}" != "-"* ]]; then - used_args+=("${args[0]}") - fi - args=("${args[@]:1}") - index=$((index+1)) - done - - - if [[ $cur == -* ]]; then - # flags - completion=() - - if [[ $cur != --* ]]; then - true - fi - - - COMPREPLY=($(compgen -W "${completion[*]}" -- "$cur")) - return - fi - - - return - fi -} - -# register completion -complete -F _caddy_completions caddy - diff --git a/caddy.spec b/caddy.spec index 95d8355..964175d 100644 --- a/caddy.spec +++ b/caddy.spec @@ -29,8 +29,6 @@ Source20: caddy.service Source21: caddy-api.service Source30: poweredby-white.png Source31: poweredby-black.png -Source40: bash-completion -Source41: zsh-completion # downstream only patch to disable commands that can alter the binary Patch: 0001-Disable-commands-that-can-alter-the-binary.patch @@ -346,9 +344,11 @@ ln -s ../testpage/index.html %{buildroot}%{_datadir}/caddy/index.html install -d -m 0755 %{buildroot}%{_datadir}/caddy/icons ln -s ../../pixmaps/poweredby.png %{buildroot}%{_datadir}/caddy/icons/poweredby.png -# shell completion -install -D -p -m 0644 %{S:40} %{buildroot}%{_datadir}/bash-completion/completions/caddy -install -D -p -m 0644 %{S:41} %{buildroot}%{_datadir}/zsh/site-functions/_caddy +# shell completions +install -d -m 0755 %{buildroot}%{_datadir}/bash-completion/completions +./bin/caddy completion bash > %{buildroot}%{_datadir}/bash-completion/completions/caddy +install -d -m 0755 %{buildroot}%{_datadir}/zsh/site-functions +./bin/caddy completion zsh > %{buildroot}%{_datadir}/zsh/site-functions/_caddy %check @@ -445,6 +445,7 @@ fi * Thu Aug 24 2023 Carl George - 2.6.4-1 - Update to version 2.6.4 - Add man pages +- Use generated shell completion files instead of static ones * Wed Mar 01 2023 Carl George - 2.4.6-6 - Backport of upstream fix for CVE-2022-29718 diff --git a/zsh-completion b/zsh-completion deleted file mode 100644 index 66f50b7..0000000 --- a/zsh-completion +++ /dev/null @@ -1,166 +0,0 @@ -#compdef caddy - -function _caddy { - local _line - - _arguments -C \ - "1: :(adapt build-info environ file-server fmt hash-password help list-modules reload reverse-proxy run start stop trust untrust validate version)" \ - "*::arg:->args" - - case $line[1] in - adapt) - __caddy_adapt - ;; - build-info) - __caddy_build-info - ;; - environ) - __caddy_environ - ;; - file-server) - __caddy_file-server - ;; - fmt) - __caddy_fmt - ;; - hash-password) - __caddy_hash-password - ;; - help) - __caddy_help - ;; - list-modules) - __caddy_list-modules - ;; - reload) - __caddy_reload - ;; - reverse-proxy) - __caddy_reverse-proxy - ;; - run) - __caddy_run - ;; - start) - __caddy_start - ;; - stop) - __caddy_stop - ;; - trust) - __caddy_trust - ;; - untrust) - __caddy_untrust - ;; - validate) - __caddy_validate - ;; - version) - __caddy_version - ;; - esac -} - -function __caddy_adapt { - _arguments \ - "--pretty: :" \ - "--validate: :" \ - "--adapter: :_files" \ - "--config: :_files" \ - -} -function __caddy_build-info { - -} -function __caddy_environ { - -} -function __caddy_file-server { - _arguments \ - "--browse: :" \ - "--templates: :" \ - "--domain: :_files" \ - "--listen: :_files" \ - "--root: :_dirs" \ - -} -function __caddy_fmt { - _arguments \ - "--overwrite: :" \ - -} -function __caddy_hash-password { - _arguments \ - "--algorithm: :_files" \ - "--plaintext: :_files" \ - "--salt: :_files" \ - -} -function __caddy_help { - -} -function __caddy_list-modules { - _arguments \ - "--versions: :" \ - -} -function __caddy_reload { - _arguments \ - "--adapter: :_files" \ - "--config: :_files" \ - "--address: :_files" \ - -} -function __caddy_reverse-proxy { - _arguments \ - "--change-host-header: :" \ - "--from: :_files" \ - "--to: :_files" \ - -} -function __caddy_run { - _arguments \ - "--environ: :" \ - "--resume: :" \ - "--watch: :" \ - "--adapter: :_files" \ - "--config: :_files" \ - "--pingback: :_files" \ - "--pidfile: :_files" \ - -} -function __caddy_start { - _arguments \ - "--watch: :" \ - "--adapter: :_files" \ - "--config: :_files" \ - "--pidfile: :_files" \ - -} -function __caddy_stop { - _arguments \ - "--address: :_files" \ - -} -function __caddy_trust { - -} -function __caddy_untrust { - _arguments \ - "--ca: :_files" \ - "--cert: :_files" \ - -} -function __caddy_validate { - _arguments \ - "--config: :_files" \ - "--adapter: :_files" \ - -} -function __caddy_version { - -} - -_caddy - From 9db3ba7c6339ad9d3046a5e01920cffb3a46c7b4 Mon Sep 17 00:00:00 2001 From: Carl George Date: Tue, 15 Aug 2023 18:04:10 -0500 Subject: [PATCH 09/10] Add fish shell completions --- caddy.spec | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/caddy.spec b/caddy.spec index 964175d..d227e0f 100644 --- a/caddy.spec +++ b/caddy.spec @@ -349,6 +349,8 @@ install -d -m 0755 %{buildroot}%{_datadir}/bash-completion/completions ./bin/caddy completion bash > %{buildroot}%{_datadir}/bash-completion/completions/caddy install -d -m 0755 %{buildroot}%{_datadir}/zsh/site-functions ./bin/caddy completion zsh > %{buildroot}%{_datadir}/zsh/site-functions/_caddy +install -d -m 0755 %{buildroot}%{_datadir}/fish/vendor_completions.d +./bin/caddy completion fish > %{buildroot}%{_datadir}/fish/vendor_completions.d/caddy.fish %check @@ -439,6 +441,10 @@ fi %dir %{_datadir}/zsh %dir %{_datadir}/zsh/site-functions %{_datadir}/zsh/site-functions/_caddy +# own parent directories in case fish is not installed +%dir %{_datadir}/fish +%dir %{_datadir}/fish/vendor_completions.d +%{_datadir}/fish/vendor_completions.d/caddy.fish %changelog @@ -446,6 +452,7 @@ fi - Update to version 2.6.4 - Add man pages - Use generated shell completion files instead of static ones +- Add fish shell completions * Wed Mar 01 2023 Carl George - 2.4.6-6 - Backport of upstream fix for CVE-2022-29718 From 70d52d912cc6da66ff57e4f4c2728c361694f34c Mon Sep 17 00:00:00 2001 From: Carl George Date: Mon, 30 Oct 2023 14:12:51 -0500 Subject: [PATCH 10/10] Test page updates - Update poweredby logos - Add symlink for system_noindex_logo.png on EL9 - Symlink directly to fedora-testpage directory on Fedora --- caddy.spec | 13 +++++++++++-- poweredby-black.png | Bin 1769 -> 5500 bytes poweredby-white.png | Bin 1766 -> 4548 bytes 3 files changed, 11 insertions(+), 2 deletions(-) diff --git a/caddy.spec b/caddy.spec index d227e0f..6fac5a8 100644 --- a/caddy.spec +++ b/caddy.spec @@ -2,7 +2,7 @@ Name: caddy Version: 2.6.4 -Release: 1%{?dist} +Release: 2%{?dist} Summary: Web server with automatic HTTPS # main source code is Apache-2.0 # see comments above provides tags for bundled license breakdown @@ -337,12 +337,16 @@ install -d -m 0750 %{buildroot}%{_sharedstatedir}/caddy # welcome page %if %{defined fedora} install -D -p -m 0644 %{S:30} %{buildroot}%{_datadir}/caddy/poweredby.png +ln -s ../fedora-testpage/index.html %{buildroot}%{_datadir}/caddy/index.html %else install -D -p -m 0644 %{S:31} %{buildroot}%{_datadir}/caddy/poweredby.png -%endif ln -s ../testpage/index.html %{buildroot}%{_datadir}/caddy/index.html +%endif install -d -m 0755 %{buildroot}%{_datadir}/caddy/icons ln -s ../../pixmaps/poweredby.png %{buildroot}%{_datadir}/caddy/icons/poweredby.png +%if %{defined rhel} && 0%{?rhel} >= 9 +ln -s ../pixmaps/system-noindex-logo.png %{buildroot}%{_datadir}/caddy/system_noindex_logo.png +%endif # shell completions install -d -m 0755 %{buildroot}%{_datadir}/bash-completion/completions @@ -448,6 +452,11 @@ fi %changelog +* Mon Oct 30 2023 Carl George - 2.6.4-2 +- Update poweredby logos +- Add symlink for system_noindex_logo.png on EL9 +- Symlink directly to fedora-testpage directory on Fedora + * Thu Aug 24 2023 Carl George - 2.6.4-1 - Update to version 2.6.4 - Add man pages diff --git a/poweredby-black.png b/poweredby-black.png index eb8e2843a42082ce2e6398893f1fd978893a8fe1..f0df626a82f033c6d86dc7b98598a06f7e29c80c 100644 GIT binary patch literal 5500 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 delta 1752 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