FEATURE: allows to remove invitees from the modal listing them
This commit is contained in:
parent
4e5fad6b4f
commit
5c5ffdaaab
|
|
@ -3,7 +3,7 @@
|
|||
module DiscoursePostEvent
|
||||
class InviteesController < DiscoursePostEventController
|
||||
def index
|
||||
event = Event.find(params['event-id'])
|
||||
event = Event.find(params[:post_id])
|
||||
|
||||
event_invitees = event.invitees
|
||||
|
||||
|
|
@ -22,28 +22,37 @@ module DiscoursePostEvent
|
|||
end
|
||||
|
||||
def update
|
||||
invitee = Invitee.find(params[:id])
|
||||
invitee = Invitee.find_by(id: params[:id], post_id: params[:post_id])
|
||||
guardian.ensure_can_act_on_invitee!(invitee)
|
||||
invitee.update_attendance!(invitee_params[:status])
|
||||
render json: InviteeSerializer.new(invitee)
|
||||
end
|
||||
|
||||
def create
|
||||
event = Event.find(invitee_params[:post_id])
|
||||
event = Event.find(params[:post_id])
|
||||
guardian.ensure_can_see!(event.post)
|
||||
|
||||
invitee = Invitee.create_attendance!(
|
||||
current_user.id,
|
||||
invitee_params[:post_id],
|
||||
params[:post_id],
|
||||
invitee_params[:status]
|
||||
)
|
||||
render json: InviteeSerializer.new(invitee)
|
||||
end
|
||||
|
||||
def destroy
|
||||
event = Event.find_by(id: params[:post_id])
|
||||
invitee = event.invitees.find_by(id: params[:id])
|
||||
guardian.ensure_can_act_on_discourse_post_event!(event)
|
||||
invitee.destroy!
|
||||
event.publish_update!
|
||||
render json: success_json
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def invitee_params
|
||||
params.require(:invitee).permit(:status, :post_id)
|
||||
params.require(:invitee).permit(:status)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
|
||||
module DiscoursePostEvent
|
||||
class InviteeSerializer < ApplicationSerializer
|
||||
attributes :id, :status, :user
|
||||
attributes :id, :status, :user, :post_id
|
||||
|
||||
def status
|
||||
object.status ? Invitee.statuses[object.status] : nil
|
||||
|
|
|
|||
|
|
@ -1,11 +1,65 @@
|
|||
import { Result } from "discourse/adapters/rest";
|
||||
import { ajax } from "discourse/lib/ajax";
|
||||
import DiscoursePostEventAdapter from "./discourse-post-event-adapter";
|
||||
import { underscore } from "@ember/string";
|
||||
|
||||
export default DiscoursePostEventAdapter.extend({
|
||||
// TODO: destroy/update/create should be improved in core to allow for nested models
|
||||
destroyRecord(store, type, record) {
|
||||
return ajax(
|
||||
this.pathFor(store, type, {
|
||||
post_id: record.post_id,
|
||||
invitee_id: record.id
|
||||
}),
|
||||
{
|
||||
type: "DELETE"
|
||||
}
|
||||
);
|
||||
},
|
||||
|
||||
update(store, type, id, attrs) {
|
||||
const data = {};
|
||||
const typeField = underscore(this.apiNameFor(type));
|
||||
data[typeField] = attrs;
|
||||
|
||||
return ajax(
|
||||
this.pathFor(store, type, { invitee_id: id, post_id: attrs.post_id }),
|
||||
this.getPayload("PUT", data)
|
||||
).then(function(json) {
|
||||
return new Result(json[typeField], json);
|
||||
});
|
||||
},
|
||||
|
||||
createRecord(store, type, attrs) {
|
||||
const data = {};
|
||||
const typeField = underscore(this.apiNameFor(type));
|
||||
data[typeField] = attrs;
|
||||
return ajax(
|
||||
this.pathFor(store, type, attrs),
|
||||
this.getPayload("POST", data)
|
||||
).then(function(json) {
|
||||
return new Result(json[typeField], json);
|
||||
});
|
||||
},
|
||||
|
||||
pathFor(store, type, findArgs) {
|
||||
const post_id = findArgs["post_id"];
|
||||
delete findArgs["post_id"];
|
||||
|
||||
const invitee_id = findArgs["invitee_id"];
|
||||
delete findArgs["invitee_id"];
|
||||
|
||||
let path =
|
||||
this.basePath(store, type, findArgs) +
|
||||
underscore(store.pluralize(this.apiNameFor(type)));
|
||||
this.basePath(store, type, {}) +
|
||||
"events/" +
|
||||
post_id +
|
||||
"/" +
|
||||
underscore(store.pluralize(this.apiNameFor()));
|
||||
|
||||
if (invitee_id) {
|
||||
path += `/${invitee_id}`;
|
||||
}
|
||||
|
||||
return this.appendQueryParams(path, findArgs);
|
||||
},
|
||||
|
||||
|
|
|
|||
|
|
@ -17,13 +17,20 @@ export default Controller.extend(ModalFunctionality, {
|
|||
debounce(this, this._fetchInvitees, filter, 250);
|
||||
},
|
||||
|
||||
@action
|
||||
removeInvitee(invitee) {
|
||||
invitee
|
||||
.destroyRecord({ parent: this.model })
|
||||
.then(() => this._fetchInvitees());
|
||||
},
|
||||
|
||||
_fetchInvitees(filter) {
|
||||
this.set("isLoading", true);
|
||||
|
||||
this.store
|
||||
.findAll("discourse-post-event-invitee", {
|
||||
"event-id": this.model.id,
|
||||
filter
|
||||
filter,
|
||||
post_id: this.model.id
|
||||
})
|
||||
.then(invitees => this.set("invitees", invitees))
|
||||
.finally(() => this.set("isLoading", false));
|
||||
|
|
|
|||
|
|
@ -11,6 +11,7 @@
|
|||
{{#each invitees as |invitee|}}
|
||||
<li class="invitee">
|
||||
{{render-invitee invitee}}
|
||||
|
||||
{{#if invitee.status}}
|
||||
<span class="status {{invitee.status}}">
|
||||
{{i18n (concat "discourse_post_event.models.invitee.status." invitee.status)}}
|
||||
|
|
@ -20,6 +21,14 @@
|
|||
-
|
||||
</span>
|
||||
{{/if}}
|
||||
|
||||
{{#if model.can_act_on_discourse_post_event}}
|
||||
{{d-button
|
||||
class="btn-danger"
|
||||
icon="times"
|
||||
action=(action "removeInvitee" invitee)
|
||||
}}
|
||||
{{/if}}
|
||||
</li>
|
||||
{{/each}}
|
||||
</ul>
|
||||
|
|
|
|||
|
|
@ -6,8 +6,7 @@ export default createWidget("discourse-post-event-invitees", {
|
|||
|
||||
transform(attrs) {
|
||||
return {
|
||||
isPrivateEvent: attrs.eventModel.status === "private",
|
||||
showAll: attrs.eventModel.stats.invited > 10
|
||||
isPrivateEvent: attrs.eventModel.status === "private"
|
||||
};
|
||||
},
|
||||
|
||||
|
|
@ -22,17 +21,15 @@ export default createWidget("discourse-post-event-invitees", {
|
|||
{{/if}}
|
||||
</div>
|
||||
|
||||
{{#if transformed.showAll}}
|
||||
{{attach
|
||||
widget="button"
|
||||
attrs=(hash
|
||||
className="show-all btn-small"
|
||||
label="discourse_post_event.event_ui.show_all"
|
||||
action="showAllInvitees"
|
||||
actionParam=(hash postId=attrs.eventModel.id)
|
||||
)
|
||||
}}
|
||||
{{/if}}
|
||||
{{attach
|
||||
widget="button"
|
||||
attrs=(hash
|
||||
className="show-all btn-small"
|
||||
label="discourse_post_event.event_ui.show_all"
|
||||
action="showAllInvitees"
|
||||
actionParam=(hash postId=attrs.eventModel.id)
|
||||
)
|
||||
}}
|
||||
</div>
|
||||
<ul class="event-invitees-avatars">
|
||||
{{#each attrs.eventModel.sample_invitees as |invitee|}}
|
||||
|
|
|
|||
|
|
@ -93,7 +93,7 @@ export default createWidget("discourse-post-event", {
|
|||
this.store.update(
|
||||
"discourse-post-event-invitee",
|
||||
this.state.eventModel.watching_invitee.id,
|
||||
{ status }
|
||||
{ status, post_id: this.state.eventModel.id }
|
||||
);
|
||||
} else {
|
||||
this.store
|
||||
|
|
|
|||
|
|
@ -112,9 +112,10 @@ after_initialize do
|
|||
post '/discourse-post-event/events/:id/csv-bulk-invite' => 'events#csv_bulk_invite'
|
||||
post '/discourse-post-event/events/:id/bulk-invite' => 'events#bulk_invite', format: :json
|
||||
post '/discourse-post-event/events/:id/invite' => 'events#invite'
|
||||
put '/discourse-post-event/invitees/:id' => 'invitees#update'
|
||||
post '/discourse-post-event/invitees' => 'invitees#create'
|
||||
get '/discourse-post-event/invitees' => 'invitees#index'
|
||||
put '/discourse-post-event/events/:post_id/invitees/:id' => 'invitees#update'
|
||||
post '/discourse-post-event/events/:post_id/invitees' => 'invitees#create'
|
||||
get '/discourse-post-event/events/:post_id/invitees' => 'invitees#index'
|
||||
delete '/discourse-post-event/events/:post_id/invitees/:id' => 'invitees#destroy'
|
||||
get '/upcoming-events' => 'upcoming_events#index'
|
||||
end
|
||||
|
||||
|
|
|
|||
|
|
@ -28,21 +28,49 @@ module DiscoursePostEvent
|
|||
pe
|
||||
}
|
||||
|
||||
it 'updates its status' do
|
||||
invitee = post_event_2.invitees.first
|
||||
context "updating invitee" do
|
||||
it 'updates its status' do
|
||||
invitee = post_event_2.invitees.first
|
||||
|
||||
expect(invitee.status).to eq(0)
|
||||
expect(invitee.status).to eq(0)
|
||||
|
||||
put "/discourse-post-event/invitees/#{invitee.id}.json", params: {
|
||||
invitee: {
|
||||
status: 'interested'
|
||||
put "/discourse-post-event/events/#{post_event_2.id}/invitees/#{invitee.id}.json", params: {
|
||||
invitee: {
|
||||
status: 'interested'
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
invitee.reload
|
||||
invitee.reload
|
||||
|
||||
expect(invitee.status).to eq(1)
|
||||
expect(invitee.post_id).to eq(post_1.id)
|
||||
expect(invitee.status).to eq(1)
|
||||
expect(invitee.post_id).to eq(post_1.id)
|
||||
end
|
||||
end
|
||||
|
||||
context 'destroying invitee' do
|
||||
context 'acting user can act on discourse event' do
|
||||
it 'destroys the invitee' do
|
||||
invitee = post_event_2.invitees.first
|
||||
delete "/discourse-post-event/events/#{post_event_2.id}/invitees/#{invitee.id}.json"
|
||||
expect(Invitee.where(id: invitee.id).length).to eq(0)
|
||||
expect(response.status).to eq(200)
|
||||
end
|
||||
end
|
||||
|
||||
context 'acting user can’t act on discourse event' do
|
||||
let(:lurker) { Fabricate(:user) }
|
||||
|
||||
before do
|
||||
sign_in(lurker)
|
||||
end
|
||||
|
||||
it 'doesn’t destroy the invitee' do
|
||||
invitee = post_event_2.invitees.first
|
||||
delete "/discourse-post-event/events/#{post_event_2.id}/invitees/#{invitee.id}.json"
|
||||
expect(Invitee.where(id: invitee.id).length).to eq(1)
|
||||
expect(response.status).to eq(403)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
context 'when changing status' do
|
||||
|
|
@ -51,7 +79,7 @@ module DiscoursePostEvent
|
|||
|
||||
expect(invitee.status).to eq(0)
|
||||
|
||||
put "/discourse-post-event/invitees/#{invitee.id}.json", params: {
|
||||
put "/discourse-post-event/events/#{post_event_2.id}/invitees/#{invitee.id}.json", params: {
|
||||
invitee: {
|
||||
status: 'interested'
|
||||
}
|
||||
|
|
@ -60,7 +88,7 @@ module DiscoursePostEvent
|
|||
tu = TopicUser.get(invitee.event.post.topic, invitee.user)
|
||||
expect(tu.notification_level).to eq(TopicUser.notification_levels[:tracking])
|
||||
|
||||
put "/discourse-post-event/invitees/#{invitee.id}.json", params: {
|
||||
put "/discourse-post-event/events/#{post_event_2.id}/invitees/#{invitee.id}.json", params: {
|
||||
invitee: {
|
||||
status: 'going'
|
||||
}
|
||||
|
|
@ -69,7 +97,7 @@ module DiscoursePostEvent
|
|||
tu = TopicUser.get(invitee.event.post.topic, invitee.user)
|
||||
expect(tu.notification_level).to eq(TopicUser.notification_levels[:watching])
|
||||
|
||||
put "/discourse-post-event/invitees/#{invitee.id}.json", params: {
|
||||
put "/discourse-post-event/events/#{post_event_2.id}/invitees/#{invitee.id}.json", params: {
|
||||
invitee: {
|
||||
status: 'not_going'
|
||||
}
|
||||
|
|
@ -85,26 +113,23 @@ module DiscoursePostEvent
|
|||
let(:post_event_2) { Fabricate(:event, post: post_1) }
|
||||
|
||||
it 'creates an invitee' do
|
||||
post "/discourse-post-event/invitees.json", params: {
|
||||
post "/discourse-post-event/events/#{post_event_2.id}/invitees.json", params: {
|
||||
invitee: {
|
||||
user_id: user.id,
|
||||
post_id: post_event_2.id,
|
||||
status: 'not_going',
|
||||
}
|
||||
}
|
||||
|
||||
expect(Invitee).to exist(
|
||||
post_id: post_event_2.id,
|
||||
user_id: user.id,
|
||||
status: 2,
|
||||
)
|
||||
end
|
||||
|
||||
it 'sets tracking of the topic' do
|
||||
post "/discourse-post-event/invitees.json", params: {
|
||||
post "/discourse-post-event/events/#{post_event_2.id}/invitees.json", params: {
|
||||
invitee: {
|
||||
user_id: user.id,
|
||||
post_id: post_event_2.id,
|
||||
status: 'going',
|
||||
}
|
||||
}
|
||||
|
|
@ -121,9 +146,8 @@ module DiscoursePostEvent
|
|||
it 'creates an invitee' do
|
||||
expect(post_event_2.invitees.length).to eq(0)
|
||||
|
||||
post "/discourse-post-event/invitees.json", params: {
|
||||
post "/discourse-post-event/events/#{post_event_2.id}/invitees.json", params: {
|
||||
invitee: {
|
||||
post_id: post_1.id,
|
||||
status: 'interested'
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue