From fed3d4c11e211d656e701b5e7724b9f56656bc5f Mon Sep 17 00:00:00 2001 From: Ferdinand Thiessen Date: Wed, 28 Jun 2023 03:24:39 +0200 Subject: [PATCH] feat: Implement custom submission message This message is shown when a user submits the form and can be formatted using markdown. Make the custom submission message hidden behind a checkbox Null on submissionMessage means disabled Co-authored-by: Chartman123 Signed-off-by: Ferdinand Thiessen --- docs/API.md | 1 + docs/DataStructure.md | 27 ++--- lib/Constants.php | 1 + lib/Controller/ApiController.php | 6 +- lib/Db/Form.php | 6 +- .../Version030400Date20230628011500.php | 61 ++++++++++++ .../SidebarTabs/SettingsSidebarTab.vue | 98 +++++++++++++++++++ src/scssmixins/markdownOutput.scss | 7 +- src/views/Submit.vue | 22 ++++- tests/Integration/Api/ApiV2Test.php | 5 + tests/Unit/Controller/ApiControllerTest.php | 3 +- tests/Unit/FormsMigratorTest.php | 3 +- tests/Unit/Service/FormsServiceTest.php | 4 +- 13 files changed, 223 insertions(+), 21 deletions(-) create mode 100644 lib/Migration/Version030400Date20230628011500.php diff --git a/docs/API.md b/docs/API.md index 9473fe12e..833e2d6b7 100644 --- a/docs/API.md +++ b/docs/API.md @@ -120,6 +120,7 @@ Returns the full-depth object of the requested form (without submissions). "title": "Form 1", "description": "Description Text", "ownerId": "jonas", + "submissionMessage": "Thank **you** for submitting the form." "created": 1611240961, "access": { "permitAllUsers": false, diff --git a/docs/DataStructure.md b/docs/DataStructure.md index d04740759..68f33d7dc 100644 --- a/docs/DataStructure.md +++ b/docs/DataStructure.md @@ -1,24 +1,25 @@ # Forms Data Structure -**State: Forms v3.0.0 - 23.03.2022** +**State: Forms v3.3.1 - 08.10.2023** This document describes the Object-Structure, that is used within the Forms App and on Forms API v2. It does partially **not** equal the actual database structure behind. ## Data Structures ### Form -| Property | Type | Restrictions | Description | -|-------------|-----------------|--------------|-------------| -| id | Integer | unique | An instance-wide unique id of the form | -| hash | 16-char String | unique | An instance-wide unique hash | -| title | String | max. 256 ch. | The form title | +| Property | Type | Restrictions | Description | +|-------------|-----------------|---------------|-------------| +| id | Integer | unique | An instance-wide unique id of the form | +| hash | 16-char String | unique | An instance-wide unique hash | +| title | String | max. 256 ch. | The form title | | description | String | max. 8192 ch. | The Form description | -| ownerId | String | | The nextcloud userId of the form owner | -| created | unix timestamp | | When the form has been created | +| ownerId | String | | The nextcloud userId of the form owner | +| submissionMessage | String | max. 2048 ch. | Optional custom message, with Markdown support, to be shown to users when the form is submitted (default is used if set to null) | +| created | unix timestamp | | When the form has been created | | access | [Access-Object](#access-object) | | Describing access-settings of the form | -| expires | unix-timestamp | | When the form should expire. Timestamp `0` indicates _never_ | -| isAnonymous | Boolean | | If Answers will be stored anonymously | -| submitMultiple | Boolean | | If users are allowed to submit multiple times to the form | -| showExpiration | Boolean | | If the expiration date will be shown on the form | -| canSubmit | Boolean | | If the user can Submit to the form, i.e. calculated information out of `submitMultiple` and existing submissions. | +| expires | unix-timestamp | | When the form should expire. Timestamp `0` indicates _never_ | +| isAnonymous | Boolean | | If Answers will be stored anonymously | +| submitMultiple | Boolean | | If users are allowed to submit multiple times to the form | +| showExpiration | Boolean | | If the expiration date will be shown on the form | +| canSubmit | Boolean | | If the user can Submit to the form, i.e. calculated information out of `submitMultiple` and existing submissions. | | permissions | Array of [Permissions](#permissions) | Array of permissions regarding the form | | questions | Array of [Questions](#question) | | Array of questions belonging to the form | | shares | Array of [Shares](#share) | | Array of shares of the form | diff --git a/lib/Constants.php b/lib/Constants.php index 639d10b31..fb2b72d2b 100644 --- a/lib/Constants.php +++ b/lib/Constants.php @@ -46,6 +46,7 @@ class Constants { public const MAX_STRING_LENGTHS = [ 'formTitle' => 256, 'formDescription' => 8192, + 'submissionMessage' => 2048, 'questionText' => 2048, 'questionDescription' => 4096, 'optionText' => 1024, diff --git a/lib/Controller/ApiController.php b/lib/Controller/ApiController.php index ae0de7564..61238a08d 100644 --- a/lib/Controller/ApiController.php +++ b/lib/Controller/ApiController.php @@ -339,8 +339,10 @@ public function updateForm(int $id, array $keyValuePairs): DataResponse { } // Create FormEntity with given Params & Id. - $form = Form::fromParams($keyValuePairs); - $form->setId($id); + foreach ($keyValuePairs as $key => $value) { + $method = 'set' . ucfirst($key); + $form->$method($value); + } // Update changed Columns in Db. $this->formMapper->update($form); diff --git a/lib/Db/Form.php b/lib/Db/Form.php index 3f0b7d0af..14e4d5803 100644 --- a/lib/Db/Form.php +++ b/lib/Db/Form.php @@ -52,6 +52,8 @@ * @method void setShowExpiration(bool $value) * @method integer getLastUpdated() * @method void setLastUpdated(integer $value) + * @method ?string getSubmissionMessage() + * @method void setSubmissionMessage(?string $value) */ class Form extends Entity { protected $hash; @@ -64,6 +66,7 @@ class Form extends Entity { protected $isAnonymous; protected $submitMultiple; protected $showExpiration; + protected $submissionMessage; protected $lastUpdated; /** @@ -102,7 +105,8 @@ public function read() { 'isAnonymous' => (bool)$this->getIsAnonymous(), 'submitMultiple' => (bool)$this->getSubmitMultiple(), 'showExpiration' => (bool)$this->getShowExpiration(), - 'lastUpdated' => (int)$this->getLastUpdated() + 'lastUpdated' => (int)$this->getLastUpdated(), + 'submissionMessage' => $this->getSubmissionMessage(), ]; } } diff --git a/lib/Migration/Version030400Date20230628011500.php b/lib/Migration/Version030400Date20230628011500.php new file mode 100644 index 000000000..4e24be632 --- /dev/null +++ b/lib/Migration/Version030400Date20230628011500.php @@ -0,0 +1,61 @@ + + * + * @author Ferdinand Thiessen + * + * @license GNU AGPL version 3 or any later version + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as + * published by the Free Software Foundation, either version 3 of the + * License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see . + * + */ + +namespace OCA\Forms\Migration; + +use Closure; +use OCP\DB\ISchemaWrapper; +use OCP\DB\Types; +use OCP\Migration\IOutput; +use OCP\Migration\SimpleMigrationStep; + +class Version030400Date20230628011500 extends SimpleMigrationStep { + + /** + * @param IOutput $output + * @param Closure $schemaClosure The `\Closure` returns a `ISchemaWrapper` + * @param array $options + * @return null|ISchemaWrapper + */ + public function changeSchema(IOutput $output, Closure $schemaClosure, array $options): ?ISchemaWrapper { + /** @var ISchemaWrapper $schema */ + $schema = $schemaClosure(); + $table = $schema->getTable('forms_v2_forms'); + + if (!$table->hasColumn('submission_message')) { + $table->addColumn('submission_message', Types::STRING, [ + 'notnull' => false, + 'default' => null, + 'length' => 2048, + 'comment' => 'custom thank you message', + ]); + + return $schema; + } + + return null; + } +} diff --git a/src/components/SidebarTabs/SettingsSidebarTab.vue b/src/components/SidebarTabs/SettingsSidebarTab.vue index e3a6f95ba..e34126aba 100644 --- a/src/components/SidebarTabs/SettingsSidebarTab.vue +++ b/src/components/SidebarTabs/SettingsSidebarTab.vue @@ -59,6 +59,35 @@ {{ t('forms', 'Show expiration date on form') }} + + {{ t('forms', 'Custom submission message') }} + +
+