Skip to content

Commit 7b15f90

Browse files
authored
fix: Improve ok() helper function (#1542)
I'm hesitant to change this function too much, since we don't know what kind of odd dependencies on its current behavior might exist. However, adding exception chaining and surfacing the original error message seems like a risk worth taking. - Eliminate duplicated version in AuthSession by delegating to a shared implementation defined on the SDKResponse companion object. - For the SDKError case: - Set Error.message from SDKError.message - Set Error.casue from SDKError.cause - Also ran `ktlint -F` on the files I changed so that `gradle check` would pass the linting stage - Also added kotlin-ci.yml to run `./gradlew jar` on kotlin changes Fixes #1539 🦕
1 parent d880219 commit 7b15f90

File tree

3 files changed

+288
-214
lines changed

3 files changed

+288
-214
lines changed

.github/workflows/kotlin-ci.yml

+63
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
# This workflow uses actions that are not certified by GitHub.
2+
# They are provided by a third-party and are governed by
3+
# separate terms of service, privacy policy, and support
4+
# documentation.
5+
# This workflow will build a Java project with Gradle and cache/restore any dependencies to improve the workflow execution time
6+
# For more information see: https://docs.github.com/en/actions/automating-builds-and-tests/building-and-testing-java-with-gradle
7+
8+
name: Kotlin CI
9+
10+
on:
11+
pull_request:
12+
paths:
13+
- kotlin/**
14+
- .github/workflows/gradle.yml
15+
16+
push:
17+
branches: [ "main" ]
18+
paths:
19+
- kotlin/**
20+
- .github/workflows/gradle.yml
21+
22+
# TODO(#1544): Also run tests
23+
jobs:
24+
build:
25+
26+
runs-on: ubuntu-latest
27+
permissions:
28+
contents: read
29+
30+
steps:
31+
- uses: actions/checkout@v4
32+
- name: Set up JDK 17
33+
uses: actions/setup-java@v4
34+
with:
35+
java-version: '17'
36+
distribution: 'temurin'
37+
- name: Setup Gradle
38+
uses: gradle/actions/setup-gradle@af1da67850ed9a4cedd57bfd976089dd991e2582 # v4.0.0
39+
- name: Build with Gradle Wrapper
40+
run: ./gradlew jar
41+
working-directory: kotlin
42+
43+
dependency-submission:
44+
45+
runs-on: ubuntu-latest
46+
permissions:
47+
contents: write
48+
49+
steps:
50+
- uses: actions/checkout@v4
51+
- name: Set up JDK 17
52+
uses: actions/setup-java@v4
53+
with:
54+
java-version: '17'
55+
distribution: 'temurin'
56+
- run: cd kotlin
57+
58+
# Generates and submits a dependency graph, enabling Dependabot Alerts for all project dependencies.
59+
# See: https://github.com/gradle/actions/blob/main/dependency-submission/README.md
60+
- name: Generate and submit dependency graph
61+
uses: gradle/actions/dependency-submission@af1da67850ed9a4cedd57bfd976089dd991e2582 # v4.0.0
62+
with:
63+
build-root-directory: kotlin

kotlin/src/main/com/looker/rtl/AuthSession.kt

+49-60
Original file line numberDiff line numberDiff line change
@@ -30,24 +30,19 @@ open class AuthSession(
3030
open val apiSettings: ConfigurationProvider,
3131
open val transport: Transport = Transport(apiSettings),
3232
) {
33-
3433
var authToken: AuthToken = AuthToken()
3534
private var sudoToken: AuthToken = AuthToken()
3635
var sudoId: String = ""
3736

38-
/**
39-
* Abstraction of AuthToken retrieval to support sudo mode
40-
*/
37+
/** Abstraction of AuthToken retrieval to support sudo mode */
4138
fun activeToken(): AuthToken {
4239
if (sudoToken.accessToken.isNotEmpty()) {
4340
return sudoToken
4441
}
4542
return authToken
4643
}
4744

48-
/**
49-
* Is there an active authentication token?
50-
*/
45+
/** Is there an active authentication token? */
5146
open fun isAuthenticated(): Boolean {
5247
val token = activeToken()
5348
if (token.accessToken.isBlank()) return false
@@ -56,8 +51,8 @@ open class AuthSession(
5651

5752
/**
5853
* Add authentication data to the pending API request
59-
* @param[init] Initialized API request properties
6054
*
55+
* @param[init] Initialized API request properties
6156
* @return The updated request properties
6257
*/
6358
fun authenticate(init: RequestSettings): RequestSettings {
@@ -69,13 +64,11 @@ open class AuthSession(
6964
return init.copy(headers = headers)
7065
}
7166

72-
fun isSudo(): Boolean {
73-
return sudoId.isNotBlank() && sudoToken.isActive()
74-
}
67+
fun isSudo(): Boolean = sudoId.isNotBlank() && sudoToken.isActive()
7568

7669
/**
77-
* Retrieve the current authentication token. If there is no active token, performs default login to retrieve the
78-
* token.
70+
* Retrieve the current authentication token. If there is no active token, performs default
71+
* login to retrieve the token.
7972
*/
8073
open fun getToken(): AuthToken {
8174
if (!isAuthenticated()) {
@@ -84,9 +77,7 @@ open class AuthSession(
8477
return activeToken()
8578
}
8679

87-
/**
88-
* Reset the authentication session
89-
*/
80+
/** Reset the authentication session */
9081
fun reset() {
9182
sudoId = ""
9283
authToken.reset()
@@ -95,13 +86,14 @@ open class AuthSession(
9586

9687
/**
9788
* Activate the authentication token for the API3 or sudo user
89+
*
9890
* @param[sudoId] If provided, impersonates the user specified
9991
*/
100-
10192
fun login(sudoId: String = ""): AuthToken = doLogin(sudoId)
10293

10394
/**
104-
* Logout the active user. If the active user is impersonated , the session reverts to the API3 user.
95+
* Logout the active user. If the active user is impersonated , the session reverts to the API3
96+
* user.
10597
*/
10698
fun logout(): Boolean {
10799
if (isAuthenticated()) {
@@ -110,14 +102,7 @@ open class AuthSession(
110102
return false
111103
}
112104

113-
fun <T> ok(response: SDKResponse): T {
114-
@Suppress("UNCHECKED_CAST")
115-
when (response) {
116-
is SDKResponse.SDKErrorResponse<*> -> throw Error(response.value.toString())
117-
is SDKResponse.SDKSuccessResponse<*> -> return response.value as T
118-
else -> throw Error("Fail!!")
119-
}
120-
}
105+
fun <T> ok(response: SDKResponse) = SDKResponse.ok<T>(response)
121106

122107
private fun sudoLogout(): Boolean {
123108
var result = false
@@ -140,57 +125,61 @@ open class AuthSession(
140125
val client_secret = "client_secret"
141126
val config = apiSettings.readConfig()
142127
val clientId =
143-
unQuote(System.getProperty("${apiSettings.environmentPrefix}_CLIENT_ID") ?: config[client_id])
128+
unQuote(
129+
System.getProperty("${apiSettings.environmentPrefix}_CLIENT_ID")
130+
?: config[client_id],
131+
)
144132
val clientSecret =
145-
unQuote(System.getProperty("${apiSettings.environmentPrefix}_CLIENT_SECRET") ?: config[client_secret])
146-
val params = mapOf(
147-
client_id to clientId,
148-
client_secret to clientSecret,
149-
)
133+
unQuote(
134+
System.getProperty("${apiSettings.environmentPrefix}_CLIENT_SECRET")
135+
?: config[client_secret],
136+
)
137+
val params = mapOf(client_id to clientId, client_secret to clientSecret)
150138
val body = UrlEncodedContent(params)
151-
val token = ok<AuthToken>(
152-
transport.request<AuthToken>(
153-
HttpMethod.POST,
154-
"$apiPath/login",
155-
emptyMap(),
156-
body,
157-
),
158-
)
139+
val token =
140+
ok<AuthToken>(
141+
transport.request<AuthToken>(
142+
HttpMethod.POST,
143+
"$apiPath/login",
144+
emptyMap(),
145+
body,
146+
),
147+
)
159148
authToken = token
160149
}
161150

162151
if (sudoId.isNotBlank()) {
163152
val token = activeToken()
164-
val sudoToken = transport.request<AuthToken>(
165-
HttpMethod.POST,
166-
"/login/$newId",
167-
) { requestSettings ->
168-
val headers = requestSettings.headers.toMutableMap()
169-
if (token.accessToken.isNotBlank()) {
170-
headers["Authorization"] = "Bearer ${token.accessToken}"
153+
val sudoToken =
154+
transport.request<AuthToken>(HttpMethod.POST, "/login/$newId") { requestSettings ->
155+
val headers = requestSettings.headers.toMutableMap()
156+
if (token.accessToken.isNotBlank()) {
157+
headers["Authorization"] = "Bearer ${token.accessToken}"
158+
}
159+
requestSettings.copy(headers = headers)
171160
}
172-
requestSettings.copy(headers = headers)
173-
}
174161
this.sudoToken = ok(sudoToken)
175162
}
176163
return activeToken()
177164
}
178165

179166
private fun doLogout(): Boolean {
180167
val token = activeToken()
181-
val resp = transport.request<String>(HttpMethod.DELETE, "/logout") {
182-
val headers = it.headers.toMutableMap()
183-
if (token.accessToken.isNotBlank()) {
184-
headers["Authorization"] = "Bearer ${token.accessToken}"
168+
val resp =
169+
transport.request<String>(HttpMethod.DELETE, "/logout") {
170+
val headers = it.headers.toMutableMap()
171+
if (token.accessToken.isNotBlank()) {
172+
headers["Authorization"] = "Bearer ${token.accessToken}"
173+
}
174+
it.copy(headers = headers)
185175
}
186-
it.copy(headers = headers)
187-
}
188176

189-
val success = when (resp) {
190-
is SDKResponse.SDKSuccessResponse<*> -> true
191-
is SDKResponse.SDKErrorResponse<*> -> false
192-
else -> false
193-
}
177+
val success =
178+
when (resp) {
179+
is SDKResponse.SDKSuccessResponse<*> -> true
180+
is SDKResponse.SDKErrorResponse<*> -> false
181+
else -> false
182+
}
194183
if (sudoId.isNotBlank()) {
195184
sudoId = ""
196185
sudoToken.reset()

0 commit comments

Comments
 (0)