changeset 12:1c194fa9bbf4

Fix auth tests.
author Paul Fisher <paul@pfish.zone>
date Thu, 29 Oct 2015 21:25:12 -0400
parents e246c8a4d28e
children da6c493cf08a
files auth/auth.go auth/auth_test.go
diffstat 2 files changed, 52 insertions(+), 116 deletions(-) [+]
line wrap: on
line diff
--- a/auth/auth.go	Sun Oct 25 11:48:53 2015 -0400
+++ b/auth/auth.go	Thu Oct 29 21:25:12 2015 -0400
@@ -18,7 +18,7 @@
 	bcryptCost = 12
 	// we only generate passwords from lowercases for non-ambiguity
 	lowercases = "abcdefghijklmnopqrstuvwxyz"
-	template   = "____-____-____-____"
+	template   = "????-????-????-????"
 )
 
 var (
@@ -27,7 +27,7 @@
 )
 
 var (
-	ShortEntryError      error = errors.New("multipass/auth: password entry must have 3 or more fields")
+	WrongLengthError      error = errors.New("multipass/auth: password entry must have 3 fields")
 	BadIDError                 = errors.New("multipass/auth: ID field invalid")
 	Base64Error                = errors.New("multipass/auth: can't decode base64 data")
 	LongDescriptionError       = errors.New("multipass/auth: description must be less than 255 bytes")
@@ -43,15 +43,14 @@
 	id          uint64
 	hash        string
 	description string
-	rest        []string
 }
 
 // EntryFromShadow creates a new entry from a line in a multipass shadow file.
 // The line should not end in a newline.
 func EntryFromShadow(shadow string) (*Entry, error) {
 	segments := strings.Split(shadow, ":")
-	if len(segments) < 2 {
-		return nil, ShortEntryError
+	if len(segments) != 3 {
+		return nil, WrongLengthError
 	}
 	entry := new(Entry)
 	id, err := strconv.ParseUint(segments[0], 10, 64)
@@ -60,14 +59,11 @@
 	}
 	entry.id = id
 	entry.hash = segments[1]
-	if len(segments) > 2 {
-		description, err := base64.StdEncoding.DecodeString(segments[2])
-		if err != nil {
-			return nil, Base64Error
-		}
-		entry.description = string(description)
-		entry.rest = segments[3:]
+	description, err := base64.StdEncoding.DecodeString(segments[2])
+	if err != nil {
+		return nil, Base64Error
 	}
+	entry.description = string(description)
 	return entry, nil
 }
 
@@ -114,16 +110,14 @@
 		e.hash,
 		base64.StdEncoding.EncodeToString([]byte(e.description)),
 	}
-	segments = append(segments, e.rest...)
 	return strings.Join(segments, ":")
 }
 
 func genPassword() []byte {
 	password := []byte(template)
-	for group := 0; group < 4; group++ {
-		base := group * 5
-		for chr := 0; chr < 4; chr++ {
-			password[base+chr] = randChr()
+	for i, chr := range password {
+		if chr == '?' {
+			password[i] = randChr()
 		}
 	}
 	return password
--- a/auth/auth_test.go	Sun Oct 25 11:48:53 2015 -0400
+++ b/auth/auth_test.go	Thu Oct 29 21:25:12 2015 -0400
@@ -7,8 +7,8 @@
 
 var passPattern *regexp.Regexp = regexp.MustCompile(`^(?:[a-z]{4}-){3}[a-z]{4}$`)
 
-const basicShadow = "jhh:9999:$2a$12$tcv2MrtXgibAJHsSwVfHiOevXBFmiGy0HTNoOB8QzIhEh46iWS1uC:YW55dGhpbmcgbW9yZSB0aGFuIDUgcmVwcyBpcyBjYXJkaW8="
-const extraDataShadow = "skw:1:$2a$12$lINQdYWHOcLKoqhNOr3mNOpZSAu5JOBS2F7T/VDfYn2rvv6qUJehG::additional:fields"
+const basicShadow = "9999:$2a$12$tcv2MrtXgibAJHsSwVfHiOevXBFmiGy0HTNoOB8QzIhEh46iWS1uC:YW55dGhpbmcgbW9yZSB0aGFuIDUgcmVwcyBpcyBjYXJkaW8="
+const anotherShadow = "1:$2a$12$lINQdYWHOcLKoqhNOr3mNOpZSAu5JOBS2F7T/VDfYn2rvv6qUJehG:"
 
 func TestEntryFromShadow(t *testing.T) {
 	cases := []struct {
@@ -21,39 +21,39 @@
 		rest        []string
 	}{
 		{
-			shadow:   "pfish:1234:$2a$12$apFtWGXKtWBavVy5eo.22Ohs43GudT5IYTqyQkIBX9LpS7YtvKBpa",
-			username: "pfish",
+			shadow:   "1234:$2a$12$apFtWGXKtWBavVy5eo.22Ohs43GudT5IYTqyQkIBX9LpS7YtvKBpa:",
 			id:       1234,
 			hash:     "$2a$12$apFtWGXKtWBavVy5eo.22Ohs43GudT5IYTqyQkIBX9LpS7YtvKBpa",
 		},
 		{
 			shadow:      basicShadow,
-			username:    "jhh",
 			id:          9999,
 			hash:        "$2a$12$tcv2MrtXgibAJHsSwVfHiOevXBFmiGy0HTNoOB8QzIhEh46iWS1uC",
 			description: "anything more than 5 reps is cardio",
 		},
 		{
-			shadow:   extraDataShadow,
-			username: "skw",
+			shadow:   anotherShadow,
 			id:       1,
 			hash:     "$2a$12$lINQdYWHOcLKoqhNOr3mNOpZSAu5JOBS2F7T/VDfYn2rvv6qUJehG",
-			rest:     []string{"additional", "fields"},
 		},
 		{
-			shadow:  "user:one:bogushash",
+			shadow:  "one:bogushash:",
 			wantErr: true,
 		},
 		{
-			shadow:  "user:-1:bogushash",
+			shadow:  "-1:bogushash:",
 			wantErr: true,
 		},
 		{
-			shadow:  "tooshort",
+			shadow:  "0:tooshort",
 			wantErr: true,
 		},
 		{
-			shadow:  "test:0:bogushash:invalid base64",
+			shadow:  "0:bogushash:invalid base64",
+			wantErr: true,
+		},
+		{
+			shadow: "1:bogushash::more things",
 			wantErr: true,
 		},
 	}
@@ -68,8 +68,8 @@
 		if err != nil {
 			t.Errorf("EntryFromShadow(%q) == _, %q; want nil err", c.shadow, err)
 		}
-		if c.username != entry.username {
-			t.Errorf("EntryFromShadow(%q).username = %q; want %q", c.shadow, entry.username, c.username)
+		if c.id != entry.id {
+			t.Errorf("EntryFromShadow(%q).id = %q; want %q", c.shadow, entry.id, c.id)
 		}
 		if c.hash != string(entry.hash) {
 			t.Errorf("EntryFromShadow(%q).password = %q; want %q", c.shadow, entry.hash, c.hash)
@@ -77,62 +77,43 @@
 		if c.description != entry.description {
 			t.Errorf("EntryFromShadow(%q).description = %q; want %q", c.shadow, entry.description, c.description)
 		}
-		restEqual := false
-		if len(c.rest) == len(entry.rest) {
-			restEqual = true
-			for i := range c.rest {
-				if c.rest[i] != entry.rest[i] {
-					restEqual = false
-					break
-				}
-			}
-		}
-		if !restEqual {
-			t.Errorf("EntryFromShadow(%q).rest = %q; want %q", c.shadow, entry.rest, c.rest)
-		}
 	}
 }
 
 func TestNewEntry(t *testing.T) {
 	cases := []struct {
-		username    string
 		description string
 		wantErr     bool
 	}{
-		{"pfish", "one", false},
-		{"pfish", "the other", false},
-		{"with:colons", "", true},
-		{"pfish", string(make([]byte, 1000)), true},
+		{"one", false},
+		{"the other", false},
+		{string(make([]byte, 1000)), true},
 	}
 	for _, c := range cases {
-		entry, password, err := NewEntry(c.username, c.description)
+		entry, password, err := NewEntry(c.description)
 		if c.wantErr {
 			if err == nil {
-				t.Errorf("NewEntry(%q, %q) = _, _, nil; want non-nil err", c.username, c.description)
+				t.Errorf("NewEntry(%q) = _, _, nil; want non-nil err", c.description)
 			}
 			continue
 		}
 		if err != nil {
-			t.Errorf("NewEntry(%q, %q) = _, _, %q; want nil err", c.username, c.description, err)
-		}
-		if c.username != entry.username {
-			t.Errorf("NewEntry(%q, %q).username = %q, want %q",
-				c.username, c.description, entry.username, c.username)
+			t.Errorf("NewEntry(%q) = _, _, %q; want nil err", c.description, err)
 		}
 		if entry.id == 0 {
 			// This test has a 1/(2**64) chance of failing! :o
-			t.Errorf("NewEntry(_, _).id == 0, want nonzero")
+			t.Errorf("NewEntry(_).id == 0, want nonzero")
 		}
 		if c.description != entry.description {
-			t.Errorf("NewEntry(%q, %q).description = %q, want %q",
-				c.username, c.description, entry.description, c.description)
+			t.Errorf("NewEntry(%q).description = %q, want %q",
+				c.description, entry.description, c.description)
 		}
 		if !passPattern.MatchString(password) {
-			t.Errorf("NewEntry(_, _) = _, %q, _; wanted to match xxxx-xxxx-xxxx-xxxx", password)
+			t.Errorf("NewEntry(_) = _, %q, _; wanted to match xxxx-xxxx-xxxx-xxxx", password)
 		}
-		if !entry.Authenticate(c.username, password) {
-			t.Errorf("NewEntry(%q, %q).Authenticate(%q, %q) failed",
-				c.username, c.description, c.username, password)
+		if !entry.Authenticate(password) {
+			t.Errorf("NewEntry(%q).Authenticate(%q, %q) failed",
+				c.description, password)
 		}
 	}
 }
@@ -145,26 +126,24 @@
 }
 
 func TestAuthenticate(t *testing.T) {
-	entry, password, err := NewEntry("pfish", "")
+	entry, password, err := NewEntry("")
 	if err != nil {
 		t.Errorf("Error building entry")
 	}
 	type testcase struct {
-		username, password string
+		password string
 		want               bool
 	}
 
 	cases := []testcase{
-		{"pfish", password, true},
-		{"jhh", password, false},
-		{"pfish", "not the password", false},
-		{"jhh", "not the password", false},
+		{password, true},
+		{"not the password", false},
 	}
 	for _, c := range cases {
-		got := entry.Authenticate(c.username, c.password)
+		got := entry.Authenticate(c.password)
 		if got != c.want {
-			t.Errorf("entry.Authenticate(%q, %q) == %q, want %q",
-				c.username, c.password, got, c.want)
+			t.Errorf("entry.Authenticate(%q) == %q, want %q",
+				c.password, got, c.want)
 		}
 	}
 
@@ -174,40 +153,14 @@
 	}
 
 	cases = []testcase{
-		{"jhh", "nocardio", true},
-		{"pfish", "nocardio", false},
-		{"jhh", "not the password", false},
-		{"pfish", "not the password", false},
+		{"nocardio", true},
+		{"not the password", false},
 	}
 	for _, c := range cases {
-		got := entry.Authenticate(c.username, c.password)
+		got := entry.Authenticate(c.password)
 		if got != c.want {
 			t.Errorf("entry.Authenticate(%q, %q) == %q, want %q",
-				c.username, c.password, got, c.want)
-		}
-	}
-}
-
-func testMatchesID(t *testing.T) {
-	entry, err := EntryFromShadow(basicShadow)
-	if err != nil {
-		t.Errorf("Error loading valid shadow")
-	}
-	cases := []struct {
-		username string
-		id       uint64
-		want     bool
-	}{
-		{"jhh", 1234, true},
-		{"pfish", 1234, false},
-		{"jhh", 9999, false},
-		{"pfish", 9999, false},
-	}
-	for _, c := range cases {
-		got := entry.MatchesID(c.username, c.id)
-		if got != c.want {
-			t.Errorf("entry.MatchesID(%q, %q) == %q, want %q",
-				c.username, c.id, got, c.want)
+				c.password, got, c.want)
 		}
 	}
 }
@@ -218,7 +171,7 @@
 	if err != nil {
 		t.Errorf("Error loading valid shadow")
 	}
-	extraShadowed, err := EntryFromShadow(extraDataShadow)
+	anotherShadowed, err := EntryFromShadow(anotherShadow)
 	if err != nil {
 		t.Errorf("Error loading valid shadow")
 	}
@@ -228,25 +181,14 @@
 	}{
 		{
 			&Entry{
-				username:    "testuser",
 				id:          6775,
 				hash:        "bogushash",
 				description: "something",
 			},
-			"testuser:6775:bogushash:c29tZXRoaW5n",
-		},
-		{
-			&Entry{
-				username:    "testuser",
-				id:          6775,
-				hash:        "bogushash",
-				description: "something",
-				rest:        []string{"a", "B"},
-			},
-			"testuser:6775:bogushash:c29tZXRoaW5n:a:B",
+			"6775:bogushash:c29tZXRoaW5n",
 		},
 		{shadowed, basicShadow},
-		{extraShadowed, extraDataShadow},
+		{anotherShadowed, anotherShadow},
 	}
 	for _, c := range cases {
 		got := string(c.entry.Encode())