diff --git a/.DS_Store b/.DS_Store new file mode 100644 index 0000000..5008ddf Binary files /dev/null and b/.DS_Store differ diff --git a/README.md b/README.md index 29558fb..4b8c16f 100644 --- a/README.md +++ b/README.md @@ -44,6 +44,11 @@ pkce_challenge.code_verifier # a dynamically created cryptographically random ke pkce_challenge.code_challenge # a BASE64-URL-encoded string of the SHA256 hash of the code verifier ``` +Additionally you can verify provided code_challenge based on code_verifier +```ruby +PkceChallenge.pkce_valid?(code_verifier: code_verifier, code_challenge: code_challenge) +``` + ## Development After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake spec` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment. diff --git a/lib/pkce_challenge.rb b/lib/pkce_challenge.rb index dccff9b..12e9c9f 100644 --- a/lib/pkce_challenge.rb +++ b/lib/pkce_challenge.rb @@ -23,4 +23,23 @@ class LengthOutOfRangeError < StandardError; end def self.challenge(options = {}) PkceChallenge::Challenge.new(options) end + + # Validates code challenge and verfiier + # + # Example: + # >> PkceChallenge.pkce_valid?(code_verifier: '', code_challenge: '') + # => true + # + # == Parameters: + # code_verifier:: + # A String containing code_verifier + # code_challenge:: + # A String containing code_challenge + # + # == Returns: + # An instance of Bool + # + def self.pkce_valid?(code_verifier:, code_challenge:) + PkceChallenge::Challenge.new.pkce_valid?(code_verifier: code_verifier, code_challenge: code_challenge) + end end diff --git a/lib/pkce_challenge/challenge.rb b/lib/pkce_challenge/challenge.rb index 6f07c33..a68bfe4 100644 --- a/lib/pkce_challenge/challenge.rb +++ b/lib/pkce_challenge/challenge.rb @@ -19,6 +19,10 @@ def code_challenge @code_challenge ||= generate_pkce_challenge end + def pkce_valid?(code_verifier:, code_challenge:) + code_challenge == generate_pkce_challenge(code_verifier) + end + # constants definition CHAR_LENGTH = { @@ -39,8 +43,8 @@ def generate_code_verifier urlsafe_base64(SecureRandom.base64((length * 3) / 4)) end - def generate_pkce_challenge - urlsafe_base64(Digest::SHA256.base64digest(code_verifier)) + def generate_pkce_challenge(verifier=nil) + urlsafe_base64(Digest::SHA256.base64digest(verifier || code_verifier)) end def urlsafe_base64(base64_str) diff --git a/spec/pkce_challenge_spec.rb b/spec/pkce_challenge_spec.rb index 0d589dd..df2c963 100644 --- a/spec/pkce_challenge_spec.rb +++ b/spec/pkce_challenge_spec.rb @@ -28,4 +28,16 @@ expect { invalid.code_verifier }.to raise_error(PkceChallenge::LengthOutOfRangeError) end end + + describe "#pkce_valid?" do + let(:challenge) { PkceChallenge.challenge } + + it "should returns true/false based on provided data" do + code_challenge = challenge.code_challenge + code_verifier = challenge.verifier + + expect(PkceChallenge.pkce_valid?(code_verifier: code_verifier, code_challenge: code_challenge)).to be_truthy + expect(PkceChallenge.pkce_valid?(code_verifier: code_verifier, code_challenge: 'random')).to be_falsy + end + end end