-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat: add contact and identifier types (#37)
- Loading branch information
1 parent
9339923
commit 9327b95
Showing
3 changed files
with
372 additions
and
5 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,112 @@ | ||
package healthcrm | ||
|
||
import ( | ||
"fmt" | ||
"io" | ||
"strconv" | ||
) | ||
|
||
type IdentifierType string | ||
|
||
type ContactType string | ||
|
||
const ( | ||
// Identifier types | ||
IdentifierTypeNationalID IdentifierType = "NATIONAL_ID" | ||
IdentifierTypePassportNo IdentifierType = "PASSPORT_NO" | ||
IdentifierTypeMilitaryID IdentifierType = "MILITARY_ID" | ||
IdentifierTypeAlienID IdentifierType = "ALIEN_ID" | ||
IdentifierTypeNHIFNo IdentifierType = "NHIF_NO" | ||
IdentifierTypePatientNo IdentifierType = "PATIENT_NO" | ||
IdentifierTypePayerMemberNo IdentifierType = "PAYER_MEMBER_NO" | ||
IdentifierTypeSmartMemberNo IdentifierType = "SMART_MEMBER_NO" | ||
IdentifierTypeFHIRPatientID IdentifierType = "FHIR_PATIENT_ID" | ||
IdentifierTypeERPCustomerID IdentifierType = "ERP_CUSTOMER_ID" | ||
IdentifierTypeCCCNumber IdentifierType = "CCC_NUMBER" | ||
) | ||
|
||
const ( | ||
ContactTypePhoneNumber ContactType = "PHONE_NUMBER" | ||
ContactTypeEmail ContactType = "EMAIL" | ||
) | ||
|
||
// IsValid returns true if a contact type is valid | ||
func (f ContactType) IsValid() bool { | ||
switch f { | ||
case ContactTypePhoneNumber, ContactTypeEmail: | ||
return true | ||
default: | ||
return false | ||
} | ||
} | ||
|
||
// String converts the contact type enum to a string | ||
func (f ContactType) String() string { | ||
return string(f) | ||
} | ||
|
||
// UnmarshalGQL converts the supplied value to a contact type. | ||
func (f *ContactType) UnmarshalGQL(v interface{}) error { | ||
str, ok := v.(string) | ||
if !ok { | ||
return fmt.Errorf("enums must be strings") | ||
} | ||
|
||
*f = ContactType(str) | ||
if !f.IsValid() { | ||
return fmt.Errorf("%s is not a valid ContactType type", str) | ||
} | ||
|
||
return nil | ||
} | ||
|
||
// MarshalGQL writes the contact type to the supplied writer | ||
func (f ContactType) MarshalGQL(w io.Writer) { | ||
fmt.Fprint(w, strconv.Quote(f.String())) | ||
} | ||
|
||
// IsValid returns true if an identifier type is valid | ||
func (f IdentifierType) IsValid() bool { | ||
switch f { | ||
case | ||
IdentifierTypeNationalID, | ||
IdentifierTypePassportNo, | ||
IdentifierTypeMilitaryID, | ||
IdentifierTypeAlienID, | ||
IdentifierTypeNHIFNo, | ||
IdentifierTypePatientNo, | ||
IdentifierTypePayerMemberNo, | ||
IdentifierTypeSmartMemberNo, | ||
IdentifierTypeFHIRPatientID, | ||
IdentifierTypeERPCustomerID, | ||
IdentifierTypeCCCNumber: | ||
return true | ||
default: | ||
return false | ||
} | ||
} | ||
|
||
// String converts the identifier type enum to a string | ||
func (f IdentifierType) String() string { | ||
return string(f) | ||
} | ||
|
||
// UnmarshalGQL converts the supplied value to an identifier type. | ||
func (f *IdentifierType) UnmarshalGQL(v interface{}) error { | ||
str, ok := v.(string) | ||
if !ok { | ||
return fmt.Errorf("enums must be strings") | ||
} | ||
|
||
*f = IdentifierType(str) | ||
if !f.IsValid() { | ||
return fmt.Errorf("%s is not a valid IdentifierType type", str) | ||
} | ||
|
||
return nil | ||
} | ||
|
||
// MarshalGQL writes the identifier type to the supplied writer | ||
func (f IdentifierType) MarshalGQL(w io.Writer) { | ||
fmt.Fprint(w, strconv.Quote(f.String())) | ||
} |
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,253 @@ | ||
package healthcrm | ||
|
||
import ( | ||
"bytes" | ||
"strconv" | ||
"testing" | ||
) | ||
|
||
func TestIdentifierType_String(t *testing.T) { | ||
tests := []struct { | ||
name string | ||
e IdentifierType | ||
want string | ||
}{ | ||
{ | ||
name: "happy case: enum to string", | ||
e: IdentifierTypeNationalID, | ||
want: "NATIONAL_ID", | ||
}, | ||
} | ||
for _, tt := range tests { | ||
t.Run(tt.name, func(t *testing.T) { | ||
if got := tt.e.String(); got != tt.want { | ||
t.Errorf("IdentifierType.String() = %v, want %v", got, tt.want) | ||
} | ||
}) | ||
} | ||
} | ||
|
||
func TestIdentifierType_IsValid(t *testing.T) { | ||
tests := []struct { | ||
name string | ||
e IdentifierType | ||
want bool | ||
}{ | ||
{ | ||
name: "valid type", | ||
e: IdentifierTypeNationalID, | ||
want: true, | ||
}, | ||
{ | ||
name: "invalid type", | ||
e: IdentifierType("invalid"), | ||
want: false, | ||
}, | ||
} | ||
for _, tt := range tests { | ||
t.Run(tt.name, func(t *testing.T) { | ||
if got := tt.e.IsValid(); got != tt.want { | ||
t.Errorf("IdentifierType.IsValid() = %v, want %v", got, tt.want) | ||
} | ||
}) | ||
} | ||
} | ||
|
||
func TestIdentifierType_UnmarshalGQL(t *testing.T) { | ||
value := IdentifierTypeNationalID | ||
invalid := IdentifierType("invalid") | ||
|
||
type args struct { | ||
v interface{} | ||
} | ||
|
||
tests := []struct { | ||
name string | ||
e *IdentifierType | ||
args args | ||
wantErr bool | ||
}{ | ||
{ | ||
name: "valid type", | ||
e: &value, | ||
args: args{ | ||
v: "NATIONAL_ID", | ||
}, | ||
wantErr: false, | ||
}, | ||
{ | ||
name: "invalid type", | ||
e: &invalid, | ||
args: args{ | ||
v: "this is not a valid type", | ||
}, | ||
wantErr: true, | ||
}, | ||
{ | ||
name: "non string type", | ||
e: &invalid, | ||
args: args{ | ||
v: 1, | ||
}, | ||
wantErr: true, | ||
}, | ||
} | ||
for _, tt := range tests { | ||
t.Run(tt.name, func(t *testing.T) { | ||
if err := tt.e.UnmarshalGQL(tt.args.v); (err != nil) != tt.wantErr { | ||
t.Errorf("IdentifierType.UnmarshalGQL() error = %v, wantErr %v", err, tt.wantErr) | ||
} | ||
}) | ||
} | ||
} | ||
|
||
func TestIdentifierType_MarshalGQL(t *testing.T) { | ||
w := &bytes.Buffer{} | ||
|
||
tests := []struct { | ||
name string | ||
e IdentifierType | ||
b *bytes.Buffer | ||
wantW string | ||
panic bool | ||
}{ | ||
{ | ||
name: "valid type enums", | ||
e: IdentifierTypeNationalID, | ||
b: w, | ||
wantW: strconv.Quote("NATIONAL_ID"), | ||
}, | ||
} | ||
for _, tt := range tests { | ||
t.Run(tt.name, func(t *testing.T) { | ||
tt.e.MarshalGQL(tt.b) | ||
|
||
if gotW := w.String(); gotW != tt.wantW { | ||
t.Errorf("IdentifierType.MarshalGQL() = %v, want %v", gotW, tt.wantW) | ||
} | ||
}) | ||
} | ||
} | ||
|
||
func TestContactType_String(t *testing.T) { | ||
tests := []struct { | ||
name string | ||
e ContactType | ||
want string | ||
}{ | ||
{ | ||
name: "happy case: enum to string", | ||
e: ContactTypePhoneNumber, | ||
want: "PHONE_NUMBER", | ||
}, | ||
} | ||
for _, tt := range tests { | ||
t.Run(tt.name, func(t *testing.T) { | ||
if got := tt.e.String(); got != tt.want { | ||
t.Errorf("ContactType.String() = %v, want %v", got, tt.want) | ||
} | ||
}) | ||
} | ||
} | ||
|
||
func TestContactType_IsValid(t *testing.T) { | ||
tests := []struct { | ||
name string | ||
e ContactType | ||
want bool | ||
}{ | ||
{ | ||
name: "valid type", | ||
e: ContactTypePhoneNumber, | ||
want: true, | ||
}, | ||
{ | ||
name: "invalid type", | ||
e: ContactType("invalid"), | ||
want: false, | ||
}, | ||
} | ||
for _, tt := range tests { | ||
t.Run(tt.name, func(t *testing.T) { | ||
if got := tt.e.IsValid(); got != tt.want { | ||
t.Errorf("ContactType.IsValid() = %v, want %v", got, tt.want) | ||
} | ||
}) | ||
} | ||
} | ||
|
||
func TestContactType_UnmarshalGQL(t *testing.T) { | ||
value := ContactTypePhoneNumber | ||
invalid := ContactType("invalid") | ||
|
||
type args struct { | ||
v interface{} | ||
} | ||
|
||
tests := []struct { | ||
name string | ||
e *ContactType | ||
args args | ||
wantErr bool | ||
}{ | ||
{ | ||
name: "valid type", | ||
e: &value, | ||
args: args{ | ||
v: "PHONE_NUMBER", | ||
}, | ||
wantErr: false, | ||
}, | ||
{ | ||
name: "invalid type", | ||
e: &invalid, | ||
args: args{ | ||
v: "this is not a valid type", | ||
}, | ||
wantErr: true, | ||
}, | ||
{ | ||
name: "non string type", | ||
e: &invalid, | ||
args: args{ | ||
v: 1, | ||
}, | ||
wantErr: true, | ||
}, | ||
} | ||
for _, tt := range tests { | ||
t.Run(tt.name, func(t *testing.T) { | ||
if err := tt.e.UnmarshalGQL(tt.args.v); (err != nil) != tt.wantErr { | ||
t.Errorf("ContactType.UnmarshalGQL() error = %v, wantErr %v", err, tt.wantErr) | ||
} | ||
}) | ||
} | ||
} | ||
|
||
func TestContactType_MarshalGQL(t *testing.T) { | ||
w := &bytes.Buffer{} | ||
|
||
tests := []struct { | ||
name string | ||
e ContactType | ||
b *bytes.Buffer | ||
wantW string | ||
panic bool | ||
}{ | ||
{ | ||
name: "valid type enums", | ||
e: ContactTypePhoneNumber, | ||
b: w, | ||
wantW: strconv.Quote("PHONE_NUMBER"), | ||
}, | ||
} | ||
for _, tt := range tests { | ||
t.Run(tt.name, func(t *testing.T) { | ||
tt.e.MarshalGQL(tt.b) | ||
|
||
if gotW := w.String(); gotW != tt.wantW { | ||
t.Errorf("ContactType.MarshalGQL() = %v, want %v", gotW, tt.wantW) | ||
} | ||
}) | ||
} | ||
} |
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