diff --git a/app/controllers/api/v1_alpha/collection_items_controller.rb b/app/controllers/api/v1_alpha/collection_items_controller.rb index cc2e5cdef1..21699a5b6f 100644 --- a/app/controllers/api/v1_alpha/collection_items_controller.rb +++ b/app/controllers/api/v1_alpha/collection_items_controller.rb @@ -11,6 +11,7 @@ class Api::V1Alpha::CollectionItemsController < Api::BaseController before_action :set_collection before_action :set_account, only: [:create] + before_action :set_collection_item, only: [:destroy] after_action :verify_authorized @@ -23,6 +24,14 @@ class Api::V1Alpha::CollectionItemsController < Api::BaseController render json: @item, serializer: REST::CollectionItemSerializer end + def destroy + authorize @collection, :update? + + @collection_item.destroy + + head 200 + end + private def set_collection @@ -35,6 +44,10 @@ class Api::V1Alpha::CollectionItemsController < Api::BaseController @account = Account.find(params[:account_id]) end + def set_collection_item + @collection_item = @collection.collection_items.find(params[:id]) + end + def check_feature_enabled raise ActionController::RoutingError unless Mastodon::Feature.collections_enabled? end diff --git a/config/routes/api.rb b/config/routes/api.rb index 563191614c..3fa1aa7af2 100644 --- a/config/routes/api.rb +++ b/config/routes/api.rb @@ -13,7 +13,7 @@ namespace :api, format: false do resources :async_refreshes, only: :show resources :collections, only: [:show, :create, :update, :destroy] do - resources :items, only: [:create], controller: 'collection_items' + resources :items, only: [:create, :destroy], controller: 'collection_items' end end diff --git a/spec/requests/api/v1_alpha/collection_items_spec.rb b/spec/requests/api/v1_alpha/collection_items_spec.rb index 880fd5d47d..5c44a7edf8 100644 --- a/spec/requests/api/v1_alpha/collection_items_spec.rb +++ b/spec/requests/api/v1_alpha/collection_items_spec.rb @@ -52,4 +52,53 @@ RSpec.describe 'Api::V1Alpha::CollectionItems', feature: :collections do end end end + + describe 'DELETE /api/v1_alpha/collections/:collection_id/items/:id' do + subject do + delete "/api/v1_alpha/collections/#{collection.id}/items/#{item.id}", headers: headers + end + + let(:collection) { Fabricate(:collection, account: user.account) } + let(:item) { Fabricate(:collection_item, collection:) } + + it_behaves_like 'forbidden for wrong scope', 'read' + + context 'when user is owner of the collection' do + context 'when item belongs to collection' do + it 'deletes the collection item and returns http success' do + item # Make sure this exists before calling the API + + expect do + subject + end.to change(collection.collection_items, :count).by(-1) + + expect(response).to have_http_status(200) + end + end + + context 'when item does not belong to to collection' do + let(:item) { Fabricate(:collection_item) } + + it 'returns http not found' do + item # Make sure this exists before calling the API + + expect do + subject + end.to_not change(CollectionItem, :count) + + expect(response).to have_http_status(404) + end + end + end + + context 'when user is not the owner of the collection' do + let(:collection) { Fabricate(:collection) } + + it 'returns http forbidden' do + subject + + expect(response).to have_http_status(403) + end + end + end end