@@ -90,7 +90,53 @@ In addition, the following non-RESTful endpoints are implemented by
9090
9191### Authentication and authorization
9292
93- ** TO DO**
93+ As noted above, authentication is somewhat tricky given that it runs
94+ on a different host from the GALC UI and browser makers have in the
95+ past few years cracked down hard on cross-site cookies. This makes
96+ Rails' traditional cookie-based session mechanism infeasible and
97+ requires us to rely on JSON Web Tokens.
98+
99+ Furthermore, CAS/CalNet has no provision for API-based authentication
100+ in the background; the only way to log into CalNet is to navigate to
101+ the CalNet login page.
102+
103+ The resulting authentication / authorization flow, then, is as follows:
104+
105+ 1 . User POSTs a form from the UI to the API's ` /auth/calnet ` endpoint
106+ (` login ` in [ ` routes.rb ` ] ( config/routes.rb ) . The form includes a hidden
107+ ` origin ` field with the full UI URL to which the user should be
108+ redirected after login.
109+ 2 . The API ` /auth/calnet ` endpoint constructs a CalNet callback URL, consisting
110+ of the URL for the API ` /auth/calnet/callback ` endpoint plus a ` url ` query
111+ parameter capturing the ` origin ` value from the POST payload, and sends
112+ a ` 302 Found ` response redirecting the browser to the CalNet login page,
113+ with the API callback URL (including the captured UI callback URL) as
114+ the value of a ` service ` query parameter.
115+ 3 . The user logs into CalNet, Duo, etc. and is redirected to the callback URL
116+ provided in the ` service ` parameter - the ` /auth/calnet/callback ` endpoint.
117+ 4 . The ` /auth/calnet/callback ` endpoint reads the user's identity and other
118+ relevant fields from the Omniauth / CalNet response, constructs a
119+ [ ` User ` ] ( app/models/user.rb ) object, and serializes it as an encrypted JWT,
120+ then redirects the browser back to the UI, with the JWT appended to the
121+ UI callback URL as the ` token ` query parameter.
122+ 5 . Subsequent API calls made by the UI include the still-encrypted JWT in an
123+ ` Authorization ` header.
124+
125+ The UI can access relevant user information — name, email, privileges, etc. —
126+ by querying the ` /users ` endpoint while including that token, as mentioned above,
127+ but cannot itself decrypt / encrypt tokens.
128+
129+ Within the API application, the user information serialized and encrypted
130+ in the token is treated similarly to user information serialized in a
131+ traditional session cookie — certain endpoints require authentication,
132+ others require admin privileges, and so on.
133+
134+ ** Note:** A key difference from the Library's monolithic Rails applications
135+ such as Framework, UC BEARS, and AV Player, is that unauthenticated API requests
136+ to endpoints that require authentication cannot simply be redirected to login.
137+ Instead they return ` 401 Unauthorized ` , and it is the UI's responsibility to
138+ handle the situtation appropriately. In most other respects, GALC API
139+ authorization code is similar to those other apps.
94140
95141### JSON serialization
96142
0 commit comments