Upstream sync

This commit is contained in:
Senad Uka
2020-07-16 17:38:21 +02:00
parent c033f5df17
commit f04d34d337
50 changed files with 1626 additions and 0 deletions

View File

@@ -0,0 +1,106 @@
require "rails_helper"
RSpec.describe Admin::CastingCallInterviewsController, type: :controller do
let!(:current_user) { create(:user, :admin) }
before do
sign_in(current_user)
end
describe "#index" do
it "returns a successful response" do
get :index
expect(response).to be_successful
end
end
describe "#new" do
it "returns a successful response" do
get :new
expect(response).to be_successful
end
it "assigns user, accounts" do
get :new
expect(assigns(:casting_call_interview)).not_to be_nil
expect(assigns(:accounts)).to eq Account.all
end
end
describe "#create" do
it "does create a new record" do
expect {
post :create, params: { casting_call_interview: casting_call_interview_params }
}.to change(CastingCallInterview, :count)
end
end
describe "#edit" do
let(:casting_call_interview) { create(:casting_call_interview) }
it "returns a successful response" do
get :edit, params: { id: casting_call_interview }
expect(response).to be_successful
end
it "assigns casting call interview" do
get :edit, params: { id: casting_call_interview }
expect(assigns(:casting_call_interview)).to eq casting_call_interview
end
end
describe "#update" do
let(:casting_call_interview) { create(:casting_call_interview) }
it "redirects to casting call interviews page" do
patch :update, params: { id: casting_call_interview, casting_call_interview: update_params }
expect(response).to be_redirect
expect(response).to redirect_to admin_casting_call_interviews_path
end
it "sets a flash notice" do
patch :update, params: { id: casting_call_interview, casting_call_interview: update_params }
expect(flash.notice).to eq "The casting call interview has been updated"
end
it "updates casting call interview" do
patch :update, params: { id: casting_call_interview, casting_call_interview: update_params }
expect(casting_call_interview.reload.zoom_meeting_url).to eq("new_zoom_meeting_url")
end
end
describe "#complete" do
let(:casting_call_interview) { create(:casting_call_interview) }
it "sets interviewed_at on casting call interview" do
expect(casting_call_interview.interviewed_at).to be_nil
post :complete, params: { id: casting_call_interview }
expect(casting_call_interview.reload.interviewed_at).not_to be_nil
end
end
private
def casting_call_interview_params
casting_call = create(:casting_call)
attributes_for(:casting_call_interview).except(:interviewed_at).merge(casting_call_id: casting_call.id)
end
def update_params
{
zoom_meeting_url: "new_zoom_meeting_url"
}
end
end

View File

@@ -0,0 +1,43 @@
require "rails_helper"
RSpec.describe CastingCallInterviewsController, type: :controller do
render_views
let(:user) { create(:user) }
let(:account) { user.primary_account }
let(:project) { create(:project, account: user.primary_account) }
let(:casting_call) { create(:casting_call, project: project, title: "My Interview") }
before do
sign_in(user)
end
describe "#index" do
it "returns a successful response" do
get :index, params: { project_id: project }
expect(response).to be_successful
end
it "only shows completed interviews" do
create(:casting_call_interview, casting_call: casting_call, interviewed_at: Time.zone.now, performer_name: "John Doe")
create(:casting_call_interview, casting_call: casting_call, interviewed_at: nil, performer_name: "Jane Doe")
get :index, params: { project_id: project }
expect(response.body).to have_content("John Doe")
expect(response.body).not_to have_content("Jane Doe")
end
end
describe "#show" do
let!(:casting_call_interview) { create(:casting_call_interview, :with_files, casting_call: casting_call, interviewed_at: Time.zone.now, performer_name: "Jane Doe") }
it "shows files of casting call interview" do
get :show, params: { project_id: project, id: casting_call_interview.id }
expect(response.body).to have_content("Filename")
expect(response.body).to have_content("location_photo.png")
end
end
end

View File

@@ -0,0 +1,126 @@
require 'rails_helper'
RSpec.describe CastingCallsController, type: :controller do
render_views
let(:user) { create(:user) }
let(:account) { user.primary_account }
let(:project) { create(:project, account: user.primary_account) }
before do
sign_in user
end
describe "#index" do
it "responds successfully" do
get :index, params: { project_id: project }
expect(response).to be_successful
end
it "renders content" do
create(:casting_call, project: project)
get :index, params: { project_id: project }
expect(response.body).to have_link "Create Casting Call"
expect(response.body).to have_content "Active"
end
context "when there are many records" do
it "paginates the table" do
create_list(:casting_call, 20, project: project)
get :index, params: { project_id: project }
expect(response.body).to have_link("2", href: project_casting_calls_path(project, page: 2))
end
end
end
describe "#new" do
it "responds successfully" do
get :new, params: { project_id: project }
expect(response).to be_successful
expect(assigns(:casting_call)).to be_a_new(CastingCall)
expect(response).to render_template(:new)
end
end
describe "#create" do
it "does create a new record" do
expect {
post :create, params: { project_id: project.id, casting_call: casting_call_params }
}.to change(CastingCall, :count)
end
it "logs an event" do
expect {
post :create, params: { project_id: project.id, casting_call: casting_call_params }
}.to have_enqueued_job(TrackAnalyticsJob).with(user, account, :track_create_casting_call, user_agent: "Rails Testing", user_ip: "0.0.0.0")
end
it "submits data to hubspot form" do
expect {
post :create, params: { project_id: project.id, casting_call: casting_call_params }
}.to have_enqueued_job(SubmitHubspotFormJob)
end
end
describe "#update" do
let!(:casting_call) { create(:casting_call, project: project, description: "My description" ) }
it "updates casting call request" do
patch :update, params: { project_id: project.id, id: casting_call.id, casting_call: update_params }
expect(casting_call.reload.description).to eq("This is updated description")
end
end
describe "#show" do
let!(:casting_call) { create(:casting_call, project: project, description: "Casting Call Request") }
it "responds successfully" do
get :show, params: { project_id: project.id, id: casting_call.id }
expect(response).to be_successful
expect(assigns(:casting_call)).to eq(casting_call)
end
it "renders content" do
get :show, params: { project_id: project.id, id: casting_call.id }
expect(response.body).to have_content "Casting Call Request"
expect(response.body).to have_content "Active"
end
end
describe "#cancel" do
let!(:casting_call) { create(:casting_call, project: project, description: "Casting Call to be Cancelled") }
it "responds with redirect" do
post :cancel, params: { project_id: project.id, id: casting_call.id }
expect(response).to be_redirect
expect(response).to redirect_to(project_casting_calls_path(project))
expect(flash.notice).not_to be_nil
end
it "updates the status to 'Cancelled'" do
expect {
post :cancel, params: { project_id: project.id, id: casting_call.id }
}.to change { casting_call.reload.status }.from("Active").to("Cancelled")
end
end
private
def casting_call_params
attributes_for(:casting_call).except(:status, :user_email)
end
def update_params
{ description: "This is updated description" }
end
end

View File

@@ -0,0 +1,58 @@
require "rails_helper"
RSpec.describe InterviewDownloadsController, type: :controller do
render_views
let(:current_user) { create(:user) }
let(:project) { create(:project, :discovery_client, account: current_user.primary_account) }
let(:casting_call) { create(:casting_call, project: project, title: "My Title") }
let(:casting_call_interview) { create(:casting_call_interview, casting_call: casting_call, performer_name: "John Doe") }
before do
sign_in current_user
end
describe "#create" do
it "enqueues zip file generation job" do
expect {
post :create, params: { project_id: project.id, casting_call_interview_id: casting_call_interview.id }, format: :js
}.to have_enqueued_job(GenerateInterviewFilesZipJob)
end
it "creates a download record with 'not_started' status" do
expect {
post :create, params: { project_id: project.id, casting_call_interview_id: casting_call_interview.id }, format: :js
}.to change(Download, :count).by(1)
expect(Download.last.status).to eq('not_started')
end
context "When there is no existing job" do
it "shows a notification to user" do
allow(ProjectsChannel).to receive(:broadcast_download_generation_update).with(be_kind_of(Download), I18n.t("interview_downloads.download.pending", release_type: "Casting Call Interview"))
post :create, params: { project_id: project.id, casting_call_interview_id: casting_call_interview.id }, format: :js
expect(ProjectsChannel).to have_received(:broadcast_download_generation_update).with(be_kind_of(Download), I18n.t("interview_downloads.download.pending", release_type: "Casting Call Interview"))
end
end
context "When there are existing jobs" do
let(:appearance_release_download) { create(:download, project_id: project.id, name: "#{project.name.parameterize}_appearance-releases") }
let(:acquired_media_release_download) { create(:download, project_id: project.id, name: "#{project.name.parameterize}_acquired-media-releases", release_type: "AcquiredMediaRelease") }
before do
allow(Download).to receive_message_chain(:unfinished_desc_order, :offset).and_return([acquired_media_release_download, appearance_release_download])
allow(ProjectsChannel).to receive(:broadcast_download_generation_update)
end
it "shows names of other contracts in the notification, which are in progress" do
broadcast_message = "<p>Your Casting Call Interview files are being prepared for download. You will be notified when it's ready.\n</p>\n<p class=\"mt-3\">The following downloads are also in progress:</p> \n<ul>\n <li>Acquired Media Release contracts (as of less than a minute ago)\n </li>\n <li>Appearance Release contracts (as of less than a minute ago)\n </li>\n</ul>\n"
post :create, params: { project_id: project.id, casting_call_interview_id: casting_call_interview.id }, format: :js
expect(ProjectsChannel).to have_received(:broadcast_download_generation_update).with(be_kind_of(Download), broadcast_message)
end
end
end
end

View File

@@ -0,0 +1,44 @@
require 'rails_helper'
RSpec.describe Public::CastingCallInterviewsController, type: :controller do
render_views
describe "#show" do
let(:casting_call_interview) { create(:casting_call_interview) }
it "responds successfully" do
get :show, params: { token: casting_call_interview.token }
expect(response).to be_successful
expect(assigns(:casting_call_interview)).to eq(casting_call_interview)
end
it "shows casting call interview details" do
get :show, params: { token: casting_call_interview.token }
expect(response.body).to have_content(casting_call_interview.performer_name)
expect(response.body).to have_content(casting_call_interview.interview_date)
expect(response.body).to have_link("Start Interview")
end
end
describe "#update" do
let(:casting_call_interview) { create(:casting_call_interview) }
it "responds successfully" do
patch :update, params: { token: casting_call_interview.token, casting_call_interview: casting_call_interview_params }
expect(response).to redirect_to casting_call_interview_url(token: casting_call_interview.token)
expect(flash.notice).to be_present
end
end
private
def casting_call_interview_params
path = Rails.root.join("spec", "fixtures", "files", "contract.pdf")
file = Rack::Test::UploadedFile.new(path, "application/pdf")
{ files: [file]}
end
end

View File

@@ -0,0 +1,28 @@
require 'rails_helper'
RSpec.describe Public::CastingCallsController, type: :controller do
render_views
describe "#show" do
let(:casting_call) { create(:casting_call) }
it "responds successfully" do
get :show, params: { token: casting_call.token }
expect(response).to be_successful
expect(assigns(:casting_call)).to eq(casting_call)
end
it "shows casting call details" do
get :show, params: { token: casting_call.token }
expect(response.body).to have_content(casting_call.title)
expect(response.body).to have_content(casting_call.description)
expect(response.body).to have_content(casting_call.project_description)
expect(response.body).to have_content(casting_call.interview_instructions)
expect(response.body).to have_content(casting_call.interview_requirements)
expect(response.body).to have_content(casting_call.questions)
expect(response.body).to have_link("Schedule an Audition")
end
end
end

View File

@@ -0,0 +1,13 @@
FactoryBot.define do
factory :casting_call_interview do
association :casting_call
performer_name 'John Doe'
zoom_meeting_url 'https://us04web.zoom.us/j/1111111111?pwd=aDZCS1dzZ2lWdDZJcHBhVnNIclB4QT03'
interview_date { 10.days.from_now }
interviewed_at { nil }
trait :with_files do
files { [Rack::Test::UploadedFile.new('spec/fixtures/files/location_photo.png', 'image/png')] }
end
end
end

View File

@@ -0,0 +1,15 @@
FactoryBot.define do
factory :casting_call do
association :project
user_email 'test@email.com'
description "Casting call description"
project_description "Casting call project description"
interview_instructions "Interview instructions"
interview_requirements "Interview requirements"
questions "Questions"
trait :cancelled do
cancelled_at { Time.zone.now }
end
end
end

View File

@@ -0,0 +1,155 @@
require "rails_helper"
feature "User managing casting calls" do
let(:current_user) { create(:user) }
let(:project) { create(:project, account: current_user.primary_account) }
before :each do
sign_in current_user
end
scenario "casting calls table is visible" do
visit project_casting_calls_path(project)
expect(page).to have_content "Created On"
expect(page).to have_content "Title"
expect(page).to have_content "Status"
end
scenario "sees list of casting calls" do
visit project_casting_calls_path(project)
expect(page).to have_content no_casting_calls_label
casting_call = create(:casting_call, project: project)
visit project_casting_calls_path(project)
expect(page).not_to have_content no_casting_calls_label
expect(page).to have_content casting_call.created_at.try(:strftime, '%D')
expect(page).to have_content casting_call.title
expect(page).to have_content casting_call.status
end
scenario "can create casting call requests" do
visit project_casting_calls_path(project)
expect(page).to have_content no_casting_calls_label
click_on add_new_casting_call_label
fill_in title_field, with: "Title"
fill_in description_field, with: "Description"
fill_in project_description_field, with: "Project Description"
fill_in interview_instructions_field, with: "Interview instructions"
fill_in interview_requirements_field, with: "Interview requirements"
fill_in questions_field, with: "Questions"
click_on "Create Casting call"
expect(page).to have_content("Your casting call request was successfully submitted. Thank you. A chat window will pop up on the lower right in a few seconds.")
end
scenario "can update casting call requests" do
create(:casting_call, title: "Title", project: project)
visit project_casting_calls_path(project)
click_on manage_button
click_on "Edit"
fill_in title_field, with: "New Title"
click_on "Update Casting call"
expect(page).to have_content("The casting call request has been updated")
end
scenario "can cancel a casting call request" do
create(:casting_call, title: "Title", project: project)
visit project_casting_calls_path(project)
click_on manage_button
click_on "Cancel"
expect(page).to have_content("The casting call request has been cancelled")
end
scenario "can open casting call details" do
cc = create(:casting_call, title: "Dummy title", project: project)
visit project_casting_calls_path(project)
click_on manage_button
click_on view_button
expect(page).to have_content cc.title
expect(page).to have_content cc.description
expect(page).to have_content cc.project_description
expect(page).to have_content cc.created_at
expect(page).to have_content cc.status
expect(page).to have_content cc.interview_instructions
expect(page).to have_content cc.interview_requirements
expect(page).to have_content cc.questions
end
context "when signed out" do
scenario "user opens public accessible casting call URL" do
cc = create(:casting_call, title: "Dummy title", project: project)
sign_out
public_url = "/casting_calls/#{cc.token}"
visit public_url
expect(page).to have_content cc.title
expect(page).to have_content cc.description
expect(page).to have_content cc.project_description
expect(page).not_to have_content cc.created_at
expect(page).not_to have_content cc.status
expect(page).not_to have_content cc.interview_instructions
expect(page).not_to have_content cc.interview_requirements
expect(page).not_to have_content cc.questions
end
end
private
def no_casting_calls_label
"Casting calls will appear here"
end
def manage_button
t "casting_calls.casting_call.actions.manage"
end
def view_button
'View'
end
def add_new_casting_call_label
t "casting_calls.index.actions.new"
end
def title_field
t "casting_calls.form.labels.title"
end
def description_field
t "casting_calls.form.labels.description"
end
def project_description_field
t "casting_calls.form.labels.project_description"
end
def interview_instructions_field
t "casting_calls.form.labels.interview_instructions"
end
def interview_requirements_field
t "casting_calls.form.labels.interview_requirements"
end
def questions_field
t "casting_calls.form.labels.questions"
end
end

View File

@@ -0,0 +1,60 @@
require "rails_helper"
describe GenerateInterviewFilesZipJob do
let(:project) { create(:project) }
let(:download) { create(:download, project: project, release_type: "CastingCallInterview", name: "my-title_john-doe") }
let(:casting_call) { create(:casting_call, project: project, title: "My Title") }
let(:casting_call_interview) { create(:casting_call_interview, casting_call: casting_call, performer_name: "John Doe") }
before do
dir = Rails.root.join("spec", "fixtures", "files")
files = ["contract.pdf", "AppearanceRelease.pdf"]
# Attachments in the test environment do not persist to cloud storage
# Therefore we want to stub calls to `open` with a cloud storage URL
allow_any_instance_of(InterviewFilesCollectionService).to receive(:open).and_return(StringIO.new("file data"))
allow_any_instance_of(InterviewFilesCollectionService).to receive(:build).and_yield(dir, files)
end
describe ".perform_later" do
it "enqueues a background job for generating zip file" do
expect {
GenerateInterviewFilesZipJob.perform_later(project, download, casting_call_interview)
}.to have_enqueued_job
end
end
describe ".perform_now" do
it "updates a download record and creates attachment for it" do
GenerateInterviewFilesZipJob.perform_now(project, download, casting_call_interview)
expect(download.project).to eq project
expect(download.release_type).to eq "CastingCallInterview"
expect(download.name).to eq "my-title_john-doe"
expect(download.status).to eq "success"
expect(download.file).to be_attached
end
context "When there are errors" do
let(:error) { StandardError.new("Casting Call Interview files not found.") }
before do
allow(ProjectsChannel).to receive(:broadcast_download_generation_update).with(download, I18n.t("interview_downloads.download.failure"))
allow_any_instance_of(InterviewFilesCollectionService).to receive(:build).and_raise(StandardError, "Casting Call Interview files not found.")
end
it "updates status to 'failure' and sends user a notification" do
GenerateInterviewFilesZipJob.perform_now(project, download, casting_call_interview)
expect(download.status).to eq "failure"
expect(ProjectsChannel).to have_received(:broadcast_download_generation_update).with(download, I18n.t("interview_downloads.download.failure"))
end
end
end
after do
# Delete the file created in fixture.
# Or the tests will fail on next run due to already existing files in existing zip.
path = Rails.root.join("spec", "fixtures", "files")
File.delete("#{path}/my-title_john-doe.zip") if File.exists? "#{path}/my-title_john-doe.zip"
end
end

View File

@@ -0,0 +1,12 @@
require 'rails_helper'
RSpec.describe CastingCallInterview, type: :model do
describe "associations" do
it { is_expected.to belong_to(:casting_call) }
it { is_expected.to have_secure_token(:token) }
end
describe "validations" do
it { is_expected.to validate_presence_of(:performer_name) }
end
end

View File

@@ -0,0 +1,11 @@
require 'rails_helper'
RSpec.describe CastingCall, type: :model do
describe "associations" do
it { is_expected.to belong_to(:project) }
end
describe "validations" do
it { is_expected.to have_secure_token(:token) }
end
end

View File

@@ -0,0 +1,91 @@
require "rails_helper"
describe CastingCallPolicy do
subject { described_class }
let(:user_context) { build(:user_context, user: user, account: user.primary_account) }
context "for an associate" do
let(:user) { create(:user, :associate, admin: false) }
permissions :index? do
it { is_expected.to permit(user_context, subject) }
end
permissions :create? do
it { is_expected.to permit(user_context, subject) }
end
permissions :show? do
it { is_expected.to permit(user_context, subject) }
end
permissions :destroy? do
it { is_expected.to permit(user_context, subject) }
end
permissions :update? do
it { is_expected.to permit(user_context, subject) }
end
permissions :cancel? do
it { is_expected.to permit(user_context, subject) }
end
end
context "for a project manager" do
let(:user) { create(:user, :manager, admin: false) }
permissions :index? do
it { is_expected.to permit(user_context, subject) }
end
permissions :create? do
it { is_expected.to permit(user_context, subject) }
end
permissions :show? do
it { is_expected.to permit(user_context, subject) }
end
permissions :destroy? do
it { is_expected.to permit(user_context, subject) }
end
permissions :update? do
it { is_expected.to permit(user_context, subject) }
end
permissions :cancel? do
it { is_expected.to permit(user_context, subject) }
end
end
context "for account managers" do
let(:user) { create(:user, :account_manager, admin: false) }
permissions :index? do
it { is_expected.to permit(user_context, subject) }
end
permissions :create? do
it { is_expected.to permit(user_context, subject) }
end
permissions :show? do
it { is_expected.to permit(user_context, subject) }
end
permissions :destroy? do
it { is_expected.to permit(user_context, subject) }
end
permissions :update? do
it { is_expected.to permit(user_context, subject) }
end
permissions :cancel? do
it { is_expected.to permit(user_context, subject) }
end
end
end