Skip to content

Instantly share code, notes, and snippets.

@ffeldhaus
Last active December 6, 2023 14:30
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 2 You must be signed in to fork a gist
  • Save ffeldhaus/8959e84baebefe3df21be186ceabb7b0 to your computer and use it in GitHub Desktop.
Save ffeldhaus/8959e84baebefe3df21be186ceabb7b0 to your computer and use it in GitHub Desktop.
Using OAuth 2.0 with PowerShell to authenticate against Google Services
# configuration (adapt to your setup!)
$CertFile = "$HOME/certificate.p12"
$CertPassword = "notasecret"
$Project = "myproject"
$ServiceAccountName = "service-account"
$ServiceAccount = "$ServiceAccountName@$Project.iam.gserviceaccount.com"
$Scope = "https://www.googleapis.com/auth/cloud-platform"
$ExpirationSeconds = 3600
# import certificate
$Certificate = [System.Security.Cryptography.X509Certificates.X509Certificate2]::new($CertFile,$CertPassword,[System.Security.Cryptography.X509Certificates.X509KeyStorageFlags]::Exportable)
$RSACryptoServiceProvider = New-Object System.Security.Cryptography.RSACryptoServiceProvider
$RSACryptoServiceProvider.ImportParameters($Certificate.PrivateKey.ExportParameters($true))
# create JWT Header
$JwtHeader = '{"alg":"RS256","typ":"JWT"}'
$JwtHeaderBase64 = [Convert]::ToBase64String([Text.Encoding]::UTF8.GetBytes($JwtHeader))
$JwtHeaderBase64UrlEncoded = $JwtHeaderBase64 -replace "/","_" -replace "\+","-" -replace "=", ""
# create JWT Claim Set
$Now = (Get-Date).ToUniversalTime()
$NowUnixTimestamp = [Math]::Floor([decimal](Get-Date -Date $Now -UFormat "%s"))
$ExpirationUnixTimestamp = $NowUnixTimestamp + $ExpirationSeconds
$JwtClaimSet = @"
{"iss":"$ServiceAccount","scope":"$Scope","aud":"https://oauth2.googleapis.com/token","exp":$ExpirationUnixTimestamp,"iat":$NowUnixTimestamp}
"@
$JwtClaimSetBase64 = [Convert]::ToBase64String([Text.Encoding]::UTF8.GetBytes($JwtClaimSet))
$JwtClaimSetBase64UrlEncoded = $JwtClaimSetBase64 -replace "/","_" -replace "\+","-" -replace "=", ""
# calculate Signature
$StringToSign = $JwtHeaderBase64UrlEncoded + "." + $JwtClaimSetBase64UrlEncoded
$SHA256 = [System.Security.Cryptography.SHA256]::Create()
$Hash = $SHA256.ComputeHash([Text.Encoding]::UTF8.GetBytes($StringToSign))
$SignatureBase64 = [Convert]::ToBase64String($RSACryptoServiceProvider.SignData([System.Text.Encoding]::UTF8.GetBytes($StringToSign),"SHA256"))
$SignatureBase64UrlEncoded = $SignatureBase64 -replace "/","_" -replace "\+","-" -replace "=", ""
# create JWT
$Jwt = $JwtHeaderBase64UrlEncoded + "." + $JwtClaimSetBase64UrlEncoded + "." + $SignatureBase64UrlEncoded
# send JWT request for oauth access token
$Body = "grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Ajwt-bearer&assertion=$Jwt"
$AccessToken = Invoke-RestMethod -Method Post -Uri "https://oauth2.googleapis.com/token" -ContentType "application/x-www-form-urlencoded" -Body $Body | Select-Object -ExpandProperty access_token
# Now you can start a BigQuery request using the oauth access token
$Body = @"
{
"query": "SELECT * FROM ``bigquery-public-data.samples.wikipedia`` LIMIT 10",
"location": "US",
"useLegacySql": false
}
"@
Invoke-RestMethod -Method Post -Uri "https://bigquery.googleapis.com/bigquery/v2/projects/$Project/queries" -Headers @{"Authorization"="Bearer $AccessToken"} -Body $Body -ContentType "text/plain"
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment