Fast and extensible multi-platform HTTP/1-2-3 web server with automatic HTTPS
Mirrored from https://github.com/Slazee/caddy.git
Synced Nov 13, 15:30 UTC
cmd: Use newly-available version information (#4931)
Matt Holt committed
Aug 4, 2022 at 11:16 UTC
17ae5acaba536e98cfa86ddcd6967801f1fa1bbe
5 files changed
+103
-69
caddy.go
+91
-24
@@ -127,7 +127,9 @@ func Load(cfgJSON []byte, forceReload bool) error {
127
// forcefully reloaded, then errConfigUnchanged This function is safe for
128
// concurrent use.
129
// The ifMatchHeader can optionally be given a string of the format:
130
-// "<path> <hash>"
130
+//
131
+// "<path> <hash>"
132
+//
133
// where <path> is the absolute path in the config and <hash> is the expected hash of
134
// the config at that path. If the hash in the ifMatchHeader doesn't match
135
// the hash of the config, then an APIError with status 412 will be returned.
@@ -791,38 +793,102 @@ func InstanceID() (uuid.UUID, error) {
793
return uuid.ParseBytes(uuidFileBytes)
794
}
795
794
-// GoModule returns the build info of this Caddy
795
-// build from debug.BuildInfo (requires Go modules).
796
-// If no version information is available, a non-nil
797
-// value will still be returned, but with an
798
-// unknown version.
799
-func GoModule() *debug.Module {
800
- var mod debug.Module
801
- return goModule(&mod)
802
-}
803
-
804
-// goModule holds the actual implementation of GoModule.
805
-// Allocating debug.Module in GoModule() and passing a
806
-// reference to goModule enables mid-stack inlining.
807
-func goModule(mod *debug.Module) *debug.Module {
808
- mod.Version = "unknown"
796
+// Version returns the Caddy version in a simple/short form, and
797
+// a full version string. The short form will not have spaces and
798
+// is intended for User-Agent strings and similar, but may be
799
+// omitting valuable information. Note that Caddy must be compiled
800
+// in a special way to properly embed complete version information.
801
+// First this function tries to get the version from the embedded
802
+// build info provided by go.mod dependencies; then it tries to
803
+// get info from embedded VCS information, which requires having
804
+// built Caddy from a git repository. If no version is available,
805
+// this function returns "(devel)" becaise Go uses that, but for
806
+// the simple form we change it to "unknown".
807
+//
808
+// See relevant Go issues: https://github.com/golang/go/issues/29228
809
+// and https://github.com/golang/go/issues/50603.
810
+//
811
+// This function is experimental and subject to change or removal.
812
+func Version() (simple, full string) {
813
+ // the currently-recommended way to build Caddy involves
814
+ // building it as a dependency so we can extract version
815
+ // information from go.mod tooling; once the upstream
816
+ // Go issues are fixed, we should just be able to use
817
+ // bi.Main... hopefully.
818
+ var module *debug.Module
819
bi, ok := debug.ReadBuildInfo()
820
if ok {
811
- mod.Path = bi.Main.Path
812
- // The recommended way to build Caddy involves
813
- // creating a separate main module, which
814
- // TODO: track related Go issue: https://github.com/golang/go/issues/29228
815
- // once that issue is fixed, we should just be able to use bi.Main... hopefully.
821
+ // find the Caddy module in the dependency list
822
for _, dep := range bi.Deps {
823
if dep.Path == ImportPath {
818
- return dep
824
+ module = dep
825
+ break
826
}
827
}
821
- return &bi.Main
828
}
823
- return mod
829
+ if module != nil {
830
+ simple, full = module.Version, module.Version
831
+ if module.Sum != "" {
832
+ full += " " + module.Sum
833
+ }
834
+ if module.Replace != nil {
835
+ full += " => " + module.Replace.Path
836
+ if module.Replace.Version != "" {
837
+ simple = module.Replace.Version + "_custom"
838
+ full += "@" + module.Replace.Version
839
+ }
840
+ if module.Replace.Sum != "" {
841
+ full += " " + module.Replace.Sum
842
+ }
843
+ }
844
+ }
845
+
846
+ if full == "" {
847
+ var vcsRevision string
848
+ var vcsTime time.Time
849
+ var vcsModified bool
850
+ for _, setting := range bi.Settings {
851
+ switch setting.Key {
852
+ case "vcs.revision":
853
+ vcsRevision = setting.Value
854
+ case "vcs.time":
855
+ vcsTime, _ = time.Parse(time.RFC3339, setting.Value)
856
+ case "vcs.modified":
857
+ vcsModified, _ = strconv.ParseBool(setting.Value)
858
+ }
859
+ }
860
+
861
+ if vcsRevision != "" {
862
+ var modified string
863
+ if vcsModified {
864
+ modified = "+modified"
865
+ }
866
+ full = fmt.Sprintf("%s%s (%s)", vcsRevision, modified, vcsTime.Format(time.RFC822))
867
+ simple = vcsRevision
868
+
869
+ // use short checksum for simple, if hex-only
870
+ if _, err := hex.DecodeString(simple); err == nil {
871
+ simple = simple[:8]
872
+ }
873
+
874
+ // append date to simple since it can be convenient
875
+ // to know the commit date as part of the version
876
+ if !vcsTime.IsZero() {
877
+ simple += "-" + vcsTime.Format("20060102")
878
+ }
879
+ }
880
+ }
881
+
882
+ if simple == "" || simple == "(devel)" {
883
+ simple = "unknown"
884
+ }
885
+
886
+ return
887
}
888
889
+// ActiveContext returns the currently-active context.
890
+// This function is experimental and might be changed
891
+// or removed in the future.
892
func ActiveContext() Context {
893
currentCtxMu.RLock()
894
defer currentCtxMu.RUnlock()
@@ -867,4 +933,5 @@ var (
933
var errSameConfig = errors.New("config is unchanged")
934
935
// ImportPath is the package import path for Caddy core.
936
+// This identifier may be removed in the future.
937
const ImportPath = "github.com/caddyserver/caddy/v2"
cmd/commandfuncs.go
+4
-17
@@ -331,30 +331,17 @@ func cmdReload(fl Flags) (int, error) {
331
}
332
333
func cmdVersion(_ Flags) (int, error) {
334
- fmt.Println(CaddyVersion())
334
+ _, full := caddy.Version()
335
+ fmt.Println(full)
336
return caddy.ExitCodeSuccess, nil
337
}
338
338
-func cmdBuildInfo(fl Flags) (int, error) {
339
+func cmdBuildInfo(_ Flags) (int, error) {
340
bi, ok := debug.ReadBuildInfo()
341
if !ok {
342
return caddy.ExitCodeFailedStartup, fmt.Errorf("no build information")
343
}
343
-
344
- fmt.Printf("go_version: %s\n", runtime.Version())
345
- fmt.Printf("go_os: %s\n", runtime.GOOS)
346
- fmt.Printf("go_arch: %s\n", runtime.GOARCH)
347
- fmt.Printf("path: %s\n", bi.Path)
348
- fmt.Printf("main: %s %s %s\n", bi.Main.Path, bi.Main.Version, bi.Main.Sum)
349
- fmt.Println("dependencies:")
350
-
351
- for _, goMod := range bi.Deps {
352
- fmt.Printf("%s %s %s", goMod.Path, goMod.Version, goMod.Sum)
353
- if goMod.Replace != nil {
354
- fmt.Printf(" => %s %s %s", goMod.Replace.Path, goMod.Replace.Version, goMod.Replace.Sum)
355
- }
356
- fmt.Println()
357
- }
344
+ fmt.Println(bi)
345
return caddy.ExitCodeSuccess, nil
346
}
347
cmd/main.go
+4
-22
@@ -38,8 +38,8 @@ import (
38
39
func init() {
40
// set a fitting User-Agent for ACME requests
41
- goModule := caddy.GoModule()
42
- cleanModVersion := strings.TrimPrefix(goModule.Version, "v")
41
+ version, _ := caddy.Version()
42
+ cleanModVersion := strings.TrimPrefix(version, "v")
43
certmagic.UserAgent = "Caddy/" + cleanModVersion
44
45
// by using Caddy, user indicates agreement to CA terms
@@ -441,11 +441,12 @@ func parseEnvFile(envInput io.Reader) (map[string]string, error) {
441
}
442
443
func printEnvironment() {
444
+ _, version := caddy.Version()
445
fmt.Printf("caddy.HomeDir=%s\n", caddy.HomeDir())
446
fmt.Printf("caddy.AppDataDir=%s\n", caddy.AppDataDir())
447
fmt.Printf("caddy.AppConfigDir=%s\n", caddy.AppConfigDir())
448
fmt.Printf("caddy.ConfigAutosavePath=%s\n", caddy.ConfigAutosavePath)
448
- fmt.Printf("caddy.Version=%s\n", CaddyVersion())
449
+ fmt.Printf("caddy.Version=%s\n", version)
450
fmt.Printf("runtime.GOOS=%s\n", runtime.GOOS)
451
fmt.Printf("runtime.GOARCH=%s\n", runtime.GOARCH)
452
fmt.Printf("runtime.Compiler=%s\n", runtime.Compiler)
@@ -462,25 +463,6 @@ func printEnvironment() {
463
}
464
}
465
465
-// CaddyVersion returns a detailed version string, if available.
466
-func CaddyVersion() string {
467
- goModule := caddy.GoModule()
468
- ver := goModule.Version
469
- if goModule.Sum != "" {
470
- ver += " " + goModule.Sum
471
- }
472
- if goModule.Replace != nil {
473
- ver += " => " + goModule.Replace.Path
474
- if goModule.Replace.Version != "" {
475
- ver += "@" + goModule.Replace.Version
476
- }
477
- if goModule.Replace.Sum != "" {
478
- ver += " " + goModule.Replace.Sum
479
- }
480
- }
481
- return ver
482
-}
483
-
466
// StringSlice is a flag.Value that enables repeated use of a string flag.
467
type StringSlice []string
468
modules/caddyhttp/reverseproxy/fastcgi/fastcgi.go
+2
-4
@@ -94,10 +94,8 @@ func (t *Transport) Provision(ctx caddy.Context) error {
94
t.Root = "{http.vars.root}"
95
}
96
97
- t.serverSoftware = "Caddy"
98
- if mod := caddy.GoModule(); mod.Version != "" {
99
- t.serverSoftware += "/" + mod.Version
100
- }
97
+ version, _ := caddy.Version()
98
+ t.serverSoftware = "Caddy/" + version
99
100
// Set a relatively short default dial timeout.
101
// This is helpful to make load-balancer retries more speedy.
modules/caddyhttp/tracing/tracer.go
+2
-2
@@ -7,7 +7,6 @@ import (
7
8
"github.com/caddyserver/caddy/v2"
9
10
- caddycmd "github.com/caddyserver/caddy/v2/cmd"
10
"github.com/caddyserver/caddy/v2/modules/caddyhttp"
11
"go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp"
12
"go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc"
@@ -52,7 +51,8 @@ func newOpenTelemetryWrapper(
51
spanName: spanName,
52
}
53
55
- res, err := ot.newResource(webEngineName, caddycmd.CaddyVersion())
54
+ version, _ := caddy.Version()
55
+ res, err := ot.newResource(webEngineName, version)
56
if err != nil {
57
return ot, fmt.Errorf("creating resource error: %w", err)
58
}