Refactor email templates and add notification tasks
Moved email templates to a unified 'email' directory and added new base, header, and footer templates for emails. Implemented notification tasks in commerce for various order and refund events, and updated Carrier model to trigger notifications on shipping state changes.
This commit is contained in:
@@ -0,0 +1,160 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<title>Return/Refund Slip – Order {{ order.number|default:order.code|default:order.id }}</title>
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
<style>
|
||||
:root { --fg:#111; --muted:#666; --border:#ddd; --accent:#0f172a; --bg:#fff; }
|
||||
* { box-sizing: border-box; }
|
||||
html, body { margin:0; padding:0; background:var(--bg); color:var(--fg); font:14px/1.4 system-ui, -apple-system, Segoe UI, Roboto, Arial; }
|
||||
.sheet { max-width: 800px; margin: 24px auto; padding: 24px; border:1px solid var(--border); border-radius: 8px; }
|
||||
header { display:flex; align-items:center; justify-content:space-between; gap:12px; margin-bottom:16px; }
|
||||
.title { font-size:20px; font-weight:700; letter-spacing:.2px; }
|
||||
.sub { color:var(--muted); font-size:12px; }
|
||||
.meta { display:grid; grid-template-columns: 1fr 1fr; gap: 8px 16px; padding:12px; border:1px solid var(--border); border-radius:8px; margin-bottom:16px; }
|
||||
.meta div { display:flex; gap:8px; }
|
||||
.label { width:140px; color:var(--muted); }
|
||||
table { width:100%; border-collapse: collapse; margin: 12px 0 4px; }
|
||||
th, td { border:1px solid var(--border); padding:8px; vertical-align: top; }
|
||||
th { text-align:left; background:#f8fafc; font-weight:600; }
|
||||
.muted { color:var(--muted); }
|
||||
.section { margin-top:18px; }
|
||||
.section h3 { margin:0 0 8px; font-size:14px; text-transform:uppercase; letter-spacing:.4px; color:var(--accent); }
|
||||
.textarea { border:1px solid var(--border); border-radius:8px; min-height:90px; padding:10px; white-space:pre-wrap; }
|
||||
.grid-2 { display:grid; grid-template-columns: 1fr 1fr; gap: 12px; }
|
||||
.row { display:flex; align-items:center; gap:10px; flex-wrap:wrap; }
|
||||
.line { height:1px; background:var(--border); margin: 8px 0; }
|
||||
.sign { height:48px; border-bottom:1px solid var(--border); }
|
||||
.print-tip { color:var(--muted); font-size:12px; margin-top:8px; }
|
||||
.print-btn { display:inline-block; padding:8px 12px; border:1px solid var(--border); border-radius:6px; background:#f8fafc; cursor:pointer; font-size:13px; }
|
||||
@media print {
|
||||
.sheet { border:none; border-radius:0; margin:0; padding:0; }
|
||||
.print-btn, .print-tip { display:none !important; }
|
||||
body { font-size:12px; }
|
||||
th, td { padding:6px; }
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<div class="sheet">
|
||||
<header>
|
||||
<div>
|
||||
<div class="title">Return / Refund Slip</div>
|
||||
<div class="sub">Include this page inside the package for the shopkeeper to examine the return.</div>
|
||||
</div>
|
||||
<div>
|
||||
<button class="print-btn" onclick="window.print()">Print</button>
|
||||
</div>
|
||||
</header>
|
||||
|
||||
<div class="meta">
|
||||
<div><div class="label">Order number</div><div><strong>{{ order.number|default:order.code|default:order.id }}</strong></div></div>
|
||||
<div><div class="label">Order date</div><div>{% if order.created_at %}{{ order.created_at|date:"Y-m-d H:i" }}{% else %}{% now "Y-m-d" %}{% endif %}</div></div>
|
||||
<div><div class="label">Customer name</div><div>{{ order.customer_name|default:order.user.get_full_name|default:order.user.username|default:"" }}</div></div>
|
||||
<div><div class="label">Customer email</div><div>{{ order.customer_email|default:order.user.email|default:"" }}</div></div>
|
||||
<div><div class="label">Phone</div><div>{{ order.customer_phone|default:"" }}</div></div>
|
||||
<div><div class="label">Return created</div><div>{% now "Y-m-d H:i" %}</div></div>
|
||||
</div>
|
||||
|
||||
<div class="section">
|
||||
<h3>Returned items</h3>
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th style="width:44%">Item</th>
|
||||
<th style="width:16%">SKU</th>
|
||||
<th style="width:10%">Qty</th>
|
||||
<th style="width:30%">Reason (per item)</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
{% for it in items %}
|
||||
<tr>
|
||||
<td>
|
||||
<div><strong>{{ it.product_name|default:it.product.title|default:it.name|default:"Item" }}</strong></div>
|
||||
{% if it.variant or it.options %}
|
||||
<div class="muted" style="font-size:12px;">
|
||||
{% if it.variant %}Variant: {{ it.variant }}{% endif %}
|
||||
{% if it.options %}{% if it.variant %} • {% endif %}Options: {{ it.options }}{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
</td>
|
||||
<td>{{ it.sku|default:"—" }}</td>
|
||||
<td>{{ it.quantity|default:1 }}</td>
|
||||
<td>{% if it.reason %}{{ it.reason }}{% else %} {% endif %}</td>
|
||||
</tr>
|
||||
{% empty %}
|
||||
<tr>
|
||||
<td colspan="4" class="muted">No items listed.</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
</tbody>
|
||||
</table>
|
||||
<div class="print-tip">Tip: If the reason differs per item, write it in the last column above.</div>
|
||||
</div>
|
||||
|
||||
<div class="section">
|
||||
<h3>Return reason (customer)</h3>
|
||||
<div class="textarea">
|
||||
{% if return_reason %}{{ return_reason }}{% else %}
|
||||
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="section">
|
||||
<h3>Shopkeeper inspection</h3>
|
||||
<div class="grid-2">
|
||||
<div>
|
||||
<div class="row">
|
||||
<strong>Package condition:</strong>
|
||||
[ ] Intact
|
||||
[ ] Opened
|
||||
[ ] Damaged
|
||||
</div>
|
||||
<div class="row" style="margin-top:6px;">
|
||||
<strong>Items condition:</strong>
|
||||
[ ] New
|
||||
[ ] Light wear
|
||||
[ ] Used
|
||||
[ ] Damaged
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<div class="row">
|
||||
<strong>Resolution:</strong>
|
||||
[ ] Accept refund
|
||||
[ ] Deny
|
||||
[ ] Exchange
|
||||
</div>
|
||||
<div class="row" style="margin-top:6px;">
|
||||
<strong>Restocking fee:</strong> ________ %
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="section" style="margin-top:12px;">
|
||||
<div class="row"><strong>Notes:</strong></div>
|
||||
<div class="textarea" style="min-height:70px;"></div>
|
||||
</div>
|
||||
|
||||
<div class="grid-2" style="margin-top:16px;">
|
||||
<div>
|
||||
<div class="muted" style="font-size:12px;">Processed by (name/signature)</div>
|
||||
<div class="sign"></div>
|
||||
</div>
|
||||
<div>
|
||||
<div class="muted" style="font-size:12px;">Date</div>
|
||||
<div class="sign"></div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="line"></div>
|
||||
<div class="muted" style="font-size:12px; margin-top:8px;">
|
||||
Attach this slip inside the package. Keep a copy for your records.
|
||||
</div>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
||||
Reference in New Issue
Block a user