Skip to content

Commit

Permalink
Merge pull request #1 from ractf/dev
Browse files Browse the repository at this point in the history
dockerfile generation
  • Loading branch information
Bentechy66 authored Aug 10, 2020
2 parents 89829dd + 60eb63d commit 3937ddf
Show file tree
Hide file tree
Showing 7 changed files with 307 additions and 35 deletions.
64 changes: 64 additions & 0 deletions docker-compose.tmpl
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
version: "3"

services:
{{if index .InstallComponents "Core"}}
redis:
image: redis:5

database:
image: postgres:12-alpine
environment:
- POSTGRES_EXTENSIONS=citext
- POSTGRES_HOST_AUTH_METHOD=trust
{{end}}
{{if index .InstallComponents "Shell"}}
shell:
image: ractf/shell
ports:
- "8000:8000"
environment:
- RACTF_API_BASE=/api/v2
- RACTF_USE_HEAD_NAV=true
- RACTF_SITE_NAME={{.EventName}}
- RACTF_API_DOMAIN=https://{{.APIDomain}}
- RACTF_WSS_URL=wss://{{.APIDomain}}/api/v2/ws/
{{if index .InstallComponents "Core"}}
depends_on:
- backend
- sockets
{{end}}
{{end}}
{{if index .InstallComponents "Core"}}
backend: &backend
image: ractf/core
entrypoint: /app/entrypoints/backend.sh
command: gunicorn -w 12 -b 0.0.0.0:8000 backend.wsgi:application
environment:
- LOAD_FIXTURES=0
- FRONTEND_URL={{.FrontendURL}}
- SECRET_KEY={{.SecretKey}}
- DJANGO_SETTINGS_MODULE=backend.settings.local

- ANDROMEDA_IP=andromeda
- ANDROMEDA_URL=http://andromeda:6000

- REDIS_PORT=6379
- REDIS_HOST=redis
- REDIS_CONFIG_DB=3
- REDIS_CACHE_DB=10

- SQL_PORT=5432
- SQL_HOST=database
- SQL_USER=postgres
- SQL_DATABASE=postgres

depends_on:
- database

sockets:
<<: *backend
entrypoint: /app/entrypoints/sockets.sh
command: daphne -b 0.0.0.0 -p 8000 backend.asgi:application
depends_on:
- backend
{{end}}
6 changes: 6 additions & 0 deletions go.mod
Original file line number Diff line number Diff line change
@@ -1,3 +1,9 @@
module github.com/ractf/install

go 1.14

require (
github.com/logrusorgru/aurora v2.0.3+incompatible
github.com/manifoldco/promptui v0.7.0
github.com/markbates/pkger v0.17.0
)
43 changes: 43 additions & 0 deletions go.sum
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
github.com/chzyer/logex v1.1.10 h1:Swpa1K6QvQznwJRcfTfQJmTE72DqScAa40E+fbHEXEE=
github.com/chzyer/logex v1.1.10/go.mod h1:+Ywpsq7O8HXn0nuIou7OrIPyXbp3wmkHB+jjWRnGsAI=
github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e h1:fY5BOSpyZCqRo5OhCuC+XN+r/bBCmeuuJtjz+bCNIf8=
github.com/chzyer/readline v0.0.0-20180603132655-2972be24d48e/go.mod h1:nSuG5e5PlCu98SY8svDHJxuZscDgtXS6KTTbou5AhLI=
github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1 h1:q763qf9huN11kDQavWsoZXJNW3xEE4JJyHa5Q25/sd8=
github.com/chzyer/test v0.0.0-20180213035817-a1ea475d72b1/go.mod h1:Q3SI9o4m/ZMnBNeIyt5eFwwo7qiLfzFZmjNmxjkiQlU=
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/gobuffalo/here v0.6.0 h1:hYrd0a6gDmWxBM4TnrGw8mQg24iSVoIkHEk7FodQcBI=
github.com/gobuffalo/here v0.6.0/go.mod h1:wAG085dHOYqUpf+Ap+WOdrPTp5IYcDAs/x7PLa8Y5fM=
github.com/juju/ansiterm v0.0.0-20180109212912-720a0952cc2a h1:FaWFmfWdAUKbSCtOU2QjDaorUexogfaMgbipgYATUMU=
github.com/juju/ansiterm v0.0.0-20180109212912-720a0952cc2a/go.mod h1:UJSiEoRfvx3hP73CvoARgeLjaIOjybY9vj8PUPPFGeU=
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/logrusorgru/aurora v2.0.3+incompatible h1:tOpm7WcpBTn4fjmVfgpQq0EfczGlG91VSDkswnjF5A8=
github.com/logrusorgru/aurora v2.0.3+incompatible/go.mod h1:7rIyQOR62GCctdiQpZ/zOJlFyk6y+94wXzv6RNZgaR4=
github.com/lunixbochs/vtclean v0.0.0-20180621232353-2d01aacdc34a h1:weJVJJRzAJBFRlAiJQROKQs8oC9vOxvm4rZmBBk0ONw=
github.com/lunixbochs/vtclean v0.0.0-20180621232353-2d01aacdc34a/go.mod h1:pHhQNgMf3btfWnGBVipUOjRYhoOsdGqdm/+2c2E2WMI=
github.com/manifoldco/promptui v0.7.0 h1:3l11YT8tm9MnwGFQ4kETwkzpAwY2Jt9lCrumCUW4+z4=
github.com/manifoldco/promptui v0.7.0/go.mod h1:n4zTdgP0vr0S3w7/O/g98U+e0gwLScEXGwov2nIKuGQ=
github.com/markbates/pkger v0.17.0 h1:RFfyBPufP2V6cddUyyEVSHBpaAnM1WzaMNyqomeT+iY=
github.com/markbates/pkger v0.17.0/go.mod h1:0JoVlrol20BSywW79rN3kdFFsE5xYM+rSCQDXbLhiuI=
github.com/mattn/go-colorable v0.0.9 h1:UVL0vNpWh04HeJXV0KLcaT7r06gOH2l4OW6ddYRUIY4=
github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU=
github.com/mattn/go-isatty v0.0.4 h1:bnP0vzxcAdeI1zdubAl5PjU6zsERjGZb7raWodagDYs=
github.com/mattn/go-isatty v0.0.4/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4=
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/testify v1.4.0 h1:2E4SXV/wtOkTonXsotYi4li6zVWxYlZuYNCXe9XRJyk=
github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4=
golang.org/x/sys v0.0.0-20181122145206-62eef0e2fa9b h1:MQE+LT/ABUuuvEZ+YQAMSXindAdUh7slEmAkup74op4=
golang.org/x/sys v0.0.0-20181122145206-62eef0e2fa9b/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
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/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
gopkg.in/yaml.v2 v2.2.7 h1:VUgggvou5XRW9mHwD/yXxIYSMtY0zoKQf/v226p2nyo=
gopkg.in/yaml.v2 v2.2.7/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
126 changes: 91 additions & 35 deletions main.go
Original file line number Diff line number Diff line change
@@ -1,58 +1,114 @@
package main

import (
"errors"
"fmt"

. "github.com/logrusorgru/aurora"
"github.com/manifoldco/promptui"
"github.com/markbates/pkger"
"io/ioutil"
"os"
"strings"
"text/template"
)

type options struct {
EventName string
InstallComponents map[string]bool
SecretKey string
FrontendURL string
APIDomain string
}

func main() {
fmt.Println(Cyan("Welcome to the"), Bold("RACTF"), Cyan("setup script"))

selectedComponents := cumulativeSelect("Which services would you like to install?", []string{"Andromeda", "Core", "Shell", "Confirm"})
installOptions := options{}

if len(selectedComponents) == 0 {
fmt.Println(Red("You must select at least one component to continue."))
installOptions.InstallComponents = cumulativeSelect("Which services would you like to install?", []string{"Andromeda", "Core", "Shell"})

var installCount int
for _, v := range installOptions.InstallComponents {
if v {
installCount += 1
}
}

if installCount == 0 {
fmt.Println(Red("You must select at least one service to continue."))
return
}
if installOptions.InstallComponents["Andromeda"] {
fmt.Println(Red("Andromeda install is not currently supported by this script."))
return
}
}

func cumulativeSelect(prompt string, items []string) []string {
var selected []string
if installOptions.InstallComponents["Shell"] {
installOptions.EventName = promptString("What's the (short) name of your event (e.g. RACTF)?", stringValidator)
installOptions.APIDomain = promptString("What's the public URL of your API? (Don't include http(s) or a trailing slash, include a port if necessary)", partialDomainValidator)
}

for index := 0; ; {
prompt := promptui.Select{
Label: fmt.Sprintf("%s (Currently selected: %s)", Yellow(prompt), selected),
Items: items,
HideSelected: true,
CursorPos: index,
}
if installOptions.InstallComponents["Core"] {
installOptions.FrontendURL = promptString("What URL will visitors access your site through? (Include http(s) and a trailing /)", fullDomainValidator)
}

index, choice, err := prompt.Run()
installOptions.SecretKey = GenerateRandomString(64)

if err != nil {
fmt.Println("Prompt failed to display.")
break
}
fmt.Println(Green("Proceeding with installation of"), Bold(installCount), Green("components."))
generateAndWriteDockerFile(installOptions)
}

if index == 3 {
break
}
func generateAndWriteDockerFile(options options) {
tf, err := pkger.Open("/docker-compose.tmpl")
if err != nil {
fmt.Println(err)
}
templ, err := ioutil.ReadAll(tf)
if err != nil {
fmt.Println(err)
}

var removedFromSelected bool
t, err := template.New("dockerCompose").Parse(string(templ))
if err != nil {
fmt.Println(err)
return
}

for i, val := range selected {
if val == choice {
selected = append(selected[:i], selected[i+1:]...)
removedFromSelected = true
break
}
}
if !removedFromSelected {
selected = append(selected, choice)
}
f, err := os.Create("docker-compose.yaml")
if err != nil {
fmt.Println("create file: ", err)
return
}

err = t.Execute(f, options)
if err != nil {
fmt.Println(err)
return
}
}

func stringValidator(input string) error {
if len(input) == 0 {
return errors.New("input must be longer than one char")
}
return nil
}

return selected
func partialDomainValidator(input string) error {
if strings.HasPrefix(input, "http") {
return errors.New("string should not start with http")
}
if strings.HasSuffix(input, "/") {
return errors.New("string should not end with /")
}
return nil
}

func fullDomainValidator(input string) error {
if !strings.HasPrefix(input, "http") {
return errors.New("string should start with http")
}
if !strings.HasSuffix(input, "/") {
return errors.New("string should end with /")
}
return nil
}
12 changes: 12 additions & 0 deletions pkged.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

66 changes: 66 additions & 0 deletions prompt_utils.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
package main

import (
"fmt"
. "github.com/logrusorgru/aurora"
"github.com/manifoldco/promptui"
"strings"
)

func promptString(promptMessage string, validate promptui.ValidateFunc) string {
prompt := promptui.Prompt{
Label: fmt.Sprintf("%s", Yellow(promptMessage)),
Validate: validate,
}

result, err := prompt.Run()

if err != nil {
fmt.Println(Red("Prompt failed to display."))
return ""
}

return result
}

func cumulativeSelect(prompt string, items []string) map[string]bool {
selected := make(map[string]bool)
for _, v := range items {
selected[v] = false
}

items = append(items, "Confirm")

for {
var enabledList []string
for i, v := range selected {
if v {
enabledList = append(enabledList, i)
}
}
if len(enabledList) == 0 {
enabledList = []string{"[None]"}
}

prompt := promptui.Select{
Label: fmt.Sprintf("%s (Currently selected: %s)", Yellow(prompt), strings.Join(enabledList, ", ")),
Items: items,
HideSelected: true,
}

index, choice, err := prompt.Run()

if err != nil {
fmt.Println(Red("Prompt failed to display."))
break
}

if index == len(items)-1 {
break
}

selected[choice] = !selected[choice]
}

return selected
}
25 changes: 25 additions & 0 deletions rand_utils.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
package main

import "crypto/rand"

func GenerateRandomBytes(n int) ([]byte, error) {
b := make([]byte, n)
_, err := rand.Read(b)
if err != nil {
return nil, err
}

return b, nil
}

func GenerateRandomString(n int) string {
const letters = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz-"
bytes, err := GenerateRandomBytes(n)
if err != nil {
return ""
}
for i, b := range bytes {
bytes[i] = letters[b%byte(len(letters))]
}
return string(bytes)
}

0 comments on commit 3937ddf

Please sign in to comment.