func TestEdit(t *testing.T) { defer context.Close() c := context.NewContext(nil) // Set it. m := map[string]string{ "A": "1", } cnfg, err := GetOrInsert(c, "first", m) // Change it. cnfg.Values["A"] = "2" // Save it. err = cnfg.Put(c) checkErr(t, err) // Confirm. cnfg, err = Get(c, "first") checkErr(t, err) if x := cnfg.Values["A"]; x != "2" { t.Errorf(`cnfg["A"]: %v, want %v`, x, "2") } }
func verifyHandler(w http.ResponseWriter, r *http.Request) { //code := r.FormValue("code") var e *Email var et *token.Token var err error c := context.NewContext(r) code := r.URL.Query().Get("code") errURL := "/" successURL := "/" et, err = token.Get(c, code) if err != nil { goto Error } e, err = Get(c, et.EmailAddress) if err != nil { goto Error } e.Status = verified if err = e.Put(c); err != nil { goto Error } http.Redirect(w, r, successURL, http.StatusFound) Error: // TODO added error to session http.Redirect(w, r, errURL, http.StatusNotFound) }
// Authenticate process the request and returns a populated UserProfile. // If the Authenticate method can not authenticate the User based on the // request, an error or a redirect URL wll be return. func (p *Provider) Authenticate(w http.ResponseWriter, r *http.Request) ( up *profile.Profile, redirectURL string, err error) { c := context.NewContext(r) url := r.FormValue("provider") // Set provider info. up = profile.New(p.Name, url) // Check for current User. u := aeuser.Current(c) if u == nil { redirectURL := r.URL.Path + "/callback" loginUrl, err := aeuser.LoginURLFederated(c, redirectURL, url) return up, loginUrl, err } if u.FederatedIdentity != "" { up.ID = u.FederatedIdentity } else { up.ID = u.ID } per := new(person.Person) per.Email = u.Email per.Emails = []*person.PersonEmails{ &person.PersonEmails{true, "home", u.Email}, } per.URL = u.FederatedIdentity up.Person = per return up, "", nil }
func Test_handler(t *testing.T) { setup() defer teardown() _ = context.NewContext(nil) // Register the Provider p := &TPComplete{} Register("example5", p) r, _ := http.NewRequest("GET", "http://localhost:8080/-/auth/example5", nil) w := httptest.NewRecorder() // Run it through the auth handler. handler(w, r) // Inspected the redirect. hdr := w.Header() if hdr["Location"][0] != SuccessURL { t.Errorf(`hdr["Location"]: %q, want %q`, hdr["Location"][0], SuccessURL) t.Errorf(`w: %q`, w) t.Errorf(`hdr: %q`, hdr) } }
func TestDelete(t *testing.T) { setup() c := context.NewContext(nil) defer tearDown() var x interface{} // Put A x = &A{S: "a", I: 1, B: []byte{}, T: now} key := datastore.NewKey(c, "A", "1", 0, nil) key, _ = Put(c, key, x) // Delete A err := Delete(c, key) if err != nil { t.Errorf(`err = %s; expected nil`, err) } // Test Store for absence of values x = &A{} err = memory.Get(c, key, x) if err != dserrors.ErrNoSuchEntity { t.Errorf(`err = %s; expected %s`, err, dserrors.ErrNoSuchEntity) } err = memcache.Get(c, key, x) if err != dserrors.ErrNoSuchEntity { t.Errorf(`err = %s; expected %s`, err, dserrors.ErrNoSuchEntity) } err = dsds.Get(c, key, x) if err != dserrors.ErrNoSuchEntity { t.Errorf(`err = %s; expected %s`, err, dserrors.ErrNoSuchEntity) } }
func TestDelete(t *testing.T) { setup() defer tearDown() c := context.NewContext(nil) // Put. k, x := NewX(c, "1") _, err := s.Put(c, k, x) // Delete. err = s.Delete(c, k) if err != nil { t.Errorf("err: %v; want: %v.", err, nil) } // Delete non-existence k = datastore.NewKey(c, "X", "fakekey", 0, nil) r := new(X) err = s.Get(c, k, r) if err != dse.ErrNoSuchEntity { t.Errorf("err: %v; want: %v.", err, dse.ErrNoSuchEntity) } }
func TestGetOrInsert(t *testing.T) { defer context.Close() c := context.NewContext(nil) // Set it. m := map[string]string{ "A": "1", } cnfg, err := GetOrInsert(c, "first", m) // Confirm. checkErr(t, err) if x := cnfg.Values["A"]; x != "1" { t.Errorf(`config["A"]: %v, want %v`, x, "1") } // The orginal map should be returned. m = map[string]string{ "A": "2", } cnfg, err = GetOrInsert(c, "first", m) // Confirm. checkErr(t, err) if x := cnfg.Values["A"]; x != "1" { t.Errorf(`config["A"]: %v, want %v`, x, "1") } }
func TestPut(t *testing.T) { setup() defer tearDown() c := context.NewContext(nil) k, x1 := NewX(c, "1") _, err := s.Put(c, k, x1) if err != nil { t.Errorf("err: %v; want: %v.", err, nil) } }
func TestNewKey(t *testing.T) { c := context.NewContext(nil) defer tearDown() k1 := datastore.NewKey(c, "AuthProfile", "google|12345", 0, nil) k2 := newKey(c, "Google", "12345") if k1.String() != k2.String() { t.Errorf("k2: %q, want %q.", k2, k1) t.Errorf("k1:", k1) t.Errorf("k2:", k2) } }
func (p *Provider) callback(r *http.Request) error { // Exchange code for an access token at OAuth provider. code := r.FormValue("code") t := &oauth.Transport{ Config: p.Config(r.URL), Transport: &urlfetch.Transport{ Context: context.NewContext(r), }, } _, err := t.Exchange(code) return err }
// CreateAndLogin does the following: // // - Search for an existing user - session -> Profile -> email address // - Saves the Profile to the datastore // - Creates a User or appends the AuthID to the Requesting user's account // - Logs in the User // - Adds the admin role to the User if they are an GAE Admin. func CreateAndLogin(w http.ResponseWriter, r *http.Request, p *profile.Profile) (u *user.User, err error) { c := context.NewContext(r) if u, err = p.UpdateUser(w, r); err != nil { return } if err = user.CurrentUserSetID(w, r, p.UserID); err != nil { return } err = p.Put(c) return }
// Current returns the current users password object minus the password func (s *Service) Current(w http.ResponseWriter, r *http.Request, args *Args, reply *Args) (err error) { c := context.NewContext(r) var isSet bool userID, _ := user.CurrentUserID(r) _, err = profile.Get(c, profile.GenAuthID("Password", userID)) if err == nil { isSet = true } reply.Password = &Password{IsSet: isSet} return nil }
// Current checks the requesting User's session to see if they have an // account. If they do, the provided User struct is populated with the // information that is saved in the datastore. If they don't an error is // returned. func Current(r *http.Request) (*User, error) { id, _ := CurrentUserID(r) if id != "" { c := context.NewContext(r) u := new(User) key := datastore.NewKey(c, "User", id, 0, nil) err := ds.Get(c, key, u) u.Key = key return u, err } return nil, ErrNoLoggedInUser }
func (s *Service) GetAll(w http.ResponseWriter, r *http.Request, args *Args, reply *Reply) (err error) { c := context.NewContext(r) u, err := user.Current(r) if err != nil { return err } if reply.Profiles, err = GetPersonMulti(c, u.AuthIDs); err != nil { return err } return nil }
func TestGetMulti(t *testing.T) { setup() defer tearDown() c := context.NewContext(nil) if cnt := s.Count(c); cnt != 0 { t.Errorf(`Before Put; s.Count(c): %v; want %v`, cnt, 0) } // Put. k1, x1 := NewX(c, "1") k2, x2 := NewX(c, "2") k3, x3 := NewX(c, "3") keys := []*datastore.Key{k1, k2, k3} xs := []*X{x1, x2, x3} keys, err := s.PutMulti(c, keys, xs) // Get. xs = []*X{&X{}, &X{}, &X{}} err = s.GetMulti(c, keys, xs) // Confirm. if err != nil { t.Errorf("err: %v; want: %v.", err, nil) } CheckX(c, t, xs[0], "1") CheckX(c, t, xs[1], "2") CheckX(c, t, xs[2], "3") // Get non-existence k4, _ := NewX(c, "4") k5, _ := NewX(c, "5") xs = []*X{&X{}, &X{}, &X{}, &X{}, &X{}} keys = []*datastore.Key{k1, k2, k3, k4, k5} err = s.GetMulti(c, keys, xs) if err.Error() != "ds: no such entity (and 1 other error)" { t.Errorf("err: %v; want: %v.", err.Error(), "ds: no such entity (and 1 other error)") } // Check. CheckX(c, t, xs[0], "1") CheckX(c, t, xs[1], "2") CheckX(c, t, xs[2], "3") }
func TestDeleteMulti(t *testing.T) { setup() defer tearDown() c := context.NewContext(nil) // Put. k1, x1 := NewX(c, "1") k2, x2 := NewX(c, "2") k3, x3 := NewX(c, "3") keys := []*datastore.Key{k1, k2, k3} xs := []*X{x1, x2, x3} keys, err := s.PutMulti(c, keys, xs) // Delete. err = s.DeleteMulti(c, keys) // Confirm. if err != nil { t.Errorf("err: %v; want: %v.", err, nil) } if cnt := len(xs); cnt != 3 { t.Errorf(`After DeleteMulti; len(xs): %v; want %v`, cnt, 3) } // Delete non-existence // Put. k1, x1 = NewX(c, "1") k2, x2 = NewX(c, "2") k3, x3 = NewX(c, "3") keys = []*datastore.Key{k1, k2, k3} xs = []*X{x1, x2, x3} keys, err = s.PutMulti(c, keys, xs) k4, _ := NewX(c, "4") k5, _ := NewX(c, "5") xs = []*X{&X{}, &X{}, &X{}, &X{}, &X{}} keys = []*datastore.Key{k1, k2, k3, k4, k5} err = s.DeleteMulti(c, keys) //if err.Error() != "ds: no such entity (and 1 other error)" { // t.Errorf("err: %v; want: %v.", err.Error(), "ds: no such entity (and 1 other error)") //} }
func TestCan(t *testing.T) { setUp() defer tearDown() c := context.NewContext(nil) u := New() // User key key := datastore.NewKey(c, "User", "1", 0, nil) u.Key = key if !u.Can(c, "write", key) { t.Error(`User should be able to "write" their own User object`) } }
func TestPutMulti(t *testing.T) { setup() defer tearDown() c := context.NewContext(nil) k1, x1 := NewX(c, "X1") k2, x2 := NewX(c, "X2") k3, x3 := NewX(c, "X3") keys := []*datastore.Key{k1, k2, k3} xs := []*X{x1, x2, x3} keys, err := s.PutMulti(c, keys, xs) if err != nil { t.Errorf("err: %v; want: %v.", err, nil) } }
func (s *Service) Authenticate(w http.ResponseWriter, r *http.Request, args *Args, reply *Args) (err error) { c := context.NewContext(r) args.Person.Email = args.Password.Email userID, _ := user.CurrentUserIDByEmail(r, args.Password.Email) pf, err := authenticate(c, args.Password, args.Person, userID) if err != nil { return err } if _, err = auth.CreateAndLogin(w, r, pf); err != nil { return err } reply.Person = pf.Person return nil }
func TestAllocateIDs(t *testing.T) { setup() c := context.NewContext(nil) defer tearDown() cnt := 5 low, high, err := AllocateIDs(c, "D", nil, cnt) if err != nil { t.Errorf(`err = %s; expected nil`, err) } ncnt := int(high - low) if ncnt != cnt { t.Errorf(`ncnt = %v, %v`, ncnt, cnt) t.Errorf(`low = %v`, low) t.Errorf(`high = %v`, high) } }
// Authenticate process the request and returns a populated Profile. // If the Authenticate method can not authenticate the User based on the // request, an error or a redirect URL wll be return. func (p *Provider) Authenticate(w http.ResponseWriter, r *http.Request) ( pf *profile.Profile, url string, err error) { p.URL = r.URL.Host pf = profile.New(p.Name, p.URL) pass := &Password{ New: r.FormValue("Password.New"), Current: r.FormValue("Password.Current"), Email: r.FormValue("Email"), } c := context.NewContext(r) userID, _ := user.CurrentUserIDByEmail(r, pass.Email) pers := decodePerson(r) pf, err = authenticate(c, pass, pers, userID) return pf, "", err }
func TestPut(t *testing.T) { setup() defer tearDown() c := context.NewContext(nil) k, x1 := NewX(c, "1") if cnt := s.Count(c); cnt != 0 { t.Errorf(`Before put; s.Count(c) = %v; want %v`, cnt, 0) } _, err := s.Put(c, k, x1) if err != nil { t.Errorf("err: %v; want: %v.", err, nil) } if cnt := s.Count(c); cnt != 1 { t.Errorf(`After put; s.Count(c): %v; want %v`, cnt, 1) } }
// CurrentUserIDByEmail returns the userId of the requesting user. Or the userID // associated with the provided email. func CurrentUserIDByEmail(r *http.Request, emailAddress string) (string, error) { // TODO: User merge if the session UserID is different then the email UserID // search session sessID, _ := CurrentUserID(r) if sessID != "" { // TODO: maybe confirm that the UserID exists? // There are case where the session may have an incorrect UserID. return sessID, nil } // search by email c := context.NewContext(r) e, err := email.Get(c, emailAddress) if err != nil { return "", err } return e.UserID, nil }
func TestCreateFromPerson(t *testing.T) { c := context.NewContext(nil) defer tearDown() var err error var u *User var u2 *User var e *email.Email // Round #1 New User with email & password // Save it. if u, err = CreateFromPerson(c, p1); err != nil { t.Errorf(`err: %v, want nil`, err) } // Check User // Get from ds to confirm save if u, err = Get(c, u.Key.StringID()); err != nil { t.Errorf(`err: %v, want nil`, err) } if u.Email != p1.Email { t.Errorf(`u.Email: %v, want %v`, u.Email, p1.Email) } if u.Person.ID != u.Key.StringID() { t.Errorf(`u.Person.ID: %v, want %v`, u.Person.ID, u.Key.StringID()) } // Check Email if e, err = email.Get(c, u.Email); err != nil { t.Errorf(`err: %v, want nil`, err) } if e.UserID != u.Key.StringID() { t.Errorf(`u.UserID: %v, want %v`, e.UserID, u.Key.StringID()) } // Round #2 Existing User with email & password // Get it if u2, err = UpdateFromPerson(c, u.Person); err != nil { t.Errorf(`err: %v, want nil`, err) } if u2.Key.StringID() != u.Key.StringID() { t.Errorf(`u2.Key.StringID: %v, want %v`, u2.Key.StringID(), u.Key.StringID()) } }
func TestPutMulti(t *testing.T) { setup() defer tearDown() c := context.NewContext(nil) if cnt := s.Count(c); cnt != 0 { t.Errorf(`Before Put; s.Count(c): %v; want %v`, cnt, 0) } k1, x1 := NewX(c, "X1") k2, x2 := NewX(c, "X2") k3, x3 := NewX(c, "X3") keys := []*datastore.Key{k1, k2, k3} xs := []*X{x1, x2, x3} keys, err := s.PutMulti(c, keys, xs) if err != nil { t.Errorf("err: %v; want: %v.", err, nil) } if cnt := s.Count(c); cnt != 3 { t.Errorf(`After Put; s.Count(c): %v; want %v`, cnt, 3) } }
func TestDeleteMulti(t *testing.T) { setup() c := context.NewContext(nil) defer tearDown() var x interface{} // Put As x = []*A{ &A{S: "a", I: 1, B: []byte{}, T: now}, &A{S: "a", I: 1, B: []byte{}, T: now}, } key := []*datastore.Key{ datastore.NewKey(c, "A", "1", 0, nil), datastore.NewKey(c, "A", "2", 0, nil), } key, _ = PutMulti(c, key, x) // Delete As err := DeleteMulti(c, key) if err != nil { t.Errorf(`err = %s; expected nil`, err) } // Test Store for absence of values x = []*A{&A{}, &A{}} err = memory.GetMulti(c, key, x) if reflect.TypeOf(err) != reflect.TypeOf(dserrors.MultiError{}) { t.Errorf(`err = %s; expected %s`, reflect.TypeOf(err), reflect.TypeOf(dserrors.MultiError{})) } err = memcache.GetMulti(c, key, x) if reflect.TypeOf(err) != reflect.TypeOf(dserrors.MultiError{}) { t.Errorf(`err = %s; expected %s`, reflect.TypeOf(err), reflect.TypeOf(dserrors.MultiError{})) } // TODO(kylefinley) add this test back. // err = dsds.GetMulti(c, key, x) // if reflect.TypeOf(err) != reflect.TypeOf(dserrors.MultiError{}) { // t.Errorf(`err = %s; expected %s`, reflect.TypeOf(err), reflect.TypeOf(dserrors.MultiError{})) // } }
func TestPutGetMulti(t *testing.T) { setup() c := context.NewContext(nil) defer tearDown() // Put As key := []*datastore.Key{ datastore.NewKey(c, "A", "1", 0, nil), datastore.NewKey(c, "A", "2", 0, nil), } x := []*A{ &A{S: "a", I: 1, B: []byte{}, T: now}, &A{S: "a", I: 1, B: []byte{}, T: now}, } key, err := PutMulti(c, key, x) if err != nil { t.Errorf(`err = %s; expected nil`, err) } // Test Store for values x = []*A{&A{}, &A{}} err = dsds.GetMulti(c, key, x) if err != nil { t.Errorf(`err = %s; expected nil`, err) } }
func TestGet(t *testing.T) { c := context.NewContext(nil) defer tearDown() // Save it. u := New() u.Email = "*****@*****.**" u.Key = datastore.NewKey(c, "User", "", 0, nil) err := u.Put(c) if err != nil { t.Errorf(`err: %q, want nil`, err) } // Get it. u2, err := Get(c, u.Key.StringID()) if err != nil { t.Errorf(`err: %v, want nil`, err) } if u2.Email != "*****@*****.**" { t.Errorf(`u2.Email: %v, want "*****@*****.**"`, u2.Email) } }
func TestPutGet(t *testing.T) { setup() c := context.NewContext(nil) defer tearDown() var x interface{} // Put A x = &A{S: "a", I: 1, B: []byte{}, T: now} key := datastore.NewKey(c, "A", "1", 0, nil) key, err := Put(c, key, x) if err != nil { t.Errorf(`err = %s; expected nil`, err) } // Test Store for values x = new(A) err = memory.Get(c, key, x) if err != nil { t.Errorf(`err = %s; expected nil`, err) } err = memcache.Get(c, key, x) if err != nil { t.Errorf(`err = %s; expected nil`, err) } err = dsds.Get(c, key, x) if err != nil { t.Errorf(`err = %s; expected nil`, err) } // Put B x = &B{S: "a", I: 1, B: []byte{}, T: now} key = datastore.NewKey(c, "B", "1", 0, nil) key, err = Put(c, key, x) if err != nil { t.Errorf(`err = %s; expected nil`, err) } // Test Store for values x = new(B) err = memory.Get(c, key, x) if err != dserrors.ErrNoSuchEntity { t.Errorf(`err = %s; expected %s`, err, dserrors.ErrNoSuchEntity) } err = memcache.Get(c, key, x) if err != nil { t.Errorf(`err = %s; expected nil`, err) } err = dsds.Get(c, key, x) if err != nil { t.Errorf(`err = %s; expected nil`, err) } // Put C x = &C{S: "a", I: 1, B: []byte{}, T: now} key = datastore.NewKey(c, "C", "1", 0, nil) key, err = Put(c, key, x) if err != nil { t.Errorf(`err = %s; expected nil`, err) } x = new(C) // Test Store for values err = memory.Get(c, key, x) if err != dserrors.ErrNoSuchEntity { t.Errorf(`err = %s; expected %s`, err, dserrors.ErrNoSuchEntity) } err = memcache.Get(c, key, x) if err != dserrors.ErrNoSuchEntity { t.Errorf(`err = %s; expected %s`, err, dserrors.ErrNoSuchEntity) } err = dsds.Get(c, key, x) if err != nil { t.Errorf(`err = %s; expected nil`, err) } }
// Scenario #2: // - No User session // - Yes Email Saved // - Yes Profile Saved func TestAuthenticate_Scenario2(t *testing.T) { pro := setup() defer tearDown() var pf *profile.Profile var uRL string var err error var v url.Values var r *http.Request c := context.NewContext(nil) w := httptest.NewRecorder() // Profile Not found v = url.Values{} v.Set("Email", "*****@*****.**") v.Set("Password.Current", "secret1") r = createRequest(v) // Check. if pf, uRL, err = pro.Authenticate(w, r); uRL != "" || err != ErrProfileNotFound { t.Errorf(`url: %v, want: ""`, uRL) t.Errorf(`err: %v, want: %v`, err, ErrProfileNotFound) } // Setup. pf = profile.New("Password", "") pf.UserID = "1" pf.ID = "1" passHash, _ := GenerateFromPassword([]byte("secret1")) pf.Auth = passHash pf.SetKey(c) pf.Person = &person.Person{ Name: &person.PersonName{ GivenName: "Barack", FamilyName: "Obama", }, } _ = pf.Put(c) e := email.New() e.UserID = "1" e.SetKey(c, "*****@*****.**") _ = e.Put(c) // 1. Login // a. Correct password. v = url.Values{} v.Set("Email", "*****@*****.**") v.Set("Password.Current", "secret1") v.Set("Name.GivenName", "Berry") r = createRequest(v) // Check. if pf, uRL, err = pro.Authenticate(w, r); uRL != "" || err != nil { t.Errorf(`url: %v, want: ""`, uRL) t.Fatalf(`err: %v, want: %v`, err, nil) } if x := pf.Person.Name.GivenName; x != "Barack" { t.Errorf(`.Person should not be updated on login`) } // b. In-Correct password. v = url.Values{} v.Set("Email", "*****@*****.**") v.Set("Password.Current", "fakepass") r = createRequest(v) // Check. if _, _, err = pro.Authenticate(w, r); err != ErrPasswordMismatch { t.Errorf(`err: %v, want: %v`, err, ErrPasswordMismatch) } // 2. Update // a. Correct password. v = url.Values{} v.Set("Email", "*****@*****.**") v.Set("Password.Current", "secret1") v.Set("Password.New", "secret2") v.Set("Name.GivenName", "Berry") r = createRequest(v) // Check. if pf, uRL, err = pro.Authenticate(w, r); uRL != "" || err != nil { t.Errorf(`url: %v, want: ""`, uRL) t.Errorf(`err: %v, want: %v`, err, nil) } if x := pf.Person.Name.GivenName; x != "Berry" { t.Errorf(`pf.Person should be updated on update`) } if x := pf.UserID; x != "1" { t.Errorf(`pf.UserID: %v, want %v`, x, "1") } if err := CompareHashAndPassword(pf.Auth, []byte("secret2")); err != nil { t.Errorf(`Password was not changed`) } // b. In-Correct password. v = url.Values{} v.Set("Email", "*****@*****.**") v.Set("Password.Current", "fakepass") v.Set("Password.New", "hacked") v.Set("Name.GivenName", "Bob") r = createRequest(v) // Check. if _, _, err = pro.Authenticate(w, r); err != ErrPasswordMismatch { t.Errorf(`err: %v, want: %v`, err, ErrPasswordMismatch) } // 2. Create - Should login user // a. Correct password. v = url.Values{} v.Set("Email", "*****@*****.**") v.Set("Password.New", "secret1") v.Set("Name.GivenName", "Bob1") r = createRequest(v) // Check. if pf, uRL, err = pro.Authenticate(w, r); uRL != "" || err != nil { t.Errorf(`url: %v, want: ""`, uRL) t.Errorf(`err: %v, want: %v`, err, nil) } if x := pf.Person.Name.GivenName; x != "Bob1" { t.Errorf(`.Person should be updated on update`) } if x := pf.UserID; x != "1" { t.Errorf(`pf.UserID: %v, want %v`, x, "1") } if err := CompareHashAndPassword(pf.Auth, []byte("secret1")); err != nil { t.Errorf(`Password was not changed`) } // b. In-Correct password. v = url.Values{} v.Set("Email", "*****@*****.**") v.Set("Password.New", "fakepass") v.Set("Name.GivenName", "Bob2") r = createRequest(v) // Check. if _, _, err = pro.Authenticate(w, r); err != ErrPasswordMismatch { t.Errorf(`err: %v, want: %v`, err, ErrPasswordMismatch) } }