Skip to content

Commit

Permalink
ui/ux(admin): Improve description for BlueprintEdit view. Add reusabl…
Browse files Browse the repository at this point in the history
…e info-collapsible component.
  • Loading branch information
Nico-AP committed Jul 17, 2024
1 parent 776b384 commit 0745f6c
Show file tree
Hide file tree
Showing 6 changed files with 204 additions and 47 deletions.
53 changes: 52 additions & 1 deletion ddm/static/ddm/css/research-interface-base.css
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,10 @@
align-items: center;
}

.fs-08 {
font-size: 0.8rem !important;
}

.ddm-nav-icon {
color: #1a1a1a !important;
font-size: 1.5rem;
Expand Down Expand Up @@ -168,7 +172,6 @@
.ddm-admin-section-body {
padding: 20px;
border-radius: 0 0 5px 5px;
background: #fbfbfb;
}
.ddm-admin-section-body tbody {
border-top: none !important;
Expand Down Expand Up @@ -391,4 +394,52 @@
}
.version-info {
color: lightgray;
}

.ddm-info-accordion {
border-left: 2px solid black;
border-right: 2px solid black;
margin: 15px 10PX 25px 10px;
}

.ddm-info-accordion-header {
background: #f2f2f2;
}

.ddm-info-accordion-button {
padding: 5px 15px;
background: none;
border: none;
width: 100%;
text-align: left;
}

.ddm-info-accordion-button:after {
content: "\F229";
font-family: "bootstrap-icons";
display: inline-block;
float: right;
transition-duration: .35s;
}

.ddm-info-accordion-button:not(.collapsed):after {
content: "\F229";
font-family: "bootstrap-icons";
display: inline-block;
transform: rotate(-180deg);
transition-duration: .35s;
float: right;
}

.ddm-info-accordion-body {
padding: 15px 21px;
border-bottom: 1px solid lightgrey;
}

.ddm-info-accordion-body ol {
line-height: 1.5rem;
}

.ddm-info-accordion-body li {
padding-left: 5px;
}
22 changes: 14 additions & 8 deletions ddm/static/ddm/js/processing-rule-modal.js
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
hideOrShowReplacementAndComparisonValue = function( id ) {
hideOrShowReplacementAndComparisonValue = function (id) {
let replacementInput = $("#id_processingrule_set-" + id + "-replacement_value");
let comparisonValue = $("#id_processingrule_set-" + id + "-comparison_value");

let val = $("[id$=" + id + "-comparison_operator]").val();

if (val.indexOf("regex-replace-match") >= 0 ) {
if (val.indexOf("regex-replace-match") >= 0) {
replacementInput.parent().show();
comparisonValue.parent().show();
} else if (val === "") {
Expand All @@ -14,21 +14,27 @@ hideOrShowReplacementAndComparisonValue = function( id ) {
replacementInput.parent().hide();
comparisonValue.parent().show();
}

if (val.indexOf("regex") >= 0) {
$('label[for="id_processingrule_set-' + id + '-comparison_value"]').text("Regular expression (regex):");
} else {
$('label[for="id_processingrule_set-' + id + '-comparison_value"]').text("Comparison value:");
}
}

$( "body" ).on("change", "select[id$='-comparison_operator']", function() {
$("body").on("change", "select[id$='-comparison_operator']", function () {
const current_id = $(this).attr("id").match(/\d+/)[0];
hideOrShowReplacementAndComparisonValue(current_id);
});

$(document).ready(function() {
$(document).ready(function () {
let IDs = new Set();
$("[id$=-comparison_operator]").each(function() {
if( /\d+/.test($( this ).attr("id")) ) {
IDs.add($( this ).attr("id").match(/\d+/)[0]);
$("[id$=-comparison_operator]").each(function () {
if (/\d+/.test($(this).attr("id"))) {
IDs.add($(this).attr("id").match(/\d+/)[0]);
}
});
for ( const id of IDs ) {
for (const id of IDs) {
hideOrShowReplacementAndComparisonValue(id);
}
});
19 changes: 19 additions & 0 deletions ddm/templates/ddm/admin/components/info_collapsible.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
<div class="ddm-info-accordion">

<div class="ddm-info-accordion-header" id="info-collapsible-heading-{{ element_id }}">
<button class="ddm-info-accordion-button collapsed" type="button" data-bs-toggle="collapse" data-bs-target="#info-collapsible-{{ element_id }}" aria-expanded="false" aria-controls="info-collapsible-{{ element_id }}">
<i class="bi bi-info-circle"></i>&nbsp;&nbsp;{{ title }}
</button>
</div>

<div id="info-collapsible-{{ element_id }}" class="accordion-collapse collapse" aria-labelledby="info-collapsible-heading-{{ element_id }}">
<div class="ddm-info-accordion-body">
{% if include_path != "" %}
{% include include_path %}
{% else %}
{{ body|safe }}
{% endif %}
</div>
</div>

</div>
Original file line number Diff line number Diff line change
@@ -1,15 +1,90 @@
<h5 class="pt-4"><b>Data Extraction</b></h5>
<ul>
<li>The data extraction follows <i>extraction rules</i> which can be configured below. These rules are applied
consecutively in the defined order.
<p class="mt-0">
If a file has been successfully validated, the relevant information will be extracted according to <code>extraction rules</code> which can be configured below.
These rules are applied to the uploaded data consecutively in the defined order. If no rules are configured, no data are extracted.
All the data extraction steps are executed on the participant's device in the browser using JavaScript.
</p>

<p>To configure the data extraction, follow these steps:</p>

<ol class="mb-2 mt-2">
<li>
For every field that you want to keep in the uploaded data, create an <code>extraction rule</code> with the "Keep field" operator.
</li>
<li><b>Keep data:</b> For every field/column/variable that you want to
keep in the donated data, you first have to define an extraction rule with the "Keep field" operator.
<li>
Next, you can add rules to filter (i.e., delete) or alter entries in the uploaded data. For this, several comparison and regex operations are available (see below for an overview).
</li>
<li><b>Filter and alter data:</b> Next, you can add rules to filter (i.e., delete) or alter entries in the
uploaded data
(e.g., to delete all entries where the date is < 01.01.2020, or to replace
e-mail-addresses with "ANONYMIZED EMAIL"). For this, there are several comparison and regex operations
available.
</li>
</ul>
</ol>

<p>When a file is uploaded, the configured rules are applied row-wise/entry-wise. This means, for every data row/entry in the uploaded data, the rules are applied in the configured order.</p>

<p><b>Available extraction operators</b></p>

<table id="inlineform-table" class="table table-borderless fs-08">
<tr class="border-bottom">
<th>Extraction Operator</th>
<th>Description</th>
<th>Note</th>
</tr>
<tr>
<td>Keep Field</td>
<td>Keep this field in the uploaded data.</td>
<td></td>
</tr>
<tr>
<td>Equal (==)</td>
<td>Delete row/entry if the value contained in the given <code>field</code> equals the <code>comparison value</code>.</td>
<td>Works for strings, integers, and dates<sup>1</sup>.</td>
</tr>
<tr>
<td>Not Equal !=</td>
<td>Delete row/entry if the value contained in the given <code>field</code> does not equal the <code>comparison value</code>.</td>
<td>Works for strings, integers, and dates<sup>1</sup>.</td>
</tr>
<tr>
<td>Greater than (>)</td>
<td>Delete row/entry if the value contained in the given <code>field</code> is greater than the <code>comparison value</code>.</td>
<td>Works for integers and dates<sup>1</sup>. String values are skipped and the row will be kept in the data.</td>
</tr>
<tr>
<td>Smaller than (<)</td>
<td>Delete row/entry if the value contained in the given <code>field</code> is smaller than the <code>comparison value</code>.</td>
<td>Works for integers and dates<sup>1</sup>. String values are skipped and the row will be kept in the data.</td>
</tr>
<tr>
<td>Greater than or equal (>=)</td>
<td>Delete row/entry if the value contained in the given <code>field</code> is greater than or equal to the <code>comparison value</code>.</td>
<td>Works for integers and dates<sup>1</sup>. String values are skipped and the row will be kept in the data.</td>
</tr>
<tr>
<td>Smaller than or equal (<=)</td>
<td>Delete row/entry if the value contained in the given <code>field</code> is smaller than or equal to the <code>comparison value</code>.</td>
<td>Works for integers and dates<sup>1</sup>. String values are skipped and the row will be kept in the data.</td>
</tr>
<tr>
<td>Delete match (regex)</td>
<td>Delete parts of the value contained in the given <code>field</code> that match the given <code>regular expression (regex)</code>
(e.g., if the <code>regular expression (regex)</code> = "^Watched " and a field contains the value "Watched video XY" the following
value will be kept in the uploaded data: "video XY").</td>
<td>All field values are converted to strings before this operation is applied.</td>
</tr>
<tr>
<td>Replace match (regex)</td>
<td>Replace parts of the value contained in the given <code>field</code> that match the given <code>regular expression (regex)</code>
(e.g., if the <code>regular expression (regex)</code> = "[\w-\.]+@([\w-]+\.)+[\w-]{2,4}" and
the <code>replacement value</code> = "_anonymized_" and a field contains the value "some text email@address.com" the following
value will be kept in the uploaded data: "some text _anonymized_").</td>
<td>All field values are converted to strings before this operation is applied.</td>
</tr>
<tr>
<td>Delete row when match (regex)</td>
<td>Delete row/entry if the value contained in the given <code>field</code> matches the given <code>regular expression (regex)</code> (e.g., if
<code>regular expression (regex)</code> = "^Watched " and a field contains the value "Watched video XY"
the row/entry will be deleted from the uploaded data).</td>
<td>All field values are converted to strings before this operation is applied.</td>
</tr>
</table>

<p style="font-size: 0.75rem; color: grey;">
<sup>1</sup>Dates are inferred from string values if they are formatted according to ISO, RFC2822, or HTTP standards,
and only if both the field value and the comparison value follow the same format. Otherwise, the entry will be treated as a regular string.
</p>
Original file line number Diff line number Diff line change
@@ -1,17 +1,11 @@
<div class="ddm-admin-form pt-5">
<h4>Data Extraction Settings</h4>

<p>Data Extraction is a two-step process consisting of first the <b>file validation</b> and second the <b>data extraction</b>.</p>

<h5><b>File Validation</b></h5>
<ul>
<li>First, it is checked whether the expected file is included in the uploaded data (only applies to ZIP uploads).
If the associated File Uploader expects a ZIP Upload, the correct file is identified
using the provided <code>file path</code> (this is skipped for single file uploads).</li>
<li>Second, it is checked whether the uploaded file is in the <code>expected file format</code>.</li>
<li>Third, it is checked whether the identified file contains <b>all</b> <code>expected fields</code>.</li>
<li>
If any of these validation steps fail, the participant will be shown an
exception message explaining what went wrong and no data is extracted.</li>
</ul>
</div>
<p class="mt-0">
When a file is uploaded, it is first validated following these steps:
</p>
<ol class="mb-2 mt-2">
<li><span class="fs-08">[Only applies to ZIP uploads]</span> It is checked whether the uploaded ZIP container contains the expected file as specified in the <code>file path</code> setting.</li>
<li>It is checked whether the uploaded file is in the <code>expected file format</code>.</li>
<li>It is checked whether the identified file contains <i>all</i> <code>expected fields</code>.</li>
</ol>
<p class="mt-0">
If any of these validation steps fail, no data is extracted and an exception message explaining what went wrong will be shown to the participant.
</p>
28 changes: 20 additions & 8 deletions ddm/templates/ddm/admin/data_donation/donation_blueprint/edit.html
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@
{{ form.non_field_errors }}

<div class="ddm-admin-form">
<h5>General Settings</h5>

{% for field in form %}
{% if field.name not in "expected_fields,expected_fields_regex_matching,regex_path,exp_file_format,csv_delimiter,json_extraction_root" %}
<p>
Expand All @@ -25,9 +27,13 @@
{% endfor %}
</div>

{% include "ddm/admin/data_donation/donation_blueprint/block_file_validation.html" %}
<hr class="mt-5 mb-5">

<div class="ddm-admin-form">
<h5>File Validation Settings</h5>

{% include "ddm/admin/components/info_collapsible.html" with element_id="filevalidation" title="How the file validation works" include_path="ddm/admin/data_donation/donation_blueprint/block_file_validation.html" body="" %}

{% for field in form %}
{% if field.name in "expected_fields,expected_fields_regex_matching,regex_path,exp_file_format,csv_delimiter,json_extraction_root" %}
<p>
Expand All @@ -40,12 +46,16 @@
{% endfor %}
</div>

{% include "ddm/admin/data_donation/donation_blueprint/block_data_extraction.html" %}
<hr class="mt-5 mb-5">

{{ formset.management_form }}
<div class="ddm-admin-form">
<h6>Extraction Rules</h6>
<table id="inlineform-table" class="table table-borderless">
<h5>Data Extraction Settings</h5>
{% include "ddm/admin/components/info_collapsible.html" with element_id="dataextraction" title="How the data extraction works" include_path="ddm/admin/data_donation/donation_blueprint/block_data_extraction.html" body="" %}

{{ formset.management_form }}

<b>Extraction Rules</b>
<table id="inlineform-table" class="table table-borderless fs-08">
<tr class="border-bottom">
<th>Order</th>
<th>Rule name</th>
Expand Down Expand Up @@ -138,8 +148,8 @@ <h6>Extraction Rules</h6>
{% for field in formset.empty_form %}
{% if field.name in 'name,field,regex_field,execution_order,input_type,comparison_operator,comparison_value,replacement_value' %}
<p {% if field.name in 'replacement_value,comparison_value' %}style="display: none"{% endif %}>
{{ field.label }}
<span class="helptext"><br>{{ field.help_text }}</span>
{{ field.label_tag }}
<span class="helptext">{{ field.help_text }}</span>
{{ field }}
{{ field.errors }}
<span class="form-error" style="display: none; color: red;">Please provide a value for this field.</span>
Expand All @@ -149,7 +159,9 @@ <h6>Extraction Rules</h6>
</div>
</div>

<input class="ddm-btn" type="submit" value="Save Blueprint">
<hr class="mt-5 mb-5">

<input class="ddm-btn mt-3" type="submit" value="Save Blueprint">
<p class="mt-3">
<a href="{% url 'data-donation-overview' project.pk %}">&#129040; Back</a>
</p>
Expand Down

0 comments on commit 0745f6c

Please sign in to comment.