Change for external config
This commit is contained in:
parent
13f6281a00
commit
ac43fa1572
34
.woodpecker.yml
Normal file
34
.woodpecker.yml
Normal file
@ -0,0 +1,34 @@
|
||||
steps:
|
||||
build-only:
|
||||
image: woodpeckerci/plugin-docker-buildx
|
||||
settings:
|
||||
repo: git.sebclem.fr/sebclem/${CI_REPO_NAME}
|
||||
cache_from: git.sebclem.fr/sebclem/${CI_REPO_NAME}
|
||||
registry: git.sebclem.fr
|
||||
dry_run: true
|
||||
auto_tag: true
|
||||
logins:
|
||||
- registry: https://git.sebclem.fr
|
||||
username:
|
||||
from_secret: docker_user
|
||||
password:
|
||||
from_secret: docker_token
|
||||
when:
|
||||
event: [push, pull_request, manual]
|
||||
|
||||
publish:
|
||||
image: woodpeckerci/plugin-docker-buildx
|
||||
settings:
|
||||
platforms: linux/amd64
|
||||
auto_tag: true
|
||||
repo: git.sebclem.fr/sebclem/${CI_REPO_NAME}
|
||||
cache_from: git.sebclem.fr/sebclem/${CI_REPO_NAME}
|
||||
logins:
|
||||
- registry: https://git.sebclem.fr
|
||||
username:
|
||||
from_secret: docker_user
|
||||
password:
|
||||
from_secret: docker_token
|
||||
when:
|
||||
event:
|
||||
- tag
|
29
Dockerfile
Normal file
29
Dockerfile
Normal file
@ -0,0 +1,29 @@
|
||||
# syntax=docker/dockerfile:1
|
||||
|
||||
FROM golang:1.20.5-alpine
|
||||
|
||||
# Set destination for COPY
|
||||
WORKDIR /app
|
||||
|
||||
# Download Go modules
|
||||
COPY go.mod go.sum ./
|
||||
RUN go mod download
|
||||
|
||||
# Copy the source code. Note the slash at the end, as explained in
|
||||
# https://docs.docker.com/engine/reference/builder/#copy
|
||||
COPY *.go ./
|
||||
|
||||
# Build
|
||||
RUN CGO_ENABLED=0 GOOS=linux go build -o /woodpecker-config-service
|
||||
|
||||
# Optional:
|
||||
# To bind to a TCP port, runtime parameters must be supplied to the docker command.
|
||||
# But we can document in the Dockerfile what ports
|
||||
# the application is going to listen on by default.
|
||||
# https://docs.docker.com/engine/reference/builder/#expose
|
||||
EXPOSE 8000
|
||||
VOLUME [ "/data/woodpecker.pub" ]
|
||||
ENV CONFIG_SERVICE_PUBLIC_KEY_FILE=/data/woodpecker.pub
|
||||
|
||||
# Run
|
||||
CMD ["/woodpecker-config-service"]
|
@ -24,3 +24,6 @@ WOODPECKER_CONFIG_SERVICE_ENDPOINT=http://<service>:8000/ciconfig
|
||||
WOODPECKER_CONFIG_SERVICE_PUBLIC_KEY_FILE=public-key.pem
|
||||
```
|
||||
|
||||
|
||||
|
||||
For docker, simply mount the woodpecker key to /data/woodpecker.pub
|
@ -1,5 +0,0 @@
|
||||
pipeline:
|
||||
centralized:
|
||||
image: alpine
|
||||
commands:
|
||||
- echo "Hello there from a central place"
|
1
go.mod
1
go.mod
@ -6,4 +6,5 @@ require (
|
||||
github.com/go-ap/httpsig v0.0.0-20210714162115-62a09257db51
|
||||
github.com/joho/godotenv v1.4.0
|
||||
github.com/woodpecker-ci/woodpecker v0.15.1
|
||||
gopkg.in/yaml.v3 v3.0.0-20210107192922-496545a6307b
|
||||
)
|
||||
|
6
go.sum
6
go.sum
@ -763,11 +763,13 @@ github.com/kr/logfmt v0.0.0-20140226030751-b84e30acd515/go.mod h1:+0opPa2QZZtGFB
|
||||
github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo=
|
||||
github.com/kr/pretty v0.2.0/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI=
|
||||
github.com/kr/pretty v0.2.1/go.mod h1:ipq/a2n7PKx3OHsz4KJII5eveXtPO4qwEXGdVfWzfnI=
|
||||
github.com/kr/pretty v0.3.0 h1:WgNl7dwNpEZ6jJ9k1snq4pZsg7DOEN8hP9Xw0Tsjwk0=
|
||||
github.com/kr/pretty v0.3.0/go.mod h1:640gp4NfQd8pI5XOwp5fnNeVWj67G7CFk/SaSQn7NBk=
|
||||
github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ=
|
||||
github.com/kr/pty v1.1.5/go.mod h1:9r2w37qlBe7rQ6e1fg1S/9xpWHSnaqNdHD3WcMdbPDA=
|
||||
github.com/kr/pty v1.1.8/go.mod h1:O1sed60cT9XZ5uDucP5qwvh+TE3NnUj51EiZO/lmSfw=
|
||||
github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI=
|
||||
github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY=
|
||||
github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE=
|
||||
github.com/kulti/thelper v0.5.1/go.mod h1:vMu2Cizjy/grP+jmsvOFDx1kYP6+PD1lqg4Yu5exl2U=
|
||||
github.com/kunwardeep/paralleltest v1.0.3/go.mod h1:vLydzomDFpk7yu5UX02RmP0H8QfRPOV/oFhWN85Mjb4=
|
||||
@ -1051,6 +1053,7 @@ github.com/rogpeppe/fastuuid v1.2.0/go.mod h1:jVj6XXZzXRy/MSR5jhDC/2q6DgLz+nrA6L
|
||||
github.com/rogpeppe/go-internal v1.3.0/go.mod h1:M8bDsm7K2OlrFYOpmOWEs/qY81heoFRclV5y23lUDJ4=
|
||||
github.com/rogpeppe/go-internal v1.6.1/go.mod h1:xXDCJY+GAPziupqXw64V24skbSoqbTEfhy4qGm1nDQc=
|
||||
github.com/rogpeppe/go-internal v1.8.0/go.mod h1:WmiCO8CzOY8rg0OYDC4/i/2WRWAB6poM+XZ2dLUbcbE=
|
||||
github.com/rogpeppe/go-internal v1.8.1 h1:geMPLpDpQOgVyCg5z5GoRwLHepNdb71NXb67XFkP+Eg=
|
||||
github.com/rogpeppe/go-internal v1.8.1/go.mod h1:JeRgkft04UBgHMgCIwADu4Pn6Mtm5d4nPKWu0nJ5d+o=
|
||||
github.com/rs/cors v1.7.0/go.mod h1:gFx+x8UowdsKA9AchylcLynDq+nNFfI8FkUZdN/jGCU=
|
||||
github.com/rs/xid v1.2.1/go.mod h1:+uKXf+4Djp6Md1KODXJxgGQPKngRmWyn10oCKFzNHOQ=
|
||||
@ -1194,8 +1197,6 @@ github.com/vishvananda/netns v0.0.0-20200728191858-db3c7e526aae/go.mod h1:DD4vA1
|
||||
github.com/willf/bitset v1.1.11-0.20200630133818-d5bec3311243/go.mod h1:RjeCKbqT1RxIR/KWY6phxZiaY1IyutSBfGjNPySAYV4=
|
||||
github.com/willf/bitset v1.1.11/go.mod h1:83CECat5yLh5zVOf4P1ErAgKA5UDvKtgyUABdr3+MjI=
|
||||
github.com/woodpecker-ci/expr v0.0.0-20210628233344-164b8b3d0915/go.mod h1:PbzlZ93HrA1cf16OUP1vckAPq57gtF+ccnwZeDkmC9s=
|
||||
github.com/woodpecker-ci/woodpecker v0.15.0 h1:p3svFdtoXwmsd7w0/PJwyqfGejk2HaS8f6cC69xRxUE=
|
||||
github.com/woodpecker-ci/woodpecker v0.15.0/go.mod h1:gWRKIzkowiQmy8WC/fp5Ktn3QHZc15GtneRuoalysxg=
|
||||
github.com/woodpecker-ci/woodpecker v0.15.1 h1:S9RgkDoUQ0tvOL8/yJDDvDxdXUdE+XOdlZf/I6D3SRg=
|
||||
github.com/woodpecker-ci/woodpecker v0.15.1/go.mod h1:gWRKIzkowiQmy8WC/fp5Ktn3QHZc15GtneRuoalysxg=
|
||||
github.com/xanzy/go-gitlab v0.55.1/go.mod h1:F0QEXwmqiBUxCgJm8fE9S+1veX4XC9Z4cfaAbqwk4YM=
|
||||
@ -1860,6 +1861,7 @@ gopkg.in/check.v1 v1.0.0-20141024133853-64131543e789/go.mod h1:Co6ibVJAznAaIkqp8
|
||||
gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/check.v1 v1.0.0-20200227125254-8fa46927fb4f/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk=
|
||||
gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c/go.mod h1:JHkPIbrfpd72SG/EVd6muEfDQjcINNoR0C8j2r3qZ4Q=
|
||||
gopkg.in/cheggaaa/pb.v1 v1.0.25/go.mod h1:V/YB90LKu/1FcN3WVnfiiE5oMCibMjukxqG/qStrOgw=
|
||||
gopkg.in/cheggaaa/pb.v1 v1.0.28/go.mod h1:V/YB90LKu/1FcN3WVnfiiE5oMCibMjukxqG/qStrOgw=
|
||||
|
65
main.go
65
main.go
@ -10,11 +10,11 @@ import (
|
||||
"log"
|
||||
"net/http"
|
||||
"os"
|
||||
"regexp"
|
||||
"strings"
|
||||
|
||||
"github.com/go-ap/httpsig"
|
||||
"github.com/joho/godotenv"
|
||||
"github.com/woodpecker-ci/woodpecker/server/model"
|
||||
"gopkg.in/yaml.v3"
|
||||
)
|
||||
|
||||
type config struct {
|
||||
@ -28,23 +28,17 @@ type incoming struct {
|
||||
Configuration []*config `json:"configs"`
|
||||
}
|
||||
|
||||
//go:embed central-pipeline-config.yml
|
||||
var overrideConfiguration string
|
||||
type pipeline struct {
|
||||
Extend string `yaml:"extend"`
|
||||
}
|
||||
|
||||
func main() {
|
||||
log.Println("Woodpecker central config server")
|
||||
|
||||
err := godotenv.Load()
|
||||
if err != nil {
|
||||
log.Fatalf("Error loading .env file: %v", err)
|
||||
}
|
||||
|
||||
pubKeyPath := os.Getenv("CONFIG_SERVICE_PUBLIC_KEY_FILE") // Key in format of the one fetched from http(s)://your-woodpecker-server/api/signature/public-key
|
||||
host := os.Getenv("CONFIG_SERVICE_HOST")
|
||||
filterRegex := os.Getenv("CONFIG_SERVICE_OVERRIDE_FILTER")
|
||||
|
||||
if pubKeyPath == "" && host == "" {
|
||||
log.Fatal("Please make sure CONFIG_SERVICE_HOST and CONFIG_SERVICE_PUBLIC_KEY_FILE are set properly")
|
||||
if pubKeyPath == "" {
|
||||
log.Fatal("Please make sure CONFIG_SERVICE_PUBLIC_KEY_FILE is set properly")
|
||||
}
|
||||
|
||||
pubKeyRaw, err := ioutil.ReadFile(pubKeyPath)
|
||||
@ -63,8 +57,6 @@ func main() {
|
||||
log.Fatal("Failed to parse public key file")
|
||||
}
|
||||
|
||||
filter := regexp.MustCompile(filterRegex)
|
||||
|
||||
http.HandleFunc("/ciconfig", func(w http.ResponseWriter, r *http.Request) {
|
||||
if r.Method != http.MethodPost {
|
||||
w.WriteHeader(http.StatusMethodNotAllowed)
|
||||
@ -106,14 +98,40 @@ func main() {
|
||||
return
|
||||
}
|
||||
|
||||
if filter.MatchString(req.Repo.Name) {
|
||||
change := false
|
||||
configOverride := []config{}
|
||||
for _, conf := range req.Configuration {
|
||||
originalPipeline := pipeline{}
|
||||
err := yaml.Unmarshal([]byte(conf.Data), &originalPipeline)
|
||||
if err != nil {
|
||||
http.Error(w, "Failed to parse yaml"+err.Error(), http.StatusBadRequest)
|
||||
}
|
||||
if originalPipeline.Extend != "" {
|
||||
resp, err := http.Get(originalPipeline.Extend)
|
||||
if err != nil {
|
||||
http.Error(w, "Failed to download extend pipeline: "+err.Error(), http.StatusBadRequest)
|
||||
return
|
||||
}
|
||||
if resp.StatusCode != 200 {
|
||||
http.Error(w, "Failed to download extend pipeline: "+resp.Status, http.StatusBadRequest)
|
||||
return
|
||||
}
|
||||
|
||||
body, err := ioutil.ReadAll(resp.Body)
|
||||
if err != nil {
|
||||
http.Error(w, "Failed to download extend pipeline: "+err.Error(), http.StatusBadRequest)
|
||||
return
|
||||
}
|
||||
splited := strings.Split(originalPipeline.Extend, "/")
|
||||
confName := splited[len(splited)-1]
|
||||
configOverride = append(configOverride, config{Name: confName, Data: string(body)})
|
||||
change = true
|
||||
}
|
||||
|
||||
}
|
||||
if change {
|
||||
w.WriteHeader(http.StatusOK)
|
||||
err = json.NewEncoder(w).Encode(map[string]interface{}{"configs": []config{
|
||||
{
|
||||
Name: "central pipe",
|
||||
Data: overrideConfiguration,
|
||||
},
|
||||
}})
|
||||
err = json.NewEncoder(w).Encode(map[string]interface{}{"configs": configOverride})
|
||||
if err != nil {
|
||||
log.Printf("Error on encoding json %v\n", err)
|
||||
}
|
||||
@ -121,10 +139,9 @@ func main() {
|
||||
w.WriteHeader(http.StatusNoContent) // use default config
|
||||
// No need to write a response body
|
||||
}
|
||||
|
||||
})
|
||||
|
||||
err = http.ListenAndServe(os.Getenv("CONFIG_SERVICE_HOST"), nil)
|
||||
err = http.ListenAndServe(":8000", nil)
|
||||
if err != nil {
|
||||
log.Fatalf("Error on listen: %v", err)
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user