1
0
mirror of https://github.com/mainflux/mainflux.git synced 2025-04-26 13:48:53 +08:00

NOISSUE - Add API keys functions to CLI (#1537)

* Add API keys to cli

Signed-off-by: Filip Bugarski <filipbugarski@gmail.com>

* Fix typo

Signed-off-by: Filip Bugarski <filipbugarski@gmail.com>

* Fix issue func, and sdk

Signed-off-by: Filip Bugarski <filipbugarski@gmail.com>

* Remove email, hide type and fix name

Signed-off-by: Filip Bugarski <filipbugarski@gmail.com>

* Remove type and add README

Signed-off-by: Filip Bugarski <filipbugarski@gmail.com>

* Fix issue response

Signed-off-by: Filip Bugarski <filipbugarski@gmail.com>

* Fix magic number and move struct to private

Signed-off-by: Filip Bugarski <filipbugarski@gmail.com>

* Remove const and import auth

Signed-off-by: Filip Bugarski <filipbugarski@gmail.com>

* Removing auth

Signed-off-by: Filip Bugarski <filipbugarski@gmail.com>

Co-authored-by: Dušan Borovčanin <dusan.borovcanin@mainflux.com>
This commit is contained in:
Filip Bugarski 2022-01-27 15:42:31 +01:00 committed by GitHub
parent 81b2a1a2d3
commit 4f56986c8e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 139 additions and 15 deletions

View File

@ -240,3 +240,17 @@ mainflux-cli groups members <group_id> <user_auth_token>
```bash
mainflux-cli groups membership <user_id> <user_auth_token>
```
### Keys management
#### Issue a new Key
```bash
mainflux-cli keys issue <duration> <user_auth_token>
```
#### Remove API key from database
```bash
mainflux-cli keys revoke <key_id> <user_auth_token>
```
#### Retrieve API key with given id
```bash
mainflux-cli keys retrieve <key_id> <user_auth_token>
```

93
cli/keys.go Normal file
View File

@ -0,0 +1,93 @@
// Copyright (c) Mainflux
// SPDX-License-Identifier: Apache-2.0
package cli
import (
"time"
"github.com/spf13/cobra"
)
var cmdAPIKeys = []cobra.Command{
{
Use: "issue",
Short: "issue <duration> <user_auth_token>",
Long: `Issues a new Key`,
Run: func(cmd *cobra.Command, args []string) {
if len(args) != 2 {
logUsage(cmd.Short)
return
}
d, err := time.ParseDuration(args[0])
if err != nil {
logError(err)
return
}
resp, err := sdk.Issue(args[1], d)
if err != nil {
logError(err)
return
}
logJSON(resp)
},
},
{
Use: "revoke",
Short: "revoke <key_id> <user_auth_token>",
Long: `Removes API key from database`,
Run: func(cmd *cobra.Command, args []string) {
if len(args) != 2 {
logUsage(cmd.Short)
return
}
if err := sdk.Revoke(args[0], args[1]); err != nil {
logError(err)
return
}
logOK()
},
},
{
Use: "retrieve",
Short: "retrieve <key_id> <user_auth_token>",
Long: `Retrieves API key with given id`,
Run: func(cmd *cobra.Command, args []string) {
if len(args) != 2 {
logUsage(cmd.Short)
return
}
rk, err := sdk.RetrieveKey(args[0], args[1])
if err != nil {
logError(err)
return
}
logJSON(rk)
},
},
}
// NewKeysCmd returns keys command.
func NewKeysCmd() *cobra.Command {
cmd := cobra.Command{
Use: "keys",
Short: "Keys management",
Long: `Keys management: issue, revoke, or retrieve API key.`,
Run: func(cmd *cobra.Command, args []string) {
logUsage("keys [issue | revoke | retrieve]")
},
}
for i := range cmdAPIKeys {
cmd.AddCommand(&cmdAPIKeys[i])
}
return &cmd
}

View File

@ -50,6 +50,7 @@ func main() {
provisionCmd := cli.NewProvisionCmd()
bootstrapCmd := cli.NewBootstrapCmd()
certsCmd := cli.NewCertsCmd()
keysCmd := cli.NewKeysCmd()
// Root Commands
rootCmd.AddCommand(healthCmd)
@ -61,6 +62,7 @@ func main() {
rootCmd.AddCommand(provisionCmd)
rootCmd.AddCommand(bootstrapCmd)
rootCmd.AddCommand(certsCmd)
rootCmd.AddCommand(keysCmd)
// Root Flags
rootCmd.PersistentFlags().StringVarP(

View File

@ -6,43 +6,59 @@ import (
"fmt"
"io/ioutil"
"net/http"
"time"
"github.com/mainflux/mainflux/pkg/errors"
)
type keyReq struct {
Type uint32 `json:"type,omitempty"`
Duration time.Duration `json:"duration,omitempty"`
}
const keysEndpoint = "keys"
func (sdk mfSDK) Issue(token string, k Key) (issueKeyRes, error) {
data, err := json.Marshal(k)
const (
// LoginKey is temporary User key received on successfull login.
LoginKey uint32 = iota
// RecoveryKey represents a key for resseting password.
RecoveryKey
// APIKey enables the one to act on behalf of the user.
APIKey
)
func (sdk mfSDK) Issue(token string, d time.Duration) (KeyRes, error) {
datareq := keyReq{Type: APIKey, Duration: d}
data, err := json.Marshal(datareq)
if err != nil {
return issueKeyRes{}, err
return KeyRes{}, err
}
url := fmt.Sprintf("%s/%s", sdk.authURL, keysEndpoint)
req, err := http.NewRequest(http.MethodPost, url, bytes.NewReader(data))
if err != nil {
return issueKeyRes{}, err
return KeyRes{}, err
}
resp, err := sdk.sendRequest(req, token, string(CTJSON))
if err != nil {
return issueKeyRes{}, err
return KeyRes{}, err
}
defer resp.Body.Close()
body, err := ioutil.ReadAll(resp.Body)
if err != nil {
return issueKeyRes{}, err
return KeyRes{}, err
}
if resp.StatusCode != http.StatusCreated {
return issueKeyRes{}, errors.Wrap(ErrFailedCreation, errors.New(resp.Status))
return KeyRes{}, errors.Wrap(ErrFailedCreation, errors.New(resp.Status))
}
var key issueKeyRes
var key KeyRes
if err := json.Unmarshal(body, &key); err != nil {
return issueKeyRes{}, err
return KeyRes{}, err
}
return key, nil

View File

@ -61,22 +61,22 @@ type MembersPage struct {
pageRes
}
type issueKeyRes struct {
type KeyRes struct {
ID string `json:"id,omitempty"`
Value string `json:"value,omitempty"`
IssuedAt time.Time `json:"issued_at,omitempty"`
ExpiresAt *time.Time `json:"expires_at,omitempty"`
}
func (res issueKeyRes) Code() int {
func (res KeyRes) Code() int {
return http.StatusCreated
}
func (res issueKeyRes) Headers() map[string]string {
func (res KeyRes) Headers() map[string]string {
return map[string]string{}
}
func (res issueKeyRes) Empty() bool {
func (res KeyRes) Empty() bool {
return res.Value == ""
}
@ -84,7 +84,6 @@ type retrieveKeyRes struct {
ID string `json:"id,omitempty"`
IssuerID string `json:"issuer_id,omitempty"`
Subject string `json:"subject,omitempty"`
Type uint32 `json:"type,omitempty"`
IssuedAt time.Time `json:"issued_at,omitempty"`
ExpiresAt *time.Time `json:"expires_at,omitempty"`
}

View File

@ -270,7 +270,7 @@ type SDK interface {
RevokeCert(thingID, certID, token string) error
// Issue issues a new key, returning its token value alongside.
Issue(token string, key Key) (issueKeyRes, error)
Issue(token string, duration time.Duration) (KeyRes, error)
// Revoke removes the key with the provided ID that is issued by the user identified by the provided key.
Revoke(token, id string) error