diff --git a/cmd/frostfs-adm/internal/modules/morph/frostfsid.go b/cmd/frostfs-adm/internal/modules/morph/frostfsid.go index 79ff0cdd0..a40ba4d4c 100644 --- a/cmd/frostfs-adm/internal/modules/morph/frostfsid.go +++ b/cmd/frostfs-adm/internal/modules/morph/frostfsid.go @@ -16,11 +16,13 @@ import ( ) const ( - namespaceFlag = "namespace" - subjectNameFlag = "subject-name" - subjectKeyFlag = "subject-key" - includeNamesFlag = "include-names" - groupNameFlag = "group-name" + namespaceFlag = "namespace" + subjectNameFlag = "subject-name" + subjectKeyFlag = "subject-key" + subjectAddressFlag = "subject-address" + includeNamesFlag = "include-names" + groupNameFlag = "group-name" + groupIDFlag = "group-id" ) var ( @@ -108,6 +110,36 @@ var ( }, Run: frostfsidListGroups, } + + frostfsidAddSubjectToGroupCmd = &cobra.Command{ + Use: "add-subject-to-group", + Short: "Add subject to group", + PreRun: func(cmd *cobra.Command, _ []string) { + _ = viper.BindPFlag(alphabetWalletsFlag, cmd.Flags().Lookup(alphabetWalletsFlag)) + _ = viper.BindPFlag(endpointFlag, cmd.Flags().Lookup(endpointFlag)) + }, + Run: frostfsidAddSubjectToGroup, + } + + frostfsidRemoveSubjectFromGroupCmd = &cobra.Command{ + Use: "remove-subject-from-group", + Short: "Remove subject from group", + PreRun: func(cmd *cobra.Command, _ []string) { + _ = viper.BindPFlag(alphabetWalletsFlag, cmd.Flags().Lookup(alphabetWalletsFlag)) + _ = viper.BindPFlag(endpointFlag, cmd.Flags().Lookup(endpointFlag)) + }, + Run: frostfsidRemoveSubjectFromGroup, + } + + frostfsidListGroupSubjectsCmd = &cobra.Command{ + Use: "list-group-subjects", + Short: "List subjects in group", + PreRun: func(cmd *cobra.Command, _ []string) { + _ = viper.BindPFlag(alphabetWalletsFlag, cmd.Flags().Lookup(alphabetWalletsFlag)) + _ = viper.BindPFlag(endpointFlag, cmd.Flags().Lookup(endpointFlag)) + }, + Run: frostfsidListGroupSubjects, + } ) func initFrostfsIDCreateNamespaceCmd() { @@ -162,6 +194,28 @@ func initFrostfsIDListGroupsCmd() { frostfsidListGroupsCmd.Flags().String(namespaceFlag, "", "Namespace to list groups") } +func initFrostfsIDAddSubjectToGroupCmd() { + frostfsidCmd.AddCommand(frostfsidAddSubjectToGroupCmd) + frostfsidAddSubjectToGroupCmd.Flags().StringP(endpointFlag, endpointFlagShort, "", endpointFlagDesc) + frostfsidAddSubjectToGroupCmd.Flags().String(subjectAddressFlag, "", "Subject address") + frostfsidAddSubjectToGroupCmd.Flags().Int64(groupIDFlag, 0, "Group id") +} + +func initFrostfsIDRemoveSubjectFromGroupCmd() { + frostfsidCmd.AddCommand(frostfsidRemoveSubjectFromGroupCmd) + frostfsidRemoveSubjectFromGroupCmd.Flags().StringP(endpointFlag, endpointFlagShort, "", endpointFlagDesc) + frostfsidRemoveSubjectFromGroupCmd.Flags().String(subjectAddressFlag, "", "Subject address") + frostfsidRemoveSubjectFromGroupCmd.Flags().Int64(groupIDFlag, 0, "Group id") +} + +func initFrostfsIDListGroupSubjectsCmd() { + frostfsidCmd.AddCommand(frostfsidListGroupSubjectsCmd) + frostfsidListGroupSubjectsCmd.Flags().StringP(endpointFlag, endpointFlagShort, "", endpointFlagDesc) + frostfsidListGroupSubjectsCmd.Flags().String(namespaceFlag, "", "Namespace name") + frostfsidListGroupSubjectsCmd.Flags().Int64(groupIDFlag, 0, "Group id") + frostfsidListGroupSubjectsCmd.Flags().Bool(includeNamesFlag, false, "Whether include subject name (require additional requests)") +} + type ffsidMethodArgs struct { name string args []any @@ -277,6 +331,48 @@ func frostfsidListGroups(cmd *cobra.Command, _ []string) { } } +func frostfsidAddSubjectToGroup(cmd *cobra.Command, _ []string) { + subjectAddress := getFrostfsIDSubjectAddress(cmd) + groupID, _ := cmd.Flags().GetInt64(groupIDFlag) + + err := sendFrostfsIDTx(cmd, ffsidMethodArgs{name: "addSubjectToGroup", args: []any{subjectAddress, groupID}}) + commonCmd.ExitOnErr(cmd, "add subject to namespace error: %w", err) +} + +func frostfsidRemoveSubjectFromGroup(cmd *cobra.Command, _ []string) { + subjectAddress := getFrostfsIDSubjectAddress(cmd) + groupID, _ := cmd.Flags().GetInt64(groupIDFlag) + + err := sendFrostfsIDTx(cmd, ffsidMethodArgs{name: "removeSubjectFromGroup", args: []any{subjectAddress, groupID}}) + commonCmd.ExitOnErr(cmd, "remove subject to namespace error: %w", err) +} + +func frostfsidListGroupSubjects(cmd *cobra.Command, _ []string) { + ns, _ := cmd.Flags().GetString(namespaceFlag) + groupID, _ := cmd.Flags().GetInt64(groupIDFlag) + includeNames, _ := cmd.Flags().GetBool(includeNamesFlag) + + ffsid, err := frostfsIDClient(cmd) + commonCmd.ExitOnErr(cmd, "init contract client: %w", err) + + subjects, err := ffsid.ListGroupSubjects(ns, groupID) + commonCmd.ExitOnErr(cmd, "list group subjects: %w", err) + + sort.Slice(subjects, func(i, j int) bool { return subjects[i].Less(subjects[j]) }) + + for _, subjAddr := range subjects { + if !includeNames { + cmd.Println(address.Uint160ToString(subjAddr)) + continue + } + + subj, err := ffsid.GetSubject(subjAddr) + commonCmd.ExitOnErr(cmd, "get subject: %w", err) + + cmd.Printf("%s (%s)\n", address.Uint160ToString(subjAddr), subj.Name) + } +} + func sendFrostfsIDTx(cmd *cobra.Command, methodArgs ...ffsidMethodArgs) error { wCtx, err := newInitializeContext(cmd, viper.GetViper()) if err != nil { diff --git a/cmd/frostfs-adm/internal/modules/morph/frostfsid_util.go b/cmd/frostfs-adm/internal/modules/morph/frostfsid_util.go index 529d98dde..dc7e581eb 100644 --- a/cmd/frostfs-adm/internal/modules/morph/frostfsid_util.go +++ b/cmd/frostfs-adm/internal/modules/morph/frostfsid_util.go @@ -41,20 +41,9 @@ func getFrostfsIDSubjectKey(cmd *cobra.Command) *keys.PublicKey { return subjKey } -//func decodeFrostfsIDNamespaces(resStack []stackitem.Item) ([]string, error) { -// var res []string -// -// if len(resStack) == 0 { -// return res, nil -// } -// -// if len(resStack) > 0 { -// nodes, err := decodeNodeList(resStack[0]) -// if err != nil { -// return nil, err -// } -// -// nm.SetNodes(nodes) -// } -// -//} +func getFrostfsIDSubjectAddress(cmd *cobra.Command) util.Uint160 { + subjAddress, _ := cmd.Flags().GetString(subjectAddressFlag) + subjAddr, err := address.StringToUint160(subjAddress) + commonCmd.ExitOnErr(cmd, "invalid subject address: %w", err) + return subjAddr +} diff --git a/cmd/frostfs-adm/internal/modules/morph/root.go b/cmd/frostfs-adm/internal/modules/morph/root.go index 6db262175..600fe21c8 100644 --- a/cmd/frostfs-adm/internal/modules/morph/root.go +++ b/cmd/frostfs-adm/internal/modules/morph/root.go @@ -303,6 +303,9 @@ func init() { initFrostfsIDCreateGroupCmd() initFrostfsIDDeleteGroupCmd() initFrostfsIDListGroupsCmd() + initFrostfsIDAddSubjectToGroupCmd() + initFrostfsIDRemoveSubjectFromGroupCmd() + initFrostfsIDListGroupSubjectsCmd() } func initProxyAddAccount() {