From ad89cbb410b13b15da0cce1077f94b3964f2845f Mon Sep 17 00:00:00 2001 From: Christopher Cameron <101140818+chriscameron-vertexinc@users.noreply.github.com> Date: Wed, 15 May 2024 18:51:24 -0400 Subject: [PATCH] feat: Add data:application/json;base64 support to AuthenticationOauth2 (#263) * feat: Add data:application/json;base64 support to AuthenticationOauth2 * Refactoring * Fix build --------- Co-authored-by: Vladimir Shchur --- global.json | 2 +- .../Auth/Oauth2/AuthenticationOauth2.fs | 33 +++++++++++++++---- 2 files changed, 27 insertions(+), 8 deletions(-) diff --git a/global.json b/global.json index e99a8a81..7fa817ce 100644 --- a/global.json +++ b/global.json @@ -1,5 +1,5 @@ { "sdk": { - "version": "8.0.202" + "version": "8.0.300" } } \ No newline at end of file diff --git a/src/Pulsar.Client/Auth/Oauth2/AuthenticationOauth2.fs b/src/Pulsar.Client/Auth/Oauth2/AuthenticationOauth2.fs index 81158dbf..ff907c9d 100644 --- a/src/Pulsar.Client/Auth/Oauth2/AuthenticationOauth2.fs +++ b/src/Pulsar.Client/Auth/Oauth2/AuthenticationOauth2.fs @@ -6,7 +6,7 @@ open System.IO open System.Text.Json open System.Net.Http open System.Text.Json.Serialization -open Microsoft.Extensions.DependencyInjection +open System.Threading.Tasks open Pulsar.Client.Api open Pulsar.Client.Common open FSharp.UMX @@ -50,7 +50,7 @@ type Credentials = IssuerUrl : string } -type internal AuthenticationOauth2(issuerUrl: Uri, audience: string, privateKey: Uri, scope: string) = +type internal AuthenticationOauth2(issuerUrl: Uri, audience: string, credentialsUrl: Uri, scope: string) = inherit Authentication() let mutable token : Option = None @@ -74,13 +74,32 @@ type internal AuthenticationOauth2(issuerUrl: Uri, audience: string, privateKey: return TokenClient(Uri(metadata.TokenEndpoint), httpClient) } - let openAndDeserializeCreds uri = + let getCredsFromFile (credentialsUrl: Uri) = backgroundTask { - use fs = new FileStream(uri, FileMode.Open, FileAccess.Read) - let! temp = JsonSerializer.DeserializeAsync(fs) - return temp + use fs = new FileStream(credentialsUrl.LocalPath, FileMode.Open, FileAccess.Read) + return! JsonSerializer.DeserializeAsync(fs) } + let getCredsFromDataEncodedUri (credentialsUrl: Uri) = + match credentialsUrl.LocalPath.Split(',', 2) with + | [| contentType; data |] when contentType = "application/json;base64" -> + data + |> Convert.FromBase64String + |> JsonSerializer.Deserialize + | [| contentType; _ |] -> + raise <| NotSupportedException $"Content type '{contentType}' is not supported." + | _ -> + raise <| FormatException "The credentials are not in the expected format." + + let deserializeCreds (credentialsUrl: Uri) = + match credentialsUrl.Scheme with + | "file" -> + getCredsFromFile credentialsUrl + | "data" -> + getCredsFromDataEncodedUri credentialsUrl |> Task.FromResult + | _ -> + raise <| NotSupportedException($"Scheme '{credentialsUrl.Scheme}' is not supported.") + //https://datatracker.ietf.org/doc/html/rfc6749#section-4.2.2 let tryGetToken() = token @@ -101,7 +120,7 @@ type internal AuthenticationOauth2(issuerUrl: Uri, audience: string, privateKey: | None -> let newToken = (backgroundTask { - let! credentials = openAndDeserializeCreds(privateKey.LocalPath) + let! credentials = deserializeCreds credentialsUrl let! tokenClient = getTokenClient() return! tokenClient.ExchangeClientCredentials(