How to revoke token

Hi all,
I am trying to set up a client using Ruby.
It gets a token from hydra (after user consent), this works.
Now clients wants the user to logout and therefore revoking the access token is required.

docker-compose exec hydra hydra clients create \
	--endpoint http://127.0.0.1:4445 \
	--id test-1 \
	--secret secret \
	--grant-types authorization_code,refresh_token \
	--response-types code,id_token \
	--scope openid,offline hydra,hydra.clients,hydra.introspect \
	--callbacks http://localhost:3000/callback \
	--token-endpoint-auth-method client_secret_post

I have not created any policy (not sure, what was required for revoke).

now when I call hydra.revokeOAuth2Token(token)
it gives me following error -

  def revoke(access_token)
    agent = Faraday.new(url: 'http://hydra:4444/')
    res = agent.post('/oauth2/revoke') do |req|
      req.headers['Accept'] = 'application/json'
      req.headers['Content-Type'] = 'application/x-www-form-urlencoded'
      req.headers['Authorization'] = "Bearer #{access_token}"
      req.body = { token: access_token }.to_json
    end
    JSON.parse(res.body)
  end


I think the header and parameters are implemented correctly, but the following error is returned.

[4] pry(main)> Hydra::Client.revoke(t)
=> {"error"=>"invalid_request",
 "error_description"=>"The request is missing a required parameter, includes an invalid parameter value, includes a parameter more than once, or is otherwise malformed",
 "error_hint"=>"Make sure that the various parameters are correct, be aware of case sensitivity and trim your parameters. Make sure that the client you are using has exactly whitelisted the redirect_uri you specified.",
 "status_code"=>400}

Did I make a mistake in what I requested?
Please help me.
Thanks for reading.

I just spent a day on this same problem. Your client was created with –token-endpoint-auth-method client_secret_post. That means you need to include the client and secret as parameters in the for body. Note, that the form body is not json. It should be form url encoded. Something like this ought to work:

res = Faraday.post(url.to_s) do |req|
    req.headers['Content-Type'] = 'application/x-www-form-urlencoded'
    req.headers['Accept'] = 'application/json'
    req.body = "client_id=#{client}&client_secret#{client_secret}&token=#{token}"
end

Alternatively you can recreate your client without the token-endpoint-auth-method parameter and it will default to client_secret_basic. Then you can encode it in the Authorization header like so:

res = Faraday.post(url.to_s) do |req|
    req.headers['Content-Type'] = 'application/x-www-form-urlencoded'
    req.headers['Accept'] = 'application/json'
    auth = Base64.encode64([client, client_secret].join(':'))
    auth.delete!("\n")
    req.headers['Authorization'] = "Basic #{auth}"
    req.body = "client_id=#{client}&client_secret#{client_secret}&token=#{token}"
end

If like me, you’re writing this code because the oauth2 gem doesn’t have a token revocation method and you switch to basic auth for the token endpoint, you’ll need to change how you initialize your OAuth client and pass in :auth_scheme => :basic_auth when you create the client. My code for creating the client is:

client = OAuth2::Client.new(config.client_id, config.client_secret, :site => config.auth_server_url, :authorize_url => '/oauth2/auth', :token_url => '/oauth2/token', :auth_scheme => :basic_auth)

It’s rather a mess and not easy figuring out all of this. Good luck.

1 Like