Initial version of the push to Dokku action
This commit is contained in:
parent
b65b39a231
commit
2bb5d7f528
14
action.yaml
Normal file
14
action.yaml
Normal file
|
@ -0,0 +1,14 @@
|
||||||
|
name: 'Push to Dokku'
|
||||||
|
description: 'Pushes a repository to a remote Dokku host'
|
||||||
|
runs:
|
||||||
|
using: 'go'
|
||||||
|
main: 'main.go'
|
||||||
|
inputs:
|
||||||
|
host:
|
||||||
|
description: 'Remote hostname'
|
||||||
|
required: true
|
||||||
|
app:
|
||||||
|
description: 'App name'
|
||||||
|
required: true
|
||||||
|
private-key:
|
||||||
|
description: 'Private SSH key to connect to remote host'
|
17
config.go
Normal file
17
config.go
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import "os"
|
||||||
|
|
||||||
|
type config struct {
|
||||||
|
HostName string
|
||||||
|
AppName string
|
||||||
|
PrivateKey string
|
||||||
|
}
|
||||||
|
|
||||||
|
func readConfig() config {
|
||||||
|
return config{
|
||||||
|
HostName: os.Getenv("host"),
|
||||||
|
AppName: os.Getenv("app"),
|
||||||
|
PrivateKey: os.Getenv("private-key"),
|
||||||
|
}
|
||||||
|
}
|
10
go.mod
Normal file
10
go.mod
Normal file
|
@ -0,0 +1,10 @@
|
||||||
|
module lmika.dev/actions/push-to-dokku
|
||||||
|
|
||||||
|
go 1.22.4
|
||||||
|
|
||||||
|
require (
|
||||||
|
github.com/bitfield/script v0.22.1 // indirect
|
||||||
|
github.com/itchyny/gojq v0.12.13 // indirect
|
||||||
|
github.com/itchyny/timefmt-go v0.1.5 // indirect
|
||||||
|
mvdan.cc/sh/v3 v3.7.0 // indirect
|
||||||
|
)
|
8
go.sum
Normal file
8
go.sum
Normal file
|
@ -0,0 +1,8 @@
|
||||||
|
github.com/bitfield/script v0.22.1 h1:DphxoC5ssYciwd0ZS+N0Xae46geAD/0mVWh6a2NUxM4=
|
||||||
|
github.com/bitfield/script v0.22.1/go.mod h1:fv+6x4OzVsRs6qAlc7wiGq8fq1b5orhtQdtW0dwjUHI=
|
||||||
|
github.com/itchyny/gojq v0.12.13 h1:IxyYlHYIlspQHHTE0f3cJF0NKDMfajxViuhBLnHd/QU=
|
||||||
|
github.com/itchyny/gojq v0.12.13/go.mod h1:JzwzAqenfhrPUuwbmEz3nu3JQmFLlQTQMUcOdnu/Sf4=
|
||||||
|
github.com/itchyny/timefmt-go v0.1.5 h1:G0INE2la8S6ru/ZI5JecgyzbbJNs5lG1RcBqa7Jm6GE=
|
||||||
|
github.com/itchyny/timefmt-go v0.1.5/go.mod h1:nEP7L+2YmAbT2kZ2HfSs1d8Xtw9LY8D2stDBckWakZ8=
|
||||||
|
mvdan.cc/sh/v3 v3.7.0 h1:lSTjdP/1xsddtaKfGg7Myu7DnlHItd3/M2tomOcNNBg=
|
||||||
|
mvdan.cc/sh/v3 v3.7.0/go.mod h1:K2gwkaesF/D7av7Kxl0HbF5kGOd2ArupNTX3X44+8l8=
|
22
main.go
Normal file
22
main.go
Normal file
|
@ -0,0 +1,22 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import "log"
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
cfg := readConfig()
|
||||||
|
log.Println("Reading config")
|
||||||
|
|
||||||
|
svc := NewServices(cfg)
|
||||||
|
|
||||||
|
if err := svc.AddPrivateKey(); err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := svc.ConfigureSSH(); err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := svc.PushRepository(); err != nil {
|
||||||
|
log.Fatal(err)
|
||||||
|
}
|
||||||
|
}
|
98
services.go
Normal file
98
services.go
Normal file
|
@ -0,0 +1,98 @@
|
||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bytes"
|
||||||
|
"fmt"
|
||||||
|
"github.com/bitfield/script"
|
||||||
|
"log"
|
||||||
|
"os"
|
||||||
|
"text/template"
|
||||||
|
)
|
||||||
|
|
||||||
|
type Services struct {
|
||||||
|
cfg config
|
||||||
|
}
|
||||||
|
|
||||||
|
func NewServices(cfg config) *Services {
|
||||||
|
return &Services{cfg: cfg}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Services) AddPrivateKey() error {
|
||||||
|
log.Println("Adding private key")
|
||||||
|
|
||||||
|
if err := script.Exec(`mkdir -p $HOME/.ssh`).Error(); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := script.Exec(`chmod 700 $HOME/.ssh`).Error(); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
_, err := script.Echo(s.cfg.PrivateKey).WriteFile(os.ExpandEnv(`${HOME}/.ssh/id_rsa`))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := script.Exec(`chmod -R 400 $HOME/.ssh/.`).Error(); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Services) ConfigureSSH() error {
|
||||||
|
log.Println("Configuring SSH")
|
||||||
|
|
||||||
|
var bfr bytes.Buffer
|
||||||
|
if err := sshConfigTemplate.Execute(&bfr, struct {
|
||||||
|
Cfg config
|
||||||
|
Home string
|
||||||
|
}{
|
||||||
|
Cfg: s.cfg,
|
||||||
|
Home: os.Getenv("HOME"),
|
||||||
|
}); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
if _, err := script.Echo(bfr.String()).WriteFile(os.ExpandEnv(`${HOME}/.ssh/config`)); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
if err := script.Exec(`chmod 400 $HOME/.ssh/config`).Error(); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (s *Services) PushRepository() error {
|
||||||
|
sshUrl := fmt.Sprintf(`dokku@%v`, s.cfg.HostName)
|
||||||
|
remoteUrl := fmt.Sprintf(`ssh://%v:22/%v`, sshUrl, s.cfg.AppName)
|
||||||
|
|
||||||
|
log.Println("Testing Dokku SSH connection")
|
||||||
|
if err := script.Exec(fmt.Sprintf(`ssh %v version`, sshUrl)).Error(); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
log.Println("SSH connection good. Pushing repository")
|
||||||
|
if err := script.Exec(fmt.Sprintf(`git remote add dokku '%v'`, remoteUrl)).Error(); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
if err := script.Exec(`git push dokku main`).Error(); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
var (
|
||||||
|
sshConfigTemplate = template.Must(template.New("ssh-config").Parse(`
|
||||||
|
Host *
|
||||||
|
StrictHostKeyChecking no
|
||||||
|
|
||||||
|
Host {{.Cfg.Host}}
|
||||||
|
HostName {{.Cfg.Host}}
|
||||||
|
User dokku
|
||||||
|
IdentityFile {{.Home}}/.ssh/id_rsa
|
||||||
|
`))
|
||||||
|
)
|
Loading…
Reference in a new issue