Merge branch 'docusealco:master' into master

pull/402/head
Vincent Barrier 8 months ago committed by GitHub
commit 8ef574347e
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

@ -0,0 +1,58 @@
---
:position: before
:position_in_additional_file_patterns: before
:position_in_class: before
:position_in_factory: before
:position_in_fixture: before
:position_in_routes: before
:position_in_serializer: before
:position_in_test: before
:classified_sort: true
:exclude_controllers: true
:exclude_factories: true
:exclude_fixtures: false
:exclude_helpers: true
:exclude_scaffolds: true
:exclude_serializers: false
:exclude_sti_subclasses: false
:exclude_tests: false
:force: false
:format_markdown: false
:format_rdoc: false
:format_yard: false
:frozen: false
:ignore_model_sub_dir: false
:ignore_unknown_models: false
:include_version: false
:show_check_constraints: false
:show_complete_foreign_keys: false
:show_foreign_keys: true
:show_indexes: true
:simple_indexes: false
:sort: false
:timestamp: false
:trace: false
:with_comment: true
:with_column_comments: true
:with_table_comments: true
:active_admin: false
:command:
:debug: false
:hide_default_column_types: ''
:hide_limit_column_types: ''
:ignore_columns:
:ignore_routes:
:models: true
:routes: false
:skip_on_db_migrate: false
:target_action: :do_annotations
:wrapper:
:wrapper_close:
:wrapper_open:
:classes_default_to_s: []
:additional_file_patterns: []
:model_dir:
- app/models
:require: []
:root_dir:
- ''

@ -77,6 +77,33 @@ jobs:
run: |
./node_modules/eslint/bin/eslint.js "app/javascript/**/*.js"
brakeman:
name: Brakeman
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Install Ruby
uses: ruby/setup-ruby@v1
with:
ruby-version: 3.4.1
- name: Cache gems
uses: actions/cache@v4
with:
path: vendor/bundle
key: ${{ runner.os }}-gem-${{ hashFiles('**/Gemfile.lock') }}
restore-keys: |
${{ runner.os }}-gem-
- name: Install gems
run: |
gem install bundler
bundle config path vendor/bundle
bundle install --jobs 4 --retry 4
yarn install
sudo apt-get update
sudo apt-get install libvips
- name: Run Brakeman
run: bundle exec brakeman -q --exit-on-warn
rspec:
name: RSpec
runs-on: ubuntu-latest

@ -7,7 +7,7 @@ on:
jobs:
build:
runs-on: ubuntu-latest
runs-on: ubuntu-24.04-arm
steps:
- name: Checkout code

@ -1,4 +1,4 @@
FROM ruby:3.4.1-alpine as fonts
FROM ruby:3.4.1-alpine AS fonts
WORKDIR /fonts
@ -6,7 +6,7 @@ RUN apk --no-cache add fontforge wget && wget https://github.com/satbyy/go-noto-
RUN fontforge -lang=py -c 'font1 = fontforge.open("FreeSans.ttf"); font2 = fontforge.open("NotoSansSymbols2-Regular.ttf"); font1.mergeFonts(font2); font1.generate("FreeSans.ttf")'
FROM ruby:3.4.1-alpine as webpack
FROM ruby:3.4.1-alpine AS webpack
ENV RAILS_ENV=production
ENV NODE_ENV=production
@ -32,7 +32,7 @@ COPY ./app/views ./app/views
RUN echo "gem 'shakapacker'" > Gemfile && ./bin/shakapacker
FROM ruby:3.4.1-alpine as app
FROM ruby:3.4.1-alpine AS app
ENV RAILS_ENV=production
ENV BUNDLE_WITHOUT="development:test"

@ -46,7 +46,6 @@ gem 'twitter_cldr', require: false
gem 'tzinfo-data'
group :development, :test do
gem 'annotate'
gem 'better_html'
gem 'bullet'
gem 'debug'
@ -63,6 +62,9 @@ group :development, :test do
end
group :development do
gem 'annotaterb'
gem 'brakeman', require: false
gem 'foreman', require: false
gem 'letter_opener_web'
gem 'web-console'
end

@ -74,9 +74,7 @@ GEM
uri (>= 0.13.1)
addressable (2.8.7)
public_suffix (>= 2.0.2, < 7.0)
annotate (2.6.5)
activerecord (>= 2.3.0)
rake (>= 0.8.7)
annotaterb (4.14.0)
arabic-letter-connector (0.1.1)
ast (2.4.2)
aws-eventstream (1.3.0)
@ -120,6 +118,8 @@ GEM
bindex (0.8.1)
bootsnap (1.18.4)
msgpack (~> 1.2)
brakeman (7.0.0)
racc
builder (3.3.0)
bullet (8.0.0)
activesupport (>= 3.0.0)
@ -229,6 +229,7 @@ GEM
ffi (1.17.1-arm64-darwin)
ffi (1.17.1-x86_64-linux-gnu)
ffi (1.17.1-x86_64-linux-musl)
foreman (0.88.1)
geom2d (0.4.1)
globalid (1.2.1)
activesupport (>= 6.1)
@ -337,18 +338,18 @@ GEM
net-smtp (0.5.0)
net-protocol
nio4r (2.7.4)
nokogiri (1.18.2)
nokogiri (1.18.3)
mini_portile2 (~> 2.8.2)
racc (~> 1.4)
nokogiri (1.18.2-aarch64-linux-gnu)
nokogiri (1.18.3-aarch64-linux-gnu)
racc (~> 1.4)
nokogiri (1.18.2-aarch64-linux-musl)
nokogiri (1.18.3-aarch64-linux-musl)
racc (~> 1.4)
nokogiri (1.18.2-arm64-darwin)
nokogiri (1.18.3-arm64-darwin)
racc (~> 1.4)
nokogiri (1.18.2-x86_64-linux-gnu)
nokogiri (1.18.3-x86_64-linux-gnu)
racc (~> 1.4)
nokogiri (1.18.2-x86_64-linux-musl)
nokogiri (1.18.3-x86_64-linux-musl)
racc (~> 1.4)
oj (3.16.8)
bigdecimal (>= 3.0)
@ -588,13 +589,14 @@ PLATFORMS
x86_64-linux-musl
DEPENDENCIES
annotate
annotaterb
arabic-letter-connector
aws-sdk-s3
aws-sdk-secretsmanager
azure-storage-blob
better_html
bootsnap
brakeman
bullet
cancancan
capybara
@ -610,6 +612,7 @@ DEPENDENCIES
faker
faraday
faraday-follow_redirects
foreman
google-cloud-storage
hexapdf
image_processing

@ -39,7 +39,7 @@ class AccountConfigsController < ApplicationController
end
def account_config_params
params.required(:account_config).permit!.tap do |attrs|
params.required(:account_config).permit(:key, :value, { value: {} }, { value: [] }).tap do |attrs|
attrs[:value] = attrs[:value] == '1' if attrs[:value].in?(%w[1 0])
end
end

@ -146,9 +146,15 @@ module Api
if attrs[:completed]
submitter.values = Submitters::SubmitValues.merge_default_values(submitter)
submitter.values = Submitters::SubmitValues.merge_formula_values(submitter)
submitter.values = Submitters::SubmitValues.maybe_remove_condition_values(submitter)
formula_values = Submitters::SubmitValues.build_formula_values(submitter)
if formula_values.present?
submitter.values = submitter.values.merge(formula_values)
submitter.values = Submitters::SubmitValues.maybe_remove_condition_values(submitter)
end
submitter.values = submitter.values.transform_values do |v|
v == '{{date}}' ? Time.current.in_time_zone(submitter.account.timezone).to_date.to_s : v
end

@ -39,7 +39,7 @@ class NotificationsSettingsController < ApplicationController
end
def email_config_params
params.require(:account_config).permit!.tap do |attrs|
params.require(:account_config).permit(:key, :value, { value: {} }, { value: [] }).tap do |attrs|
attrs[:key] = nil unless attrs[:key].in?([AccountConfig::BCC_EMAILS, AccountConfig::SUBMITTER_REMINDERS])
end
end

@ -50,7 +50,7 @@ class PersonalizationSettingsController < ApplicationController
end
def account_config_params
attrs = params.require(:account_config).permit!
attrs = params.require(:account_config).permit(:key, :value, { value: {} }, { value: [] })
return attrs if attrs[:value].is_a?(String)

@ -20,7 +20,7 @@ class SubmissionsPreviewController < ApplicationController
@submission ||= Submission.find_by!(slug: params[:slug])
raise ActionController::RoutingError if @submission.account.archived_at?
raise ActionController::RoutingError, I18n.t('not_found') if @submission.account.archived_at?
if !@submission.submitters.all?(&:completed_at?) && !signature_valid &&
(!current_user || !current_ability.can?(:read, @submission))

@ -26,7 +26,7 @@ class UserConfigsController < ApplicationController
end
def user_config_params
params.required(:user_config).permit!.tap do |attrs|
params.required(:user_config).permit(:key, :value, { value: {} }, { value: [] }).tap do |attrs|
attrs[:value] = attrs[:value] == '1' if attrs[:value].in?(%w[1 0])
end
end

@ -45,17 +45,16 @@ class UsersController < ApplicationController
return redirect_to settings_users_path, notice: I18n.t('unable_to_update_user') if Docuseal.demo?
attrs = user_params.compact_blank.merge(user_params.slice(:archived_at))
attrs.delete(:role) if !role_valid?(attrs[:role]) || current_user == @user
if params.dig(:user, :account_id).present?
account = Account.accessible_by(current_ability).find(params[:user][:account_id])
account = Account.accessible_by(current_ability).find(params.dig(:user, :account_id))
authorize!(:manage, account)
@user.account = account
end
if @user.update(attrs)
if @user.update(attrs.except(current_user == @user ? :role : nil))
redirect_back fallback_location: settings_users_path, notice: I18n.t('user_has_been_updated')
else
render turbo_stream: turbo_stream.replace(:modal, template: 'users/edit'), status: :unprocessable_entity
@ -84,8 +83,11 @@ class UsersController < ApplicationController
def user_params
if params.key?(:user)
params.require(:user).permit(:email, :first_name, :last_name, :password,
:role, :archived_at, :account_id)
permitted_params = %i[email first_name last_name password archived_at]
permitted_params << :role if role_valid?(params.dig(:user, :role))
params.require(:user).permit(permitted_params)
else
{}
end

@ -1037,7 +1037,7 @@ export default {
}, [])
},
formulaFields () {
return this.fields.filter((f) => f.preferences?.formula && f.type !== 'payment')
return this.fields.filter((f) => f.preferences?.formula && f.type !== 'payment' && this.checkFieldConditions(f) && this.checkFieldDocumentsConditions(f))
},
attachmentsIndex () {
return this.attachments.reduce((acc, a) => {

@ -55,6 +55,7 @@ class Submitter < ApplicationRecord
has_many_attached :attachments
has_many_attached :preview_documents
has_many :template_accesses, through: :template
has_many :email_events, as: :emailable, dependent: (Docuseal.multitenant? ? nil : :destroy)
has_many :document_generation_events, dependent: :destroy
has_many :submission_events, dependent: :destroy
@ -63,6 +64,8 @@ class Submitter < ApplicationRecord
scope :completed, -> { where.not(completed_at: nil) }
after_destroy :anonymize_email_events, if: -> { Docuseal.multitenant? }
def status
if declined_at?
'declined'
@ -108,4 +111,12 @@ class Submitter < ApplicationRecord
fields.any? { |f| f['submitter_uuid'] == uuid && signature_field_types.include?(f['type']) }
end
end
private
def anonymize_email_events
email_events.each do |event|
event.update!(email: Digest::MD5.base64digest(event.email))
end
end
end

@ -285,12 +285,12 @@
<div class="form-control">
<%= ff.text_field :name, class: 'w-full outline-none border-transparent focus:border-transparent focus:ring-0 bg-base-100 px-1 peer mb-2', autocomplete: 'off', placeholder: "#{index + 1}#{(index + 1).ordinal} Party", required: true %>
<% if @template.submitters.size == 2 %>
<%= ff.email_field :email, class: 'base-input', autocomplete: 'off', placeholder: t('default_email'), disabled: ff.object.is_requester || ff.object.invite_by_uuid.present? || ff.object.optional_invite_by_uuid.present?, id: field_uuid = SecureRandom.uuid %>
<%= tag.input name: ff.field_name(:email), value: ff.object.email, type: :email, class: 'base-input', multiple: true, autocomplete: 'off', placeholder: t('default_email'), disabled: ff.object.is_requester || ff.object.invite_by_uuid.present? || ff.object.optional_invite_by_uuid.present?, id: field_uuid = SecureRandom.uuid %>
<% else %>
<toggle-attribute data-target-id="<%= email_field_uuid = SecureRandom.uuid %>" data-class-name="hidden" data-value="email">
<%= ff.select :option, [[t('not_specified'), 'not_set'], [t('submission_requester'), 'is_requester'], [t('specified_email'), 'email'], *(@template.submitters - [submitter]).flat_map { |e| [[t('invite_by_name', name: e['name']), "invite_by_#{e['uuid']}"], [t('invite_by_name', name: e['name']) + " (#{t(:optional).capitalize})", "optional_invite_by_#{e['uuid']}"]] }, *(@template.submitters - [submitter]).map { |e| [t('same_as_name', name: e['name']), "linked_to_#{e['uuid']}"] }], {}, class: 'base-select mb-3' %>
</toggle-attribute>
<%= ff.email_field :email, class: "base-input #{'hidden' if item.option != 'email'}", autocomplete: 'off', placeholder: t('default_email'), id: email_field_uuid %>
<%= tag.input name: ff.field_name(:email), type: :email, value: ff.object.email, multiple: true, class: "base-input #{'hidden' if item.option != 'email'}", autocomplete: 'off', placeholder: t('default_email'), id: email_field_uuid %>
<% end %>
</div>
<% if @template.submitters.size == 2 %>

@ -0,0 +1,8 @@
{
"ignored_warnings": [
{
"fingerprint": "25f4ce5fee1e1180fa1919dc4ee78db3ab3457a956e4679503aa745771a43836",
"note": "Permitted parameters are necessary for creating submitters via API"
}
]
}

@ -0,0 +1,37 @@
# frozen_string_literal: true
class CreateConsole1984Tables < ActiveRecord::Migration[7.0]
def change
create_table :console1984_sessions do |t|
t.text :reason
t.references :user, null: false, index: false
t.timestamps
t.index :created_at
t.index %i[user_id created_at]
end
create_table :console1984_users do |t|
t.string :username, null: false
t.timestamps
t.index [:username]
end
create_table :console1984_commands do |t|
t.text :statements
t.references :sensitive_access
t.references :session, null: false, index: false
t.timestamps
t.index %i[session_id created_at sensitive_access_id], name: 'on_session_and_sensitive_chronologically'
end
create_table :console1984_sensitive_accesses do |t|
t.text :justification
t.references :session, null: false
t.timestamps
end
end
end

@ -10,7 +10,7 @@
#
# It's strongly recommended that you check this file into your version control system.
ActiveRecord::Schema[7.2].define(version: 2024_12_07_172237) do
ActiveRecord::Schema[8.0].define(version: 2025_02_25_111255) do
# These are extensions that must be enabled in order to support this database
enable_extension "plpgsql"
@ -112,6 +112,40 @@ ActiveRecord::Schema[7.2].define(version: 2024_12_07_172237) do
t.index ["submitter_id"], name: "index_completed_submitters_on_submitter_id", unique: true
end
create_table "console1984_commands", force: :cascade do |t|
t.text "statements"
t.bigint "sensitive_access_id"
t.bigint "session_id", null: false
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["sensitive_access_id"], name: "index_console1984_commands_on_sensitive_access_id"
t.index ["session_id", "created_at", "sensitive_access_id"], name: "on_session_and_sensitive_chronologically"
end
create_table "console1984_sensitive_accesses", force: :cascade do |t|
t.text "justification"
t.bigint "session_id", null: false
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["session_id"], name: "index_console1984_sensitive_accesses_on_session_id"
end
create_table "console1984_sessions", force: :cascade do |t|
t.text "reason"
t.bigint "user_id", null: false
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["created_at"], name: "index_console1984_sessions_on_created_at"
t.index ["user_id", "created_at"], name: "index_console1984_sessions_on_user_id_and_created_at"
end
create_table "console1984_users", force: :cascade do |t|
t.string "username", null: false
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["username"], name: "index_console1984_users_on_username"
end
create_table "document_generation_events", force: :cascade do |t|
t.bigint "submitter_id", null: false
t.string "event_name", null: false

@ -8,19 +8,20 @@ module DownloadUtils
module_function
def call(url)
uri = Addressable::URI.parse(url)
uri = begin
URI(url)
rescue URI::Error
Addressable::URI.parse(url).normalize
end
if Docuseal.multitenant?
raise UnableToDownload, "Error loading: #{uri.display_uri}. Only HTTPS is allowed." if uri.scheme != 'https'
if uri.host.in?(LOCALHOSTS)
raise UnableToDownload, "Error loading: #{uri.display_uri}. Can't download from localhost."
end
raise UnableToDownload, "Error loading: #{uri}. Only HTTPS is allowed." if uri.scheme != 'https'
raise UnableToDownload, "Error loading: #{uri}. Can't download from localhost." if uri.host.in?(LOCALHOSTS)
end
resp = conn.get(uri.display_uri.to_s)
resp = conn.get(uri)
raise UnableToDownload, "Error loading: #{uri.display_uri}" if resp.status >= 400
raise UnableToDownload, "Error loading: #{uri}" if resp.status >= 400
resp
end

@ -15,7 +15,10 @@ module ReplaceEmailVariables
SUBMITTER_SLUG = /\{+submitter\.slug\}+/i
SUBMISSION_LINK = /\{+submission\.link\}+/i
SUBMISSION_ID = /\{+submission\.id\}+/i
SUBMISSION_SUBMITTERS = /\{+submission\.submitters\}+/i
SUBMITTERS = /\{+(?:submission\.)?submitters\}+/i
SUBMITTERS_N_EMAIL = /\{+submitters\[(?<index>\d+)\]\.email\}+/i
SUBMITTERS_N_NAME = /\{+submitters\[(?<index>\d+)\]\.name\}+/i
SUBMITTERS_N_FIRST_NAME = /\{+submitters\[(?<index>\d+)\]\.first_name\}+/i
DOCUMENTS_LINKS = /\{+documents\.links\}+/i
DOCUMENTS_LINK = /\{+documents\.link\}+/i
@ -37,13 +40,25 @@ module ReplaceEmailVariables
text = replace(text, SUBMISSION_LINK, html_escape:) do
submitter.submission ? build_submission_link(submitter.submission) : ''
end
text = replace(text, SUBMISSION_SUBMITTERS, html_escape:) { build_submission_submitters(submitter.submission) }
text = replace(text, SUBMITTERS, html_escape:) { build_submission_submitters(submitter.submission) }
text = replace(text, DOCUMENTS_LINKS, html_escape:) { build_documents_links_text(submitter, sig) }
text = replace(text, DOCUMENTS_LINK, html_escape:) { build_documents_links_text(submitter, sig) }
text = replace(text, ACCOUNT_NAME, html_escape:) { submitter.submission.account.name }
text = replace(text, SENDER_NAME, html_escape:) { submitter.submission.created_by_user&.full_name }
text = replace(text, SENDER_FIRST_NAME, html_escape:) { submitter.submission.created_by_user&.first_name }
text = replace(text, SUBMITTERS_N_NAME, html_escape:) do |match|
build_submitters_n_field(submitter.submission, match[:index].to_i - 1, :name)
end
text = replace(text, SUBMITTERS_N_EMAIL, html_escape:) do |match|
build_submitters_n_field(submitter.submission, match[:index].to_i - 1, :email)
end
text = replace(text, SUBMITTERS_N_FIRST_NAME, html_escape:) do |match|
build_submitters_n_field(submitter.submission, match[:index].to_i - 1, :first_name)
end
replace(text, SENDER_EMAIL, html_escape:) { submitter.submission.created_by_user&.email.to_s.sub(/\+\w+@/, '@') }
end
# rubocop:enable Metrics
@ -54,12 +69,18 @@ module ReplaceEmailVariables
)
end
def build_submitters_n_field(submission, index, field_name)
uuid = (submission.template_submitters || submission.template.submitters).dig(index, 'uuid')
submission.submitters.find { |s| s.uuid == uuid }.try(field_name)
end
def replace(text, var, html_escape: false)
text.gsub(var) do
if html_escape
ERB::Util.html_escape(yield)
ERB::Util.html_escape(yield(Regexp.last_match))
else
yield
yield(Regexp.last_match)
end
end
end

@ -3,10 +3,28 @@
module SendWebhookRequest
USER_AGENT = 'DocuSeal.com Webhook'
LOCALHOSTS = %w[0.0.0.0 127.0.0.1 localhost].freeze
HttpsError = Class.new(StandardError)
LocalhostError = Class.new(StandardError)
module_function
def call(webhook_url, event_type:, data:)
Faraday.post(webhook_url.url) do |req|
uri = begin
URI(webhook_url.url)
rescue URI::Error
Addressable::URI.parse(webhook_url.url).normalize
end
if Docuseal.multitenant?
raise HttpsError, 'Only HTTPS is allowed.' if uri.scheme != 'https' &&
!AccountConfig.exists?(key: :allow_http,
account_id: webhook_url.account_id)
raise LocalhostError, "Can't send to localhost." if uri.host.in?(LOCALHOSTS)
end
Faraday.post(uri) do |req|
req.headers['Content-Type'] = 'application/json'
req.headers['User-Agent'] = USER_AGENT
req.headers.merge!(webhook_url.secret.to_h) if webhook_url.secret.present?

@ -107,6 +107,7 @@ module Submissions
def normalize_email(email)
return if email.blank?
return if email.is_a?(Numeric)
return email.downcase if email.to_s.include?(',') ||
email.to_s.match?(/\.(?:gob|om|mm|cm|et|mo|nz|za|ie)\z/) ||

@ -225,9 +225,15 @@ module Submissions
def assign_completed_attributes(submitter)
submitter.values = Submitters::SubmitValues.merge_default_values(submitter)
submitter.values = Submitters::SubmitValues.merge_formula_values(submitter)
submitter.values = Submitters::SubmitValues.maybe_remove_condition_values(submitter)
formula_values = Submitters::SubmitValues.build_formula_values(submitter)
if formula_values.present?
submitter.values = submitter.values.merge(formula_values)
submitter.values = Submitters::SubmitValues.maybe_remove_condition_values(submitter)
end
submitter.values = submitter.values.transform_values do |v|
v == '{{date}}' ? Time.current.in_time_zone(submitter.submission.account.timezone).to_date.to_s : v
end

@ -53,9 +53,17 @@ module Submitters
submitter.completed_at = Time.current
submitter.ip = request.remote_ip
submitter.ua = request.user_agent
submitter.values = merge_default_values(submitter)
submitter.values = maybe_remove_condition_values(submitter)
submitter.values = merge_formula_values(submitter)
formula_values = build_formula_values(submitter)
if formula_values.present?
submitter.values = submitter.values.merge(formula_values)
submitter.values = maybe_remove_condition_values(submitter)
end
submitter.values = submitter.values.transform_values do |v|
v == '{{date}}' ? Time.current.in_time_zone(submitter.account.timezone).to_date.to_s : v
end
@ -149,7 +157,7 @@ module Submitters
default_values.compact_blank.merge(submitter.values)
end
def merge_formula_values(submitter)
def build_formula_values(submitter)
computed_values = submitter.submission.template_fields.each_with_object({}) do |field, acc|
next if field['submitter_uuid'] != submitter.uuid
next if field['type'] == 'payment'
@ -161,7 +169,7 @@ module Submitters
acc[field['uuid']] = calculate_formula_value(formula, submitter.values.merge(acc.compact_blank))
end
submitter.values.merge(computed_values.compact_blank)
computed_values.compact_blank
end
def calculate_formula_value(_formula, _values)

@ -0,0 +1,10 @@
# frozen_string_literal: true
# This rake task was added by annotate_rb gem.
# Can set `ANNOTATERB_SKIP_ON_DB_TASKS` to be anything to skip this
if Rails.env.development? && ENV['ANNOTATERB_SKIP_ON_DB_TASKS'].nil?
require 'annotate_rb'
AnnotateRb::Core.load_rake_tasks
end

@ -1,57 +0,0 @@
# frozen_string_literal: true
if Rails.env.development?
require 'annotate'
task set_annotation_options: :environment do
Annotate.set_defaults(
'active_admin' => 'false',
'additional_file_patterns' => [],
'routes' => 'false',
'models' => 'true',
'position_in_routes' => 'before',
'position_in_class' => 'before',
'position_in_test' => 'before',
'position_in_fixture' => 'before',
'position_in_factory' => 'before',
'position_in_serializer' => 'before',
'show_foreign_keys' => 'true',
'show_complete_foreign_keys' => 'false',
'show_indexes' => 'true',
'simple_indexes' => 'false',
'model_dir' => 'app/models',
'root_dir' => '',
'include_version' => 'false',
'require' => '',
'exclude_tests' => 'true',
'exclude_fixtures' => 'true',
'exclude_factories' => 'true',
'exclude_serializers' => 'false',
'exclude_scaffolds' => 'true',
'exclude_controllers' => 'true',
'exclude_helpers' => 'true',
'exclude_sti_subclasses' => 'false',
'ignore_model_sub_dir' => 'false',
'ignore_columns' => nil,
'ignore_routes' => nil,
'ignore_unknown_models' => 'false',
'hide_limit_column_types' => 'integer,bigint,boolean',
'hide_default_column_types' => 'json,jsonb,hstore',
'skip_on_db_migrate' => 'false',
'format_bare' => 'true',
'format_rdoc' => 'false',
'format_yard' => 'false',
'format_markdown' => 'false',
'sort' => 'false',
'force' => 'false',
'frozen' => 'false',
'classified_sort' => 'true',
'trace' => 'false',
'wrapper_open' => nil,
'wrapper_close' => nil,
'with_comment' => 'true'
)
end
Annotate.load_tasks
end

@ -9,7 +9,6 @@ module Templates
template.external_id = external_id
template.author = author
template.preferences = original_template.preferences.deep_dup
template.name = name.presence || "#{original_template.name} (#{I18n.t('clone')})"
if folder_name.present?
@ -18,10 +17,11 @@ module Templates
template.folder_id = original_template.folder_id
end
template.submitters, template.fields, template.schema =
template.submitters, template.fields, template.schema, template.preferences =
update_submitters_and_fields_and_schema(original_template.submitters.deep_dup,
original_template.fields.deep_dup,
original_template.schema.deep_dup)
original_template.schema.deep_dup,
original_template.preferences.deep_dup)
if name.present? && template.schema.size == 1 &&
original_template.schema.first['name'] == original_template.name &&
@ -33,7 +33,7 @@ module Templates
end
# rubocop:disable Metrics, Style/CombinableLoops
def update_submitters_and_fields_and_schema(cloned_submitters, cloned_fields, cloned_schema)
def update_submitters_and_fields_and_schema(cloned_submitters, cloned_fields, cloned_schema, cloned_preferences)
submitter_uuids_replacements = {}
field_uuids_replacements = {}
@ -58,6 +58,10 @@ module Templates
end
end
cloned_preferences['submitters'].to_a.each do |submitter|
submitter['uuid'] = submitter_uuids_replacements[submitter['uuid']]
end
cloned_fields.each do |field|
new_field_uuid = SecureRandom.uuid
@ -88,7 +92,7 @@ module Templates
end
end
[cloned_submitters, cloned_fields, cloned_schema]
[cloned_submitters, cloned_fields, cloned_schema, cloned_preferences]
end
# rubocop:enable Metrics, Style/CombinableLoops
end

@ -101,7 +101,7 @@ module Templates
{
uuid: SecureRandom.uuid,
required: false,
required: field.flags.include?(:required),
preferences: {},
areas:,
**field_properties

Loading…
Cancel
Save