diff options
author | pg9182 <96569817+pg9182@users.noreply.github.com> | 2023-02-27 00:28:35 -0500 |
---|---|---|
committer | pg9182 <96569817+pg9182@users.noreply.github.com> | 2023-03-04 00:49:32 -0500 |
commit | e662e1297b2d5b6b46549788171a79eedf4caca7 (patch) | |
tree | 806a65637820f5784b039eb4de10cf91008a343c /pkg/api/api0 | |
parent | d905e4eca49f121dbd374254daa6b506d102045e (diff) | |
download | Atlas-e662e1297b2d5b6b46549788171a79eedf4caca7.tar.gz Atlas-e662e1297b2d5b6b46549788171a79eedf4caca7.zip |
pkg/atlas, pkg/api/api0: Make username source configurable
Diffstat (limited to 'pkg/api/api0')
-rw-r--r-- | pkg/api/api0/api.go | 7 | ||||
-rw-r--r-- | pkg/api/api0/client.go | 141 |
2 files changed, 95 insertions, 53 deletions
diff --git a/pkg/api/api0/api.go b/pkg/api/api0/api.go index 1c2683f..3ed5999 100644 --- a/pkg/api/api0/api.go +++ b/pkg/api/api0/api.go @@ -43,8 +43,11 @@ type Handler struct { // PdataStorage stores player data. It must be non-nil. PdataStorage PdataStorage - // OriginAuthMgr manages Origin nucleus tokens (used for checking - // usernames). If not provided, usernames will not be updated. + // UsernameSource configures the source to use for usernames. + UsernameSource UsernameSource + + // OriginAuthMgr, if provided, manages Origin nucleus tokens for checking + // usernames. OriginAuthMgr *origin.AuthMgr // CleanBadWords is used to filter bad words from server names and diff --git a/pkg/api/api0/client.go b/pkg/api/api0/client.go index b64659a..9b1408f 100644 --- a/pkg/api/api0/client.go +++ b/pkg/api/api0/client.go @@ -18,6 +18,17 @@ import ( "github.com/rs/zerolog/hlog" ) +// UsernameSource determines where to get player in-game usernames from. +type UsernameSource string + +const ( + // Don't get usernames. + UsernameSourceNone UsernameSource = "" + + // Get the username from the Origin API. + UsernameSourceOrigin UsernameSource = "origin" +) + type MainMenuPromos struct { NewInfo MainMenuPromosNew `json:"newInfo"` LargeButton MainMenuPromosButtonLarge `json:"largeButton"` @@ -186,56 +197,7 @@ func (h *Handler) handleClientOriginAuth(w http.ResponseWriter, r *http.Request) } } - var username string - if h.OriginAuthMgr != nil { - originStart := time.Now() - if tok, ours, err := h.OriginAuthMgr.OriginAuth(false); err == nil { - var notfound bool - if ui, err := origin.GetUserInfo(r.Context(), tok, uid); err == nil { - if len(ui) == 1 { - username = ui[0].EAID - h.m().client_originauth_origin_username_lookup_calls_total.success.Inc() - } else { - notfound = true - h.m().client_originauth_origin_username_lookup_calls_total.notfound.Inc() - } - } else if errors.Is(err, origin.ErrAuthRequired) { - if tok, ours, err := h.OriginAuthMgr.OriginAuth(true); err == nil { - if ui, err := origin.GetUserInfo(r.Context(), tok, uid); err == nil { - if len(ui) == 1 { - username = ui[0].EAID - h.m().client_originauth_origin_username_lookup_calls_total.success.Inc() - } else { - notfound = true - h.m().client_originauth_origin_username_lookup_calls_total.notfound.Inc() - } - } - } else if ours { - hlog.FromRequest(r).Error(). - Err(err). - Msgf("origin auth token refresh failure") - h.m().client_originauth_origin_username_lookup_calls_total.fail_authtok_refresh.Inc() - } - } else if !errors.Is(err, context.Canceled) { - hlog.FromRequest(r).Error(). - Err(err). - Msgf("failed to get origin user info") - h.m().client_originauth_origin_username_lookup_calls_total.fail_other_error.Inc() - } - if notfound { - hlog.FromRequest(r).Warn(). - Err(err). - Uint64("uid", uid). - Msgf("no username found for uid") - } - } else if ours { - hlog.FromRequest(r).Error(). - Err(err). - Msgf("origin auth token refresh failure") - h.m().client_originauth_origin_username_lookup_calls_total.fail_authtok_refresh.Inc() - } - h.m().client_originauth_origin_username_lookup_duration_seconds.UpdateDuration(originStart) - } + username := h.lookupUsername(r, uid) // note: there's small chance of race conditions here if there are multiple // concurrent origin_auth calls, but since we only ever support one session @@ -258,7 +220,7 @@ func (h *Handler) handleClientOriginAuth(w http.ResponseWriter, r *http.Request) } if acct != nil && username != "" && acct.Username != username { - hlog.FromRequest(r).Info().Uint64("uid", acct.UID).Str("username", username).Str("prev_username", acct.Username).Msg("got updated username from origin") + hlog.FromRequest(r).Info().Uint64("uid", acct.UID).Str("username", username).Str("prev_username", acct.Username).Msg("got updated username") } if acct == nil { acct = &Account{ @@ -306,6 +268,83 @@ func (h *Handler) handleClientOriginAuth(w http.ResponseWriter, r *http.Request) }) } +// lookupUsername gets the username for uid according to the configured +// UsernameSource, returning an empty string if not found or on error. +func (h *Handler) lookupUsername(r *http.Request, uid uint64) (username string) { + switch h.UsernameSource { + case UsernameSourceNone: + break + case UsernameSourceOrigin: + username, _ = h.lookupUsernameOrigin(r, uid) + default: + hlog.FromRequest(r).Error(). + Msgf("unknown username source %q", h.UsernameSource) + } + return +} + +// lookupUsernameOrigin gets the username for uid from the Origin API, returning +// an empty string if a username does not exist for the uid, and false on error. +func (h *Handler) lookupUsernameOrigin(r *http.Request, uid uint64) (username string, ok bool) { + if h.OriginAuthMgr == nil { + hlog.FromRequest(r).Error(). + Str("username_source", "origin"). + Msgf("no origin auth available for username lookup") + return + } + originStart := time.Now() + if tok, ours, err := h.OriginAuthMgr.OriginAuth(false); err == nil { + if ui, err := origin.GetUserInfo(r.Context(), tok, uid); err == nil { + if len(ui) == 1 { + username = ui[0].EAID + h.m().client_originauth_origin_username_lookup_calls_total.success.Inc() + } else { + h.m().client_originauth_origin_username_lookup_calls_total.notfound.Inc() + } + ok = true + } else if errors.Is(err, origin.ErrAuthRequired) { + if tok, ours, err := h.OriginAuthMgr.OriginAuth(true); err == nil { + if ui, err := origin.GetUserInfo(r.Context(), tok, uid); err == nil { + if len(ui) == 1 { + username = ui[0].EAID + h.m().client_originauth_origin_username_lookup_calls_total.success.Inc() + } else { + h.m().client_originauth_origin_username_lookup_calls_total.notfound.Inc() + } + ok = true + } + } else if ours { + hlog.FromRequest(r).Error(). + Err(err). + Str("username_source", "origin"). + Msgf("origin auth token refresh failure") + h.m().client_originauth_origin_username_lookup_calls_total.fail_authtok_refresh.Inc() + } + } else if !errors.Is(err, context.Canceled) { + hlog.FromRequest(r).Error(). + Err(err). + Str("username_source", "origin"). + Msgf("failed to get origin user info") + h.m().client_originauth_origin_username_lookup_calls_total.fail_other_error.Inc() + } + if username == "" && ok { + hlog.FromRequest(r).Warn(). + Err(err). + Uint64("uid", uid). + Str("username_source", "origin"). + Msgf("no origin username found for uid") + } + } else if ours { + hlog.FromRequest(r).Error(). + Err(err). + Str("username_source", "origin"). + Msgf("origin auth token refresh failure") + h.m().client_originauth_origin_username_lookup_calls_total.fail_authtok_refresh.Inc() + } + h.m().client_originauth_origin_username_lookup_duration_seconds.UpdateDuration(originStart) + return +} + func (h *Handler) handleClientAuthWithServer(w http.ResponseWriter, r *http.Request) { if r.Method != http.MethodOptions && r.Method != http.MethodPost { h.m().client_authwithserver_requests_total.http_method_not_allowed.Inc() |