You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
297 lines
11 KiB
297 lines
11 KiB
From ce4b2828ec800f0d1782b97b9400bd71154e5bbf Mon Sep 17 00:00:00 2001
|
|
From: =?UTF-8?q?Manuel=20R=C3=BCger?= <manuel@rueg.eu>
|
|
Date: Tue, 18 Sep 2018 15:42:24 +0200
|
|
Subject: [PATCH] server: Read config from file
|
|
|
|
---
|
|
README.md | 4 ++
|
|
config.yml.example | 37 ++++++++++++++++
|
|
go.mod | 1 +
|
|
go.sum | 4 ++
|
|
server.go | 107 +++++++++++++++++++++++++++++++--------------
|
|
5 files changed, 119 insertions(+), 34 deletions(-)
|
|
create mode 100644 config.yml.example
|
|
|
|
diff --git a/README.md b/README.md
|
|
index 3c93191a..23b1b33c 100644
|
|
--- a/README.md
|
|
+++ b/README.md
|
|
@@ -212,6 +212,7 @@ Flags:
|
|
-u, --username username for the registry (default: <none>)
|
|
--listen-address address to listen on (default: <none>)
|
|
--asset-path Path to assets and templates (default: <none>)
|
|
+ --config Path to config file (default: <none>)
|
|
-f, --force-non-ssl force allow use of non-ssl (default: false)
|
|
--once generate the templates once and then exit (default: false)
|
|
--skip-ping skip pinging the registry while establishing connection (default: false)
|
|
@@ -227,6 +228,9 @@ Flags:
|
|
-p, --password password for the registry (default: <none>)
|
|
```
|
|
|
|
+Alternatively you can provide configuration to `reg server` via a file passed to
|
|
+`reg server` via as `--config`. See also config.yml.example in this repository.
|
|
+
|
|
**Screenshots:**
|
|
|
|
![home.png](server/home.png)
|
|
diff --git a/config.yml.example b/config.yml.example
|
|
new file mode 100644
|
|
index 00000000..9d4be25f
|
|
--- /dev/null
|
|
+++ b/config.yml.example
|
|
@@ -0,0 +1,37 @@
|
|
+### Reg Server Settings
|
|
+
|
|
+## Path to server TLS certificate:
|
|
+# cert:
|
|
+## Path to server TLS key:
|
|
+# key:
|
|
+## Address to listen on:
|
|
+# listen-address: 0.0.0.0
|
|
+## Port to listen on:
|
|
+# port: 8080
|
|
+## Path Assets are stored under:
|
|
+# asset-path: /var/lib/reg
|
|
+## Generate static website and exit:
|
|
+# once: false
|
|
+## Refresh interval:
|
|
+# interval: 1h0m0s
|
|
+## Debug output
|
|
+# debug: false
|
|
+## Skip initial ping
|
|
+# skip-ping: false
|
|
+## Timeout
|
|
+# timeout: 1m0s
|
|
+
|
|
+
|
|
+### Registry and Clair Server Settings
|
|
+## Registry Server:
|
|
+# registry: r.j3ss.co
|
|
+## Username to authenticate against registry server
|
|
+# username:
|
|
+## Password to authenticate against registry server
|
|
+# password:
|
|
+## If true, do not verify TLS certificates
|
|
+# insecure: false
|
|
+## Force allow use of non-TLS connections
|
|
+# force-nonssl: false
|
|
+## Clair Server:
|
|
+# clair:
|
|
diff --git a/go.mod b/go.mod
|
|
index 4e7583e8..914297a8 100644
|
|
--- a/go.mod
|
|
+++ b/go.mod
|
|
@@ -35,5 +35,6 @@ require (
|
|
github.com/sirupsen/logrus v1.4.2
|
|
golang.org/x/time v0.0.0-20190308202827-9d24e82272b4 // indirect
|
|
google.golang.org/grpc v1.23.1
|
|
+ gopkg.in/yaml.v2 v2.0.0-20170812160011-eb3733d160e7
|
|
gotest.tools v2.2.0+incompatible // indirect
|
|
)
|
|
diff --git a/go.sum b/go.sum
|
|
index 71f46e16..ff078b3f 100644
|
|
--- a/go.sum
|
|
+++ b/go.sum
|
|
@@ -54,8 +54,10 @@ github.com/kisielk/errcheck v1.2.0/go.mod h1:/BMXB+zMLi60iA8Vv6Ksmxu/1UDYcXs4uQL
|
|
github.com/kisielk/gotool v1.0.0/go.mod h1:XhKaO+MFFWcvkIS/tQcRk01m1F5IRFswLeQ+oQHNcck=
|
|
github.com/konsorten/go-windows-terminal-sequences v1.0.1 h1:mweAR1A6xJ3oS2pRaGiHgQ4OO8tzTaLawm8vnODuwDk=
|
|
github.com/konsorten/go-windows-terminal-sequences v1.0.1/go.mod h1:T0+1ngSBFLxvqU3pZ+m/2kptfBszLMUkC4ZK/EgS/cQ=
|
|
+github.com/kr/pretty v0.1.0 h1:L/CwN0zerZDmRFUapSPitk6f+Q3+0za1rQkzVuMiMFI=
|
|
github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
|
|
github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
|
|
+github.com/kr/text v0.1.0 h1:45sCR5RtlFHMR4UwH9sdQ5TC8v0qDQCHnXt+kaKSTVE=
|
|
github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
|
|
github.com/mitchellh/go-wordwrap v1.0.0 h1:6GlHJ/LTGMrIJbwgdqdl2eEH8o+Exx/0m8ir9Gns0u4=
|
|
github.com/mitchellh/go-wordwrap v1.0.0/go.mod h1:ZXFpozHsX6DPmq2I0TCekCxypsnAUbP2oI0UX1GXzOo=
|
|
@@ -115,8 +117,10 @@ google.golang.org/genproto v0.0.0-20180817151627-c66870c02cf8/go.mod h1:JiN7NxoA
|
|
google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c=
|
|
google.golang.org/grpc v1.23.1 h1:q4XQuHFC6I28BKZpo6IYyb3mNO+l7lSOxRuYTCiDfXk=
|
|
google.golang.org/grpc v1.23.1/go.mod h1:Y5yQAOtifL1yxbo5wqy6BxZv8vAUGQwXBOALyacEbxg=
|
|
+gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127 h1:qIbj1fsPNlZgppZ+VLlY7N33q108Sa+fhmuc+sWQYwY=
|
|
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
|
gopkg.in/resty.v1 v1.12.0/go.mod h1:mDo4pnntr5jdWRML875a/NmxYqAlA73dVijT2AXvQQo=
|
|
+gopkg.in/yaml.v2 v2.0.0-20170812160011-eb3733d160e7 h1:+t9dhfO+GNOIGJof6kPOAenx7YgrZMTdRPV+EsnPabk=
|
|
gopkg.in/yaml.v2 v2.0.0-20170812160011-eb3733d160e7/go.mod h1:JAlM8MvJe8wmxCU4Bli9HhUf9+ttbYbLASfIpnQbh74=
|
|
gotest.tools v2.2.0+incompatible h1:VsBPFP1AI068pPrMxtb/S8Zkgf9xEmTLJjfM+P5UIEo=
|
|
gotest.tools v2.2.0+incompatible/go.mod h1:DsYFclhRJ6vuDpmuTbkuFWG+y2sxOXAzmJt81HFBacw=
|
|
diff --git a/server.go b/server.go
|
|
index fcd4cd71..0c84d85d 100644
|
|
--- a/server.go
|
|
+++ b/server.go
|
|
@@ -4,7 +4,9 @@ import (
|
|
"context"
|
|
"flag"
|
|
"fmt"
|
|
+ "gopkg.in/yaml.v2"
|
|
"html/template"
|
|
+ "io/ioutil"
|
|
"net/http"
|
|
"os"
|
|
"path/filepath"
|
|
@@ -29,39 +31,76 @@ func (cmd *serverCommand) LongHelp() string { return serverHelp }
|
|
func (cmd *serverCommand) Hidden() bool { return false }
|
|
|
|
func (cmd *serverCommand) Register(fs *flag.FlagSet) {
|
|
- fs.DurationVar(&cmd.interval, "interval", time.Hour, "interval to generate new index.html's at")
|
|
+ fs.DurationVar(&cmd.Interval, "interval", time.Hour, "interval to generate new index.html's at")
|
|
|
|
- fs.StringVar(&cmd.registryServer, "registry", "", "URL to the private registry (ex. r.j3ss.co)")
|
|
- fs.StringVar(&cmd.registryServer, "r", "", "URL to the private registry (ex. r.j3ss.co)")
|
|
+ fs.StringVar(&cmd.RegistryServer, "registry", "", "URL to the private registry (ex. r.j3ss.co)")
|
|
+ fs.StringVar(&cmd.RegistryServer, "r", "", "URL to the private registry (ex. r.j3ss.co)")
|
|
|
|
- fs.StringVar(&cmd.clairServer, "clair", "", "url to clair instance")
|
|
+ fs.StringVar(&cmd.ClairServer, "clair", "", "url to clair instance")
|
|
|
|
- fs.StringVar(&cmd.cert, "cert", "", "path to ssl cert")
|
|
- fs.StringVar(&cmd.key, "key", "", "path to ssl key")
|
|
- fs.StringVar(&cmd.listenAddress, "listen-address", "", "address to listen on")
|
|
- fs.StringVar(&cmd.port, "port", "8080", "port for server to run on")
|
|
- fs.StringVar(&cmd.assetPath, "asset-path", "", "Path to assets and templates")
|
|
+ fs.StringVar(&cmd.Cert, "cert", "", "path to ssl cert")
|
|
+ fs.StringVar(&cmd.Key, "key", "", "path to ssl key")
|
|
+ fs.StringVar(&cmd.ListenAddress, "listen-address", "", "address to listen on")
|
|
+ fs.StringVar(&cmd.Port, "port", "8080", "port for server to run on")
|
|
|
|
- fs.BoolVar(&cmd.generateAndExit, "once", false, "generate the templates once and then exit")
|
|
+ fs.StringVar(&cmd.AssetPath, "asset-path", "", "Path to assets and templates")
|
|
+ fs.StringVar(&cmd.configPath, "config", "", "Path to config file")
|
|
+
|
|
+ fs.BoolVar(&cmd.GenerateAndExit, "once", false, "generate the templates once and then exit")
|
|
}
|
|
|
|
type serverCommand struct {
|
|
- interval time.Duration
|
|
- registryServer string
|
|
- clairServer string
|
|
-
|
|
- generateAndExit bool
|
|
-
|
|
- cert string
|
|
- key string
|
|
- listenAddress string
|
|
- port string
|
|
- assetPath string
|
|
+ Interval time.Duration `yaml:"interval"`
|
|
+ RegistryServer string `yaml:"registry"`
|
|
+ ClairServer string `yaml:"clair"`
|
|
+ GenerateAndExit bool `yaml:"once"`
|
|
+ Cert string `yaml:"cert"`
|
|
+ Key string `yaml:"key"`
|
|
+ ListenAddress string `yaml:"listen-address"`
|
|
+ Port string `yaml:"port"`
|
|
+ AssetPath string `yaml:"asset-path"`
|
|
+ configPath string
|
|
+
|
|
+ Password string `yaml:"password"`
|
|
+ Username string `yaml:"username"`
|
|
+ Insecure bool `yaml:"insecure"`
|
|
+ Debug bool `yaml:"debug"`
|
|
+ SkipPing bool `yaml:"skip-ping"`
|
|
+ ForceNonSSL bool `yaml:"force-nonssl"`
|
|
+ Timeout time.Duration `yaml:"timeout"`
|
|
}
|
|
|
|
func (cmd *serverCommand) Run(ctx context.Context, args []string) error {
|
|
// Create the registry client.
|
|
- r, err := createRegistryClient(ctx, cmd.registryServer)
|
|
+ if len(cmd.configPath) > 0 {
|
|
+ config, err := ioutil.ReadFile(cmd.configPath)
|
|
+ if err != nil {
|
|
+ return err
|
|
+ }
|
|
+ yaml.Unmarshal(config, cmd)
|
|
+ if err != nil {
|
|
+ return err
|
|
+ }
|
|
+ if len(cmd.Username) > 0 {
|
|
+ username = cmd.Username
|
|
+ }
|
|
+ if len(cmd.Password) > 0 {
|
|
+ password = cmd.Password
|
|
+ }
|
|
+ if cmd.Debug {
|
|
+ debug = cmd.Debug
|
|
+ }
|
|
+ if cmd.Insecure {
|
|
+ insecure = cmd.Insecure
|
|
+ }
|
|
+ if cmd.SkipPing {
|
|
+ skipPing = cmd.SkipPing
|
|
+ }
|
|
+ if cmd.Timeout != 0 {
|
|
+ timeout = cmd.Timeout
|
|
+ }
|
|
+ }
|
|
+ r, err := createRegistryClient(ctx, cmd.RegistryServer)
|
|
if err != nil {
|
|
return err
|
|
}
|
|
@@ -69,25 +108,25 @@ func (cmd *serverCommand) Run(ctx context.Context, args []string) error {
|
|
// Create the registry controller for the handlers.
|
|
rc := registryController{
|
|
reg: r,
|
|
- generateOnly: cmd.generateAndExit,
|
|
+ generateOnly: cmd.GenerateAndExit,
|
|
}
|
|
|
|
// Create a clair client if the user passed in a server address.
|
|
- if len(cmd.clairServer) > 0 {
|
|
- rc.cl, err = clair.New(cmd.clairServer, clair.Opt{
|
|
+ if len(cmd.ClairServer) > 0 {
|
|
+ rc.cl, err = clair.New(cmd.ClairServer, clair.Opt{
|
|
Insecure: insecure,
|
|
Debug: debug,
|
|
Timeout: timeout,
|
|
})
|
|
if err != nil {
|
|
- return fmt.Errorf("creation of clair client at %s failed: %v", cmd.clairServer, err)
|
|
+ return fmt.Errorf("creation of clair client at %s failed: %v", cmd.ClairServer, err)
|
|
}
|
|
} else {
|
|
rc.cl = nil
|
|
}
|
|
// Get the path to the asset directory.
|
|
- assetDir := cmd.assetPath
|
|
- if len(cmd.assetPath) <= 0 {
|
|
+ assetDir := cmd.AssetPath
|
|
+ if len(cmd.AssetPath) <= 0 {
|
|
assetDir, err = os.Getwd()
|
|
if err != nil {
|
|
return err
|
|
@@ -131,12 +170,12 @@ func (cmd *serverCommand) Run(ctx context.Context, args []string) error {
|
|
return fmt.Errorf("creating index failed: %v", err)
|
|
}
|
|
|
|
- if cmd.generateAndExit {
|
|
+ if cmd.GenerateAndExit {
|
|
logrus.Info("output generated, exiting...")
|
|
return nil
|
|
}
|
|
|
|
- rc.interval = cmd.interval
|
|
+ rc.interval = cmd.Interval
|
|
ticker := time.NewTicker(rc.interval)
|
|
go func() {
|
|
// Create more indexes every X minutes based off interval.
|
|
@@ -174,12 +213,12 @@ func (cmd *serverCommand) Run(ctx context.Context, args []string) error {
|
|
|
|
// Set up the server.
|
|
server := &http.Server{
|
|
- Addr: cmd.listenAddress + ":" + cmd.port,
|
|
+ Addr: cmd.ListenAddress + ":" + cmd.Port,
|
|
Handler: mux,
|
|
}
|
|
- logrus.Infof("Starting server on port %q", cmd.port)
|
|
- if len(cmd.cert) > 0 && len(cmd.key) > 0 {
|
|
- return server.ListenAndServeTLS(cmd.cert, cmd.key)
|
|
+ logrus.Infof("Starting server on port %q", cmd.Port)
|
|
+ if len(cmd.Cert) > 0 && len(cmd.Key) > 0 {
|
|
+ return server.ListenAndServeTLS(cmd.Cert, cmd.Key)
|
|
}
|
|
return server.ListenAndServe()
|
|
}
|
|
--
|
|
2.34.1
|
|
|