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
98 changes: 2 additions & 96 deletions cli/cmd/get.go
Original file line number Diff line number Diff line change
@@ -1,16 +1,7 @@
package cmd

import (
"fmt"

"github.com/spf13/cobra"
"google.golang.org/grpc"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/credentials/insecure"
"google.golang.org/grpc/status"

"github.com/openkcm/krypton/cli/output"
"github.com/openkcm/krypton/pkg/api/v1/proto/admin"
)

func getCmd() *cobra.Command {
Expand All @@ -21,93 +12,8 @@ func getCmd() *cobra.Command {

cmd.AddCommand(getTenantCmd())
cmd.AddCommand(getTenantsCmd())

return cmd
}

func getTenantCmd() *cobra.Command {
var asJSON bool

cmd := &cobra.Command{
Use: "tenant <id>",
Short: "Get a tenant by ID",
Args: cobra.ExactArgs(1),
RunE: func(cmd *cobra.Command, args []string) error {
// TODO: insecure.NewCredentials is a temporary workaround until TLS is configured
conn, err := grpc.NewClient(
serverAddr,
grpc.WithTransportCredentials(insecure.NewCredentials()),
)
if err != nil {
return fmt.Errorf("failed to connect: %w", err)
}
defer conn.Close()

client := admin.NewTenantServiceClient(conn)

resp, err := client.GetTenant(cmd.Context(), &admin.GetTenantRequest{
Id: args[0],
})
if err != nil {
if st, ok := status.FromError(err); ok && st.Code() == codes.NotFound {
return fmt.Errorf("tenant %q not found", args[0])
}
return fmt.Errorf("failed to get tenant: %w", err)
}

tenant := admin.TenantFromProto(resp.GetTenant())

builder, err := output.From(tenant)
if err != nil {
return fmt.Errorf("failed to format output: %w", err)
}

return formatOutput(builder, asJSON).To(cmd.OutOrStdout())
},
}

cmd.Flags().BoolVar(&asJSON, "json", false, "output in JSON format")

return cmd
}

func getTenantsCmd() *cobra.Command {
var asJSON bool

cmd := &cobra.Command{
Use: "tenants",
Short: "Get tenants",
Args: cobra.NoArgs,
RunE: func(cmd *cobra.Command, args []string) error {
// TODO: insecure.NewCredentials is a temporary workaround until TLS is configured
conn, err := grpc.NewClient(
serverAddr,
grpc.WithTransportCredentials(insecure.NewCredentials()),
)
if err != nil {
return fmt.Errorf("failed to connect: %w", err)
}
defer conn.Close()

client := admin.NewTenantServiceClient(conn)

resp, err := client.ListTenants(cmd.Context(), &admin.ListTenantsRequest{})
if err != nil {
return fmt.Errorf("failed to list tenants: %w", err)
}

tenants := admin.TenantsFromProto(resp.GetTenants())

builder, err := output.From(tenants)
if err != nil {
return fmt.Errorf("failed to format output: %w", err)
}

return formatOutput(builder, asJSON).To(cmd.OutOrStdout())
},
}

cmd.Flags().BoolVar(&asJSON, "json", false, "output in JSON format")
cmd.AddCommand(getKeyParentsCmd())
cmd.AddCommand(getKeyDescendantsCmd())

return cmd
}
159 changes: 159 additions & 0 deletions cli/cmd/key.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,159 @@
package cmd

import (
"fmt"

"github.com/spf13/cobra"
"google.golang.org/grpc"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/credentials/insecure"
"google.golang.org/grpc/status"

"github.com/openkcm/krypton/cli/output"
"github.com/openkcm/krypton/pkg/api/v1/proto/admin"
)

type keyTreeRow struct {
Kind string
ID string
ParentID string
Name string
ManagedBy string
Status string
}

func newKeyTreeRow(k *admin.Key) keyTreeRow {
return keyTreeRow{
Kind: k.GetKind(),
ID: k.GetId(),
ParentID: k.GetParentId(),
Name: k.GetName(),
ManagedBy: k.GetManagedBy(),
Status: k.GetKeyProcessingState().GetStatus(),
}
}

func getKeyParentsCmd() *cobra.Command {
var keyID, tenantID string
var asJSON bool

cmd := &cobra.Command{
Use: "parent-keys",
Short: "Get parent keys by tenant & key ID",
Args: cobra.NoArgs,
RunE: func(cmd *cobra.Command, args []string) error {
// TODO: insecure.NewCredentials is a temporary workaround until TLS is configured
conn, err := grpc.NewClient(
serverAddr,
grpc.WithTransportCredentials(insecure.NewCredentials()),
)
if err != nil {
return fmt.Errorf("failed to connect: %w", err)
}
defer conn.Close()

client := admin.NewKeyServiceClient(conn)

resp, err := client.GetParentKeys(cmd.Context(), &admin.GetParentKeysRequest{
Id: keyID,
TenantId: tenantID,
})
if err != nil {
if st, ok := status.FromError(err); ok && st.Code() == codes.NotFound {
return fmt.Errorf("parent keys for tenant:[%s] and key:[%s] not found", tenantID, keyID)
}
return fmt.Errorf("failed to get parent keys: %w", err)
}

ks := resp.GetKeys()
treeRows := make([]keyTreeRow, 0, len(ks))
for _, k := range ks {
treeRows = append(treeRows, newKeyTreeRow(k))
}

builder, err := output.From(treeRows)
if err != nil {
return fmt.Errorf("failed to format output: %w", err)
}

return formatOutput(builder, asJSON).To(cmd.OutOrStdout())
},
}

cmd.Flags().StringVar(&keyID, "key-id", "", "id of the key")
cmd.Flags().StringVar(&tenantID, "tenant-id", "", "id of the tenant")
cmd.Flags().BoolVar(&asJSON, "json", false, "output in JSON format")
_ = cmd.MarkFlagRequired("key-id")
_ = cmd.MarkFlagRequired("tenant-id")

return cmd
}

func getKeyDescendantsCmd() *cobra.Command {
var keyID, tenantID string
var asJSON bool

cmd := &cobra.Command{
Use: "descendant-keys",
Short: "Get descendants by key & tenant ID",
Args: cobra.NoArgs,
RunE: func(cmd *cobra.Command, args []string) error {
// TODO: insecure.NewCredentials is a temporary workaround until TLS is configured
conn, err := grpc.NewClient(
serverAddr,
grpc.WithTransportCredentials(insecure.NewCredentials()),
)
if err != nil {
return fmt.Errorf("failed to connect: %w", err)
}
defer conn.Close()

client := admin.NewKeyServiceClient(conn)

resp, err := client.GetDescendantKeys(cmd.Context(), &admin.GetDescendantKeysRequest{
Id: keyID,
TenantId: tenantID,
})
if err != nil {
if st, ok := status.FromError(err); ok && st.Code() == codes.NotFound {
return fmt.Errorf("descendant keys for tenant:[%s] and key:[%s] not found", tenantID, keyID)
}
return fmt.Errorf("failed to get descendant keys: %w", err)
}

totalLen := 0
trees := resp.GetKeyTree()
for i := range trees {
totalLen += len(trees[i].GetKeys())
if !asJSON {
totalLen++
}
}

treeRows := make([]keyTreeRow, 0, totalLen)
for _, tree := range trees {
for _, k := range tree.GetKeys() {
treeRows = append(treeRows, newKeyTreeRow(k))
}
if !asJSON {
treeRows = append(treeRows, keyTreeRow{}) // add empty row for space between layers
}
}

builder, err := output.From(treeRows)
if err != nil {
return fmt.Errorf("failed to format output: %w", err)
}

return formatOutput(builder, asJSON).To(cmd.OutOrStdout())
},
}

cmd.Flags().StringVar(&keyID, "key-id", "", "id of the key")
cmd.Flags().StringVar(&tenantID, "tenant-id", "", "id of the tenant")
cmd.Flags().BoolVar(&asJSON, "json", false, "output in JSON format")
_ = cmd.MarkFlagRequired("key-id")
_ = cmd.MarkFlagRequired("tenant-id")

return cmd
}
101 changes: 101 additions & 0 deletions cli/cmd/tenant.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,101 @@
package cmd

import (
"fmt"

"github.com/spf13/cobra"
"google.golang.org/grpc"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/credentials/insecure"
"google.golang.org/grpc/status"

"github.com/openkcm/krypton/cli/output"
"github.com/openkcm/krypton/pkg/api/v1/proto/admin"
)

func getTenantCmd() *cobra.Command {
var asJSON bool

cmd := &cobra.Command{
Use: "tenant <id>",
Short: "Get a tenant by ID",
Args: cobra.ExactArgs(1),
RunE: func(cmd *cobra.Command, args []string) error {
// TODO: insecure.NewCredentials is a temporary workaround until TLS is configured
conn, err := grpc.NewClient(
serverAddr,
grpc.WithTransportCredentials(insecure.NewCredentials()),
)
if err != nil {
return fmt.Errorf("failed to connect: %w", err)
}
defer conn.Close()

client := admin.NewTenantServiceClient(conn)

resp, err := client.GetTenant(cmd.Context(), &admin.GetTenantRequest{
Id: args[0],
})
if err != nil {
if st, ok := status.FromError(err); ok && st.Code() == codes.NotFound {
return fmt.Errorf("tenant %q not found", args[0])
}
return fmt.Errorf("failed to get tenant: %w", err)
}

tenant := admin.TenantFromProto(resp.GetTenant())

builder, err := output.From(tenant)
if err != nil {
return fmt.Errorf("failed to format output: %w", err)
}

return formatOutput(builder, asJSON).To(cmd.OutOrStdout())
},
}

cmd.Flags().BoolVar(&asJSON, "json", false, "output in JSON format")

return cmd
}

func getTenantsCmd() *cobra.Command {
var asJSON bool

cmd := &cobra.Command{
Use: "tenants",
Short: "Get tenants",
Args: cobra.NoArgs,
RunE: func(cmd *cobra.Command, args []string) error {
// TODO: insecure.NewCredentials is a temporary workaround until TLS is configured
conn, err := grpc.NewClient(
serverAddr,
grpc.WithTransportCredentials(insecure.NewCredentials()),
)
if err != nil {
return fmt.Errorf("failed to connect: %w", err)
}
defer conn.Close()

client := admin.NewTenantServiceClient(conn)

resp, err := client.ListTenants(cmd.Context(), &admin.ListTenantsRequest{})
if err != nil {
return fmt.Errorf("failed to list tenants: %w", err)
}

tenants := admin.TenantsFromProto(resp.GetTenants())

builder, err := output.From(tenants)
if err != nil {
return fmt.Errorf("failed to format output: %w", err)
}

return formatOutput(builder, asJSON).To(cmd.OutOrStdout())
},
}

cmd.Flags().BoolVar(&asJSON, "json", false, "output in JSON format")

return cmd
}
Loading
Loading