django-helpdeskmig/helpdesk/templates/helpdesk/ticket.html
2024-02-05 11:34:56 +01:00

327 lines
18 KiB
HTML

{% extends "helpdesk/base.html" %}
{% load i18n bootstrap4form humanize %}
{% load static %}
{% block helpdesk_title %}{{ ticket.queue.slug }}-{{ ticket.id }} : {% trans "View Ticket Details" %}{% endblock %}
{% block h1_title %}{{ ticket.ticket_for_url }}{% endblock %}
{% block helpdesk_breadcrumb %}
<li class="breadcrumb-item">
<a href="{% url 'helpdesk:list' %}">{% trans "Tickets" %}</a>
</li>
<li class="breadcrumb-item active">
{{ ticket.queue.slug }}-{{ ticket.id }}
</li>
{% endblock %}
{% block helpdesk_body %}
{% if helpdesk_settings.HELPDESK_TRANSLATE_TICKET_COMMENTS %}
<div id="google_translate_element"></div>
<script src="//translate.google.com/translate_a/element.js?cb=googleTranslateElementInit"></script>
{% endif %}
{% include "helpdesk/ticket_desc_table.html" %}
{% if ticket.merged_to %}
<div class="card card-body bg-light">
<h3 class="text-center">
{% trans "This ticket has been merged into ticket" %}
<a href="{{ ticket.merged_to.get_absolute_url }}">{{ ticket.merged_to }}</a>
</h3>
</div>
{% else %}
{% if ticket.followup_set.all %}
{% load ticket_to_link %}
<div class="card mb-3">
<div class="card-header"><i class="fas fa-clock fa-fw fa-lg"></i>&nbsp;{% trans "Follow-Ups" %}</div>
<div class="card-body">
<div class="list-group">
{% for followup in ticket.followup_set.all %}
<div class="list-group-item list-group-item-action">
<div class="d-flex w-100 justify-content-between">
<h5 class="mb-1">{{ followup.title|num_to_link }}</h5>
<small><i class="fas fa-clock"></i>&nbsp;<span class='byline text-info'>{% if followup.user %}by {{ followup.user }},{% endif %} <span title='{{ followup.date|date:"DATETIME_FORMAT" }}'>{{ followup.date|naturaltime }}</span>{% if helpdesk_settings.HELPDESK_ENABLE_TIME_SPENT_ON_TICKET %}{% if followup.time_spent %}{% endif %}, <span>{% trans "time spent" %}: {{ followup.time_spent_formated }}</span>{% endif %} {% if not followup.public %} <span class='private'>({% trans "Private" %})</span>{% endif %}</span></small>
</div>
<p class="mb-1">
{% if followup.comment %}
<p>{{ followup.get_markdown|urlizetrunc:50|num_to_link }}</p>
{% endif %}
{% for change in followup.ticketchange_set.all %}
{% if forloop.first %}<div class='changes'><ul>{% endif %}
<li>{% blocktrans with change.field as field and change.old_value as old_value and change.new_value as new_value %}Changed {{ field }} from {{ old_value }} to {{ new_value }}.{% endblocktrans %}</li>
{% if forloop.last %}</ul></div>{% endif %}
{% endfor %}
{% for attachment in followup.followupattachment_set.all %}{% if forloop.first %}{% trans "Attachments" %}:<div class='attachments'><ul>{% endif %}
<li><a href='{{ attachment.file.url }}'>{{ attachment.filename }}</a> ({{ attachment.mime_type }}, {{ attachment.size|filesizeformat }})
{% if followup.user and request.user == followup.user %}
<a href='{% url 'helpdesk:attachment_del' ticket.id attachment.id %}'><button class="btn btn-danger btn-sm"><i class="fas fa-trash"></i></button></a>
{% endif %}
</li>
{% if forloop.last %}</ul></div>{% endif %}
{% endfor %}
</p>
<!--- ugly long test to suppress the following if it will be empty, to save vertical space -->
{% with possible=helpdesk_settings.HELPDESK_SHOW_EDIT_BUTTON_FOLLOW_UP %}
{% if possible and followup.user and request.user == followup.user and not followup.ticketchange_set.all or possible and user.is_superuser and helpdesk_settings.HELPDESK_SHOW_DELETE_BUTTON_SUPERUSER_FOLLOW_UP %}
<small>
{% if helpdesk_settings.HELPDESK_SHOW_EDIT_BUTTON_FOLLOW_UP %}
{% if followup.user and request.user == followup.user and not followup.ticketchange_set.all %}
<a href="{% url 'helpdesk:followup_edit' ticket.id followup.id %}" class='followup-edit'><button type="button" class="btn btn-warning btn-sm float-right"><i class="fas fa-edit"></i></button></a>
{% endif %}
{% endif %}
{% if user.is_superuser and helpdesk_settings.HELPDESK_SHOW_DELETE_BUTTON_SUPERUSER_FOLLOW_UP %}
<a href="{% url 'helpdesk:followup_delete' ticket.id followup.id %}" class='followup-edit'><button type="button" class="btn btn-warning btn-sm float-right"><i class="fas fa-trash"></i></button></a>
{% endif %}
</small>
{% endif %}{% endwith %}
</div>
<!-- /.list-group-item -->
{% endfor %}
</div>
<!-- /.list-group -->
</div>
<!-- /.card-body -->
</div>
<!-- /.card -->
{% endif %}
<div class="card mb-3">
<div class="card-header">{% trans "Respond to this ticket" %}</div>
<div class="card-body">
<form method='post' action='update/' enctype='multipart/form-data'>
<fieldset>
<dl>
{% if preset_replies %}
<dt><label for='id_preset'>{% trans "Use a Pre-set Reply" %}</label> <span class='form_optional'>{% trans "(Optional)" %}</span></dt>
<dd><select name='preset' id='id_preset'><option value=''>------</option>{% for preset in preset_replies %}<option value='{{ preset.id }}'>{{ preset.name }}</option>{% endfor %}</select></dd>
<dd class='form_help_text'>{% trans "Selecting a pre-set reply will over-write your comment below. You can then modify the pre-set reply to your liking before saving this update." %}</dd>
{% endif %}
<dt><label for='commentBox'>{% trans "Comment / Resolution" %}</label></dt>
<dd><textarea rows='8' cols='70' name='comment' id='commentBox'></textarea></dd>
<dd class='form_help_text'>{% trans "You can insert ticket and queue details in your message. For more information, see the <a href='../../help/context/'>context help page</a>." %}</dd>
<dt><label>{% trans "New Status" %}</label></dt>
{% if not ticket.can_be_resolved %}<dd>{% trans "This ticket cannot be resolved or closed until the tickets it depends on are resolved." %}</dd>{% endif %}
<dd><div class="form-group">
{% for status_choice in ticket.get_allowed_status_flow %}
<label for='st_{{ status_choice.1|lower }}' class='{% if ticket.status == status_choice.0 %}active {% endif %}radio-inline'><input type='radio' name='new_status' value='{{ status_choice.0 }}' id='st_{{ status_choice.1|lower }}'{% if not ticket.can_be_resolved %} disabled='disabled'{% endif %}{% if ticket.status == status_choice.0 %} checked='checked'{% endif %}>{{ status_choice.1 }}{% if forloop.last %}{% else %} &raquo;{% endif %}</label>
{% endfor %}
</div></dd>
{% if helpdesk_settings.HELPDESK_UPDATE_PUBLIC_DEFAULT %}
<input type='hidden' name='public' value='1'>
{% else %}
<dt>
<label for='id_public'>{% trans "Is this update public?" %}</label> <span class='form_optional'>{% trans "(Optional)" %}</span>
</dt>
<dd><input type='checkbox' name='public' value='1' checked='checked' />&nbsp; {% trans 'Yes, make this update public.' %}</dd>
<dd class='form_help_text'>{% trans "If this is public, the submitter will be e-mailed your comment or resolution." %}</dd>
{% endif %}
{% if helpdesk_settings.HELPDESK_ENABLE_TIME_SPENT_ON_TICKET %}
{% if user.is_staff %}
<dt>
<label for='id_time_spent'>{% trans "Time spent" %}</label> <span class='form_optional'>{% trans "(Optional)" %}</span>
</dt>
<dd><input name='time_spent' type="time" /></dd>
{% endif %}
{% endif %}
</dl>
<p id='ShowFurtherOptPara'><button type="button" class="btn btn-warning btn-sm" id='ShowFurtherEditOptions'>{% trans "Change Further Details &raquo;" %}</button></p>
<div id='FurtherEditOptions' style='display: none;'>
<dl>
<dt><label for='id_title'>{% trans "Title" %}</label></dt>
<dd><input type='text' name='title' value='{{ ticket.title|escape }}' /></dd>
<dt><label for='id_owner'>{% trans "Owner" %}</label></dt>
<dd><select id='id_owner' name='owner'><option value='0'>{% trans "Unassign" %}</option>{% for u in active_users %}{% if u.id == ticket.assigned_to.id %}<option value='{{ u.id }}' selected>{{ u }}</option>{% else %}<option value='{{ u.id }}'>{{ u }}</option>{% endif %}{% endfor %}</select></dd>
<dt><label for='id_priority'>{% trans "Priority" %}</label></dt>
<dd><select id='id_priority' name='priority'>{% for p in priorities %}{% if p.0 == ticket.priority %}<option value='{{ p.0 }}' selected='selected'>{{ p.1 }}</option>{% else %}<option value='{{ p.0 }}'>{{ p.1 }}</option>{% endif %}{% endfor %}</select></dd>
<dt><label for='id_due_date'>{% trans "Due on" %}</label></dt>
<dd>{{ form.due_date }}</dd>
</dl>
</div>
{% if ticket.checklists.exists %}
<p>
<button type="button" class="btn btn-warning btn-sm" id='ShowChecklistEditOptions'>
{% trans "Update checklists" %} &raquo;
</button>
</p>
<div id="checklistEdit" style="display: none">
<div class="row">
{% for checklist in ticket.checklists.all %}
<div class="col-sm-4 col-xs-12">
<div class="card mb-4">
<div class="card-header">
<h5>{{ checklist }}</h5>
</div>
<div class="card-body">
<div class="list-group">
{% for task in checklist.tasks.all %}
<div class="list-group-item"{% if task.completion_date %} title="{% trans "Completed on" %} {{ task.completion_date }}" {% endif %}>
<label>
<input type="checkbox" name="checklist-{{ checklist.id }}" value="{{ task.id }}" {% if task.completion_date %} checked{% endif %}>
{{ task }}
</label>
</div>
{% endfor %}
</div>
</div>
</div>
</div>
{% endfor %}
</div>
</div>
{% endif %}
<p id='ShowFileUploadPara'><button type="button" class="btn btn-warning btn-sm" id='ShowFileUpload'>{% trans "Attach File(s) &raquo;" %}</button></p>
<div id='FileUpload' style='display: none;'>
<dl>
<dt><label for='id_file'>{% trans "Attach a File" %}</label></dt>
<dd>
<div class="add_file_fields_wrap">
<button class="add_file_field_button btn btn-success btn-xs">{% trans "Add Another File" %}</button>
<div><label class='btn btn-primary btn-sm btn-file'>
Browse... <input type="file" name='attachment' id='file0' style='display: none;'/>
</label><span>&nbsp;</span><span id='selectedfilename0'>{% trans 'No files selected.' %}</span></div>
</div>
</dd>
</dl>
</div>
</fieldset>
<button class="btn btn-primary float-right" type='submit'>{% trans "Update This Ticket" %}</button>
{% csrf_token %}</form>
</div>
</div>
<div class="modal fade" id="createChecklistModal" tabindex="-1" role="dialog" aria-labelledby="exampleModalCenterTitle" aria-hidden="true">
<div class="modal-dialog modal-dialog-centered" role="document">
<div class="modal-content">
<form method="post">
{% csrf_token %}
<div class="modal-header">
<h5 class="modal-title">{% trans "Add a new checklist" %}</h5>
<button type="button" class="close" data-dismiss="modal" aria-label="{% trans 'Close' %}">
<span aria-hidden="true">&times;</span>
</button>
</div>
<div class="modal-body">
<p>{% trans "You can select a template to generate a checklist with a predefined set of tasks." %}</p>
<p>{% trans "Ignore it and only give a name to create an empty checklist." %}</p>
{{ checklist_form.as_p }}
</div>
<div class="modal-footer">
<a class="btn btn-secondary" href="{% url 'helpdesk:checklist_templates' %}">
{% trans "Manage templates" %}
</a>
<button type="submit" class="btn btn-primary">{% trans "Add" %}</button>
</div>
</form>
</div>
</div>
</div>
{% endif %}
{% endblock %}
{% block helpdesk_js %}
<script type='text/javascript' language='javascript'>
$( function() {
$( "#id_due_date" ).datepicker({dateFormat: 'yy-mm-dd'});
} );
</script>
<script type='text/javascript' language='javascript'>
$(document).ready(function() {
$("#ShowFurtherEditOptions").click(function() {
$("#FurtherEditOptions").toggle();
});
$("#ShowChecklistEditOptions").click(function() {
$("#checklistEdit").toggle();
});
$("#ShowFileUpload").click(function() {
$("#FileUpload").fadeIn();
$("#ShowFileUploadPara").hide();
});
$('#id_preset').change(function() {
preset = $('#id_preset').val();
if (preset != '') {
$.get("{% url 'helpdesk:raw' 'preset' %}?id=" + preset, function(data) {
$("#commentBox").val(data)
});
}
});
// Preset name of checklist when a template is selected
$('#id_checklist_template').on('change', function() {
const nameField = $('#id_name')
const selectedTemplate = $(this).children(':selected')
if (nameField.val() === '' && selectedTemplate.val()) {
nameField.val(selectedTemplate.text())
}
})
$('.disabledTask').on('click', () => {
alert('{% trans 'If you want to update state of checklist tasks, please do a Follow-Up response and click on "Update checklists"' %}')
})
$("[data-toggle=tooltip]").tooltip();
// lists for file input change events, then updates the associated text label
// with the file name selected
$('.add_file_fields_wrap').on('fileselect', ':file', function(event, numFiles, label, browseButtonNum) {
$("#selectedfilename"+browseButtonNum).html(label);
});
var x = 0;
var wrapper = $(".add_file_fields_wrap"); //Fields wrapper
var add_button = $(".add_file_field_button"); //Add button ID
$(add_button).click(function(e){ //on add input button click
x++;
e.preventDefault();
$(wrapper).append("<div><label class='btn btn-primary btn-sm btn-file'>Browse... <input type='file' name='attachment' id='file" + x + "' multiple style='display: none;'/></label><span>&nbsp;</span><span id='selectedfilename" + x + "'>{% trans 'No files selected.' %}</span></div>"); //add input box
});
});
// this function listens for changes on any file input, and
// emits the appropriate event to update the input's text.
// Needed to have properly styled file input buttons! (this really shouldn't be this hard...)
$(document).on('change', ':file', function() {
var input = $(this),
inputWidgetNum = $(this).attr('id').split("file")[1],
numFiles = input.get(0).files ? input.get(0).files.length : 1,
label = input.val().replace(/\\/g, '/').replace(/.*\//, '');
input.trigger('fileselect', [numFiles, label, inputWidgetNum]);
});
</script>
{% endblock %}