diff --git a/internal/command/command.go b/internal/command/command.go index 4d0f627e8..ebbc60df7 100644 --- a/internal/command/command.go +++ b/internal/command/command.go @@ -34,8 +34,6 @@ import ( "sync" "time" - "github.com/onflow/flow-cli/internal/prompt" - "github.com/coreos/go-semver/semver" "github.com/dukex/mixpanel" "github.com/getsentry/sentry-go" @@ -43,11 +41,14 @@ import ( "github.com/spf13/cobra" "github.com/onflow/flowkit/v2" + "github.com/onflow/flowkit/v2/accounts" "github.com/onflow/flowkit/v2/config" "github.com/onflow/flowkit/v2/gateway" "github.com/onflow/flowkit/v2/output" "github.com/onflow/flow-cli/build" + "github.com/onflow/flow-cli/common/branding" + "github.com/onflow/flow-cli/internal/prompt" "github.com/onflow/flow-cli/internal/settings" "github.com/onflow/flow-cli/internal/util" ) @@ -131,6 +132,9 @@ func (c Command) AddToParent(parent *cobra.Command) { checkVersion(logger) } + // warn about inline keys in config + checkForInlineKeys(state, logger) + // record command usage wg := sync.WaitGroup{} go UsageMetrics(c.Cmd, &wg) @@ -328,6 +332,33 @@ func isDevelopment() bool { return build.Semver() == "undefined" } +// checkForInlineKeys warns users if they have accounts with inline private keys in flow.json +func checkForInlineKeys(state *flowkit.State, logger output.Logger) { + if state == nil { + return + } + + var inlineKeyAccounts []string + for _, account := range *state.Accounts() { + if _, isHexKey := account.Key.(*accounts.HexKey); isHexKey { + inlineKeyAccounts = append(inlineKeyAccounts, account.Name) + } + } + + if len(inlineKeyAccounts) > 0 { + cmd := branding.GreenStyle.Render("flow config extract-key --all") + logger.Info(fmt.Sprintf( + "\n%s Security warning: %d account(s) have private keys stored directly in flow.json: %s\n"+ + " Extract them to separate key files by running: %s\n"+ + " Learn more: https://developers.flow.com/build/tools/flow-cli/flow.json/security\n", + output.WarningEmoji(), + len(inlineKeyAccounts), + strings.Join(inlineKeyAccounts, ", "), + cmd, + )) + } +} + // initCrashReporting set-ups sentry as crash reporting tool, it also sets listener for panics // and asks before sending the error for a permission to do so from the user. func initCrashReporting() {