diff --git a/kotlin/src/main/com/looker/rtl/AuthSession.kt b/kotlin/src/main/com/looker/rtl/AuthSession.kt index 869d67cc7..83a044bc0 100644 --- a/kotlin/src/main/com/looker/rtl/AuthSession.kt +++ b/kotlin/src/main/com/looker/rtl/AuthSession.kt @@ -295,13 +295,20 @@ open class AuthSession( if (sudoId.isNotBlank()) { val token = activeToken() val sudoToken = - transport.request(HttpMethod.POST, "/login/$newId") { requestSettings -> - val headers = requestSettings.headers.toMutableMap() - if (token.accessToken.isNotBlank()) { - headers["Authorization"] = "token ${token.accessToken}" - } - requestSettings.copy(headers = headers) - } + transport.request( + HttpMethod.POST, + "/login/$newId", + authenticator = { requestSettings -> + val headers = requestSettings.headers.toMutableMap() + fetchIapToken()?.let { iapToken -> + headers["Proxy-Authorization"] = "Bearer $iapToken" + } + if (token.accessToken.isNotBlank()) { + headers["Authorization"] = "token ${token.accessToken}" + } + requestSettings.copy(headers = headers) + }, + ) this.sudoToken = ok(sudoToken) } return activeToken() diff --git a/kotlin/src/test/TestAuthSession.kt b/kotlin/src/test/TestAuthSession.kt index 993656a5d..6a0470151 100644 --- a/kotlin/src/test/TestAuthSession.kt +++ b/kotlin/src/test/TestAuthSession.kt @@ -22,20 +22,26 @@ * THE SOFTWARE. */ +import com.google.api.client.http.HttpTransport +import com.google.api.client.http.LowLevelHttpRequest +import com.google.api.client.http.LowLevelHttpResponse import com.looker.rtl.AuthSession import com.looker.rtl.OAuthSession import com.looker.rtl.Transport +import com.looker.rtl.TransportOptions import org.junit.Test +import java.io.ByteArrayInputStream import java.io.File +import java.io.InputStream import kotlin.test.assertEquals import kotlin.test.assertFalse import kotlin.test.assertTrue @ExperimentalUnsignedTypes class TestAuthSession { - val config = TestConfig() - val settings = config.settings - val testSettings = config.testSettings(settings) + val config by lazy { TestConfig() } + val settings by lazy { config.settings } + val testSettings by lazy { config.testSettings(settings) } @Test fun testTestFiles() { @@ -73,6 +79,62 @@ class TestAuthSession { assertFalse(session.isAuthenticated()) } + @Test + fun testSudoLoginUsesApiPrefixAndAuthHeader() { + val mockSettings = MockSettings(bareMinimum) + val requests = mutableListOf>() + val requestHeaders = mutableListOf>() + + val mockHttpTransport = object : HttpTransport() { + override fun buildRequest(method: String, url: String): LowLevelHttpRequest { + return object : LowLevelHttpRequest() { + private val headers = mutableMapOf() + + override fun addHeader(name: String, value: String) { + headers[name] = value + } + + override fun execute(): LowLevelHttpResponse { + requests.add(method to url) + requestHeaders.add(headers.toMap()) + val responseJson = if (url.endsWith("/login")) { + """{"access_token":"admin_token","token_type":"Bearer","expires_in":3600}""" + } else { + """{"access_token":"sudo_token","token_type":"Bearer","expires_in":3600}""" + } + return object : LowLevelHttpResponse() { + override fun getContent(): InputStream = + ByteArrayInputStream(responseJson.toByteArray(Charsets.UTF_8)) + override fun getContentEncoding(): String? = null + override fun getContentLength(): Long = responseJson.length.toLong() + override fun getContentType(): String = "application/json" + override fun getStatusLine(): String = "HTTP/1.1 200 OK" + override fun getStatusCode(): Int = 200 + override fun getReasonPhrase(): String = "OK" + override fun getHeaderCount(): Int = 0 + override fun getHeaderName(index: Int): String? = null + override fun getHeaderValue(index: Int): String? = null + } + } + } + } + } + + val mockTransport = object : Transport(mockSettings) { + override fun initTransport(options: TransportOptions): HttpTransport = mockHttpTransport + } + + val session = AuthSession(mockSettings, mockTransport) + val token = session.login("user_123") + + assertEquals(2, requests.size) + assertEquals("POST" to "https://my.looker.com:19999/api/4.0/login", requests[0]) + assertEquals("POST" to "https://my.looker.com:19999/api/4.0/login/user_123", requests[1]) + assertEquals("token admin_token", requestHeaders[1]["Authorization"]) + assertTrue(session.isSudo()) + assertEquals("sudo_token", token.accessToken) + } + @Test fun testSha256() { val session = OAuthSession(settings, Transport(testSettings))