github.com/prysmaticlabs/prysm@v1.4.4/validator/slashing-protection/cli_export.go (about) 1 package slashingprotection 2 3 import ( 4 "encoding/json" 5 "path/filepath" 6 7 "github.com/pkg/errors" 8 "github.com/prysmaticlabs/prysm/cmd/validator/flags" 9 "github.com/prysmaticlabs/prysm/shared/cmd" 10 "github.com/prysmaticlabs/prysm/shared/fileutil" 11 "github.com/prysmaticlabs/prysm/validator/accounts/prompt" 12 "github.com/prysmaticlabs/prysm/validator/db/kv" 13 export "github.com/prysmaticlabs/prysm/validator/slashing-protection/local/standard-protection-format" 14 "github.com/urfave/cli/v2" 15 ) 16 17 const ( 18 jsonExportFileName = "slashing_protection.json" 19 ) 20 21 // ExportSlashingProtectionJSONCli extracts a validator's slashing protection 22 // history from their database and formats it into an EIP-3076 standard JSON 23 // file via a CLI entrypoint to make it easy to migrate machines or Ethereum consensus clients. 24 // 25 // Steps: 26 // 1. Parse a path to the validator's datadir from the CLI context. 27 // 2. Open the validator database. 28 // 3. Call the function which actually exports the data from 29 // from the validator's db into an EIP standard slashing protection format 30 // 4. Format and save the JSON file to a user's specified output directory. 31 func ExportSlashingProtectionJSONCli(cliCtx *cli.Context) error { 32 var err error 33 dataDir := cliCtx.String(cmd.DataDirFlag.Name) 34 if !cliCtx.IsSet(cmd.DataDirFlag.Name) { 35 dataDir, err = prompt.InputDirectory(cliCtx, prompt.DataDirDirPromptText, cmd.DataDirFlag) 36 if err != nil { 37 return err 38 } 39 } 40 41 // ensure that the validator.db is found under the specified dir or its subdirectories 42 found, _, err := fileutil.RecursiveFileFind(kv.ProtectionDbFileName, dataDir) 43 if err != nil { 44 return errors.Wrapf(err, "error finding validator database at path %s", dataDir) 45 } 46 if !found { 47 return errors.Wrapf(err, "validator database not found at path %s", dataDir) 48 } 49 50 validatorDB, err := kv.NewKVStore(cliCtx.Context, dataDir, &kv.Config{}) 51 if err != nil { 52 return errors.Wrapf(err, "could not access validator database at path %s", dataDir) 53 } 54 defer func() { 55 if err := validatorDB.Close(); err != nil { 56 log.WithError(err).Errorf("Could not close validator DB") 57 } 58 }() 59 eipJSON, err := export.ExportStandardProtectionJSON(cliCtx.Context, validatorDB) 60 if err != nil { 61 return errors.Wrap(err, "could not export slashing protection history") 62 } 63 outputDir, err := prompt.InputDirectory( 64 cliCtx, 65 "Enter your desired output directory for your slashing protection history", 66 flags.SlashingProtectionExportDirFlag, 67 ) 68 if err != nil { 69 return errors.Wrap(err, "could not get slashing protection json file") 70 } 71 if outputDir == "" { 72 return errors.New("output directory not specified") 73 } 74 exists, err := fileutil.HasDir(outputDir) 75 if err != nil { 76 return errors.Wrapf(err, "could not check if output directory %s already exists", outputDir) 77 } 78 if !exists { 79 if err := fileutil.MkdirAll(outputDir); err != nil { 80 return errors.Wrapf(err, "could not create output directory %s", outputDir) 81 } 82 } 83 outputFilePath := filepath.Join(outputDir, jsonExportFileName) 84 encoded, err := json.MarshalIndent(eipJSON, "", "\t") 85 if err != nil { 86 return errors.Wrap(err, "could not JSON marshal slashing protection history") 87 } 88 return fileutil.WriteFile(outputFilePath, encoded) 89 }