query userinfo unit test

This commit is contained in:
Tim Möhlmann
2023-11-14 17:23:06 +02:00
parent 9cbd0ede9d
commit c7d571889c
6 changed files with 346 additions and 13 deletions

View File

@@ -0,0 +1,45 @@
{
"user": {
"id": "231965491734773762",
"creation_date": "2023-09-15T06:10:07.434142+00:00",
"change_date": "2023-11-14T13:27:02.072318+00:00",
"sequence": 1148,
"state": 1,
"resource_owner": "231848297847848962",
"username": "tim+tesmail@zitadel.com",
"human": {
"first_name": "Tim",
"last_name": "Mohlmann",
"nick_name": "muhlemmer",
"display_name": "Tim Mohlmann",
"avatar_key": null,
"email": "tim+tesmail@zitadel.com",
"is_email_verified": true,
"phone": "+40123456789",
"is_phone_verified": false
},
"machine": null
},
"org": {
"name": "demo",
"primary_domain": "demo.localhost"
},
"metadata": [
{
"creation_date": "2023-11-14T13:26:03.553702+00:00",
"change_date": "2023-11-14T13:26:03.553702+00:00",
"sequence": 1147,
"resource_owner": "231848297847848962",
"key": "bar",
"value": "Zm9v"
},
{
"creation_date": "2023-11-14T13:25:57.171368+00:00",
"change_date": "2023-11-14T13:25:57.171368+00:00",
"sequence": 1146,
"resource_owner": "231848297847848962",
"key": "foo",
"value": "YmFy"
}
]
}

View File

@@ -0,0 +1,28 @@
{
"user": {
"id": "231965491734773762",
"creation_date": "2023-09-15T06:10:07.434142+00:00",
"change_date": "2023-11-14T13:27:02.072318+00:00",
"sequence": 1148,
"state": 1,
"resource_owner": "231848297847848962",
"username": "tim+tesmail@zitadel.com",
"human": {
"first_name": "Tim",
"last_name": "Mohlmann",
"nick_name": "muhlemmer",
"display_name": "Tim Mohlmann",
"avatar_key": null,
"email": "tim+tesmail@zitadel.com",
"is_email_verified": true,
"phone": "+40123456789",
"is_phone_verified": false
},
"machine": null
},
"org": {
"name": "demo",
"primary_domain": "demo.localhost"
},
"metadata": null
}

View File

@@ -0,0 +1,38 @@
{
"user": {
"id": "240707570677841922",
"creation_date": "2023-11-14T13:34:52.473732+00:00",
"change_date": "2023-11-14T13:35:02.861342+00:00",
"sequence": 2,
"state": 1,
"resource_owner": "231848297847848962",
"username": "tests",
"human": null,
"machine": {
"name": "tests",
"description": "My test service user"
}
},
"org": {
"name": "demo",
"primary_domain": "demo.localhost"
},
"metadata": [
{
"creation_date": "2023-11-14T13:35:30.126849+00:00",
"change_date": "2023-11-14T13:35:30.126849+00:00",
"sequence": 3,
"resource_owner": "231848297847848962",
"key": "first",
"value": "SGVsbG8gV29ybGQh"
},
{
"creation_date": "2023-11-14T13:35:44.028343+00:00",
"change_date": "2023-11-14T13:35:44.028343+00:00",
"sequence": 4,
"resource_owner": "231848297847848962",
"key": "second",
"value": "QnllIFdvcmxkIQ=="
}
]
}

View File

@@ -0,0 +1,5 @@
{
"user": null,
"org": null,
"metadata": null
}

View File

@@ -5,7 +5,6 @@ import (
"database/sql"
_ "embed"
"encoding/json"
"fmt"
"github.com/zitadel/zitadel/internal/api/authz"
"github.com/zitadel/zitadel/internal/errors"
@@ -19,16 +18,17 @@ func (q *Queries) GetOIDCUserInfo(ctx context.Context, userID string) (_ *OIDCUs
ctx, span := tracing.NewSpan(ctx)
defer func() { span.EndWithError(err) }()
userInfo := new(OIDCUserInfo)
var data []byte
err = q.client.QueryRowContext(ctx, func(row *sql.Row) error {
var data []byte
if err := row.Scan(&data); err != nil {
return err
}
return json.Unmarshal(data, userInfo)
return row.Scan(&data)
}, oidcUserInfoQuery, userID, authz.GetInstance(ctx).InstanceID())
if err != nil {
return nil, fmt.Errorf("get oidc user info: %w", err)
return nil, errors.ThrowInternal(err, "QUERY-Oath6", "Errors.Internal")
}
userInfo := new(OIDCUserInfo)
if err = json.Unmarshal(data, userInfo); err != nil {
return nil, errors.ThrowInternal(err, "QUERY-Vohs6", "Errors.Internal")
}
if userInfo.User == nil {
return nil, errors.ThrowNotFound(nil, "QUERY-ahs4S", "Errors.User.NotFound")
@@ -40,9 +40,11 @@ func (q *Queries) GetOIDCUserInfo(ctx context.Context, userID string) (_ *OIDCUs
type OIDCUserInfo struct {
User *User `json:"user,omitempty"`
Metadata []UserMetadata `json:"metadata,omitempty"`
Org *struct {
ID string `json:"id,omitempty"`
Name string `json:"name,omitempty"`
PrimaryDomain string `json:"primary_domain,omitempty"`
} `json:"org,omitempty"`
Org *userInfoOrg `json:"org,omitempty"`
}
type userInfoOrg struct {
ID string `json:"id,omitempty"`
Name string `json:"name,omitempty"`
PrimaryDomain string `json:"primary_domain,omitempty"`
}

View File

@@ -0,0 +1,215 @@
package query
import (
"database/sql"
"database/sql/driver"
_ "embed"
"regexp"
"testing"
"time"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
"github.com/zitadel/zitadel/internal/api/authz"
"github.com/zitadel/zitadel/internal/database"
"github.com/zitadel/zitadel/internal/errors"
)
var (
//go:embed testdata/userinfo_not_found.json
testdataUserInfoNotFound string
//go:embed testdata/userinfo_human_no_md.json
testdataUserInfoHumanNoMD string
//go:embed testdata/userinfo_human.json
testdataUserInfoHuman string
//go:embed testdata/userinfo_machine.json
testdataUserInfoMachine string
)
func TestQueries_GetOIDCUserInfo(t *testing.T) {
expQuery := regexp.QuoteMeta(oidcUserInfoQuery)
type args struct {
userID string
}
tests := []struct {
name string
args args
mock sqlExpectation
want *OIDCUserInfo
wantErr error
}{
{
name: "query error",
args: args{
userID: "231965491734773762",
},
mock: mockQueryErr(expQuery, sql.ErrConnDone, "231965491734773762", "instanceID"),
wantErr: sql.ErrConnDone,
},
{
name: "unmarshal error",
args: args{
userID: "231965491734773762",
},
mock: mockQuery(expQuery, []string{"json_build_object"}, []driver.Value{`~~~`}, "231965491734773762", "instanceID"),
wantErr: errors.ThrowInternal(nil, "QUERY-Vohs6", "Errors.Internal"),
},
{
name: "user not found",
args: args{
userID: "231965491734773762",
},
mock: mockQuery(expQuery, []string{"json_build_object"}, []driver.Value{testdataUserInfoNotFound}, "231965491734773762", "instanceID"),
wantErr: errors.ThrowNotFound(nil, "QUERY-ahs4S", "Errors.User.NotFound"),
},
{
name: "human without metadata",
args: args{
userID: "231965491734773762",
},
mock: mockQuery(expQuery, []string{"json_build_object"}, []driver.Value{testdataUserInfoHumanNoMD}, "231965491734773762", "instanceID"),
want: &OIDCUserInfo{
User: &User{
ID: "231965491734773762",
CreationDate: time.Date(2023, time.September, 15, 6, 10, 7, 434142000, time.FixedZone("", 0)),
ChangeDate: time.Date(2023, time.November, 14, 13, 27, 2, 72318000, time.FixedZone("", 0)),
Sequence: 1148,
State: 1,
ResourceOwner: "231848297847848962",
Username: "tim+tesmail@zitadel.com",
Human: &Human{
FirstName: "Tim",
LastName: "Mohlmann",
NickName: "muhlemmer",
DisplayName: "Tim Mohlmann",
AvatarKey: "",
Email: "tim+tesmail@zitadel.com",
IsEmailVerified: true,
Phone: "+40123456789",
IsPhoneVerified: false,
},
Machine: nil,
},
Org: &userInfoOrg{
Name: "demo",
PrimaryDomain: "demo.localhost",
},
Metadata: nil,
},
},
{
name: "human with metadata",
args: args{
userID: "231965491734773762",
},
mock: mockQuery(expQuery, []string{"json_build_object"}, []driver.Value{testdataUserInfoHuman}, "231965491734773762", "instanceID"),
want: &OIDCUserInfo{
User: &User{
ID: "231965491734773762",
CreationDate: time.Date(2023, time.September, 15, 6, 10, 7, 434142000, time.FixedZone("", 0)),
ChangeDate: time.Date(2023, time.November, 14, 13, 27, 2, 72318000, time.FixedZone("", 0)),
Sequence: 1148,
State: 1,
ResourceOwner: "231848297847848962",
Username: "tim+tesmail@zitadel.com",
Human: &Human{
FirstName: "Tim",
LastName: "Mohlmann",
NickName: "muhlemmer",
DisplayName: "Tim Mohlmann",
AvatarKey: "",
Email: "tim+tesmail@zitadel.com",
IsEmailVerified: true,
Phone: "+40123456789",
IsPhoneVerified: false,
},
Machine: nil,
},
Org: &userInfoOrg{
Name: "demo",
PrimaryDomain: "demo.localhost",
},
Metadata: []UserMetadata{
{
CreationDate: time.Date(2023, time.November, 14, 13, 26, 3, 553702000, time.FixedZone("", 0)),
ChangeDate: time.Date(2023, time.November, 14, 13, 26, 3, 553702000, time.FixedZone("", 0)),
Sequence: 1147,
ResourceOwner: "231848297847848962",
Key: "bar",
Value: []byte("foo"),
},
{
CreationDate: time.Date(2023, time.November, 14, 13, 25, 57, 171368000, time.FixedZone("", 0)),
ChangeDate: time.Date(2023, time.November, 14, 13, 25, 57, 171368000, time.FixedZone("", 0)),
Sequence: 1146,
ResourceOwner: "231848297847848962",
Key: "foo",
Value: []byte("bar"),
},
},
},
},
{
name: "machine with metadata",
args: args{
userID: "240707570677841922",
},
mock: mockQuery(expQuery, []string{"json_build_object"}, []driver.Value{testdataUserInfoMachine}, "240707570677841922", "instanceID"),
want: &OIDCUserInfo{
User: &User{
ID: "240707570677841922",
CreationDate: time.Date(2023, time.November, 14, 13, 34, 52, 473732000, time.FixedZone("", 0)),
ChangeDate: time.Date(2023, time.November, 14, 13, 35, 2, 861342000, time.FixedZone("", 0)),
Sequence: 2,
State: 1,
ResourceOwner: "231848297847848962",
Username: "tests",
Human: nil,
Machine: &Machine{
Name: "tests",
Description: "My test service user",
},
},
Org: &userInfoOrg{
Name: "demo",
PrimaryDomain: "demo.localhost",
},
Metadata: []UserMetadata{
{
CreationDate: time.Date(2023, time.November, 14, 13, 35, 30, 126849000, time.FixedZone("", 0)),
ChangeDate: time.Date(2023, time.November, 14, 13, 35, 30, 126849000, time.FixedZone("", 0)),
Sequence: 3,
ResourceOwner: "231848297847848962",
Key: "first",
Value: []byte("Hello World!"),
},
{
CreationDate: time.Date(2023, time.November, 14, 13, 35, 44, 28343000, time.FixedZone("", 0)),
ChangeDate: time.Date(2023, time.November, 14, 13, 35, 44, 28343000, time.FixedZone("", 0)),
Sequence: 4,
ResourceOwner: "231848297847848962",
Key: "second",
Value: []byte("Bye World!"),
},
},
},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
execMock(t, tt.mock, func(db *sql.DB) {
q := &Queries{
client: &database.DB{
DB: db,
Database: &prepareDB{},
},
}
ctx := authz.NewMockContext("instanceID", "orgID", "loginClient")
got, err := q.GetOIDCUserInfo(ctx, tt.args.userID)
require.ErrorIs(t, err, tt.wantErr)
assert.Equal(t, tt.want, got)
})
})
}
}