From 38e68814cfcd890adc1b215220686855e816e27c Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Tue, 29 Apr 2025 18:01:08 +0300 Subject: [PATCH 01/30] fix color --- app/views/icons/_arrow_sort.html.erb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/views/icons/_arrow_sort.html.erb b/app/views/icons/_arrow_sort.html.erb index 9298a506..478bf8c7 100644 --- a/app/views/icons/_arrow_sort.html.erb +++ b/app/views/icons/_arrow_sort.html.erb @@ -1,4 +1,4 @@ - + From 96bb4eb6e5b2672f98a5c34ac6da43872d8c81c9 Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Tue, 29 Apr 2025 20:15:32 +0300 Subject: [PATCH 02/30] fix standalone radio --- lib/templates/find_acro_fields.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/templates/find_acro_fields.rb b/lib/templates/find_acro_fields.rb index b9fcc3d8..b02bbdfc 100644 --- a/lib/templates/find_acro_fields.rb +++ b/lib/templates/find_acro_fields.rb @@ -161,7 +161,7 @@ module Templates options: build_options(field.allowed_values, 'radio'), default_value: selected_option } - elsif field.field_type == :Btn && field.concrete_field_type == :check_box + elsif field.field_type == :Btn && %i[check_box radio_button].include?(field.concrete_field_type) { **attrs, type: 'checkbox', From 6efe8027f1045cfd9160ce6ef63cbf2605997df9 Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Wed, 30 Apr 2025 16:54:56 +0300 Subject: [PATCH 03/30] disable multiple sign --- app/views/esign_settings/show.html.erb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/views/esign_settings/show.html.erb b/app/views/esign_settings/show.html.erb index 05169a4b..319aa43b 100644 --- a/app/views/esign_settings/show.html.erb +++ b/app/views/esign_settings/show.html.erb @@ -141,7 +141,7 @@ <%= t('preferences') %> - <% if can?(:manage, account_config) %> + <% if can?(:manage, account_config) && (can?(:manage, :personalization_advanced) || !Docuseal.multitenant?) %> <%= form_for account_config, url: account_configs_path, method: :post do |f| %> <%= f.hidden_field :key %>
From 4a8e2a82e5a092039385d8c3710532a67aace549 Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Wed, 30 Apr 2025 22:58:50 +0300 Subject: [PATCH 04/30] tsa fallback --- lib/submissions/timestamp_handler.rb | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/lib/submissions/timestamp_handler.rb b/lib/submissions/timestamp_handler.rb index 03b45d43..da8eb845 100644 --- a/lib/submissions/timestamp_handler.rb +++ b/lib/submissions/timestamp_handler.rb @@ -20,6 +20,7 @@ module Submissions signature[:SubFilter] = :'ETSI.RFC3161' end + # rubocop:disable Metrics def sign(io, byte_range) digest = OpenSSL::Digest.new(HASH_ALGORITHM) @@ -49,7 +50,12 @@ module Submissions end OpenSSL::Timestamp::Response.new(response.body).token.to_der + rescue StandardError => e + Rollbar.error(e) if defined?(Rollbar) + + OpenSSL::ASN1::GeneralizedTime.new(Time.now.utc).to_der end + # rubocop:enable Metrics def build_payload(digest) req = OpenSSL::Timestamp::Request.new From e5f7739952994c868cf4249282bf664cdafc31f9 Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Wed, 30 Apr 2025 23:48:03 +0300 Subject: [PATCH 05/30] use sha 256 for tsa --- lib/submissions/timestamp_handler.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/submissions/timestamp_handler.rb b/lib/submissions/timestamp_handler.rb index da8eb845..9f10064a 100644 --- a/lib/submissions/timestamp_handler.rb +++ b/lib/submissions/timestamp_handler.rb @@ -2,7 +2,7 @@ module Submissions class TimestampHandler - HASH_ALGORITHM = 'SHA512' + HASH_ALGORITHM = 'SHA256' TimestampError = Class.new(StandardError) From 231177f057d5e9fb0defe401d20f8ca20f7d0005 Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Thu, 1 May 2025 00:14:04 +0300 Subject: [PATCH 06/30] add log --- lib/submissions/timestamp_handler.rb | 1 + 1 file changed, 1 insertion(+) diff --git a/lib/submissions/timestamp_handler.rb b/lib/submissions/timestamp_handler.rb index 9f10064a..1daab423 100644 --- a/lib/submissions/timestamp_handler.rb +++ b/lib/submissions/timestamp_handler.rb @@ -52,6 +52,7 @@ module Submissions OpenSSL::Timestamp::Response.new(response.body).token.to_der rescue StandardError => e Rollbar.error(e) if defined?(Rollbar) + Rails.logger.error(e) OpenSSL::ASN1::GeneralizedTime.new(Time.now.utc).to_der end From 3ef0d28ffec99cde6493dc0750b3c4d9096c164d Mon Sep 17 00:00:00 2001 From: Alex Turchyn Date: Thu, 1 May 2025 22:35:11 +0300 Subject: [PATCH 07/30] adjust app tour --- config/locales/i18n.yml | 72 ++++++++++++++++++++--------------------- 1 file changed, 36 insertions(+), 36 deletions(-) diff --git a/config/locales/i18n.yml b/config/locales/i18n.yml index d5845178..91b1c298 100644 --- a/config/locales/i18n.yml +++ b/config/locales/i18n.yml @@ -760,11 +760,11 @@ en: &en previous: Previous next: Next template_and_submissions: 'Templates and Submissions' - template_and_submissions_description: "You can select the view that best suits your workflow. Choose the 'Templates' view if you create reusable document templates, or the 'Submissions' view when you sign individual documents or review the status of each signing request." + template_and_submissions_description: "You can select the view that best suits your workflow. Choose the 'Templates' view to create reusable document templates, or the 'Submissions' view to sign individual documents or review the status of each signature request." upload_a_pdf_file: 'Upload a PDF file' - upload_a_pdf_file_description: 'Upload a document to use it for creating a signing form template.' + upload_a_pdf_file_description: 'Upload a PDF document to create a signing form template.' select_a_signer_party: 'Select a signer party' - select_a_signer_party_description: 'This dropdown allows you to select a signing party role or add a new party to the document when it needs to be signed by two or more parties.' + select_a_signer_party_description: 'This dropdown allows you to select a signing party role or add a new party to the document if it requires 2 or more signatures.' available_parties: 'Available parties' available_parties_description: 'This list contains all available parties with their role names. Once selected, you can add and configure fields for the signer party.' available_field_types: 'Available field types' @@ -772,7 +772,7 @@ en: &en text_input_field: 'Text input field' text_input_field_description: 'This field allows users to enter text-based information, such as names or emails.' signature_field: 'Signature field' - signature_field_description: 'This field allows for collecting signatures from the signers.' + signature_field_description: 'This field is used to collect signatures from the signers.' added_fields: 'Added fields' added_fields_description: 'This list displays all fields added to the document. You can reorder, edit, or remove them.' open_field_settings: 'Open field settings' @@ -786,10 +786,10 @@ en: &en copy_and_share_link: 'Copy & share link' copy_and_share_link_description: 'Copy this link to share the document. Anyone with the link can sign it after entering their email.' sign_the_document: 'Sign the document' - sign_the_document_description: 'If you are one of the signers signer, this button allows you to sign the document yourself.' + sign_the_document_description: 'If you are one of the signers, this button allows you to sign the document.' send_for_signing: 'Send for signing' add_recipients: 'Add recipients' - add_recipients_description: 'Add new recipients for the document to be signed. You can enter their email addresses or phone numbers.' + add_recipients_description: 'Add new recipients for the document to be signed by entering their email addresses or phone numbers.' settings: 'Settings' settings_account_description: 'With comprehensive account settings, you can customize the eSigning experience and invite more users.' support: 'Support' @@ -1542,11 +1542,11 @@ es: &es previous: Anterior next: Siguiente template_and_submissions: 'Plantillas y Envíos' - template_and_submissions_description: "Puedes seleccionar la vista que mejor se adapte a tu flujo de trabajo. Elige la vista de 'Plantillas' si creas plantillas reutilizables de documentos, o la vista de 'Envíos' cuando firmas documentos individuales o revisas el estado de cada solicitud de firma." + template_and_submissions_description: "Puedes seleccionar la vista que mejor se adapte a tu flujo de trabajo. Elige la vista 'Plantillas' para crear plantillas reutilizables de documentos, o la vista 'Envíos' para firmar documentos individuales o revisar el estado de cada solicitud de firma." upload_a_pdf_file: 'Subir un archivo PDF' - upload_a_pdf_file_description: 'Sube un documento para usarlo como plantilla de formulario de firma.' + upload_a_pdf_file_description: 'Sube un documento PDF para crear una plantilla de formulario de firma.' select_a_signer_party: 'Seleccionar parte firmante' - select_a_signer_party_description: 'Este menú desplegable te permite seleccionar un rol de firmante o agregar una nueva parte al documento cuando debe ser firmado por dos o más partes.' + select_a_signer_party_description: 'Este menú desplegable te permite seleccionar un rol de firmante o agregar una nueva parte al documento si requiere 2 o más firmas.' available_parties: 'Partes disponibles' available_parties_description: 'Esta lista contiene todas las partes disponibles con sus roles. Una vez seleccionada, puedes añadir y configurar campos para esa parte.' available_field_types: 'Tipos de campo disponibles' @@ -1554,7 +1554,7 @@ es: &es text_input_field: 'Campo de texto' text_input_field_description: 'Este campo permite a los usuarios introducir información de texto, como nombres o correos electrónicos.' signature_field: 'Campo de firma' - signature_field_description: 'Este campo permite recopilar firmas de los firmantes.' + signature_field_description: 'Este campo se utiliza para recopilar las firmas de los firmantes.' added_fields: 'Campos añadidos' added_fields_description: 'Esta lista muestra todos los campos añadidos al documento. Puedes reordenarlos, editarlos o eliminarlos.' open_field_settings: 'Abrir configuración del campo' @@ -1568,10 +1568,10 @@ es: &es copy_and_share_link: 'Copiar y compartir enlace' copy_and_share_link_description: 'Copia este enlace para compartir el documento. Cualquiera con el enlace puede firmarlo tras ingresar su correo electrónico.' sign_the_document: 'Firmar el documento' - sign_the_document_description: 'Si eres uno de los firmantes, este botón te permite firmar el documento tú mismo.' + sign_the_document_description: 'Si eres uno de los firmantes, este botón te permite firmar el documento.' send_for_signing: 'Enviar para firma' add_recipients: 'Agregar destinatarios' - add_recipients_description: 'Agrega nuevos destinatarios para que el documento sea firmado. Puedes ingresar sus correos electrónicos o números de teléfono.' + add_recipients_description: 'Agrega nuevos destinatarios para que firmen el documento ingresando sus correos electrónicos o números de teléfono.' settings: 'Configuración' settings_account_description: 'Con una configuración completa de la cuenta, puedes personalizar la experiencia de firma y añadir más usuarios.' support: 'Soporte' @@ -2323,11 +2323,11 @@ it: &it previous: Precedente next: Successivo template_and_submissions: 'Modelli e Invii' - template_and_submissions_description: "Puoi selezionare la vista che meglio si adatta al tuo flusso di lavoro. Scegli la vista 'Modelli' se crei modelli riutilizzabili di documenti, oppure la vista 'Invii' quando firmi documenti singoli o controlli lo stato di ogni richiesta di firma." + template_and_submissions_description: "Puoi selezionare la visualizzazione più adatta al tuo flusso di lavoro. Scegli la visualizzazione 'Modelli' per creare modelli di documenti riutilizzabili o 'Invii' per firmare documenti singoli o controllare lo stato di ciascuna richiesta di firma." upload_a_pdf_file: 'Carica un file PDF' - upload_a_pdf_file_description: 'Carica un documento da utilizzare per creare un modello di modulo di firma.' + upload_a_pdf_file_description: 'Carica un documento PDF per creare un modello di modulo di firma.' select_a_signer_party: 'Seleziona una parte firmataria' - select_a_signer_party_description: 'Questo menu a discesa consente di selezionare un ruolo di firmatario o aggiungere una nuova parte al documento quando deve essere firmato da due o più parti.' + select_a_signer_party_description: 'Questo menu a discesa consente di selezionare un ruolo di firmatario o aggiungere una nuova parte al documento se richiede 2 o più firme.' available_parties: 'Parti disponibili' available_parties_description: 'Questo elenco contiene tutte le parti disponibili con i relativi ruoli. Una volta selezionata, puoi aggiungere e configurare i campi per la parte firmataria.' available_field_types: 'Tipi di campo disponibili' @@ -2335,7 +2335,7 @@ it: &it text_input_field: 'Campo di testo' text_input_field_description: 'Questo campo consente agli utenti di inserire informazioni testuali, come nomi o email.' signature_field: 'Campo firma' - signature_field_description: 'Questo campo consente di raccogliere firme dai firmatari.' + signature_field_description: 'Questo campo viene utilizzato per raccogliere le firme dei firmatari.' added_fields: 'Campi aggiunti' added_fields_description: 'Questo elenco mostra tutti i campi aggiunti al documento. Puoi riordinarli, modificarli o rimuoverli.' open_field_settings: 'Apri le impostazioni del campo' @@ -2349,10 +2349,10 @@ it: &it copy_and_share_link: 'Copia e condividi il link' copy_and_share_link_description: 'Copia questo link per condividere il documento. Chiunque abbia il link potrà firmarlo dopo aver inserito la propria email.' sign_the_document: 'Firma il documento' - sign_the_document_description: 'Se sei uno dei firmatari, questo pulsante ti consente di firmare il documento personalmente.' + sign_the_document_description: 'Se sei uno dei firmatari, questo pulsante ti consente di firmare il documento.' send_for_signing: 'Invia per la firma' add_recipients: 'Aggiungi destinatari' - add_recipients_description: 'Aggiungi nuovi destinatari per la firma del documento. Puoi inserire il loro indirizzo email o numero di telefono.' + add_recipients_description: 'Aggiungi nuovi destinatari inserendo i loro indirizzi email o numeri di telefono per far firmare il documento.' settings: 'Impostazioni' settings_account_description: "Con impostazioni complete dell'account, puoi personalizzare l'esperienza di firma elettronica e invitare altri utenti." support: 'Supporto' @@ -3056,7 +3056,7 @@ fr: &fr submission_created_via_source_html: 'Soumission créée via %{source}' pro_user_seats_used: Places utilisateur Pro en cours d'utilisation manage_plan: Gérer le plan - this_submission_has_multiple_signers_which_prevents_the_use_of_a_sharing_link_html: 'Cette soumission comporte plusieurs signataires, ce qui empêche l’utilisation d’un lien de partage, car il n’est pas clair quel signataire est responsable de quels champs. Pour résoudre ce problème, suivez ce guide pour définir les détails du signataire par défaut.' + this_submission_has_multiple_signers_which_prevents_the_use_of_a_sharing_link_html: "Cette soumission comporte plusieurs signataires, ce qui empêche l'utilisation d'un lien de partage, car il n'est pas clair quel signataire est responsable de quels champs. Pour résoudre ce problème, suivez ce guide pour définir les détails du signataire par défaut." welcome_to_docuseal: Bienvenue sur DocuSeal start_a_quick_tour_to_learn_how_to_create_an_send_your_first_document: Lancez une visite rapide pour apprendre à créer et envoyer votre premier document. start_tour: Démarrer @@ -3106,11 +3106,11 @@ fr: &fr previous: Précédent next: Suivant template_and_submissions: 'Modèles et Soumissions' - template_and_submissions_description: "Vous pouvez sélectionner la vue qui correspond le mieux à votre flux de travail. Choisissez la vue 'Modèles' si vous créez des modèles de documents réutilisables, ou la vue 'Soumissions' lorsque vous signez des documents individuels ou vérifiez l'état de chaque demande de signature." + template_and_submissions_description: "Vous pouvez sélectionner la vue qui correspond le mieux à votre flux de travail. Choisissez la vue 'Modèles' pour créer des modèles de documents réutilisables ou la vue 'Soumissions' pour signer des documents individuels ou vérifier l'état de chaque demande de signature." upload_a_pdf_file: 'Téléverser un fichier PDF' - upload_a_pdf_file_description: "Téléversez un document pour l'utiliser comme modèle de formulaire de signature." + upload_a_pdf_file_description: 'Téléversez un document PDF pour créer un modèle de formulaire de signature.' select_a_signer_party: 'Sélectionner une partie signataire' - select_a_signer_party_description: "Ce menu déroulant vous permet de sélectionner un rôle de signataire ou d'ajouter une nouvelle partie au document lorsqu'il doit être signé par deux parties ou plus." + select_a_signer_party_description: "Ce menu déroulant vous permet de sélectionner un rôle de signataire ou d'ajouter une nouvelle partie au document s'il nécessite 2 signatures ou plus." available_parties: 'Parties disponibles' available_parties_description: 'Cette liste contient toutes les parties disponibles avec leurs rôles. Une fois sélectionnée, vous pouvez ajouter et configurer les champs pour cette partie.' available_field_types: 'Types de champs disponibles' @@ -3118,7 +3118,7 @@ fr: &fr text_input_field: 'Champ de texte' text_input_field_description: 'Ce champ permet aux utilisateurs de saisir des informations textuelles telles que des noms ou des adresses e-mail.' signature_field: 'Champ de signature' - signature_field_description: 'Ce champ permet de collecter les signatures des signataires.' + signature_field_description: 'Ce champ est utilisé pour recueillir les signatures des signataires.' added_fields: 'Champs ajoutés' added_fields_description: 'Cette liste affiche tous les champs ajoutés au document. Vous pouvez les réorganiser, les modifier ou les supprimer.' open_field_settings: 'Ouvrir les paramètres du champ' @@ -3132,10 +3132,10 @@ fr: &fr copy_and_share_link: 'Copier et partager le lien' copy_and_share_link_description: 'Copiez ce lien pour partager le document. Toute personne disposant du lien pourra le signer après avoir saisi son e-mail.' sign_the_document: 'Signer le document' - sign_the_document_description: 'Si vous êtes l’un des signataires, ce bouton vous permet de signer le document vous-même.' + sign_the_document_description: "Si vous êtes l'n des signataires, ce bouton vous permet de signer le document." send_for_signing: 'Envoyer pour signature' add_recipients: 'Ajouter des destinataires' - add_recipients_description: 'Ajoutez de nouveaux destinataires pour que le document soit signé. Vous pouvez saisir leur adresse e-mail ou leur numéro de téléphone.' + add_recipients_description: "Ajoutez de nouveaux destinataires en saisissant leurs adresses e-mail ou numéros de téléphone pour faire signer le document." settings: 'Paramètres' settings_account_description: "Grâce à des paramètres de compte complets, vous pouvez personnaliser l'expérience de signature électronique et inviter d'autres utilisateurs." support: 'Assistance' @@ -3888,11 +3888,11 @@ pt: &pt previous: Anterior next: Próximo template_and_submissions: 'Modelos e Envios' - template_and_submissions_description: "Você pode selecionar a visualização que melhor se adapta ao seu fluxo de trabalho. Escolha a visualização 'Modelos' se criar modelos de documentos reutilizáveis, ou 'Envios' ao assinar documentos individuais ou revisar o status de cada solicitação de assinatura." + template_and_submissions_description: "Você pode selecionar a visualização que melhor se adapta ao seu fluxo de trabalho. Escolha a visualização 'Modelos' para criar modelos reutilizáveis de documentos ou 'Envios' para assinar documentos individuais ou verificar o status de cada solicitação de assinatura." upload_a_pdf_file: 'Enviar um arquivo PDF' - upload_a_pdf_file_description: 'Envie um documento para usá-lo como modelo de formulário de assinatura.' + upload_a_pdf_file_description: 'Envie um documento PDF para criar um modelo de formulário de assinatura.' select_a_signer_party: 'Selecionar parte assinante' - select_a_signer_party_description: 'Este menu suspenso permite selecionar um papel de assinante ou adicionar uma nova parte ao documento quando ele precisa ser assinado por duas ou mais partes.' + select_a_signer_party_description: 'Este menu suspenso permite selecionar um papel de assinante ou adicionar uma nova parte ao documento, se forem necessárias 2 ou mais assinaturas.' available_parties: 'Partes disponíveis' available_parties_description: 'Esta lista contém todas as partes disponíveis com seus respectivos papéis. Após selecionar, você poderá adicionar e configurar os campos para essa parte.' available_field_types: 'Tipos de campo disponíveis' @@ -3900,7 +3900,7 @@ pt: &pt text_input_field: 'Campo de texto' text_input_field_description: 'Este campo permite que os usuários insiram informações baseadas em texto, como nomes ou e-mails.' signature_field: 'Campo de assinatura' - signature_field_description: 'Este campo permite coletar assinaturas dos signatários.' + signature_field_description: 'Este campo é usado para coletar assinaturas dos signatários.' added_fields: 'Campos adicionados' added_fields_description: 'Esta lista exibe todos os campos adicionados ao documento. Você pode reordená-los, editá-los ou removê-los.' open_field_settings: 'Abrir configurações do campo' @@ -3917,7 +3917,7 @@ pt: &pt sign_the_document_description: 'Se você for um dos signatários, este botão permite que você assine o documento.' send_for_signing: 'Enviar para assinatura' add_recipients: 'Adicionar destinatários' - add_recipients_description: 'Adicione novos destinatários para que o documento seja assinado. Você pode inserir seus e-mails ou números de telefone.' + add_recipients_description: 'Adicione novos destinatários inserindo seus endereços de e-mail ou números de telefone para assinar o documento.' settings: 'Configurações' settings_account_description: 'Com configurações completas de conta, você pode personalizar a experiência de assinatura eletrônica e convidar mais usuários.' support: 'Suporte' @@ -4671,11 +4671,11 @@ de: &de previous: Zurück next: Weiter template_and_submissions: 'Vorlagen und Übermittlungen' - template_and_submissions_description: "Du kannst die Ansicht wählen, die am besten zu deinem Arbeitsablauf passt. Wähle die Ansicht 'Vorlagen', wenn du wiederverwendbare Dokumentenvorlagen erstellst, oder 'Übermittlungen', wenn du einzelne Dokumente unterschreibst oder den Status jeder Signaturanfrage überprüfen möchtest." + template_and_submissions_description: "Du kannst die Ansicht wählen, die am besten zu deinem Arbeitsablauf passt. Wähle die Ansicht 'Vorlagen', um wiederverwendbare Dokumentvorlagen zu erstellen, oder 'Übermittlungen', um einzelne Dokumente zu unterschreiben oder den Status jeder Signaturanfrage zu überprüfen." upload_a_pdf_file: 'PDF-Datei hochladen' - upload_a_pdf_file_description: 'Lade ein Dokument hoch, um es als Vorlage für ein Signaturformular zu verwenden.' + upload_a_pdf_file_description: 'Lade ein PDF-Dokument hoch, um eine Vorlage für ein Signaturformular zu erstellen.' select_a_signer_party: 'Signaturpartei auswählen' - select_a_signer_party_description: 'Dieses Dropdown-Menü ermöglicht es dir, eine Signaturrolle auszuwählen oder eine neue Partei zum Dokument hinzuzufügen, wenn es von zwei oder mehr Parteien unterzeichnet werden muss.' + select_a_signer_party_description: 'Dieses Dropdown-Menü ermöglicht es dir, eine Signaturrolle auszuwählen oder eine neue Partei zum Dokument hinzuzufügen, wenn es 2 oder mehr Unterschriften erfordert.' available_parties: 'Verfügbare Parteien' available_parties_description: 'Diese Liste enthält alle verfügbaren Parteien mit ihren Rollennamen. Nach der Auswahl kannst du Felder für die Partei hinzufügen und konfigurieren.' available_field_types: 'Verfügbare Feldtypen' @@ -4683,7 +4683,7 @@ de: &de text_input_field: 'Textfeld' text_input_field_description: 'Dieses Feld ermöglicht es Benutzern, textbasierte Informationen wie Namen oder E-Mails einzugeben.' signature_field: 'Signaturfeld' - signature_field_description: 'Dieses Feld dient der Erfassung von Signaturen der Unterzeichner.' + signature_field_description: 'Dieses Feld wird verwendet, um die Unterschriften der Unterzeichner zu erfassen.' added_fields: 'Hinzugefügte Felder' added_fields_description: 'Diese Liste zeigt alle dem Dokument hinzugefügten Felder. Du kannst sie neu anordnen, bearbeiten oder entfernen.' open_field_settings: 'Feld-Einstellungen öffnen' @@ -4697,10 +4697,10 @@ de: &de copy_and_share_link: 'Link kopieren und teilen' copy_and_share_link_description: 'Kopiere diesen Link, um das Dokument zu teilen. Jeder mit dem Link kann es unterschreiben, nachdem er seine E-Mail-Adresse eingegeben hat.' sign_the_document: 'Dokument unterschreiben' - sign_the_document_description: 'Wenn du einer der Unterzeichner bist, kannst du das Dokument mit diesem Button selbst unterschreiben.' + sign_the_document_description: 'Wenn du einer der Unterzeichner bist, kannst du das Dokument mit diesem Button unterschreiben.' send_for_signing: 'Zum Unterschreiben senden' add_recipients: 'Empfänger hinzufügen' - add_recipients_description: 'Füge neue Empfänger hinzu, damit das Dokument unterschrieben werden kann. Du kannst deren E-Mail-Adressen oder Telefonnummern eingeben.' + add_recipients_description: 'Füge neue Empfänger hinzu, indem du ihre E-Mail-Adressen oder Telefonnummern eingibst, damit sie das Dokument unterschreiben können.' settings: 'Einstellungen' settings_account_description: 'Mit umfangreichen Kontoeinstellungen kannst du das Signiererlebnis anpassen und weitere Benutzer einladen.' support: 'Support' From 7676db219606cb66c54d467a11e21b330f0a4dfd Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Fri, 2 May 2025 12:33:27 +0300 Subject: [PATCH 08/30] hex colors --- lib/submissions/generate_result_attachments.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/submissions/generate_result_attachments.rb b/lib/submissions/generate_result_attachments.rb index 87c04402..5414ff22 100644 --- a/lib/submissions/generate_result_attachments.rb +++ b/lib/submissions/generate_result_attachments.rb @@ -209,7 +209,7 @@ module Submissions font_size = preferences_font_size font_size ||= (([page.box.width, page.box.height].min / A4_SIZE[0].to_f) * FONT_SIZE).to_i - fill_color = field.dig('preferences', 'color').presence + fill_color = field.dig('preferences', 'color').to_s.delete_prefix('#').presence font_name = field.dig('preferences', 'font') font_variant = (field.dig('preferences', 'font_type').presence || 'none').to_sym From ff46993de68f175f3c73f983c3dd789115df9c96 Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Fri, 2 May 2025 12:54:00 +0300 Subject: [PATCH 09/30] fix spec --- spec/signing_form_helper.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/spec/signing_form_helper.rb b/spec/signing_form_helper.rb index b00d5f8b..a0b05a2a 100644 --- a/spec/signing_form_helper.rb +++ b/spec/signing_form_helper.rb @@ -47,7 +47,7 @@ module SigningFormHelper drawStep(); JS - sleep 0.5 + sleep 0.1 end def field_value(submitter, field_name) From 5f5dabd0e5a95ecb8ea212d93753c8f1864b1871 Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Fri, 2 May 2025 19:11:29 +0300 Subject: [PATCH 10/30] advanced formats --- app/views/templates/_upload_button.html.erb | 2 +- lib/docuseal.rb | 4 ++++ 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/app/views/templates/_upload_button.html.erb b/app/views/templates/_upload_button.html.erb index b2281e50..12f36df0 100644 --- a/app/views/templates/_upload_button.html.erb +++ b/app/views/templates/_upload_button.html.erb @@ -14,6 +14,6 @@ - + <% end %> diff --git a/lib/docuseal.rb b/lib/docuseal.rb index 15db4be0..3c11deda 100644 --- a/lib/docuseal.rb +++ b/lib/docuseal.rb @@ -55,6 +55,10 @@ module Docuseal ENV['MULTITENANT'] == 'true' end + def advanced_formats? + multitenant? + end + def demo? ENV['DEMO'] == 'true' end From 5b1a4ebffd66cd220eb0b4f4f5cc3b1b9db5052e Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Sat, 3 May 2025 13:59:15 +0300 Subject: [PATCH 11/30] improve log --- .../active_storage_blobs_proxy_controller.rb | 10 +++++---- .../api/submitter_email_clicks_controller.rb | 6 ++--- .../api/submitter_form_views_controller.rb | 12 +++++----- .../preview_document_page_controller.rb | 2 ++ .../submissions_download_controller.rb | 14 ++++++------ .../submit_form_download_controller.rb | 22 +++++++++---------- config/environments/production.rb | 14 ++++++++++-- 7 files changed, 47 insertions(+), 33 deletions(-) diff --git a/app/controllers/api/active_storage_blobs_proxy_controller.rb b/app/controllers/api/active_storage_blobs_proxy_controller.rb index f023f021..6f505992 100644 --- a/app/controllers/api/active_storage_blobs_proxy_controller.rb +++ b/app/controllers/api/active_storage_blobs_proxy_controller.rb @@ -21,7 +21,11 @@ module Api blob = ActiveStorage::Blob.find_by!(uuid: blob_uuid) - authorization_check!(blob) if exp.blank? + attachment = blob.attachments.take + + @record = attachment.record + + authorization_check!(attachment) if exp.blank? if request.headers['Range'].present? send_blob_byte_range_data blob, request.headers['Range'] @@ -37,9 +41,7 @@ module Api private - def authorization_check!(blob) - attachment = blob.attachments.take - + def authorization_check!(attachment) is_authorized = attachment.name.in?(%w[logo preview_images]) || (current_user && attachment.record.account.id == current_user.account_id) || (current_user && !Docuseal.multitenant? && current_user.role == 'superadmin') || diff --git a/app/controllers/api/submitter_email_clicks_controller.rb b/app/controllers/api/submitter_email_clicks_controller.rb index 87221680..cef26542 100644 --- a/app/controllers/api/submitter_email_clicks_controller.rb +++ b/app/controllers/api/submitter_email_clicks_controller.rb @@ -6,10 +6,10 @@ module Api skip_authorization_check def create - submitter = Submitter.find_by!(slug: params[:submitter_slug]) + @submitter = Submitter.find_by!(slug: params[:submitter_slug]) - if params[:t] == SubmissionEvents.build_tracking_param(submitter, 'click_email') - SubmissionEvents.create_with_tracking_data(submitter, 'click_email', request) + if params[:t] == SubmissionEvents.build_tracking_param(@submitter, 'click_email') + SubmissionEvents.create_with_tracking_data(@submitter, 'click_email', request) end render json: {} diff --git a/app/controllers/api/submitter_form_views_controller.rb b/app/controllers/api/submitter_form_views_controller.rb index 98d7f5b5..e8b52095 100644 --- a/app/controllers/api/submitter_form_views_controller.rb +++ b/app/controllers/api/submitter_form_views_controller.rb @@ -6,15 +6,15 @@ module Api skip_authorization_check def create - submitter = Submitter.find_by!(slug: params[:submitter_slug]) + @submitter = Submitter.find_by!(slug: params[:submitter_slug]) - submitter.opened_at = Time.current - submitter.save + @submitter.opened_at = Time.current + @submitter.save - SubmissionEvents.create_with_tracking_data(submitter, 'view_form', request) + SubmissionEvents.create_with_tracking_data(@submitter, 'view_form', request) - WebhookUrls.for_account_id(submitter.account_id, 'form.viewed').each do |webhook_url| - SendFormViewedWebhookRequestJob.perform_async('submitter_id' => submitter.id, + WebhookUrls.for_account_id(@submitter.account_id, 'form.viewed').each do |webhook_url| + SendFormViewedWebhookRequestJob.perform_async('submitter_id' => @submitter.id, 'webhook_url_id' => webhook_url.id) end diff --git a/app/controllers/preview_document_page_controller.rb b/app/controllers/preview_document_page_controller.rb index 5bf42138..5e59e74a 100644 --- a/app/controllers/preview_document_page_controller.rb +++ b/app/controllers/preview_document_page_controller.rb @@ -12,6 +12,8 @@ class PreviewDocumentPageController < ActionController::API return head :not_found unless attachment + @template = attachment.record + preview_image = attachment.preview_images.joins(:blob) .find_by(blob: { filename: ["#{params[:id]}.png", "#{params[:id]}.jpg"] }) diff --git a/app/controllers/submissions_download_controller.rb b/app/controllers/submissions_download_controller.rb index e4af5f49..62836650 100644 --- a/app/controllers/submissions_download_controller.rb +++ b/app/controllers/submissions_download_controller.rb @@ -8,20 +8,20 @@ class SubmissionsDownloadController < ApplicationController FILES_TTL = 5.minutes def index - submitter = Submitter.find_signed(params[:sig], purpose: :download_completed) if params[:sig].present? + @submitter = Submitter.find_signed(params[:sig], purpose: :download_completed) if params[:sig].present? signature_valid = - if submitter&.slug == params[:submitter_slug] + if @submitter&.slug == params[:submitter_slug] true else - submitter = nil + @submitter = nil end - submitter ||= Submitter.find_by!(slug: params[:submitter_slug]) + @submitter ||= Submitter.find_by!(slug: params[:submitter_slug]) - Submissions::EnsureResultGenerated.call(submitter) + Submissions::EnsureResultGenerated.call(@submitter) - last_submitter = submitter.submission.submitters.where.not(completed_at: nil).order(:completed_at).last + last_submitter = @submitter.submission.submitters.where.not(completed_at: nil).order(:completed_at).last return head :not_found unless last_submitter @@ -34,7 +34,7 @@ class SubmissionsDownloadController < ApplicationController end if params[:combined] == 'true' - url = build_combined_url(submitter) + url = build_combined_url(@submitter) if url render json: [url] diff --git a/app/controllers/submit_form_download_controller.rb b/app/controllers/submit_form_download_controller.rb index 9be5c0ac..07447940 100644 --- a/app/controllers/submit_form_download_controller.rb +++ b/app/controllers/submit_form_download_controller.rb @@ -7,25 +7,25 @@ class SubmitFormDownloadController < ApplicationController FILES_TTL = 5.minutes def index - submitter = Submitter.find_by!(slug: params[:submit_form_slug]) + @submitter = Submitter.find_by!(slug: params[:submit_form_slug]) - return redirect_to submitter_download_index_path(submitter.slug) if submitter.completed_at? + return redirect_to submitter_download_index_path(@submitter.slug) if @submitter.completed_at? - return head :unprocessable_entity if submitter.declined_at? || - submitter.submission.archived_at? || - submitter.submission.expired? || - submitter.submission.template.archived_at? + return head :unprocessable_entity if @submitter.declined_at? || + @submitter.submission.archived_at? || + @submitter.submission.expired? || + @submitter.submission.template.archived_at? - last_completed_submitter = submitter.submission.submitters - .where.not(id: submitter.id) - .where.not(completed_at: nil) - .max_by(&:completed_at) + last_completed_submitter = @submitter.submission.submitters + .where.not(id: @submitter.id) + .where.not(completed_at: nil) + .max_by(&:completed_at) attachments = if last_completed_submitter Submitters.select_attachments_for_download(last_completed_submitter) else - submitter.submission.template.schema_documents.preload(:blob) + @submitter.submission.template.schema_documents.preload(:blob) end urls = attachments.map do |attachment| diff --git a/config/environments/production.rb b/config/environments/production.rb index fee6352c..36b0bfaa 100644 --- a/config/environments/production.rb +++ b/config/environments/production.rb @@ -134,7 +134,15 @@ Rails.application.configure do {} end + resource = controller.instance_variable_get(:@submitter) || + controller.instance_variable_get(:@submission) || + controller.instance_variable_get(:@template) || + controller.instance_variable_get(:@record) + + current_user = controller.instance_variable_get(:@current_user) + { + host: controller.request.host, fwd: controller.request.remote_ip, params: { id: params[:id], @@ -148,8 +156,10 @@ Rails.application.configure do params[:submit_form_slug] || params[:template_slug]).to_s.first(5) }.compact_blank, - host: controller.request.host, - uid: controller.instance_variable_get(:@current_user).try(:id) + uid: current_user.try(:id), + aid: current_user.try(:account_id), + rid: resource.try(:id), + raid: resource.try(:account_id) } end end From 21d81e38bfad639893d6d5e54fd70a2e5c68d776 Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Tue, 6 May 2025 15:10:02 +0300 Subject: [PATCH 12/30] add email events --- app/models/submission_event.rb | 2 ++ app/views/submission_events/index.html.erb | 2 ++ config/locales/i18n.yml | 18 +++++++++++++++--- 3 files changed, 19 insertions(+), 3 deletions(-) diff --git a/app/models/submission_event.rb b/app/models/submission_event.rb index 5cf0a255..1ae47e79 100644 --- a/app/models/submission_event.rb +++ b/app/models/submission_event.rb @@ -38,6 +38,8 @@ class SubmissionEvent < ApplicationRecord enum :event_type, { send_email: 'send_email', + bounce_email: 'bounce_email', + complaint_email: 'complaint_email', send_reminder_email: 'send_reminder_email', send_sms: 'send_sms', send_2fa_sms: 'send_2fa_sms', diff --git a/app/views/submission_events/index.html.erb b/app/views/submission_events/index.html.erb index 4b318cfb..a0a2b867 100644 --- a/app/views/submission_events/index.html.erb +++ b/app/views/submission_events/index.html.erb @@ -38,6 +38,8 @@ <%= t('submission_event_names.invite_party_by_html', invited_submitter_name: [invited_submitter.name || invited_submitter.email || invited_submitter.phone, name].join(' '), submitter_name:) %> <% elsif event.event_type.include?('send_') %> <%= t("submission_event_names.#{event.event_type}_to_html", submitter_name:) %> + <% elsif event.event_type.start_with?('bounce_') || event.event_type.start_with?('complaint_') %> + <%= t("submission_event_names.#{event.event_type}_html", submitter_name:) %> <% else %> <%= t("submission_event_names.#{event.event_type}_by_html", submitter_name:) %> <% end %> diff --git a/config/locales/i18n.yml b/config/locales/i18n.yml index 91b1c298..0ceac2f8 100644 --- a/config/locales/i18n.yml +++ b/config/locales/i18n.yml @@ -725,6 +725,8 @@ en: &en link: Link submission_event_names: send_email_to_html: 'Email sent to %{submitter_name}' + bounce_email_html: 'Email bounced %{submitter_name}' + complaint_email_html: 'Spam complaint %{submitter_name}' send_reminder_email_to_html: 'Reminder email sent to %{submitter_name}' send_sms_to_html: 'SMS sent to %{submitter_name}' send_2fa_sms_to_html: 'Verification SMS sent to %{submitter_name}' @@ -1507,6 +1509,8 @@ es: &es link: Enlace submission_event_names: send_email_to_html: 'Correo electrónico enviado a %{submitter_name}' + bounce_email_html: 'Correo electrónico rebotado %{submitter_name}' + complaint_email_html: 'Queja de spam %{submitter_name}' send_reminder_email_to_html: 'Correo de recordatorio enviado a %{submitter_name}' send_sms_to_html: 'SMS enviado a %{submitter_name}' send_2fa_sms_to_html: 'SMS de verificación enviado a %{submitter_name}' @@ -2287,7 +2291,9 @@ it: &it invite: Invito link: Link submission_event_names: - send_email_to_html: 'E-mail inviato a %{submitter_name}' + send_email_to_html: 'Email inviata a %{submitter_name}' + bounce_email_html: 'Email respinta %{submitter_name}' + complaint_email_html: 'Segnalazione spam %{submitter_name}' send_reminder_email_to_html: 'E-mail di promemoria inviato a %{submitter_name}' send_sms_to_html: 'SMS inviato a %{submitter_name}' send_2fa_sms_to_html: 'SMS di verifica inviato a %{submitter_name}' @@ -3071,6 +3077,8 @@ fr: &fr link: Lien submission_event_names: send_email_to_html: 'E-mail envoyé à %{submitter_name}' + bounce_email_html: 'Email non distribué %{submitter_name}' + complaint_email_html: 'Réclamation de spam %{submitter_name}' send_reminder_email_to_html: 'E-mail de rappel envoyé à %{submitter_name}' send_sms_to_html: 'SMS envoyé à %{submitter_name}' send_2fa_sms_to_html: 'SMS de vérification envoyé à %{submitter_name}' @@ -3852,8 +3860,10 @@ pt: &pt invite: Convite link: Link submission_event_names: - send_email_to_html: 'E-mail enviado para %{submitter_name}' - send_reminder_email_to_html: 'E-mail de lembrete enviado para %{submitter_name}' + send_email_to_html: 'Email enviado para %{submitter_name}' + bounce_email_html: 'Email não entregue %{submitter_name}' + complaint_email_html: 'Reclamação de spam %{submitter_name}' + send_reminder_email_to_html: 'Email de lembrete enviado para %{submitter_name}' send_sms_to_html: 'SMS enviado para %{submitter_name}' send_2fa_sms_to_html: 'SMS de verificação enviado para %{submitter_name}' open_email_by_html: 'E-mail aberto por %{submitter_name}' @@ -4636,6 +4646,8 @@ de: &de link: Link submission_event_names: send_email_to_html: 'E-Mail gesendet an %{submitter_name}' + bounce_email_html: 'E-Mail zurückgesendet %{submitter_name}' + complaint_email_html: 'Spam-Beschwerde %{submitter_name}' send_reminder_email_to_html: 'Erinnerungs-E-Mail gesendet an %{submitter_name}' send_sms_to_html: 'SMS gesendet an %{submitter_name}' send_2fa_sms_to_html: 'Verifizierungs-SMS gesendet an %{submitter_name}' From c5a5212947d7cb013ae506852522465998be2e5b Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Tue, 6 May 2025 15:50:58 +0300 Subject: [PATCH 13/30] disable archived template actions --- app/views/templates/show.html.erb | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/app/views/templates/show.html.erb b/app/views/templates/show.html.erb index f6696969..083feab6 100644 --- a/app/views/templates/show.html.erb +++ b/app/views/templates/show.html.erb @@ -61,7 +61,9 @@
<%= render 'submissions_filters/applied_filters', filter_params: %> <%= render 'submissions_filters/filter_button', filter_params: %> - <%= render 'submissions_filters/actions', filter_params: filter_params.merge(template_id: @template.id) %> + <% unless @template.archived_at? %> + <%= render 'submissions_filters/actions', filter_params: filter_params.merge(template_id: @template.id) %> + <% end %>
<% end %> From 330fae927f9b1b5837c99f4166e6c5f527f27417 Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Tue, 6 May 2025 16:46:08 +0300 Subject: [PATCH 14/30] skip bounce from audit --- lib/submissions/generate_audit_trail.rb | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/lib/submissions/generate_audit_trail.rb b/lib/submissions/generate_audit_trail.rb index e1febb51..ecfe9b84 100644 --- a/lib/submissions/generate_audit_trail.rb +++ b/lib/submissions/generate_audit_trail.rb @@ -379,7 +379,9 @@ module Submissions composer.text(I18n.t('event_log'), font_size: 12, padding: [10, 0, 20, 0]) - events_data = submission.submission_events.sort_by(&:event_timestamp).map do |event| + events_data = submission.submission_events.sort_by(&:event_timestamp).filter_map do |event| + next if event.event_type.in?(%w[bounce_email complaint_email]) + submitter = submission.submitters.find { |e| e.id == event.submitter_id } submitter_name = if event.event_type.include?('sms') || event.event_type.include?('phone') From 19e88358094eb3ee60065fe334241824fe04cd8e Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Tue, 6 May 2025 18:44:29 +0300 Subject: [PATCH 15/30] fix timestamp path --- lib/submissions/timestamp_handler.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/submissions/timestamp_handler.rb b/lib/submissions/timestamp_handler.rb index 1daab423..a152a97f 100644 --- a/lib/submissions/timestamp_handler.rb +++ b/lib/submissions/timestamp_handler.rb @@ -35,7 +35,7 @@ module Submissions c.basic_auth(uri.user, uri.password) if uri.password.present? end - response = conn.post(uri.path, build_payload(digest.digest), + response = conn.post(uri.request_uri, build_payload(digest.digest), 'content-type' => 'application/timestamp-query') if response.status != 200 || response.body.blank? From 5663e60f9230ab6b8a49bae3ab7d63b4505836da Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Tue, 6 May 2025 22:18:53 +0300 Subject: [PATCH 16/30] fix log --- app/controllers/start_form_controller.rb | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/app/controllers/start_form_controller.rb b/app/controllers/start_form_controller.rb index 90c32bde..35e0fbcc 100644 --- a/app/controllers/start_form_controller.rb +++ b/app/controllers/start_form_controller.rb @@ -14,7 +14,8 @@ class StartFormController < ApplicationController raise ActionController::RoutingError, I18n.t('not_found') if @template.preferences['require_phone_2fa'] == true @submitter = @template.submissions.new(account_id: @template.account_id) - .submitters.new(uuid: (filter_undefined_submitters(@template).first || + .submitters.new(account_id: @template.account_id, + uuid: (filter_undefined_submitters(@template).first || @template.submitters.first)['uuid']) end From b4a68cf79eea3f34ad65091767501beb86fded63 Mon Sep 17 00:00:00 2001 From: Pete Matsyburka Date: Thu, 8 May 2025 12:22:18 +0300 Subject: [PATCH 17/30] adjust field types prop --- app/javascript/template_builder/field_type.vue | 2 +- app/javascript/template_builder/fields.vue | 2 +- app/javascript/template_builder/mobile_fields.vue | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/app/javascript/template_builder/field_type.vue b/app/javascript/template_builder/field_type.vue index aab46ccf..df0bd488 100644 --- a/app/javascript/template_builder/field_type.vue +++ b/app/javascript/template_builder/field_type.vue @@ -30,7 +30,7 @@ v-for="(icon, type) in fieldIconsSorted" :key="type" > -
  • +