Using Proof of Key Code Exchange (PKCE) Using rack-oauth2 as an OAuth2 Client

Proof of Key Code Exchange is an OAuth2 extension that recently been adopted as the standard for both OAuth 2.1 and IndieAuth, and provides additional security for attacks on the Authorization Code flow.

As it's still not hugely widespread, there's a gap in a lot of OAuth2 libraries for support.

I use the rack-oauth2 Gem as my OAuth2 client where possible, which also appears to have a gap in its out-of-the-box support for PKCE, but following nov's Gist, we are able to add support:

require 'base64'
require 'openssl'
require 'rack/oauth2'
require 'securerandom'

def code_challenge(code_verifier)
  Base64.urlsafe_encode64(
    OpenSSL::Digest::SHA256.digest(code_verifier)
  ).gsub(/=/, '')
end

client = get_client  'https://token'
  Rack::OAuth2::Client.new(
    identifier: '...',
    redirect_uri: '...',
    host: '...',
    authorization_endpoint: 'https;//authz',,
    token_endpoint: token_endpoint,
  )

state = SecureRandom.hex(32)
code_verifier = SecureRandom.hex(32)
nonce = SecureRandom.hex(16)

authorization_uri = client.authorization_uri(
  scope: %w(draft),
  state: state,
  nonce: nonce,
  code_challenge: code_challenge(code_verifier),
  code_challenge_method: :S256,
)
# go through the flow

client.authorization_code = '...' # provide this here
access_token = client.access_token! :body,
             code_verifier: code_verifier
# success!

Written by Jamie Tanna's profile image Jamie Tanna on , and last updated on .

Content for this article is shared under the terms of the Creative Commons Attribution Non Commercial Share Alike 4.0 International, and code is shared under the Apache License 2.0.

#blogumentation #ruby #rack #oauth2.

This post was filed under articles.

Related Posts

Other posts you may be interested in:

Interactions with this post

Interactions with this post

Below you can find the interactions that this page has had using WebMention.

Have you written a response to this post? Let me know the URL:

Do you not have a website set up with WebMention capabilities? You can use Comment Parade.