-
Notifications
You must be signed in to change notification settings - Fork 64
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat(lib): Create Auth tokens using inst.Access()
- Loading branch information
Showing
11 changed files
with
285 additions
and
23 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,90 @@ | ||
package lib | ||
|
||
import ( | ||
"context" | ||
"fmt" | ||
"time" | ||
|
||
"github.com/qri-io/qri/auth/token" | ||
"github.com/qri-io/qri/profile" | ||
) | ||
|
||
// AccessMethods is a group of methods for access control & user authentication | ||
type AccessMethods struct { | ||
d dispatcher | ||
} | ||
|
||
// Name returns the name of this method group | ||
func (m AccessMethods) Name() string { | ||
return "access" | ||
} | ||
|
||
// Access returns the authentication that Instance has registered | ||
func (inst *Instance) Access() AccessMethods { | ||
return AccessMethods{d: inst} | ||
} | ||
|
||
// CreateAuthTokenParams are input parameters for Access().CreateAuthToken | ||
type CreateAuthTokenParams struct { | ||
GranteeUsername string | ||
GranteeProfileID string | ||
TTL time.Duration | ||
} | ||
|
||
// SetNonZeroDefaults uses default token time-to-live if one isn't set | ||
func (p *CreateAuthTokenParams) SetNonZeroDefaults() { | ||
if p.TTL == 0 { | ||
p.TTL = token.DefaultTokenTTL | ||
} | ||
} | ||
|
||
// Valid checks if the profile in question is valid | ||
func (p *CreateAuthTokenParams) Valid() error { | ||
if p.GranteeUsername == "" && p.GranteeProfileID == "" { | ||
return fmt.Errorf("either grantee username or profile is required") | ||
} | ||
return nil | ||
} | ||
|
||
// CreateAuthToken constructs a JWT string token suitable for making OAuth | ||
// requests as the grantee user. Creating an access token requires a stored | ||
// private key for the grantee. | ||
// Callers can provide either GranteeUsername OR GranteeProfileID | ||
func (m AccessMethods) CreateAuthToken(ctx context.Context, p *CreateAuthTokenParams) (string, error) { | ||
res, err := m.d.Dispatch(ctx, dispatchMethodName(m, "createauthtoken"), p) | ||
if s, ok := res.(string); ok { | ||
return s, err | ||
} | ||
return "", err | ||
} | ||
|
||
// accessImpl is the backing implementation for AccessMethods | ||
type accessImpl struct{} | ||
|
||
func (accessImpl) CreateAuthToken(scp scope, p *CreateAuthTokenParams) (string, error) { | ||
var ( | ||
grantee *profile.Profile | ||
err error | ||
) | ||
|
||
if p.GranteeProfileID != "" { | ||
id, err := profile.IDB58Decode(p.GranteeProfileID) | ||
if err != nil { | ||
return "", err | ||
} | ||
if grantee, err = scp.Profiles().GetProfile(id); err != nil { | ||
return "", err | ||
} | ||
} else if p.GranteeUsername != "" { | ||
if grantee, err = profile.ResolveUsername(scp.Profiles(), p.GranteeUsername); err != nil { | ||
return "", err | ||
} | ||
} | ||
|
||
pk := grantee.PrivKey | ||
if pk == nil { | ||
return "", fmt.Errorf("cannot create token for %q (id: %s), private key is required", grantee.Peername, grantee.ID.String()) | ||
} | ||
|
||
return token.NewPrivKeyAuthToken(pk, p.TTL) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
package lib | ||
|
||
import ( | ||
"context" | ||
"testing" | ||
|
||
"github.com/qri-io/qri/auth/token" | ||
) | ||
|
||
func TestAccessCreateAuthToken(t *testing.T) { | ||
ctx, cancel := context.WithCancel(context.Background()) | ||
defer cancel() | ||
inst, cleanup := NewMemTestInstance(ctx, t) | ||
defer cleanup() | ||
|
||
// create an authentication token using the owner profile | ||
p := &CreateAuthTokenParams{ | ||
GranteeUsername: inst.cfg.Profile.Peername, | ||
} | ||
s, err := inst.Access().CreateAuthToken(ctx, p) | ||
if err != nil { | ||
t.Fatal(err) | ||
} | ||
|
||
// prove we can parse & validate that token | ||
_, err = token.ParseAuthToken(s, inst.keystore) | ||
if err != nil { | ||
t.Fatal(err) | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.