Skip to content

Commit

Permalink
feat: implemented apps addition
Browse files Browse the repository at this point in the history
  • Loading branch information
DeeStarks committed Aug 9, 2022
1 parent 86f7862 commit d97128e
Show file tree
Hide file tree
Showing 6 changed files with 135 additions and 13 deletions.
72 changes: 68 additions & 4 deletions app/cli/apps.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package cli

import (
"database/sql"
"encoding/json"
"fmt"
"os"
"strings"
Expand All @@ -10,6 +11,7 @@ import (
"github.com/DeeStarks/conoid/domain/ports"
"github.com/DeeStarks/conoid/utils"
"github.com/aquasecurity/table"
"github.com/google/uuid"
)

type AppCommand struct {
Expand Down Expand Up @@ -51,6 +53,8 @@ func (ac *AppCommand) ListRunning() {
for _, p := range processes {
created_at := utils.TimeAgo(p.CreatedAt, time.Now().Unix())
listeners := strings.Join(p.Listeners, ", ")

// Handle booleans
tunnelled := "False"
if p.Tunnelled {
tunnelled = "True"
Expand All @@ -70,7 +74,7 @@ func (ac *AppCommand) ListAll() {
domainPort := port.NewDomainPort(ac.defaultDB)
processes, err := domainPort.AppProcesses().RetrieveAll()
if err != nil {
fmt.Println("Error retrieve apps:", err)
fmt.Println("Error retrieving apps:", err)
return
}

Expand All @@ -82,13 +86,19 @@ func (ac *AppCommand) ListAll() {
for _, p := range processes {
created_at := utils.TimeAgo(p.CreatedAt, time.Now().Unix())
listeners := strings.Join(p.Listeners, ", ")

// Handle booleans
tunnelled := "False"
if p.Tunnelled {
tunnelled = "True"
}
status := "Stopped"
if p.Status {
status = "Running"
}

t.AddRow(
string(p.Pid), p.Name, p.Status, p.Type, listeners, p.RootDirectory,
string(p.Pid), p.Name, status, p.Type, listeners, p.RootDirectory,
p.ClientAddress, tunnelled, created_at,
)
}
Expand All @@ -110,12 +120,66 @@ func (ac *AppCommand) Add(filepath string) {
fmt.Println("Error deserializing configuration file:", err)
return
}

// Vallidate configuration
validatedConf, err := utils.ValidateConf(conf)
if err != nil {
fmt.Println("Invalid configuration file:", err)
return
}
fmt.Println(validatedConf)

// Ensure app doesn't already exist
domainPort := port.NewDomainPort(ac.defaultDB)
processes, err := domainPort.AppProcesses().RetrieveAll()
if err != nil {
fmt.Println("Could not add app:", err)
return
}

// Check processes' names
for _, p := range processes {
if p.Name == validatedConf.Name {
fmt.Printf("Could not add app: an app with name \"%s\" already exists\n", validatedConf.Name)
return
}
}

// Convert the configurations to a map type
// First, to json
jsondata, err := json.Marshal(validatedConf)
if err != nil {
fmt.Println("Could not add app:", err)
return
}
// Now, to map
var mapConf map[string]interface{}
json.Unmarshal(jsondata, &mapConf)

// Change the "tunnelled" field from boolean type to int
if mapConf["tunnelled"].(bool) {
mapConf["tunnelled"] = 1
} else {
mapConf["tunnelled"] = 0
}

// Join the "listeners" slice and save in the database as string type
if s, ok := mapConf["listeners"].([]interface{}); ok {
ss := make([]string, len(s))
for i, v := range s {
ss[i] = fmt.Sprintf("%v", v)
}
mapConf["listeners"] = strings.Join(ss, ", ")
}

// Generate pid, status, and created at
mapConf["pid"] = strings.ReplaceAll(uuid.New().String(), "-", "") // Stripping hyphens
mapConf["status"] = 1
mapConf["created_at"] = time.Now().Unix()

_, err = domainPort.AppProcesses().Create(mapConf)
if err != nil {
fmt.Println("Could not add app:", err)
return
}
fmt.Println("Your app was successfully added. Restart conoid to start accepting request")
}
1 change: 1 addition & 0 deletions domain/ports/processes_port.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import (
type ProcessesPort interface {
RetrieveRunning() ([]repository.AppProcessModel, error)
RetrieveAll() ([]repository.AppProcessModel, error)
Create(map[string]interface{}) (repository.AppProcessModel, error)
}

func (p DomainPort) AppProcesses() ProcessesPort {
Expand Down
70 changes: 62 additions & 8 deletions domain/repository/processes.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,17 @@ package repository

import (
"database/sql"
"fmt"
"reflect"
"strings"

"github.com/DeeStarks/conoid/utils"
)

type AppProcessModel struct {
Pid string
Name string
Status string
Status bool
Type string
Listeners []string
RootDirectory string
Expand All @@ -27,7 +31,7 @@ func (p AppProcess) RetrieveRunning() ([]AppProcessModel, error) {
SELECT
pid, name, status, type, listeners,
root_directory, client_address, tunnelled, created_at
FROM processes WHERE status="running"
FROM processes WHERE status=1
`)
if err != nil {
return nil, err
Expand All @@ -37,20 +41,25 @@ func (p AppProcess) RetrieveRunning() ([]AppProcessModel, error) {
var processes []AppProcessModel
for rows.Next() {
var process AppProcessModel
var listeners string

// Handle null values
var listeners, root_directory, client_address sql.NullString

err = rows.Scan(
&process.Pid, &process.Name, &process.Status, &process.Type,
&listeners, &process.RootDirectory, &process.ClientAddress,
&listeners, &root_directory, &client_address,
&process.Tunnelled, &process.CreatedAt,
)
if err != nil {
return nil, err
}

process.RootDirectory = root_directory.String
process.ClientAddress = client_address.String
// Listeners are stored in the db as strings separated by comma
// we'll split that into slice
process.Listeners = strings.Split(listeners, ",")
process.Listeners = strings.Split(listeners.String, ", ")

// Append the process to list of processes
processes = append(processes, process)
}
Expand All @@ -73,22 +82,67 @@ func (p AppProcess) RetrieveAll() ([]AppProcessModel, error) {
var processes []AppProcessModel
for rows.Next() {
var process AppProcessModel
var listeners string

// Handle null values
var listeners, root_directory, client_address sql.NullString

err = rows.Scan(
&process.Pid, &process.Name, &process.Status, &process.Type,
&listeners, &process.RootDirectory, &process.ClientAddress,
&listeners, &root_directory, &client_address,
&process.Tunnelled, &process.CreatedAt,
)
if err != nil {
return nil, err
}

process.RootDirectory = root_directory.String
process.ClientAddress = client_address.String
// Listeners are stored in the db as strings separated by comma
// we'll split that into slice
process.Listeners = strings.Split(listeners, ",")
process.Listeners = strings.Split(listeners.String, ", ")

// Append the process to list of processes
processes = append(processes, process)
}
return processes, nil
}

func (p AppProcess) Create(data map[string]interface{}) (AppProcessModel, error) {
var process AppProcessModel

// Get keys and values
refKeys := reflect.ValueOf(data).MapKeys()
keys := make([]string, len(refKeys))
values := make([]interface{}, len(refKeys))
for i, k := range refKeys {
keys[i] = k.String()
values[i] = data[k.String()]
}

// Execute query
query := fmt.Sprintf(`
INSERT INTO processes ( %s ) VALUES ( %s )
RETURNING pid, name, status, type, listeners,
root_directory, client_address, tunnelled, created_at
`, strings.Join(keys, ", "), utils.GeneratePlaceholders(len(keys)))

// Handle null values
var listeners, root_directory, client_address sql.NullString
err := p.DB.QueryRow(query, values...).Scan(
&process.Pid, &process.Name, &process.Status, &process.Type,
&listeners, &root_directory, &client_address,
&process.Tunnelled, &process.CreatedAt,
)
if err != nil {
return AppProcessModel{}, err
}

process.RootDirectory = root_directory.String
process.ClientAddress = client_address.String
// Listeners are stored in the db as strings separated by comma
// we'll split that into slice
process.Listeners = strings.Split(listeners.String, ", ")

// Return result
return process, nil
}
2 changes: 1 addition & 1 deletion domain/schemas/default.sql
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
CREATE TABLE processes (
pid TEXT NOT NULL PRIMARY KEY,
name TEXT NOT NULL,
status TEXT NOT NULL,
status INTEGER NOT NULL,
type TEXT NOT NULL,
listeners TEXT,
root_directory TEXT,
Expand Down
1 change: 1 addition & 0 deletions go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ go 1.17

require (
github.com/aquasecurity/table v1.7.2
github.com/google/uuid v1.3.0
github.com/mattn/go-sqlite3 v1.14.14
github.com/spf13/cobra v1.5.0
gopkg.in/yaml.v3 v3.0.1
Expand Down
2 changes: 2 additions & 0 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@ github.com/cpuguy83/go-md2man/v2 v2.0.2/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46t
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/google/uuid v1.3.0 h1:t6JiXgmwXMjEs8VusXIJk2BXHsn+wx8BZdTaoZ5fu7I=
github.com/google/uuid v1.3.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
github.com/inconshreveable/mousetrap v1.0.0 h1:Z8tu5sraLXCXIcARxBp/8cbvlwVa7Z1NHg9XEKhtSvM=
github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8=
github.com/mattn/go-runewidth v0.0.13 h1:lTGmDsbAYt5DmK6OnoV7EuIF1wEIFAcxld6ypU4OSgU=
Expand Down

0 comments on commit d97128e

Please sign in to comment.