Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 0 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@


.DS_Store
.vscode
ff/ff
dist/
*.iml
Expand Down
29 changes: 29 additions & 0 deletions .vscode/launch.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
{
"version": "0.2.0",
"configurations": [
{
"name": "Debug init mode",
"type": "go",
"request": "launch",
"mode": "debug",
"program": "ff/main.go",
"args": ["init", "ethereum", "dev", "2"]
},
{
"name": "Debug remove mode",
"type": "go",
"request": "launch",
"mode": "debug",
"program": "ff/main.go",
"args": ["remove", "dev", "--force"]
},
{
"name": "Debug start mode",
"type": "go",
"request": "launch",
"mode": "debug",
"program": "ff/main.go",
"args": ["start", "dev"]
},
]
}
18 changes: 16 additions & 2 deletions cmd/init_ethereum.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ import (

"github.com/spf13/cobra"

"github.com/hyperledger/firefly-cli/internal/docker"
"github.com/hyperledger/firefly-cli/internal/log"
"github.com/hyperledger/firefly-cli/internal/stacks"
"github.com/hyperledger/firefly-cli/pkg/types"
Expand All @@ -37,14 +38,27 @@ var initEthereumCmd = &cobra.Command{
RunE: func(cmd *cobra.Command, args []string) error {
ctx := log.WithVerbosity(context.Background(), verbose)
ctx = log.WithLogger(ctx, logger)
version, err := docker.CheckDockerConfig()
if err != nil {
return err
}
// Needs this context for cleaning up as part of Remove Stack
// If an error occurs as part of init
ctx = context.WithValue(ctx, docker.CtxComposeVersionKey{}, version)

stackManager := stacks.NewStackManager(ctx)
if err := initCommon(args); err != nil {
return err
}
if err := stackManager.InitStack(&initOptions); err != nil {
if err := stackManager.RemoveStack(); err != nil {
return err
verr := stackManager.RemoveStack()

// log the remove error if present
if verr != nil {
l := log.LoggerFromContext(ctx)
l.Info(fmt.Sprintf("Error whilst removing the stack: %s", verr.Error()))
}
// return the init error to not hide the issue
return err
}
fmt.Printf("Stack '%s' created!\nTo start your new stack run:\n\n%s start %s\n", initOptions.StackName, rootCmd.Use, initOptions.StackName)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import (
"fmt"
"os"
"path/filepath"
"runtime"
"strings"

"github.com/hyperledger/firefly-cli/internal/docker"
Expand Down Expand Up @@ -54,7 +55,15 @@ func CreateTesseraKeys(ctx context.Context, image, outputDirectory, prefix, name
return "", "", "", err
}
fmt.Println("generating tessera keys")
err = docker.RunDockerCommand(ctx, outputDirectory, "run", "--rm", "-v", fmt.Sprintf("%s:/keystore", outputDirectory), image, "-keygen", "-filename", fmt.Sprintf("/keystore/%s", filename))
args := []string{"run"}
// Order of args matter and platform argument needs
// to be early in the list
if runtime.GOARCH == "arm64" {
args = append(args, "--platform", "linux/amd64")
}
args = append(args, "--rm", "-v", fmt.Sprintf("%s:/keystore", outputDirectory), image, "-keygen", "-filename", fmt.Sprintf("/keystore/%s", filename))

err = docker.RunDockerCommand(ctx, outputDirectory, args...)
if err != nil {
return "", "", "", err
}
Expand Down
20 changes: 18 additions & 2 deletions internal/blockchain/ethereum/quorum/quorum_provider.go
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ import (
"os"
"path"
"path/filepath"
"runtime"
"strconv"
"time"

Expand Down Expand Up @@ -246,7 +247,7 @@ func (p *QuorumProvider) GetDockerServiceDefinitions() []*docker.ServiceDefiniti
for i := 0; i < memberCount; i++ {
var quorumDependsOn map[string]map[string]string
if !p.stack.PrivateTransactionManager.Equals(types.PrivateTransactionManagerNone) {
quorumDependsOn = map[string]map[string]string{fmt.Sprintf("tessera_%d", i): {"condition": "service_started"}}
quorumDependsOn = map[string]map[string]string{fmt.Sprintf("tessera_%d", i): {"condition": "service_healthy"}}
serviceDefinitions[i+memberCount] = &docker.ServiceDefinition{
ServiceName: fmt.Sprintf("tessera_%d", i),
Service: &docker.Service{
Expand All @@ -257,10 +258,25 @@ func (p *QuorumProvider) GetDockerServiceDefinitions() []*docker.ServiceDefiniti
Ports: []string{fmt.Sprintf("%d:%s", p.stack.ExposedPtmPort+(i*ExposedBlockchainPortMultiplier), TmTpPort)}, // defaults 4100, 4110, 4120, 4130
Environment: p.stack.EnvironmentVars,
EntryPoint: []string{"/bin/sh", "-c", "/data/docker-entrypoint.sh"},
Deploy: map[string]interface{}{"restart_policy": map[string]string{"condition": "on-failure", "max_attempts": "3"}},
Deploy: map[string]interface{}{"restart_policy": map[string]interface{}{"condition": "on-failure", "max_attempts": int64(3)}},
HealthCheck: &docker.HealthCheck{
Test: []string{
"CMD",
"curl",
"--fail",
fmt.Sprintf("http://localhost:%s/upcheck", TmTpPort),
},
Interval: "15s", // 6000 requests in a day
Retries: 30,
},
},
VolumeNames: []string{fmt.Sprintf("tessera_%d", i)},
}

// No arm64 images for Tessera
if runtime.GOARCH == "arm64" {
serviceDefinitions[i+memberCount].Service.Platform = "linux/amd64"
}
}
serviceDefinitions[i] = &docker.ServiceDefinition{
ServiceName: fmt.Sprintf("quorum_%d", i),
Expand Down
3 changes: 2 additions & 1 deletion internal/docker/docker_config.go
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,7 @@ type Service struct {
EnvFile string `yaml:"env_file,omitempty"`
Expose []int `yaml:"expose,omitempty"`
Deploy map[string]interface{} `yaml:"deploy,omitempty"`
Platform string `yaml:"platform,omitempty"`
}

type DockerComposeConfig struct {
Expand All @@ -79,7 +80,7 @@ var StandardLogOptions = &LoggingConfig{

func CreateDockerCompose(s *types.Stack) *DockerComposeConfig {
compose := &DockerComposeConfig{
Version: "2.1",
Version: "2.4",
Services: make(map[string]*Service),
Volumes: make(map[string]struct{}),
}
Expand Down
12 changes: 11 additions & 1 deletion internal/stacks/stack_manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ import (
"os/exec"
"path"
"path/filepath"
"runtime"
"strconv"
"strings"
"sync"
Expand Down Expand Up @@ -65,6 +66,10 @@ type StackManager struct {
once sync.Once
}

var unsupportedARM64Images map[string]bool = map[string]bool{
"quorumengineering/tessera:24.4": true,
}

func ListStacks() ([]string, error) {
files, err := os.ReadDir(constants.StacksDir)
if err != nil {
Expand Down Expand Up @@ -214,6 +219,7 @@ func (s *StackManager) runDockerComposeCommand(command ...string) error {
return err
}
}
return err
}
return docker.RunDockerComposeCommand(s.ctx, s.Stack.StackDir, command...)
}
Expand Down Expand Up @@ -696,7 +702,11 @@ func (s *StackManager) PullStack(options *types.PullOptions) error {
for _, image := range images {
if _, ok := hasPulled[image]; !ok {
s.Log.Info(fmt.Sprintf("pulling '%s'", image))
if err := docker.RunDockerCommandRetry(s.ctx, s.Stack.InitDir, options.Retries, "pull", image); err != nil {
args := []string{"pull", image}
if unsupportedARM64Images[image] && runtime.GOARCH == "arm64" {
args = append(args, "--platform=linux/amd64")
}
if err := docker.RunDockerCommandRetry(s.ctx, s.Stack.InitDir, options.Retries, args[0:]...); err != nil {
return err
} else {
hasPulled[image] = true
Expand Down