123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240 |
- {% extends "tickets/base.html" %}
- {% load static %}
- {% block content %}
- <h3 class="card-title fw-bold my-3">{{ ticket.title }}</h3>
- <div class="row">
- <div class="col-12 col-md-8 mb-2 mb-md-0">
- <div class="card h-100">
- <div class="card-body">
- {% if ticket.note %}
- <div class="card-text overflow-auto">{{ ticket.note|safe|urlize|linebreaks }}</div>
- {% endif %}
- </div>
- </div>
- </div>
- <div class="col-12 col-md-4">
- <div class="card">
- <ul class="list-group list-group-flush">
- <li class="list-group-item">
- <strong>In list:</strong>
- <a href="{% url 'tickets:ticket_list_detail' ticket.ticket_list.pk %}">
- {{ ticket.ticket_list }}
- </a>
- </li>
- <li class="list-group-item">
- <strong>Created by:</strong>
- {{ ticket.created_by.username }}
- </li>
- <li class="list-group-item">
- <strong>Assigned to:</strong>
- {% if ticket.assigned_to.username %}{{ ticket.assigned_to.username }}{% else %}Anyone{% endif %}
- </li>
- <li class="list-group-item">
- <strong>Type:</strong>
- {{ ticket.get_ticket_type_display }}
- </li>
- <li class="list-group-item">
- <strong>Status:</strong>
- {{ ticket.get_status_display }}
- </li>
- <li class="list-group-item">
- <strong>Priority:</strong>
- {{ ticket.priority }}
- </li>
- <li class="list-group-item">
- <strong>Created at:</strong>
- {{ ticket.created_at }}
- </li>
- <li class="list-group-item">
- <strong>Due date:</strong>
- {{ ticket.due_date }}
- </li>
- <li class="list-group-item">
- <strong>Updated at:</strong>
- {{ ticket.updated_at }}
- </li>
- </ul>
- </div>
- {% if available_statuses %}
- <form class="my-3" method="POST">
- {% csrf_token %}
-
- <label for="select-ticket-status" class="form-label">Available statuses</label>
- <div class="input-group">
- <select class="form-select" id="select-ticket-status" name="ticket-status">
- {% for status in available_statuses %}
- <option {% if forloop.first %}selected{% endif %} value="{{ status.0 }}">{{ status.1 }}</option>
- {% endfor %}
- </select>
-
- <button class="btn btn-outline-secondary" type="submit">Change</button>
- </div>
- </form>
- {% else %}
- <p class="my-3">No available statuses</p>
- {% endif %}
-
- {% if user.is_staff or user.is_superuser or ticket.created_by == user %}
- <div class="d-flex justify-content-between">
- <button type="button" data-bs-toggle="modal" data-bs-target="#ticket-edit-modal" class="btn btn-primary">
- <i class="fa-solid fa-pen-to-square pe-1"></i>
- Edit Ticket
- </button>
- <button type="button" class="btn btn-outline-danger" data-bs-toggle="modal" data-bs-target="#ticket-delete-modal">
- <i class="fa-solid fa-trash-can"></i>
- </button>
- </div>
- <!--Ticket edit modal-->
- <div class="modal fade" id="ticket-edit-modal" tabindex="-1">
- <div class="modal-dialog modal-dialog-centered">
- <div class="modal-content">
- <div class="modal-header">
- <h1 class="modal-title fs-5">
- <i class="fa-solid fa-pen-to-square pe-1"></i>
- Edit Ticket
- </div>
- <div class="modal-body">
- <form id="ticket-create-form" action="{% url 'tickets:ticket_edit' ticket.pk %}" method="post">
- {% include 'tickets/include/form.html' %}
- </form>
- </div>
- <div class="modal-footer">
- <button type="button" class="btn btn-outline-secondary" data-bs-dismiss="modal">
- <i class="fa-solid fa-xmark pe-1"></i>
- Close
- </button>
- <button class="btn btn-primary" type="submit" form="ticket-create-form">
- <i class="fa-solid fa-check pe-1"></i>
- Confirm
- </button>
- </div>
- </div>
- </div>
- </div>
- <!--ticket delete modal-->
- <div class="modal fade" id="ticket-delete-modal" tabindex="-1">
- <div class="modal-dialog modal-dialog-centered">
- <div class="modal-content">
- <div class="modal-header">
- <h1 class="modal-title fs-5">
- <i class="fa-solid fa-trash-can pe-1"></i>
- Delete Ticket
- </h1>
- </div>
- <div class="modal-body">
- Are you sure you want to delete the ticket "{{ ticket.title }}"?
- </div>
- <div class="modal-footer">
- <button type="button" class="btn btn-primary" data-bs-dismiss="modal">
- <i class="fa-solid fa-xmark pe-1"></i>
- Close
- </button>
- <form method="post" action="{% url "tickets:ticket_delete" ticket.pk %}">
- {% csrf_token %}
- <button class="btn btn-outline-danger" type="submit">
- <i class="fa-solid fa-check pe-1"></i>
- Confirm
- </button>
- </form>
- </div>
- </div>
- </div>
- </div>
- {% endif %}
- </div>
- </div>
- <!--Attachments block-->
- <h4 class="mt-4">Attachments</h4>
- {% if ticket.attachment_set.count %}
- <div class="table-responsive">
- <table class="table mb-3">
- <thead>
- <tr>
- <th>File</th>
- <th>Uploaded</th>
- <th>By</th>
- <th>Remove</th>
- </tr>
- </thead>
- <tbody>
- {% for attachment in attachments %}
- <tr>
- <td><a href="{{ attachment.file.url }}">{{ attachment.filename }}</a></td>
- <td>{{ attachment.timestamp }}</td>
- <td>{{ attachment.added_by.username }}</td>
- <td>
- {% if user.is_staff or user.is_superuser or attachment.added_by == user or ticket.created_by == user %}
- <form action="{% url "tickets:remove_attachment" attachment.id %}" method="POST">
- {% csrf_token %}
- <button type="submit" class="btn btn-danger btn-sm">
- <i class="fa-solid fa-xmark"></i>
- </button>
- </form>
- {% endif %}
- </td>
- </tr>
- {% endfor %}
- </tbody>
- </table>
- </div>
- {% endif %}
- <form method="post" enctype="multipart/form-data">
- {% csrf_token %}
- <div class="input-group">
- <input type="file" class="form-control" id="attachment_file_input" name="attachment_file_input">
- <button class="btn btn-primary">
- <i class="fa-solid fa-upload pe-1"></i>
- Upload
- </button>
- </div>
- </form>
- <!--Discussion block-->
- <h4 class="mt-4">Discussion</h4>
- <form class="mb-3" method="post">
- {% csrf_token %}
- <textarea class="form-control" name="comment-body" rows="2" placeholder="Write your comment here" required></textarea>
- <div class="d-flex justify-content-end">
- <button class="btn btn-primary mt-2" type="submit">
- <i class="fa-solid fa-paper-plane pe-1"></i>
- Post
- </button>
- </div>
- </form>
-
- {% if comment_list %}
- {% for comment in comment_list %}
- <div class="card mb-2 bg-body-secondary">
- <div class="card-body">
- <h5>{{ comment.author_username }}</h5>
- {{ comment.body|safe|urlize|linebreaks }}
-
- <div class="text-body-secondary d-flex justify-content-between">
- <small>{{ comment.author_email }}</small>
- <small>{{ comment.date }}</small>
- </div>
- </div>
- </div>
- {% endfor %}
- {% endif %}
- {% endblock %}
- {% block extra_js %}
- <script>
- // Support file attachment uploader
- $('#attachment_file_input').on('change',function(){
- // Get the file name and remove browser-added "fakepath."
- // Then replace the "Choose a file" label.
- var fileName = $(this).val().replace('C:\\fakepath\\', " ");
- $(this).next('.custom-file-label').html(fileName);
- })
- </script>
- {% endblock extra_js %}
|