Compare commits

...

2 Commits

Author SHA1 Message Date
Matt Jankowski
8021229257
Merge 4393bd395a into 94bceb8683 2025-07-11 14:05:42 +00:00
Matt Jankowski
4393bd395a Convert to doorkeeper ORM mixin style for OAuth models 2025-07-03 18:28:24 -04:00
39 changed files with 158 additions and 157 deletions

View File

@ -4,7 +4,7 @@ class Api::V1::AppsController < Api::BaseController
skip_before_action :require_authenticated_user! skip_before_action :require_authenticated_user!
def create def create
@app = Doorkeeper::Application.create!(application_options) @app = OAuth::Application.create!(application_options)
render json: @app, serializer: REST::CredentialApplicationSerializer render json: @app, serializer: REST::CredentialApplicationSerializer
end end

View File

@ -17,7 +17,7 @@ class OAuth::AuthorizedApplicationsController < Doorkeeper::AuthorizedApplicatio
def destroy def destroy
Web::PushSubscription.unsubscribe_for(params[:id], current_resource_owner) Web::PushSubscription.unsubscribe_for(params[:id], current_resource_owner)
Doorkeeper::Application.find_by(id: params[:id])&.close_streaming_sessions(current_resource_owner) OAuth::Application.find_by(id: params[:id])&.close_streaming_sessions(current_resource_owner)
super super
end end

View File

@ -10,7 +10,7 @@ class Settings::ApplicationsController < Settings::BaseController
def show; end def show; end
def new def new
@application = Doorkeeper::Application.new( @application = OAuth::Application.new(
redirect_uri: Doorkeeper.configuration.native_redirect_uri, redirect_uri: Doorkeeper.configuration.native_redirect_uri,
scopes: 'profile' scopes: 'profile'
) )
@ -59,6 +59,6 @@ class Settings::ApplicationsController < Settings::BaseController
end end
def application_params def application_params
params.expect(doorkeeper_application: [:name, :redirect_uri, :website, scopes: []]) params.expect(oauth_application: [:name, :redirect_uri, :website, scopes: []])
end end
end end

View File

@ -1,10 +0,0 @@
# frozen_string_literal: true
module AccessGrantExtension
extend ActiveSupport::Concern
included do
scope :expired, -> { where.not(expires_in: nil).where('created_at + MAKE_INTERVAL(secs => expires_in) < NOW()') }
scope :revoked, -> { where.not(revoked_at: nil).where(revoked_at: ...Time.now.utc) }
end
end

View File

@ -1,29 +0,0 @@
# frozen_string_literal: true
module AccessTokenExtension
extend ActiveSupport::Concern
included do
include Redisable
has_many :web_push_subscriptions, class_name: 'Web::PushSubscription', inverse_of: :access_token
after_commit :push_to_streaming_api
scope :expired, -> { where.not(expires_in: nil).where('created_at + MAKE_INTERVAL(secs => expires_in) < NOW()') }
scope :not_revoked, -> { where(revoked_at: nil) }
scope :revoked, -> { where.not(revoked_at: nil).where(revoked_at: ...Time.now.utc) }
end
def revoke(clock = Time)
update(revoked_at: clock.now.utc)
end
def update_last_used(request, clock = Time)
update(last_used_at: clock.now.utc, last_used_ip: request.remote_ip)
end
def push_to_streaming_api
redis.publish("timeline:access_token:#{id}", Oj.dump(event: :kill)) if revoked? || destroyed?
end
end

View File

@ -1,49 +0,0 @@
# frozen_string_literal: true
module ApplicationExtension
extend ActiveSupport::Concern
APP_NAME_LIMIT = 60
APP_REDIRECT_URI_LIMIT = 2_000
APP_WEBSITE_LIMIT = 2_000
included do
include Redisable
has_many :created_users, class_name: 'User', foreign_key: 'created_by_application_id', inverse_of: :created_by_application
validates :name, length: { maximum: APP_NAME_LIMIT }
validates :redirect_uri, length: { maximum: APP_REDIRECT_URI_LIMIT }
validates :website, url: true, length: { maximum: APP_WEBSITE_LIMIT }, if: :website?
# The relationship used between Applications and AccessTokens is using
# dependent: delete_all, which means the ActiveRecord callback in
# AccessTokenExtension is not run, so instead we manually announce to
# streaming that these tokens are being deleted.
before_destroy :close_streaming_sessions, prepend: true
end
def confirmation_redirect_uri
redirect_uri.lines.first.strip
end
def redirect_uris
# Doorkeeper stores the redirect_uri value as a newline delimeted list in
# the database:
redirect_uri.split
end
def close_streaming_sessions(resource_owner = nil)
# TODO: #28793 Combine into a single topic
payload = Oj.dump(event: :kill)
scope = access_tokens
scope = scope.where(resource_owner_id: resource_owner.id) unless resource_owner.nil?
scope.in_batches do |tokens|
redis.pipelined do |pipeline|
tokens.ids.each do |id|
pipeline.publish("timeline:access_token:#{id}", payload)
end
end
end
end
end

View File

@ -9,12 +9,12 @@ class Vacuum::AccessTokensVacuum
private private
def vacuum_revoked_access_tokens! def vacuum_revoked_access_tokens!
Doorkeeper::AccessToken.expired.in_batches.delete_all OAuth::AccessToken.expired.in_batches.delete_all
Doorkeeper::AccessToken.revoked.in_batches.delete_all OAuth::AccessToken.revoked.in_batches.delete_all
end end
def vacuum_revoked_access_grants! def vacuum_revoked_access_grants!
Doorkeeper::AccessGrant.expired.in_batches.delete_all OAuth::AccessGrant.expired.in_batches.delete_all
Doorkeeper::AccessGrant.revoked.in_batches.delete_all OAuth::AccessGrant.revoked.in_batches.delete_all
end end
end end

7
app/models/oauth.rb Normal file
View File

@ -0,0 +1,7 @@
# frozen_string_literal: true
module OAuth
def self.table_name_prefix
'oauth_'
end
end

View File

@ -0,0 +1,8 @@
# frozen_string_literal: true
class OAuth::AccessGrant < ApplicationRecord
include ::Doorkeeper::Orm::ActiveRecord::Mixins::AccessGrant
scope :expired, -> { where.not(expires_in: nil).where('created_at + MAKE_INTERVAL(secs => expires_in) < NOW()') }
scope :revoked, -> { where.not(revoked_at: nil).where(revoked_at: ...Time.now.utc) }
end

View File

@ -0,0 +1,29 @@
# frozen_string_literal: true
class OAuth::AccessToken < ApplicationRecord
include ::Doorkeeper::Orm::ActiveRecord::Mixins::AccessToken
include Redisable
has_many :web_push_subscriptions, class_name: 'Web::PushSubscription', inverse_of: :access_token, dependent: nil
scope :expired, -> { where.not(expires_in: nil).where('created_at + MAKE_INTERVAL(secs => expires_in) < NOW()') }
scope :not_revoked, -> { where(revoked_at: nil) }
scope :revoked, -> { where.not(revoked_at: nil).where(revoked_at: ...Time.now.utc) }
after_commit :push_to_streaming_api
def revoke(clock = Time)
update(revoked_at: clock.now.utc)
end
def update_last_used(request, clock = Time)
update(last_used_at: clock.now.utc, last_used_ip: request.remote_ip)
end
private
def push_to_streaming_api
redis.publish("timeline:access_token:#{id}", Oj.dump(event: :kill)) if revoked? || destroyed?
end
end

View File

@ -0,0 +1,44 @@
# frozen_string_literal: true
class OAuth::Application < ApplicationRecord
include ::Doorkeeper::Orm::ActiveRecord::Mixins::Application
APP_NAME_LIMIT = 60
APP_REDIRECT_URI_LIMIT = 2_000
APP_WEBSITE_LIMIT = 2_000
include Redisable
has_many :created_users, class_name: 'User', foreign_key: :created_by_application_id, inverse_of: :created_by_application, dependent: nil
validates :name, length: { maximum: APP_NAME_LIMIT }
validates :redirect_uri, length: { maximum: APP_REDIRECT_URI_LIMIT }
validates :website, url: true, length: { maximum: APP_WEBSITE_LIMIT }, if: :website?
before_destroy :close_streaming_sessions, prepend: true
def confirmation_redirect_uri
redirect_uri.lines.first.strip
end
def redirect_uris
# The redirect_uri value is stored as a newline delimited list
redirect_uri.split
end
# The association between `Application` and `AccessToken` uses a setting of
# `dependent: delete_all` which means the callbacks in `AccessToken` are not
# run. Instead, announce to streaming that these tokens are being deleted.
def close_streaming_sessions(resource_owner = nil)
payload = Oj.dump(event: :kill)
scope = access_tokens
scope = scope.where(resource_owner_id: resource_owner.id) unless resource_owner.nil?
scope.in_batches do |tokens|
redis.pipelined do |pipeline|
tokens.ids.each do |id|
pipeline.publish("timeline:access_token:#{id}", payload)
end
end
end
end
end

View File

@ -32,7 +32,7 @@ class Report < ApplicationRecord
rate_limit by: :account, family: :reports rate_limit by: :account, family: :reports
belongs_to :account belongs_to :account
belongs_to :application, class_name: 'Doorkeeper::Application', optional: true belongs_to :application, class_name: 'OAuth::Application', optional: true
with_options class_name: 'Account' do with_options class_name: 'Account' do
belongs_to :target_account belongs_to :target_account

View File

@ -19,7 +19,7 @@ class SessionActivation < ApplicationRecord
include BrowserDetection include BrowserDetection
belongs_to :user, inverse_of: :session_activations belongs_to :user, inverse_of: :session_activations
belongs_to :access_token, class_name: 'Doorkeeper::AccessToken', dependent: :destroy, optional: true belongs_to :access_token, class_name: 'OAuth::AccessToken', dependent: :destroy, optional: true
belongs_to :web_push_subscription, class_name: 'Web::PushSubscription', dependent: :destroy, optional: true belongs_to :web_push_subscription, class_name: 'Web::PushSubscription', dependent: :destroy, optional: true
delegate :token, delegate :token,
@ -61,12 +61,12 @@ class SessionActivation < ApplicationRecord
private private
def assign_access_token def assign_access_token
self.access_token = Doorkeeper::AccessToken.create!(access_token_attributes) self.access_token = OAuth::AccessToken.create!(access_token_attributes)
end end
def access_token_attributes def access_token_attributes
{ {
application_id: Doorkeeper::Application.find_by(superapp: true)&.id, application_id: OAuth::Application.find_by(superapp: true)&.id,
resource_owner_id: user_id, resource_owner_id: user_id,
scopes: DEFAULT_SCOPES.join(' '), scopes: DEFAULT_SCOPES.join(' '),
expires_in: Doorkeeper.configuration.access_token_expires_in, expires_in: Doorkeeper.configuration.access_token_expires_in,

View File

@ -64,7 +64,7 @@ class Status < ApplicationRecord
update_index('statuses', :proper) update_index('statuses', :proper)
update_index('public_statuses', :proper) update_index('public_statuses', :proper)
belongs_to :application, class_name: 'Doorkeeper::Application', optional: true belongs_to :application, class_name: 'OAuth::Application', optional: true
belongs_to :account, inverse_of: :statuses belongs_to :account, inverse_of: :statuses
belongs_to :in_reply_to_account, class_name: 'Account', optional: true belongs_to :in_reply_to_account, class_name: 'Account', optional: true

View File

@ -83,11 +83,11 @@ class User < ApplicationRecord
belongs_to :account, inverse_of: :user belongs_to :account, inverse_of: :user
belongs_to :invite, counter_cache: :uses, optional: true belongs_to :invite, counter_cache: :uses, optional: true
belongs_to :created_by_application, class_name: 'Doorkeeper::Application', optional: true belongs_to :created_by_application, class_name: 'OAuth::Application', optional: true
belongs_to :role, class_name: 'UserRole', optional: true belongs_to :role, class_name: 'UserRole', optional: true
accepts_nested_attributes_for :account accepts_nested_attributes_for :account
has_many :applications, class_name: 'Doorkeeper::Application', as: :owner, dependent: nil has_many :applications, class_name: 'OAuth::Application', as: :owner, dependent: nil
has_many :backups, inverse_of: :user, dependent: nil has_many :backups, inverse_of: :user, dependent: nil
has_many :invites, inverse_of: :user, dependent: nil has_many :invites, inverse_of: :user, dependent: nil
has_many :markers, inverse_of: :user, dependent: :destroy has_many :markers, inverse_of: :user, dependent: :destroy
@ -303,7 +303,7 @@ class User < ApplicationRecord
end end
def applications_last_used def applications_last_used
Doorkeeper::AccessToken OAuth::AccessToken
.where(resource_owner_id: id) .where(resource_owner_id: id)
.where.not(last_used_at: nil) .where.not(last_used_at: nil)
.group(:application_id) .group(:application_id)
@ -314,7 +314,7 @@ class User < ApplicationRecord
def token_for_app(app) def token_for_app(app)
return nil if app.nil? || app.owner != self return nil if app.nil? || app.owner != self
Doorkeeper::AccessToken.find_or_create_by(application_id: app.id, resource_owner_id: id) do |t| OAuth::AccessToken.find_or_create_by(application_id: app.id, resource_owner_id: id) do |t|
t.scopes = app.scopes t.scopes = app.scopes
t.expires_in = Doorkeeper.configuration.access_token_expires_in t.expires_in = Doorkeeper.configuration.access_token_expires_in
t.use_refresh_token = Doorkeeper.configuration.refresh_token_enabled? t.use_refresh_token = Doorkeeper.configuration.refresh_token_enabled?
@ -368,9 +368,9 @@ class User < ApplicationRecord
end end
def revoke_access! def revoke_access!
Doorkeeper::AccessGrant.by_resource_owner(self).touch_all(:revoked_at) OAuth::AccessGrant.by_resource_owner(self).touch_all(:revoked_at)
Doorkeeper::AccessToken.by_resource_owner(self).in_batches do |batch| OAuth::AccessToken.by_resource_owner(self).in_batches do |batch|
batch.touch_all(:revoked_at) batch.touch_all(:revoked_at)
Web::PushSubscription.where(access_token_id: batch).delete_all Web::PushSubscription.where(access_token_id: batch).delete_all

View File

@ -18,7 +18,7 @@
class Web::PushSubscription < ApplicationRecord class Web::PushSubscription < ApplicationRecord
belongs_to :user belongs_to :user
belongs_to :access_token, class_name: 'Doorkeeper::AccessToken' belongs_to :access_token, class_name: 'OAuth::AccessToken'
has_one :session_activation, foreign_key: 'web_push_subscription_id', inverse_of: :web_push_subscription, dependent: nil has_one :session_activation, foreign_key: 'web_push_subscription_id', inverse_of: :web_push_subscription, dependent: nil
@ -42,7 +42,7 @@ class Web::PushSubscription < ApplicationRecord
class << self class << self
def unsubscribe_for(application_id, resource_owner) def unsubscribe_for(application_id, resource_owner)
access_token_ids = Doorkeeper::AccessToken.where(application_id: application_id, resource_owner_id: resource_owner.id).not_revoked.pluck(:id) access_token_ids = OAuth::AccessToken.where(application_id: application_id, resource_owner_id: resource_owner.id).not_revoked.pluck(:id)
where(access_token_id: access_token_ids).delete_all where(access_token_id: access_token_ids).delete_all
end end
end end

View File

@ -27,7 +27,7 @@ class AppSignUpService < BaseService
end end
def create_access_token! def create_access_token!
@access_token = Doorkeeper::AccessToken.create!( @access_token = OAuth::AccessToken.create!(
application: @app, application: @app,
resource_owner_id: @user.id, resource_owner_id: @user.id,
scopes: @app.scopes, scopes: @app.scopes,

View File

@ -26,7 +26,7 @@ class PostStatusService < BaseService
# @option [String] :scheduled_at # @option [String] :scheduled_at
# @option [Hash] :poll Optional poll to attach # @option [Hash] :poll Optional poll to attach
# @option [Enumerable] :media_ids Optional array of media IDs to attach # @option [Enumerable] :media_ids Optional array of media IDs to attach
# @option [Doorkeeper::Application] :application # @option [OAuth::Application] :application
# @option [String] :idempotency Optional idempotency key # @option [String] :idempotency Optional idempotency key
# @option [Boolean] :with_rate_limit # @option [Boolean] :with_rate_limit
# @option [Enumerable] :allowed_mentions Optional array of expected mentioned account IDs, raises `UnexpectedMentionsError` if unexpected accounts end up in mentions # @option [Enumerable] :allowed_mentions Optional array of expected mentioned account IDs, raises `UnexpectedMentionsError` if unexpected accounts end up in mentions

View File

@ -21,7 +21,7 @@ class PublishScheduledStatusWorker
def options_with_objects(options) def options_with_objects(options)
options.tap do |options_hash| options.tap do |options_hash|
options_hash[:application] = Doorkeeper::Application.find(options_hash.delete(:application_id)) if options[:application_id] options_hash[:application] = OAuth::Application.find(options_hash.delete(:application_id)) if options[:application_id]
options_hash[:thread] = Status.find(options_hash.delete(:in_reply_to_id)) if options_hash[:in_reply_to_id] options_hash[:thread] = Status.find(options_hash.delete(:in_reply_to_id)) if options_hash[:in_reply_to_id]
end end
end end

View File

@ -20,7 +20,7 @@ class Scheduler::IpCleanupScheduler
SessionActivation.where(updated_at: ...IP_RETENTION_PERIOD.ago).in_batches.update_all(ip: nil) SessionActivation.where(updated_at: ...IP_RETENTION_PERIOD.ago).in_batches.update_all(ip: nil)
User.where(current_sign_in_at: ...IP_RETENTION_PERIOD.ago).in_batches.update_all(sign_up_ip: nil) User.where(current_sign_in_at: ...IP_RETENTION_PERIOD.ago).in_batches.update_all(sign_up_ip: nil)
LoginActivity.where(created_at: ...IP_RETENTION_PERIOD.ago).in_batches.destroy_all LoginActivity.where(created_at: ...IP_RETENTION_PERIOD.ago).in_batches.destroy_all
Doorkeeper::AccessToken.where(last_used_at: ...IP_RETENTION_PERIOD.ago).in_batches.update_all(last_used_ip: nil) OAuth::AccessToken.where(last_used_at: ...IP_RETENTION_PERIOD.ago).in_batches.update_all(last_used_ip: nil)
end end
def clean_expired_ip_blocks! def clean_expired_ip_blocks!

View File

@ -117,9 +117,6 @@ module Mastodon
end end
config.to_prepare do config.to_prepare do
Doorkeeper::Application.include ApplicationExtension
Doorkeeper::AccessGrant.include AccessGrantExtension
Doorkeeper::AccessToken.include AccessTokenExtension
Devise::FailureApp.include AbstractController::Callbacks Devise::FailureApp.include AbstractController::Callbacks
Devise::FailureApp.include Localized Devise::FailureApp.include Localized
end end

View File

@ -4,6 +4,10 @@ Doorkeeper.configure do
# Change the ORM that doorkeeper will use (needs plugins) # Change the ORM that doorkeeper will use (needs plugins)
orm :active_record orm :active_record
access_grant_class 'OAuth::AccessGrant'
access_token_class 'OAuth::AccessToken'
application_class 'OAuth::Application'
# This block will be called to check whether the resource owner is authenticated or not. # This block will be called to check whether the resource owner is authenticated or not.
resource_owner_authenticator do resource_owner_authenticator do
current_user || redirect_to(new_user_session_url) current_user || redirect_to(new_user_session_url)

View File

@ -1,3 +1,3 @@
# frozen_string_literal: true # frozen_string_literal: true
Doorkeeper::Application.create_with(name: 'Web', redirect_uri: Doorkeeper.configuration.native_redirect_uri, scopes: 'read write follow push').find_or_create_by(superapp: true) OAuth::Application.create_with(name: 'Web', redirect_uri: Doorkeeper.configuration.native_redirect_uri, scopes: 'read write follow push').find_or_create_by(superapp: true)

View File

@ -134,12 +134,12 @@ namespace :tests do
exit(1) exit(1)
end end
unless Doorkeeper::Application.find(2)[:scopes] == 'write:accounts profile' unless OAuth::Application.find(2)[:scopes] == 'write:accounts profile'
puts 'Application OAuth scopes not rewritten as expected' puts 'Application OAuth scopes not rewritten as expected'
exit(1) exit(1)
end end
unless Doorkeeper::Application.find(2).access_tokens.first[:scopes] == 'write:accounts profile' unless OAuth::Application.find(2).access_tokens.first[:scopes] == 'write:accounts profile'
puts 'OAuth access token scopes not rewritten as expected' puts 'OAuth access token scopes not rewritten as expected'
exit(1) exit(1)
end end

View File

@ -5,7 +5,7 @@ require 'rails_helper'
RSpec.describe OAuth::AuthorizationsController do RSpec.describe OAuth::AuthorizationsController do
render_views render_views
let(:app) { Doorkeeper::Application.create!(name: 'test', redirect_uri: 'http://localhost/', scopes: 'read') } let(:app) { OAuth::Application.create!(name: 'test', redirect_uri: 'http://localhost/', scopes: 'read') }
describe 'GET #new' do describe 'GET #new' do
subject do subject do
@ -34,7 +34,7 @@ RSpec.describe OAuth::AuthorizationsController do
context 'when app is already authorized' do context 'when app is already authorized' do
before do before do
Doorkeeper::AccessToken.find_or_create_for( OAuth::AccessToken.find_or_create_for(
application: app, application: app,
resource_owner: user.id, resource_owner: user.id,
scopes: app.scopes, scopes: app.scopes,

View File

@ -55,7 +55,7 @@ RSpec.describe OAuth::AuthorizedApplicationsController do
it 'revokes access tokens for the application and removes subscriptions and sends kill payload to streaming' do it 'revokes access tokens for the application and removes subscriptions and sends kill payload to streaming' do
post :destroy, params: { id: application.id } post :destroy, params: { id: application.id }
expect(Doorkeeper::AccessToken.where(application: application).first.revoked_at) expect(OAuth::AccessToken.where(application: application).first.revoked_at)
.to_not be_nil .to_not be_nil
expect(Web::PushSubscription.where(user: user).count) expect(Web::PushSubscription.where(user: user).count)
.to eq(0) .to eq(0)

View File

@ -1,6 +1,6 @@
# frozen_string_literal: true # frozen_string_literal: true
Fabricator :access_grant, from: 'Doorkeeper::AccessGrant' do Fabricator :access_grant, from: OAuth::AccessGrant do
application application
resource_owner_id { Fabricate(:user).id } resource_owner_id { Fabricate(:user).id }
expires_in 3_600 expires_in 3_600

View File

@ -1,3 +1,3 @@
# frozen_string_literal: true # frozen_string_literal: true
Fabricator :access_token, from: 'Doorkeeper::AccessToken' Fabricator :access_token, from: OAuth::AccessToken

View File

@ -1,6 +1,6 @@
# frozen_string_literal: true # frozen_string_literal: true
Fabricator(:application, from: Doorkeeper::Application) do Fabricator(:application, from: OAuth::Application) do
name 'Example' name 'Example'
website 'http://example.com' website 'http://example.com'
redirect_uri 'http://example.com/callback' redirect_uri 'http://example.com/callback'

View File

@ -2,7 +2,7 @@
require 'rails_helper' require 'rails_helper'
RSpec.describe Doorkeeper::AccessGrant do RSpec.describe OAuth::AccessGrant do
describe 'Validations' do describe 'Validations' do
subject { Fabricate :access_grant } subject { Fabricate :access_grant }

View File

@ -2,7 +2,7 @@
require 'rails_helper' require 'rails_helper'
RSpec.describe Doorkeeper::AccessToken do RSpec.describe OAuth::AccessToken do
describe 'Associations' do describe 'Associations' do
it { is_expected.to have_many(:web_push_subscriptions).class_name('Web::PushSubscription').inverse_of(:access_token) } it { is_expected.to have_many(:web_push_subscriptions).class_name('Web::PushSubscription').inverse_of(:access_token) }
end end

View File

@ -2,7 +2,7 @@
require 'rails_helper' require 'rails_helper'
RSpec.describe Doorkeeper::Application do RSpec.describe OAuth::Application do
describe 'Associations' do describe 'Associations' do
it { is_expected.to have_many(:created_users).class_name('User').inverse_of(:created_by_application).with_foreign_key(:created_by_application_id) } it { is_expected.to have_many(:created_users).class_name('User').inverse_of(:created_by_application).with_foreign_key(:created_by_application_id) }
end end

View File

@ -439,7 +439,7 @@ RSpec.describe User do
it 'creates and returns a persisted token' do it 'creates and returns a persisted token' do
expect { user.token_for_app(app) } expect { user.token_for_app(app) }
.to change(Doorkeeper::AccessToken.where(resource_owner_id: user.id, application: app), :count).by(1) .to change(OAuth::AccessToken.where(resource_owner_id: user.id, application: app), :count).by(1)
end end
end end
@ -449,7 +449,7 @@ RSpec.describe User do
it 'returns a persisted token' do it 'returns a persisted token' do
expect(user.token_for_app(app)) expect(user.token_for_app(app))
.to be_a(Doorkeeper::AccessToken) .to be_a(OAuth::AccessToken)
.and eq(token) .and eq(token)
end end
end end
@ -531,7 +531,7 @@ RSpec.describe User do
end end
def remove_active_user_tokens def remove_active_user_tokens
change { Doorkeeper::AccessToken.active_for(user).count }.to(0) change { OAuth::AccessToken.active_for(user).count }.to(0)
end end
def remove_user_web_subscriptions def remove_user_web_subscriptions

View File

@ -31,7 +31,7 @@ RSpec.describe 'Apps' do
expect(response.content_type) expect(response.content_type)
.to start_with('application/json') .to start_with('application/json')
app = Doorkeeper::Application.find_by(name: client_name) app = OAuth::Application.find_by(name: client_name)
expect(app).to be_present expect(app).to be_present
expect(app.scopes.to_s).to eq scopes expect(app.scopes.to_s).to eq scopes
@ -64,7 +64,7 @@ RSpec.describe 'Apps' do
expect(response).to have_http_status(200) expect(response).to have_http_status(200)
expect(response.content_type) expect(response.content_type)
.to start_with('application/json') .to start_with('application/json')
expect(Doorkeeper::Application.find_by(name: client_name)).to be_present expect(OAuth::Application.find_by(name: client_name)).to be_present
expect(response.parsed_body) expect(response.parsed_body)
.to include( .to include(
@ -84,7 +84,7 @@ RSpec.describe 'Apps' do
expect(response.content_type) expect(response.content_type)
.to start_with('application/json') .to start_with('application/json')
app = Doorkeeper::Application.find_by(name: client_name) app = OAuth::Application.find_by(name: client_name)
expect(app).to be_present expect(app).to be_present
expect(app.scopes.to_s).to eq 'read' expect(app.scopes.to_s).to eq 'read'
@ -117,12 +117,12 @@ RSpec.describe 'Apps' do
expect(response).to have_http_status(200) expect(response).to have_http_status(200)
expect(response.content_type) expect(response.content_type)
.to start_with('application/json') .to start_with('application/json')
expect(Doorkeeper::Application.find_by(name: client_name).scopes.to_s).to eq 'read' expect(OAuth::Application.find_by(name: client_name).scopes.to_s).to eq 'read'
end end
end end
context 'with a too-long name' do context 'with a too-long name' do
let(:client_name) { 'a' * Doorkeeper::Application::APP_NAME_LIMIT * 2 } let(:client_name) { 'a' * OAuth::Application::APP_NAME_LIMIT * 2 }
it 'returns http unprocessable entity' do it 'returns http unprocessable entity' do
subject subject
@ -134,7 +134,7 @@ RSpec.describe 'Apps' do
end end
context 'with a too-long website' do context 'with a too-long website' do
let(:website) { "https://foo.bar/#{'a' * Doorkeeper::Application::APP_WEBSITE_LIMIT * 2}" } let(:website) { "https://foo.bar/#{'a' * OAuth::Application::APP_WEBSITE_LIMIT * 2}" }
it 'returns http unprocessable entity' do it 'returns http unprocessable entity' do
subject subject
@ -146,7 +146,7 @@ RSpec.describe 'Apps' do
end end
context 'with a too-long redirect_uri' do context 'with a too-long redirect_uri' do
let(:redirect_uris) { "https://app.example/#{'a' * Doorkeeper::Application::APP_REDIRECT_URI_LIMIT * 2}" } let(:redirect_uris) { "https://app.example/#{'a' * OAuth::Application::APP_REDIRECT_URI_LIMIT * 2}" }
it 'returns http unprocessable entity' do it 'returns http unprocessable entity' do
subject subject
@ -180,7 +180,7 @@ RSpec.describe 'Apps' do
expect(response.content_type) expect(response.content_type)
.to start_with('application/json') .to start_with('application/json')
app = Doorkeeper::Application.find_by(name: client_name) app = OAuth::Application.find_by(name: client_name)
expect(app).to be_present expect(app).to be_present
expect(app.redirect_uri).to eq redirect_uris expect(app.redirect_uri).to eq redirect_uris
@ -204,7 +204,7 @@ RSpec.describe 'Apps' do
expect(response.content_type) expect(response.content_type)
.to start_with('application/json') .to start_with('application/json')
app = Doorkeeper::Application.find_by(name: client_name) app = OAuth::Application.find_by(name: client_name)
expect(app).to be_present expect(app).to be_present
expect(app.redirect_uri).to eq redirect_uris.join "\n" expect(app.redirect_uri).to eq redirect_uris.join "\n"
@ -276,7 +276,7 @@ RSpec.describe 'Apps' do
expect(response.content_type) expect(response.content_type)
.to start_with('application/json') .to start_with('application/json')
app = Doorkeeper::Application.find_by(name: client_name) app = OAuth::Application.find_by(name: client_name)
expect(app).to be_present expect(app).to be_present
expect(app.website).to eq website expect(app.website).to eq website

View File

@ -169,7 +169,7 @@ RSpec.describe 'Caching behavior' do
let(:alice) { Account.find_by(username: 'alice') } let(:alice) { Account.find_by(username: 'alice') }
let(:user) { User.find_by(email: 'user@host.example') } let(:user) { User.find_by(email: 'user@host.example') }
let(:token) { Doorkeeper::AccessToken.find_by(resource_owner_id: user.id) } let(:token) { OAuth::AccessToken.find_by(resource_owner_id: user.id) }
before_all do before_all do
alice = Fabricate(:account, username: 'alice') alice = Fabricate(:account, username: 'alice')

View File

@ -25,7 +25,7 @@ RSpec.describe 'Settings / Exports' do
let(:params) do let(:params) do
{ {
doorkeeper_application: { oauth_application: {
name: 'My New App', name: 'My New App',
redirect_uri: 'urn:ietf:wg:oauth:2.0:oob', redirect_uri: 'urn:ietf:wg:oauth:2.0:oob',
website: 'http://google.com', website: 'http://google.com',
@ -36,13 +36,13 @@ RSpec.describe 'Settings / Exports' do
it 'supports passing scope values as string' do it 'supports passing scope values as string' do
expect { subject } expect { subject }
.to change(Doorkeeper::Application, :count).by(1) .to change(OAuth::Application, :count).by(1)
expect(response) expect(response)
.to redirect_to(settings_applications_path) .to redirect_to(settings_applications_path)
end end
it 'gracefully handles invalid nested params' do it 'gracefully handles invalid nested params' do
post settings_applications_path(doorkeeper_application: 'invalid') post settings_applications_path(oauth_application: 'invalid')
expect(response) expect(response)
.to have_http_status(400) .to have_http_status(400)
@ -53,7 +53,7 @@ RSpec.describe 'Settings / Exports' do
let(:application) { Fabricate :application, owner: user } let(:application) { Fabricate :application, owner: user }
it 'gracefully handles invalid nested params' do it 'gracefully handles invalid nested params' do
put settings_application_path(application.id, doorkeeper_application: 'invalid') put settings_application_path(application.id, oauth_application: 'invalid')
expect(response) expect(response)
.to have_http_status(400) .to have_http_status(400)

View File

@ -68,7 +68,7 @@ RSpec.describe 'Auth Passwords' do
end end
def user_token_count def user_token_count
Doorkeeper::AccessToken OAuth::AccessToken
.active_for(user) .active_for(user)
.count .count
end end

View File

@ -7,7 +7,7 @@ RSpec.describe 'Using OAuth from an external app' do
subject { visit "/oauth/authorize?#{params.to_query}" } subject { visit "/oauth/authorize?#{params.to_query}" }
let(:client_app) { Doorkeeper::Application.create!(name: 'test', redirect_uri: about_url(host: Rails.application.config.x.local_domain), scopes: 'read') } let(:client_app) { OAuth::Application.create!(name: 'test', redirect_uri: about_url(host: Rails.application.config.x.local_domain), scopes: 'read') }
let(:params) do let(:params) do
{ client_id: client_app.uid, response_type: 'code', redirect_uri: client_app.redirect_uri, scope: 'read' } { client_id: client_app.uid, response_type: 'code', redirect_uri: client_app.redirect_uri, scope: 'read' }
end end
@ -264,7 +264,7 @@ RSpec.describe 'Using OAuth from an external app' do
end end
def user_has_grant_with_client_app? def user_has_grant_with_client_app?
Doorkeeper::AccessGrant OAuth::AccessGrant
.exists?( .exists?(
application: client_app, application: client_app,
resource_owner_id: user.id resource_owner_id: user.id

View File

@ -34,7 +34,7 @@ RSpec.describe 'Settings applications page' do
fill_in_form fill_in_form
expect { submit_form } expect { submit_form }
.to change(Doorkeeper::Application, :count).by(1) .to change(OAuth::Application, :count).by(1)
expect(page) expect(page)
.to have_content(I18n.t('doorkeeper.applications.index.title')) .to have_content(I18n.t('doorkeeper.applications.index.title'))
.and have_content('My new app') .and have_content('My new app')
@ -47,7 +47,7 @@ RSpec.describe 'Settings applications page' do
visit new_settings_application_path visit new_settings_application_path
expect { submit_form } expect { submit_form }
.to not_change(Doorkeeper::Application, :count) .to not_change(OAuth::Application, :count)
expect(page) expect(page)
.to have_content("can't be blank") .to have_content("can't be blank")
end end
@ -60,9 +60,9 @@ RSpec.describe 'Settings applications page' do
fill_in I18n.t('activerecord.attributes.doorkeeper/application.redirect_uri'), fill_in I18n.t('activerecord.attributes.doorkeeper/application.redirect_uri'),
with: 'urn:ietf:wg:oauth:2.0:oob' with: 'urn:ietf:wg:oauth:2.0:oob'
check 'read', id: :doorkeeper_application_scopes_read check 'read', id: :oauth_application_scopes_read
check 'write', id: :doorkeeper_application_scopes_write check 'write', id: :oauth_application_scopes_write
check 'follow', id: :doorkeeper_application_scopes_follow check 'follow', id: :oauth_application_scopes_follow
end end
def submit_form def submit_form
@ -76,12 +76,12 @@ RSpec.describe 'Settings applications page' do
fill_in form_app_name_label, fill_in form_app_name_label,
with: 'My new app name with a new value' with: 'My new app name with a new value'
check 'push', id: :doorkeeper_application_scopes_push check 'push', id: :oauth_application_scopes_push
submit_form submit_form
expect(page) expect(page)
.to have_content('My new app name with a new value') .to have_content('My new app name with a new value')
.and have_checked_field('push', id: :doorkeeper_application_scopes_push) .and have_checked_field('push', id: :oauth_application_scopes_push)
end end
it 'does not update with wrong values' do it 'does not update with wrong values' do
@ -110,7 +110,7 @@ RSpec.describe 'Settings applications page' do
visit settings_applications_path visit settings_applications_path
expect { destroy_application } expect { destroy_application }
.to change(Doorkeeper::Application, :count).by(-1) .to change(OAuth::Application, :count).by(-1)
expect(page) expect(page)
.to have_no_content(application.name) .to have_no_content(application.name)
expect(redis_pipeline_stub) expect(redis_pipeline_stub)