Skip to content

Commit

Permalink
Merge pull request #568 from supabase-community/auth-tests
Browse files Browse the repository at this point in the history
Rework Auth tests
  • Loading branch information
jan-tennert authored May 6, 2024
2 parents 7478078 + 98820ad commit 5d3e634
Show file tree
Hide file tree
Showing 18 changed files with 900 additions and 477 deletions.
1 change: 1 addition & 0 deletions GoTrue/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,7 @@ kotlin {
val commonTest by getting {
dependencies {
implementation(libs.bundles.testing)
implementation(project(":test-common"))
}
}
val jvmMain by getting {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -144,12 +144,13 @@ sealed interface Auth : MainPlugin<AuthConfig>, CustomSerializationPlugin {
* @param provider The OAuth provider
* @param redirectUrl The redirect url to use. If you don't specify this, the platform specific will be used, like deeplinks on android.
* @param config Extra configuration
* @return The OAuth url to open in the browser if [ExternalAuthConfigDefaults.automaticallyOpenUrl] is false, otherwise null.
*/
suspend fun linkIdentity(
provider: OAuthProvider,
redirectUrl: String? = defaultRedirectUrl(),
config: ExternalAuthConfigDefaults.() -> Unit = {}
)
): String?

/**
* Unlinks an OAuth Identity from an existing user.
Expand Down Expand Up @@ -289,7 +290,7 @@ sealed interface Auth : MainPlugin<AuthConfig>, CustomSerializationPlugin {
/**
* Imports a user session and starts auto-refreshing if [autoRefresh] is true
*/
suspend fun importSession(session: UserSession, autoRefresh: Boolean = true, source: SessionSource = SessionSource.Unknown)
suspend fun importSession(session: UserSession, autoRefresh: Boolean = config.alwaysAutoRefresh, source: SessionSource = SessionSource.Unknown)

/**
* Imports the jwt token and retrieves the user profile.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -132,20 +132,28 @@ internal class AuthImpl(
provider: OAuthProvider,
redirectUrl: String?,
config: ExternalAuthConfigDefaults.() -> Unit
) {
): String? {
val automaticallyOpen = ExternalAuthConfigDefaults().apply(config).automaticallyOpenUrl
val fetchUrl: suspend (String?) -> String = { redirectTo: String? ->
val url = getOAuthUrl(provider, redirectTo, "user/identities/authorize", config)
val response = api.rawRequest(url) {
method = HttpMethod.Get
}
response.request.url.toString()
}
if(!automaticallyOpen) {
return fetchUrl(redirectUrl ?: "")
}
startExternalAuth(
redirectUrl = redirectUrl,
getUrl = {
val url = getOAuthUrl(provider, it, "user/identities/authorize", config)
val response = api.rawRequest(url) {
method = HttpMethod.Get
}
response.request.url.toString()
fetchUrl(it)
},
onSessionSuccess = {
importSession(it, source = SessionSource.UserIdentitiesChanged(it))
}
)
return null
}

override suspend fun unlinkIdentity(identityId: String, updateLocalUser: Boolean) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,9 +28,9 @@ interface CodeVerifierCache {
/**
* A [CodeVerifierCache] that uses the [AtomicRef] API.
*/
class MemoryCodeVerifierCache: CodeVerifierCache {
class MemoryCodeVerifierCache(codeVerifier: String? = null): CodeVerifierCache {

private var codeVerifier by atomic<String?>(null)
private var codeVerifier by atomic(codeVerifier)

override suspend fun saveCodeVerifier(codeVerifier: String) {
this.codeVerifier = codeVerifier
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import kotlin.io.encoding.ExperimentalEncodingApi

internal object PKCEConstants {
const val VERIFIER_LENGTH = 64
const val CHALLENGE_METHOD = "S256"
const val CHALLENGE_METHOD = "s256"
}

@OptIn(ExperimentalEncodingApi::class)
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
package io.github.jan.supabase.gotrue.providers

import io.github.jan.supabase.gotrue.Auth

/**
* Configuration for external authentication providers like Google, Twitter, etc.
*/
Expand All @@ -20,4 +22,9 @@ open class ExternalAuthConfigDefaults {
*/
val queryParams = mutableMapOf<String, String>()

/**
* Automatically open the URL in the browser. Only applies to [Auth.linkIdentity].
*/
var automaticallyOpenUrl: Boolean = true

}
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import io.github.jan.supabase.gotrue.auth
import io.github.jan.supabase.gotrue.generateCodeChallenge
import io.github.jan.supabase.gotrue.generateCodeVerifier
import io.github.jan.supabase.gotrue.providers.AuthProvider
import io.github.jan.supabase.gotrue.putCodeChallenge
import io.github.jan.supabase.gotrue.redirectTo
import io.github.jan.supabase.gotrue.user.UserSession
import io.github.jan.supabase.putJsonObject
Expand All @@ -19,7 +20,6 @@ import kotlinx.serialization.Serializable
import kotlinx.serialization.json.JsonObject
import kotlinx.serialization.json.buildJsonObject
import kotlinx.serialization.json.decodeFromJsonElement
import kotlinx.serialization.json.put

/**
* A default authentication provider
Expand Down Expand Up @@ -88,9 +88,8 @@ sealed interface DefaultAuthProvider<C, R> : AuthProvider<C, R> {
}
val response = gotrue.api.postJson(url, buildJsonObject {
putJsonObject(body)
codeChallenge?.let {
put("code_challenge", it)
put("code_challenge_method", "s256")
if (codeChallenge != null) {
putCodeChallenge(codeChallenge)
}
}) {
redirectUrl?.let { redirectTo(it) }
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import io.github.jan.supabase.gotrue.auth
import io.github.jan.supabase.gotrue.generateCodeChallenge
import io.github.jan.supabase.gotrue.generateCodeVerifier
import io.github.jan.supabase.gotrue.providers.AuthProvider
import io.github.jan.supabase.gotrue.putCaptchaToken
import io.github.jan.supabase.gotrue.user.UserSession
import io.github.jan.supabase.putJsonObject
import kotlinx.serialization.json.JsonObject
Expand All @@ -32,14 +33,15 @@ data object OTP: AuthProvider<OTP.Config, Unit> {
* @param phone The phone number of the user
* @param data Additional data to store with the user
* @param createUser Whether to create a new user if the user doesn't exist
*
* @param captchaToken The captcha token for the request
*/
class Config(
@PublishedApi internal val serializer: SupabaseSerializer,
var email: String? = null,
var phone: String? = null,
var data: JsonObject? = null,
var createUser: Boolean = true,
var captchaToken: String? = null
) {

/**
Expand Down Expand Up @@ -87,6 +89,7 @@ data object OTP: AuthProvider<OTP.Config, Unit> {
put("code_challenge", it)
put("code_challenge_method", "s256")
}
otpConfig.captchaToken?.let { putCaptchaToken(it) }
}) {
redirectUrl?.let { url.parameters.append("redirect_to", it) }
}
Expand All @@ -97,6 +100,6 @@ data object OTP: AuthProvider<OTP.Config, Unit> {
onSuccess: suspend (UserSession) -> Unit,
redirectUrl: String?,
config: (Config.() -> Unit)?
): Unit? = login(supabaseClient, onSuccess, redirectUrl, config)
): Unit = login(supabaseClient, onSuccess, redirectUrl, config)

}
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ data class UserSession(
val expiresIn: Long,
@SerialName("token_type")
val tokenType: String,
val user: UserInfo?,
val user: UserInfo? = null,
@SerialName("type")
val type: String = "",
val expiresAt: Instant = Clock.System.now() + (expiresIn.seconds),
Expand Down
5 changes: 5 additions & 0 deletions GoTrue/src/commonTest/kotlin/AdminApiTest.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
class AdminApiTest {

//TODO: Implement tests

}
Loading

0 comments on commit 5d3e634

Please sign in to comment.