You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
docuseal/spec/requests/templates_spec.rb

258 lines
9.2 KiB

# frozen_string_literal: true
describe 'Templates API' do
let(:account) { create(:account, :with_testing_account) }
let(:testing_account) { account.testing_accounts.first }
let(:author) { create(:user, account:) }
let(:testing_author) { create(:user, account: testing_account) }
let(:folder) { create(:template_folder, account:) }
let(:template_preferences) { { 'request_email_subject' => 'Subject text', 'request_email_body' => 'Body Text' } }
before do
allow(Accounts).to receive(:link_expires_at).and_return(Accounts::LINK_EXPIRES_AT)
end
describe 'GET /api/templates' do
it 'returns a list of templates' do
templates = [
create(:template, account:,
author:,
folder:,
external_id: SecureRandom.base58(10),
preferences: template_preferences),
create(:template, account:,
author:,
folder:,
external_id: SecureRandom.base58(10),
preferences: template_preferences)
].reverse
get '/api/templates', headers: { 'x-auth-token': author.access_token.token }
expect(response).to have_http_status(:ok)
expect(response.parsed_body['pagination']).to eq(JSON.parse({
count: templates.size,
next: templates.last.id,
prev: templates.first.id
}.to_json))
expect(response.parsed_body['data']).to eq(JSON.parse(templates.map { |t| template_body(t) }.to_json))
end
end
describe 'GET /api/templates/:id' do
it 'returns a template' do
template = create(:template, account:,
author:,
folder:,
external_id: SecureRandom.base58(10),
preferences: template_preferences)
get "/api/templates/#{template.id}", headers: { 'x-auth-token': author.access_token.token }
expect(response).to have_http_status(:ok)
expect(response.parsed_body).to eq(JSON.parse(template_body(template).to_json))
end
it 'returns an authorization error if test account API token is used with a production template' do
template = create(:template, account:,
author:,
folder:,
external_id: SecureRandom.base58(10),
preferences: template_preferences)
get "/api/templates/#{template.id}", headers: { 'x-auth-token': testing_author.access_token.token }
expect(response).to have_http_status(:forbidden)
expect(response.parsed_body).to eq(
JSON.parse({ error: "Template #{template.id} not found using testing API key; " \
'Use production API key to access production templates.' }.to_json)
)
end
it 'returns an authorization error if production account API token is used with a test template' do
template = create(:template, account: testing_account,
author: testing_author,
folder:,
external_id: SecureRandom.base58(10),
preferences: template_preferences)
get "/api/templates/#{template.id}", headers: { 'x-auth-token': author.access_token.token }
expect(response).to have_http_status(:forbidden)
expect(response.parsed_body).to eq(
JSON.parse({ error: "Template #{template.id} not found using production API key; " \
'Use testing API key to access testing templates.' }.to_json)
)
end
end
describe 'PUT /api/templates' do
let(:template) do
create(:template, account:,
author:,
folder:,
external_id: SecureRandom.base58(10),
preferences: template_preferences)
end
it 'updates a template' do
put "/api/templates/#{template.id}", headers: { 'x-auth-token': author.access_token.token }, params: {
name: 'Updated Template Name',
external_id: '123456'
}.to_json
expect(response).to have_http_status(:ok)
template.reload
expect(template.name).to eq('Updated Template Name')
expect(template.external_id).to eq('123456')
expect(response.parsed_body).to eq(JSON.parse({
id: template.id,
updated_at: template.updated_at
}.to_json))
end
it "enables the template's shared link" do
expect do
put "/api/templates/#{template.id}", headers: { 'x-auth-token': author.access_token.token }, params: {
shared_link: true
}.to_json
end.to change { template.reload.shared_link }.from(false).to(true)
end
it "disables the template's shared link" do
template.update(shared_link: true)
expect do
put "/api/templates/#{template.id}", headers: { 'x-auth-token': author.access_token.token }, params: {
shared_link: false
}.to_json
end.to change { template.reload.shared_link }.from(true).to(false)
end
end
describe 'DELETE /api/templates/:id' do
it 'archives a template' do
template = create(:template, account:,
author:,
folder:,
external_id: SecureRandom.base58(10),
preferences: template_preferences)
delete "/api/templates/#{template.id}", headers: { 'x-auth-token': author.access_token.token }
expect(response).to have_http_status(:ok)
template.reload
expect(template.archived_at).not_to be_nil
expect(response.parsed_body).to eq(JSON.parse({
id: template.id,
archived_at: template.archived_at
}.to_json))
end
end
describe 'POST /api/templates/:id/clone' do
it 'clones a template' do
template = create(:template, account:,
author:,
folder:,
external_id: SecureRandom.base58(10),
preferences: template_preferences)
expect do
post "/api/templates/#{template.id}/clone", headers: { 'x-auth-token': author.access_token.token }, params: {
name: 'Cloned Template Name',
external_id: '123456'
}.to_json
end.to change(Template, :count)
expect(response).to have_http_status(:ok)
cloned_template = Template.last
expect(cloned_template.name).to eq('Cloned Template Name')
expect(cloned_template.external_id).to eq('123456')
expect(response.parsed_body).to eq(JSON.parse(clone_template_body(cloned_template).to_json))
end
end
private
def template_body(template)
template_attachment_uuid = template.schema.first['attachment_uuid']
attachment = template.schema_documents.preload(:blob).find { |e| e.uuid == template_attachment_uuid }
first_page_blob =
ActiveStorage::Attachment.joins(:blob)
.where(blob: { filename: '0.png' })
.where(record_id: template.schema_documents.map(&:id),
record_type: 'ActiveStorage::Attachment',
name: :preview_images)
.preload(:blob)
.first
.blob
{
id: template.id,
slug: template.slug,
name: template.name,
fields: template.fields,
submitters: [
{
name: 'First Party',
uuid: template.submitters.first['uuid']
}
],
author: {
id: author.id,
first_name: author.first_name,
last_name: author.last_name,
email: author.email
},
documents: [
{
id: template.documents.first.id,
uuid: template.documents.first.uuid,
url: ActiveStorage::Blob.proxy_url(attachment.blob, expires_at: Accounts::LINK_EXPIRES_AT),
preview_image_url: ActiveStorage::Blob.proxy_url(first_page_blob, expires_at: Accounts::LINK_EXPIRES_AT),
filename: 'sample-document.pdf'
}
],
preferences: {
'request_email_subject' => 'Subject text',
'request_email_body' => 'Body Text'
},
schema: [
{
attachment_uuid: template_attachment_uuid,
name: 'sample-document'
}
],
shared_link: template.shared_link,
author_id: author.id,
archived_at: nil,
created_at: template.created_at,
updated_at: template.updated_at,
folder_id: folder.id,
folder_name: folder.name,
source: 'native',
external_id: template.external_id,
application_key: template.external_id
}
end
def clone_template_body(cloned_template)
body = template_body(cloned_template).merge(source: 'api')
body[:fields].each_with_index do |field, index|
field.merge!(
'submitter_uuid' => cloned_template.fields[index]['submitter_uuid'],
'uuid' => cloned_template.fields[index]['uuid']
)
end
body
end
end