add starred to maps API and endpoint to create/delete

This commit is contained in:
Devin Howard 2016-10-05 00:25:44 +08:00
parent e3db00f229
commit 7edaeb7c4e
11 changed files with 84 additions and 2 deletions

View file

@ -0,0 +1,29 @@
# frozen_string_literal: true
module Api
module V2
class StarsController < RestfulController
skip_before_action :load_resource
def create
@map = Map.find(params[:id])
@star = Star.new(user: current_user, map: @map)
authorize @map, :star?
create_action
if @star.errors.empty?
render json: @map, scope: default_scope, serializer: MapSerializer, root: serializer_root
else
respond_with_errors
end
end
def destroy
@map = Map.find(params[:id])
authorize @map, :unstar?
@star = @map.stars.find_by(user: current_user)
@star.destroy if @star.present?
head :no_content
end
end
end
end

View file

@ -88,6 +88,10 @@ class Map < ApplicationRecord
updated_at.strftime('%m/%d/%Y') updated_at.strftime('%m/%d/%Y')
end end
def starred_by_user?(user)
user.stars.where(map: self).exists?
end
def as_json(_options = {}) def as_json(_options = {})
json = super(methods: [:user_name, :user_image, :topic_count, :synapse_count, :contributor_count, :collaborator_ids, :screenshot_url], except: [:screenshot_content_type, :screenshot_file_size, :screenshot_file_name, :screenshot_updated_at]) json = super(methods: [:user_name, :user_image, :topic_count, :synapse_count, :contributor_count, :collaborator_ids, :screenshot_url], except: [:screenshot_content_type, :screenshot_file_size, :screenshot_file_name, :screenshot_updated_at])
json[:created_at_clean] = created_at_str json[:created_at_clean] = created_at_str

View file

@ -2,4 +2,5 @@
class Star < ActiveRecord::Base class Star < ActiveRecord::Base
belongs_to :user belongs_to :user
belongs_to :map belongs_to :map
validates :map, uniqueness: { scope: :user, message: 'You have already starred this map' }
end end

View file

@ -7,9 +7,14 @@ module Api
:desc, :desc,
:permission, :permission,
:screenshot, :screenshot,
:starred,
:created_at, :created_at,
:updated_at :updated_at
def starred
object.starred_by_user?(scope[:current_user])
end
def self.embeddable def self.embeddable
{ {
user: {}, user: {},

View file

@ -65,7 +65,10 @@ Metamaps::Application.routes.draw do
namespace :v2, path: '/v2' do namespace :v2, path: '/v2' do
resources :metacodes, only: [:index, :show] resources :metacodes, only: [:index, :show]
resources :mappings, only: [:index, :create, :show, :update, :destroy] resources :mappings, only: [:index, :create, :show, :update, :destroy]
resources :maps, only: [:index, :create, :show, :update, :destroy] resources :maps, only: [:index, :create, :show, :update, :destroy] do
post :stars, to: 'stars#create', on: :member
delete :stars, to: 'stars#destroy', on: :member
end
resources :synapses, only: [:index, :create, :show, :update, :destroy] resources :synapses, only: [:index, :create, :show, :update, :destroy]
resources :tokens, only: [:create, :destroy] do resources :tokens, only: [:create, :destroy] do
get :my_tokens, on: :collection get :my_tokens, on: :collection

View file

@ -94,3 +94,15 @@ post:
responses: responses:
204: 204:
description: No content description: No content
/stars:
post:
responses:
201:
description: Created
body:
application/json:
example: !include ../examples/map.json
delete:
responses:
204:
description: No content

View file

@ -5,6 +5,7 @@
"desc": "Example map for the API", "desc": "Example map for the API",
"permission": "commons", "permission": "commons",
"screenshot": "https://s3.amazonaws.com/metamaps-assets/site/missing-map.png", "screenshot": "https://s3.amazonaws.com/metamaps-assets/site/missing-map.png",
"starred": false,
"created_at": "2016-03-26T08:02:05.379Z", "created_at": "2016-03-26T08:02:05.379Z",
"updated_at": "2016-03-27T07:20:18.047Z", "updated_at": "2016-03-27T07:20:18.047Z",
"topic_ids": [ "topic_ids": [

View file

@ -6,6 +6,7 @@
"desc": "Example map for the API", "desc": "Example map for the API",
"permission": "commons", "permission": "commons",
"screenshot": "https://s3.amazonaws.com/metamaps-assets/site/missing-map.png", "screenshot": "https://s3.amazonaws.com/metamaps-assets/site/missing-map.png",
"starred": false,
"created_at": "2016-03-26T08:02:05.379Z", "created_at": "2016-03-26T08:02:05.379Z",
"updated_at": "2016-03-27T07:20:18.047Z", "updated_at": "2016-03-27T07:20:18.047Z",
"topic_ids": [ "topic_ids": [

View file

@ -18,6 +18,9 @@
"format": "uri", "format": "uri",
"type": "string" "type": "string"
}, },
"starred": {
"type": "boolean"
},
"created_at": { "created_at": {
"$ref": "_datetimestamp.json" "$ref": "_datetimestamp.json"
}, },
@ -61,6 +64,7 @@
"desc", "desc",
"permission", "permission",
"screenshot", "screenshot",
"starred",
"created_at", "created_at",
"updated_at" "updated_at"
] ]

View file

@ -16,7 +16,7 @@ RSpec.describe 'maps API', type: :request do
end end
it 'GET /api/v2/maps/:id' do it 'GET /api/v2/maps/:id' do
get "/api/v2/maps/#{map.id}" get "/api/v2/maps/#{map.id}", params: { access_token: token }
expect(response).to have_http_status(:success) expect(response).to have_http_status(:success)
expect(response).to match_json_schema(:map) expect(response).to match_json_schema(:map)
@ -45,6 +45,23 @@ RSpec.describe 'maps API', type: :request do
expect(Map.count).to eq 0 expect(Map.count).to eq 0
end end
it 'POST /api/v2/maps/:id/stars' do
post "/api/v2/maps/#{map.id}/stars", params: { access_token: token }
expect(response).to have_http_status(:success)
expect(response).to match_json_schema(:map)
expect(user.stars.count).to eq 1
expect(map.stars.count).to eq 1
end
it 'DELETE /api/v2/maps/:id/stars' do
create(:star, map: map, user: user)
delete "/api/v2/maps/#{map.id}/stars", params: { access_token: token }
expect(response).to have_http_status(:no_content)
expect(user.stars.count).to eq 0
expect(map.stars.count).to eq 0
end
context 'RAML example' do context 'RAML example' do
let(:resource) { get_json_example(:map) } let(:resource) { get_json_example(:map) }
let(:collection) { get_json_example(:maps) } let(:collection) { get_json_example(:maps) }

5
spec/factories/stars.rb Normal file
View file

@ -0,0 +1,5 @@
# frozen_string_literal: true
FactoryGirl.define do
factory :star do
end
end