package otp_test import ( "dev.justinjudd.org/justin/otp" ) var Issuer = "example.com" func CreateKeyForUser(user string) { opts := otp.NewHOTPKeyOptions() opts.Issuer = Issuer opts.Label = user key := otp.NewHOTPKey(opts) keyURL := key.URL() Store(user, keyURL) // Provide the URL to the customer so they can include it in their 2FA client. // Can email URL, or present QR code encoding of the URL } // Store this string variable in your database func Store(user, url string) { } // Retrieve the url string variable from your database func GetURL(user string) string { return "" } // get the OTP code from the user func getCode() string { return "" } func CheckUsersCode(user string, code string) (bool, error) { keyURL := GetURL(user) key, err := otp.FromURL(keyURL) if err != nil { return false, err } // Ensure you are using the correct key if key.Label() != user { return false, nil } success := key.Verify(code) // Counter has been updated, update this info in the database // Don't need this step for TOTP keys as the counter is time-based keyURL = key.URL() return success, nil } func Example_hOTPServer() { // Create new user user := "username" CreateKeyForUser(user) // When user is authenticating // Perform password based auth - if that is successful, then continue code := getCode() success, err := CheckUsersCode(user, code) if err != nil { // Handle error } if success { // User is authenticated } }