PageSourceSearch

https://wizfort.com/assets/cslshoes_erp/js/wholesale_order_banner.js?v=20260520c

js wizfort.com collected 2026-09-27 13:40:32 UTC 3,964 bytes, 103 lines download raw bytes

1// Gap F R2 (2026-05-20): /me dashboard banner for wholesale order confirmation.
2//
3// When place_wholesale_order successfully creates docs, the endpoint redirects to
4//   /me?gap_f_order=ok&si=ACC-SINV-...&so=SAL-ORD-...
5// (either si or so may be absent — all-in-stock omits so; all-OOS omits si).
6//
7// This file is included via hooks.py `web_include_js` so it runs on all portal pages,
8// but the path gate ensures the banner only renders on /me. Bullet-safe: any URL
9// without the expected param is a no-op.
10//
11// Banner is informational ("Order received"), NOT navigational. Customer continues
12// using /me normally. Banner can be dismissed via X button.
13
14(function () {
15  'use strict';
16
17  // Only act on /me page (defensive trailing-slash strip)
18  const path = window.location.pathname.replace(/\/+$/, '');
19  if (path !== '/me') return;
20
21  // Read query params
22  const params = new URLSearchParams(window.location.search);
23  if (params.get('gap_f_order') !== 'ok') return;
24
25  const si = params.get('si');
26  const so = params.get('so');
27  if (!si && !so) return; // nothing to confirm
28
29  // Build banner copy
30  let parts = [];
31  if (si) parts.push('items are being invoiced (pending our review)');
32  if (so) parts.push('items have been backordered');
33  const message = 'Order received! Your ' + parts.join(' and ') +
34    '. Our team will confirm shortly via email or phone.';
35
36  // Render banner at the top of #page-me (or main-content fallback)
37  function injectBanner() {
38    if (document.getElementById('csl-gap-f-order-banner')) return; // already rendered
39
40    const banner = document.createElement('div');
41    banner.id = 'csl-gap-f-order-banner';
42    banner.setAttribute('role', 'status');
43    banner.style.cssText = [
44      'background: #ecfdf5',
45      'border: 1px solid #6ee7b7',
46      'border-left: 4px solid #059669',
47      'border-radius: 8px',
48      'padding: 16px 20px',
49      'margin: 16px auto',
50      'max-width: 900px',
51      'color: #064e3b',
52      'display: flex',
53      'gap: 14px',
54      'align-items: flex-start',
55      'font-size: 0.95rem',
56      'line-height: 1.5',
57    ].join(';');
58
59    banner.innerHTML =
60      '<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" ' +
61      'style="width:24px;height:24px;flex-shrink:0;margin-top:2px;">' +
62      '<polyline points="20 6 9 17 4 12"/></svg>' +
63      '<div style="flex:1;">' +
64      '<div style="font-weight:600;margin-bottom:4px;">Order received</div>' +
65      '<div></div>' +
66      '</div>' +
67      '<button type="button" aria-label="Dismiss" style="background:none;border:none;' +
68      'color:#064e3b;cursor:pointer;font-size:1.3rem;line-height:1;padding:0 4px;">×</button>';
69
70    // Set message text via textContent to avoid HTML injection
71    banner.querySelector('div > div:nth-child(2)').textContent = message;
72
73    // Dismiss handler — removes banner + strips query params (so refresh doesn't re-show)
74    banner.querySelector('button').addEventListener('click', function () {
75      banner.remove();
76      try {
77        const url = new URL(window.location.href);
78        url.searchParams.delete('gap_f_order');
79        url.searchParams.delete('si');
80        url.searchParams.delete('so');
81        window.history.replaceState({}, '', url.toString());
82      } catch (e) { /* IE/old-browser fallback: ignore */ }
83    });
84
85    // Try a few anchors in order — /me layout varies across Frappe versions
86    const anchors = [
87      document.getElementById('page-me'),
88      document.querySelector('main'),
89      document.querySelector('.web-page'),
90      document.querySelector('.page_content'),
91      document.querySelector('#main-content'),
92      document.body,
93    ];
94    const anchor = anchors.find(function (a) { return a; });
95    if (anchor) anchor.insertBefore(banner, anchor.firstChild);
96  }
97
98  if (document.readyState === 'loading') {
99    document.addEventListener('DOMContentLoaded', injectBanner);
100  } else {
101    injectBanner();
102  }
103})();

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.