- Tech Live: TECL → TL - TechLive Qatar: added (TLQ) - TechLive Cyber: added (TLCYB) Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
703 lines
30 KiB
PHP
703 lines
30 KiB
PHP
<?php require_once __DIR__ . '/auth.php'; requireAuth(); ?>
|
|
<!DOCTYPE html>
|
|
<html lang="en">
|
|
<head>
|
|
<meta charset="UTF-8">
|
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
<title>Job Name Builder - Dow Jones</title>
|
|
<link rel="stylesheet" href="style.css">
|
|
<style>
|
|
.builder-container {
|
|
max-width: 960px;
|
|
margin: 0 auto;
|
|
padding: 20px;
|
|
}
|
|
|
|
.back-link {
|
|
display: inline-block;
|
|
margin-bottom: 20px;
|
|
color: var(--text-primary);
|
|
text-decoration: none;
|
|
font-weight: 600;
|
|
text-transform: uppercase;
|
|
letter-spacing: 0.05em;
|
|
font-size: 0.85rem;
|
|
border: 2px solid var(--text-primary);
|
|
padding: 8px 16px;
|
|
}
|
|
.back-link:hover {
|
|
background: var(--text-primary);
|
|
color: var(--bg-color);
|
|
}
|
|
|
|
/* Tabs */
|
|
.tabs {
|
|
display: flex;
|
|
gap: 0;
|
|
margin-bottom: 30px;
|
|
border-bottom: 3px solid var(--text-primary);
|
|
}
|
|
.tab {
|
|
padding: 12px 30px;
|
|
font-weight: 700;
|
|
text-transform: uppercase;
|
|
letter-spacing: 0.05em;
|
|
font-size: 0.9rem;
|
|
cursor: pointer;
|
|
background: var(--card-bg);
|
|
border: 2px solid var(--border-color);
|
|
border-bottom: none;
|
|
color: var(--text-secondary);
|
|
transition: all 0.2s;
|
|
font-family: var(--font-sans);
|
|
}
|
|
.tab:hover {
|
|
background: #eee;
|
|
}
|
|
.tab.active {
|
|
background: var(--text-primary);
|
|
color: var(--bg-color);
|
|
border-color: var(--text-primary);
|
|
}
|
|
.tab-content {
|
|
display: none;
|
|
}
|
|
.tab-content.active {
|
|
display: block;
|
|
}
|
|
|
|
/* Form */
|
|
.form-card {
|
|
background: var(--card-bg);
|
|
padding: 30px;
|
|
border-radius: 8px;
|
|
border: 1px solid var(--border-color);
|
|
margin-bottom: 25px;
|
|
}
|
|
.form-row {
|
|
display: flex;
|
|
gap: 20px;
|
|
margin-bottom: 18px;
|
|
align-items: flex-end;
|
|
}
|
|
.form-group {
|
|
flex: 1;
|
|
min-width: 0;
|
|
}
|
|
.form-group label {
|
|
display: block;
|
|
font-weight: 700;
|
|
text-transform: uppercase;
|
|
letter-spacing: 0.05em;
|
|
font-size: 0.75rem;
|
|
margin-bottom: 6px;
|
|
color: var(--text-secondary);
|
|
}
|
|
.form-group input,
|
|
.form-group select {
|
|
width: 100%;
|
|
padding: 10px 12px;
|
|
border: 2px solid var(--border-color);
|
|
border-radius: 4px;
|
|
font-size: 0.95rem;
|
|
font-family: var(--font-sans);
|
|
background: var(--bg-color);
|
|
color: var(--text-primary);
|
|
box-sizing: border-box;
|
|
}
|
|
.form-group input:focus,
|
|
.form-group select:focus {
|
|
outline: none;
|
|
border-color: var(--text-primary);
|
|
}
|
|
.form-group.hidden {
|
|
display: none;
|
|
}
|
|
|
|
/* Preview */
|
|
.preview-card {
|
|
background: #0f172a;
|
|
padding: 25px;
|
|
border-radius: 8px;
|
|
margin-bottom: 25px;
|
|
border: 1px solid var(--border-color);
|
|
}
|
|
.preview-label {
|
|
font-size: 0.75rem;
|
|
text-transform: uppercase;
|
|
letter-spacing: 0.1em;
|
|
color: #94a3b8;
|
|
margin-bottom: 8px;
|
|
font-weight: 700;
|
|
}
|
|
.preview-filename {
|
|
font-family: 'Courier New', monospace;
|
|
font-size: 1.4rem;
|
|
color: #00ff88;
|
|
word-break: break-all;
|
|
min-height: 1.6em;
|
|
}
|
|
|
|
/* Decode */
|
|
.decode-input-group {
|
|
display: flex;
|
|
gap: 10px;
|
|
margin-bottom: 25px;
|
|
}
|
|
.decode-input-group input {
|
|
flex: 1;
|
|
padding: 14px 16px;
|
|
border: 2px solid var(--text-primary);
|
|
font-size: 1rem;
|
|
font-family: 'Courier New', monospace;
|
|
background: var(--bg-color);
|
|
color: var(--text-primary);
|
|
}
|
|
.decode-input-group input:focus {
|
|
outline: none;
|
|
border-color: var(--accent-color);
|
|
}
|
|
|
|
/* Decoded breakdown */
|
|
.breakdown {
|
|
display: grid;
|
|
grid-template-columns: repeat(auto-fill, minmax(180px, 1fr));
|
|
gap: 12px;
|
|
margin-bottom: 25px;
|
|
}
|
|
.breakdown-item {
|
|
background: var(--bg-color);
|
|
border: 1px solid var(--border-color);
|
|
padding: 12px;
|
|
border-radius: 4px;
|
|
}
|
|
.breakdown-item .label {
|
|
font-size: 0.7rem;
|
|
text-transform: uppercase;
|
|
letter-spacing: 0.1em;
|
|
color: var(--text-secondary);
|
|
font-weight: 700;
|
|
margin-bottom: 4px;
|
|
}
|
|
.breakdown-item .value {
|
|
font-size: 1.1rem;
|
|
font-weight: 600;
|
|
color: var(--text-primary);
|
|
font-family: 'Courier New', monospace;
|
|
}
|
|
.breakdown-item .full-name {
|
|
font-size: 0.8rem;
|
|
color: var(--text-secondary);
|
|
margin-top: 2px;
|
|
}
|
|
|
|
.action-row {
|
|
display: flex;
|
|
gap: 10px;
|
|
margin-top: 20px;
|
|
}
|
|
</style>
|
|
</head>
|
|
<body>
|
|
<div class="builder-container">
|
|
<div style="display: flex; justify-content: space-between; align-items: center; margin-bottom: 20px;">
|
|
<a href="index.php" class="back-link" style="margin-bottom: 0;">Back to Naming Tool</a>
|
|
<div style="display: flex; gap: 10px; align-items: center;">
|
|
<span style="font-size: 0.8rem; color: var(--text-secondary);"><?php echo htmlspecialchars($CURRENT_USER); ?></span>
|
|
<a href="logout.php" class="btn btn-secondary" style="text-decoration: none;">Sign Out</a>
|
|
</div>
|
|
</div>
|
|
|
|
<header style="margin-bottom: 30px;">
|
|
<h1>JOB NAME BUILDER</h1>
|
|
<p style="color: var(--text-secondary);">Build or decode a single Dow Jones job name</p>
|
|
</header>
|
|
|
|
<!-- Tabs -->
|
|
<div class="tabs">
|
|
<div class="tab active" data-tab="build">Build</div>
|
|
<div class="tab" data-tab="decode">Decode</div>
|
|
</div>
|
|
|
|
<!-- BUILD TAB -->
|
|
<div id="tab-build" class="tab-content active">
|
|
<div class="form-card">
|
|
<div class="form-row">
|
|
<div class="form-group" style="flex: 0.7;">
|
|
<label>OMGID</label>
|
|
<input type="text" id="b-omgid" placeholder="000000" maxlength="6">
|
|
</div>
|
|
<div class="form-group">
|
|
<label>Domain</label>
|
|
<select id="b-domain">
|
|
<option value="">-- Select --</option>
|
|
<option value="PMKT">PMKT - Performance Marketing</option>
|
|
<option value="BRND">BRND - Brand</option>
|
|
<option value="EVNT">EVNT - Event</option>
|
|
<option value="B2B">B2B</option>
|
|
</select>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="form-row" id="row-subteam-brand">
|
|
<div class="form-group" id="fg-subteam">
|
|
<label>Subteam</label>
|
|
<select id="b-subteam">
|
|
<option value="">-- Select --</option>
|
|
<option value="ACQ">ACQ - Acquisition</option>
|
|
<option value="B2B">B2B</option>
|
|
<option value="CMKT">CMKT - Content Marketing</option>
|
|
<option value="ENGRT">ENGRT - Engagement/Retention</option>
|
|
<option value="ENT">ENT - Enterprise</option>
|
|
</select>
|
|
</div>
|
|
<div class="form-group" id="fg-brand">
|
|
<label>Brand</label>
|
|
<select id="b-brand">
|
|
<option value="">-- Select --</option>
|
|
<option value="WSJ">WSJ - Wall Street Journal</option>
|
|
<option value="WSJ+">WSJ+</option>
|
|
<option value="BAR">BAR - Barron's</option>
|
|
<option value="MW">MW - MarketWatch</option>
|
|
<option value="DF">DF - Dragonfly</option>
|
|
<option value="DJE">DJE - Dow Jones Energy</option>
|
|
<option value="FAC">FAC - Factiva</option>
|
|
<option value="FE">FE - Free Expression</option>
|
|
<option value="GRI">GRI - Global Risk Insights</option>
|
|
<option value="NWS">NWS - Newswires</option>
|
|
<option value="OA">OA - Oxford Analytica</option>
|
|
<option value="RSK">RSK - Risk</option>
|
|
<option value="RSKC">RSKC - Risk Center</option>
|
|
<option value="DJRJ">DJRJ - Risk Journal</option>
|
|
<option value="R&C">R&C - Risk & Compliance</option>
|
|
<option value="WECR">WECR - World ECR</option>
|
|
</select>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="form-row hidden" id="row-event">
|
|
<div class="form-group">
|
|
<label>Event</label>
|
|
<select id="b-event">
|
|
<option value="">-- Select --</option>
|
|
<option value="GH">GH - Global Horizons</option>
|
|
<option value="DJRJS">DJRJS - Risk Journal Summit</option>
|
|
<option value="WECR">WECR - World ECR</option>
|
|
<option value="FEOE">FEOE - Free Expressions Opinion Event</option>
|
|
<option value="FOH">FOH - Future of Health</option>
|
|
<option value="GFF">GFF - Global Food Forum</option>
|
|
<option value="JH">JH - Journal House</option>
|
|
<option value="TL">TL - TechLive</option>
|
|
<option value="TLQ">TLQ - TechLive Qatar</option>
|
|
<option value="TLCYB">TLCYB - TechLive Cyber</option>
|
|
<option value="FOE">FOE - The Future of Everything</option>
|
|
<option value="WSJIL">WSJIL - WSJ Invest Live</option>
|
|
<option value="BODC">BODC - Board of Directors Council</option>
|
|
<option value="CCOC">CCOC - CCO Council</option>
|
|
<option value="CEOC">CEOC - CEO Council</option>
|
|
<option value="CFOC">CFOC - CFO Council</option>
|
|
<option value="CMOC">CMOC - CMO Council</option>
|
|
<option value="CPOC">CPOC - CPO Council</option>
|
|
<option value="TECC">TECC - Technology Council</option>
|
|
<option value="WSJLI">WSJLI - WSJ Leadership Institute</option>
|
|
</select>
|
|
</div>
|
|
</div>
|
|
|
|
<div class="form-row">
|
|
<div class="form-group">
|
|
<label>Initiative</label>
|
|
<input type="text" id="b-initiative" placeholder="e.g., BIC, DEMO">
|
|
</div>
|
|
<div class="form-group" style="flex: 0.4;">
|
|
<label>Year (YY)</label>
|
|
<input type="text" id="b-yy" placeholder="26" maxlength="2">
|
|
</div>
|
|
<div class="form-group" style="flex: 0.4;">
|
|
<label>Sequence</label>
|
|
<input type="text" id="b-seq" placeholder="01" maxlength="2">
|
|
</div>
|
|
</div>
|
|
|
|
<div class="form-row">
|
|
<div class="form-group">
|
|
<label>Asset Name</label>
|
|
<input type="text" id="b-assetname" placeholder="e.g., MetaBanner, Email">
|
|
</div>
|
|
<div class="form-group" style="flex: 0.4;">
|
|
<label>Version</label>
|
|
<input type="text" id="b-version" placeholder="1" maxlength="3">
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- Live Preview -->
|
|
<div class="preview-card">
|
|
<div class="preview-label">Generated Job Name</div>
|
|
<div class="preview-filename" id="build-preview">--</div>
|
|
</div>
|
|
|
|
<div class="action-row">
|
|
<button class="btn btn-primary" id="pushBuildBtn">Push to Naming Tool</button>
|
|
<button class="btn btn-secondary" id="clearBuildBtn">Clear</button>
|
|
</div>
|
|
</div>
|
|
|
|
<!-- DECODE TAB -->
|
|
<div id="tab-decode" class="tab-content">
|
|
<div class="form-card">
|
|
<label style="display: block; font-weight: 700; text-transform: uppercase; letter-spacing: 0.05em; font-size: 0.75rem; margin-bottom: 8px; color: var(--text-secondary);">Paste a job name to decode</label>
|
|
<div class="decode-input-group">
|
|
<input type="text" id="decode-input" placeholder="e.g., 000000 - PMKT-ACQ-WSJ-BIC-26-01_MetaBanner_v1">
|
|
<button class="btn btn-primary" id="decodeBtn">Decode</button>
|
|
</div>
|
|
|
|
<div id="decode-result" style="display: none;">
|
|
<div class="breakdown" id="decode-breakdown"></div>
|
|
|
|
<!-- Preview rebuilt -->
|
|
<div class="preview-card">
|
|
<div class="preview-label">Reconstructed Job Name</div>
|
|
<div class="preview-filename" id="decode-preview">--</div>
|
|
</div>
|
|
|
|
<div class="action-row">
|
|
<button class="btn btn-primary" id="pushDecodeBtn">Push to Naming Tool</button>
|
|
<button class="btn btn-secondary" id="editDecodeBtn">Edit in Builder</button>
|
|
</div>
|
|
</div>
|
|
|
|
<div id="decode-error" style="display: none; color: var(--danger-color); font-weight: 600; margin-top: 15px;"></div>
|
|
</div>
|
|
</div>
|
|
</div>
|
|
|
|
<script>
|
|
(function() {
|
|
// --- Lookup maps ---
|
|
const DOMAIN_NAMES = { PMKT: 'Performance Marketing', BRND: 'Brand', EVNT: 'Event', B2B: 'B2B' };
|
|
const SUBTEAM_NAMES = { ACQ: 'Acquisition', B2B: 'B2B', CMKT: 'Content Marketing', ENGRT: 'Engagement/Retention', ENT: 'Enterprise' };
|
|
const BRAND_NAMES = { WSJ: 'Wall Street Journal', 'WSJ+': 'Wall Street Journal+', BAR: "Barron's", MW: 'MarketWatch', DF: 'Dragonfly', DJE: 'Dow Jones Energy', FAC: 'Factiva', FE: 'Free Expression', GRI: 'Global Risk Insights', NWS: 'Newswires', OA: 'Oxford Analytica', RSK: 'Risk', RSKC: 'Risk Center', DJRJ: 'Risk Journal', 'R&C': 'Risk & Compliance', WECR: 'World ECR' };
|
|
const EVENT_NAMES = { GH: 'Global Horizons', DJRJS: 'Risk Journal Summit', WECR: 'World ECR', FEOE: 'Free Expressions Opinion Event', FOH: 'Future of Health', GFF: 'Global Food Forum', JH: 'Journal House', TL: 'TechLive', TLQ: 'TechLive Qatar', TLCYB: 'TechLive Cyber', FOE: 'The Future of Everything', WSJIL: 'WSJ Invest Live', BODC: 'Board of Directors Council', CCOC: 'CCO Council', CEOC: 'CEO Council', CFOC: 'CFO Council', CMOC: 'CMO Council', CPOC: 'CPO Council', TECC: 'Technology Council', WSJLI: 'WSJ Leadership Institute' };
|
|
|
|
const ALL_EVENTS = Object.keys(EVENT_NAMES);
|
|
const ALL_BRANDS = Object.keys(BRAND_NAMES);
|
|
const ALL_SUBTEAMS = Object.keys(SUBTEAM_NAMES);
|
|
|
|
// --- Tab switching ---
|
|
document.querySelectorAll('.tab').forEach(tab => {
|
|
tab.addEventListener('click', () => {
|
|
document.querySelectorAll('.tab').forEach(t => t.classList.remove('active'));
|
|
document.querySelectorAll('.tab-content').forEach(c => c.classList.remove('active'));
|
|
tab.classList.add('active');
|
|
document.getElementById('tab-' + tab.dataset.tab).classList.add('active');
|
|
});
|
|
});
|
|
|
|
// --- Build: Domain toggle ---
|
|
const bDomain = document.getElementById('b-domain');
|
|
const rowSubteamBrand = document.getElementById('row-subteam-brand');
|
|
const rowEvent = document.getElementById('row-event');
|
|
|
|
bDomain.addEventListener('change', () => {
|
|
if (bDomain.value === 'EVNT') {
|
|
rowSubteamBrand.classList.add('hidden');
|
|
rowEvent.classList.remove('hidden');
|
|
} else {
|
|
rowSubteamBrand.classList.remove('hidden');
|
|
rowEvent.classList.add('hidden');
|
|
}
|
|
updateBuildPreview();
|
|
});
|
|
|
|
// --- Build: Live preview ---
|
|
const buildFields = ['b-omgid', 'b-domain', 'b-subteam', 'b-brand', 'b-event', 'b-initiative', 'b-yy', 'b-seq', 'b-assetname', 'b-version'];
|
|
buildFields.forEach(id => {
|
|
const el = document.getElementById(id);
|
|
el.addEventListener('input', updateBuildPreview);
|
|
el.addEventListener('change', updateBuildPreview);
|
|
});
|
|
|
|
function getBuildValues() {
|
|
return {
|
|
OMGID: document.getElementById('b-omgid').value.trim(),
|
|
Domain: document.getElementById('b-domain').value,
|
|
Subteam: document.getElementById('b-subteam').value,
|
|
Brand: document.getElementById('b-brand').value,
|
|
Event: document.getElementById('b-event').value,
|
|
Initiative: document.getElementById('b-initiative').value.trim().toUpperCase(),
|
|
YY: document.getElementById('b-yy').value.trim(),
|
|
Sequence: document.getElementById('b-seq').value.trim(),
|
|
AssetName: document.getElementById('b-assetname').value.trim().replace(/\s+/g, ''),
|
|
Version: document.getElementById('b-version').value.trim()
|
|
};
|
|
}
|
|
|
|
function buildFilename(v) {
|
|
let middle = '';
|
|
if (v.Domain === 'EVNT') {
|
|
const parts = ['EVNT'];
|
|
if (v.Event) parts.push(v.Event);
|
|
if (v.YY) parts.push(v.YY);
|
|
if (v.Sequence) parts.push(v.Sequence);
|
|
middle = parts.join('-');
|
|
} else {
|
|
const parts = [];
|
|
if (v.Domain) parts.push(v.Domain);
|
|
if (v.Subteam) parts.push(v.Subteam);
|
|
if (v.Brand) parts.push(v.Brand);
|
|
if (v.Initiative) parts.push(v.Initiative);
|
|
if (v.YY) parts.push(v.YY);
|
|
if (v.Sequence) parts.push(v.Sequence);
|
|
middle = parts.join('-');
|
|
}
|
|
let suffix = '';
|
|
if (v.AssetName) suffix += '_' + v.AssetName;
|
|
if (v.Version) suffix += '_v' + v.Version;
|
|
if (!v.OMGID && !middle) return '--';
|
|
return (v.OMGID ? v.OMGID + ' - ' : '') + middle + suffix;
|
|
}
|
|
|
|
function updateBuildPreview() {
|
|
const v = getBuildValues();
|
|
document.getElementById('build-preview').textContent = buildFilename(v);
|
|
}
|
|
|
|
// Set default year
|
|
document.getElementById('b-yy').value = new Date().getFullYear().toString().slice(-2);
|
|
updateBuildPreview();
|
|
|
|
// --- Build: Clear ---
|
|
document.getElementById('clearBuildBtn').addEventListener('click', () => {
|
|
buildFields.forEach(id => {
|
|
const el = document.getElementById(id);
|
|
if (el.tagName === 'SELECT') el.selectedIndex = 0;
|
|
else if (id === 'b-yy') el.value = new Date().getFullYear().toString().slice(-2);
|
|
else el.value = '';
|
|
});
|
|
rowSubteamBrand.classList.remove('hidden');
|
|
rowEvent.classList.add('hidden');
|
|
updateBuildPreview();
|
|
});
|
|
|
|
// --- Build: Push to Naming Tool ---
|
|
document.getElementById('pushBuildBtn').addEventListener('click', () => {
|
|
const v = getBuildValues();
|
|
pushToTool(v);
|
|
});
|
|
|
|
// --- Decode ---
|
|
document.getElementById('decodeBtn').addEventListener('click', decodeJobName);
|
|
document.getElementById('decode-input').addEventListener('keydown', (e) => {
|
|
if (e.key === 'Enter') decodeJobName();
|
|
});
|
|
|
|
let decodedValues = null;
|
|
|
|
function decodeJobName() {
|
|
const raw = document.getElementById('decode-input').value.trim();
|
|
const errorEl = document.getElementById('decode-error');
|
|
const resultEl = document.getElementById('decode-result');
|
|
errorEl.style.display = 'none';
|
|
resultEl.style.display = 'none';
|
|
|
|
if (!raw) {
|
|
errorEl.textContent = 'Please paste a job name to decode.';
|
|
errorEl.style.display = 'block';
|
|
return;
|
|
}
|
|
|
|
try {
|
|
decodedValues = parseJobName(raw);
|
|
renderBreakdown(decodedValues);
|
|
document.getElementById('decode-preview').textContent = buildFilename(decodedValues);
|
|
resultEl.style.display = 'block';
|
|
} catch (err) {
|
|
errorEl.textContent = 'Could not decode: ' + err.message;
|
|
errorEl.style.display = 'block';
|
|
}
|
|
}
|
|
|
|
function parseJobName(str) {
|
|
const result = { OMGID: '', Domain: '', Subteam: '', Brand: '', Event: '', Initiative: '', YY: '', Sequence: '', AssetName: '', Version: '' };
|
|
|
|
// Split on " - " to get OMGID and rest
|
|
let rest = str;
|
|
if (str.includes(' - ')) {
|
|
const idx = str.indexOf(' - ');
|
|
result.OMGID = str.substring(0, idx).trim();
|
|
rest = str.substring(idx + 3).trim();
|
|
}
|
|
|
|
// Split rest into core (before first _) and suffix (after first _)
|
|
let corePart = rest;
|
|
let suffixPart = '';
|
|
const underscoreIdx = rest.indexOf('_');
|
|
if (underscoreIdx !== -1) {
|
|
corePart = rest.substring(0, underscoreIdx);
|
|
suffixPart = rest.substring(underscoreIdx + 1);
|
|
}
|
|
|
|
// Parse suffix: AssetName_vN
|
|
if (suffixPart) {
|
|
const vMatch = suffixPart.match(/^(.+?)_v(\d+)$/);
|
|
if (vMatch) {
|
|
result.AssetName = vMatch[1];
|
|
result.Version = vMatch[2];
|
|
} else if (suffixPart.match(/^v(\d+)$/)) {
|
|
result.Version = suffixPart.replace('v', '');
|
|
} else {
|
|
result.AssetName = suffixPart;
|
|
}
|
|
}
|
|
|
|
// Parse core: Domain-Subteam-Brand-Initiative-YY-Seq (or EVNT-Event-YY-Seq)
|
|
const parts = corePart.split('-');
|
|
if (parts.length === 0) throw new Error('No segments found');
|
|
|
|
const domain = parts[0];
|
|
if (!DOMAIN_NAMES[domain]) throw new Error('Unknown domain: ' + domain);
|
|
result.Domain = domain;
|
|
|
|
if (domain === 'EVNT') {
|
|
// EVNT-[Event]-[YY]-[Seq]
|
|
if (parts.length >= 2) {
|
|
// Check if part is a known event
|
|
if (ALL_EVENTS.includes(parts[1])) {
|
|
result.Event = parts[1];
|
|
if (parts.length >= 3) result.YY = parts[2];
|
|
if (parts.length >= 4) result.Sequence = parts[3];
|
|
} else {
|
|
// Maybe YY directly
|
|
result.YY = parts[1];
|
|
if (parts.length >= 3) result.Sequence = parts[2];
|
|
}
|
|
}
|
|
} else {
|
|
// [Domain]-[Subteam]-[Brand]-[Initiative]-[YY]-[Seq]
|
|
let i = 1;
|
|
if (i < parts.length && ALL_SUBTEAMS.includes(parts[i])) {
|
|
result.Subteam = parts[i]; i++;
|
|
}
|
|
if (i < parts.length && ALL_BRANDS.includes(parts[i])) {
|
|
result.Brand = parts[i]; i++;
|
|
}
|
|
// Remaining: could be Initiative, YY, Seq
|
|
// YY is 2 digits, Seq is 2 digits
|
|
// Initiative is anything that's not a 2-digit number at the end
|
|
const remaining = parts.slice(i);
|
|
if (remaining.length >= 3) {
|
|
// Initiative-YY-Seq
|
|
result.Initiative = remaining.slice(0, -2).join('-');
|
|
result.YY = remaining[remaining.length - 2];
|
|
result.Sequence = remaining[remaining.length - 1];
|
|
} else if (remaining.length === 2) {
|
|
// Could be YY-Seq or Initiative-YY
|
|
if (remaining[0].match(/^\d{2}$/) && remaining[1].match(/^\d{2}$/)) {
|
|
result.YY = remaining[0];
|
|
result.Sequence = remaining[1];
|
|
} else {
|
|
result.Initiative = remaining[0];
|
|
result.YY = remaining[1];
|
|
}
|
|
} else if (remaining.length === 1) {
|
|
if (remaining[0].match(/^\d{2}$/)) {
|
|
result.YY = remaining[0];
|
|
} else {
|
|
result.Initiative = remaining[0];
|
|
}
|
|
}
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
function renderBreakdown(v) {
|
|
const container = document.getElementById('decode-breakdown');
|
|
container.innerHTML = '';
|
|
|
|
const fields = [
|
|
{ key: 'OMGID', label: 'OMGID' },
|
|
{ key: 'Domain', label: 'Domain', nameMap: DOMAIN_NAMES },
|
|
{ key: 'Subteam', label: 'Subteam', nameMap: SUBTEAM_NAMES },
|
|
{ key: 'Brand', label: 'Brand', nameMap: BRAND_NAMES },
|
|
{ key: 'Event', label: 'Event', nameMap: EVENT_NAMES },
|
|
{ key: 'Initiative', label: 'Initiative' },
|
|
{ key: 'YY', label: 'Year (YY)' },
|
|
{ key: 'Sequence', label: 'Sequence' },
|
|
{ key: 'AssetName', label: 'Asset Name' },
|
|
{ key: 'Version', label: 'Version' }
|
|
];
|
|
|
|
fields.forEach(f => {
|
|
const val = v[f.key];
|
|
if (!val) return; // skip empty
|
|
|
|
const item = document.createElement('div');
|
|
item.className = 'breakdown-item';
|
|
|
|
let fullName = '';
|
|
if (f.nameMap && f.nameMap[val]) {
|
|
fullName = f.nameMap[val];
|
|
}
|
|
|
|
item.innerHTML = `
|
|
<div class="label">${f.label}</div>
|
|
<div class="value">${val}</div>
|
|
${fullName ? '<div class="full-name">' + fullName + '</div>' : ''}
|
|
`;
|
|
container.appendChild(item);
|
|
});
|
|
}
|
|
|
|
// --- Decode: Push ---
|
|
document.getElementById('pushDecodeBtn').addEventListener('click', () => {
|
|
if (decodedValues) pushToTool(decodedValues);
|
|
});
|
|
|
|
// --- Decode: Edit in Builder ---
|
|
document.getElementById('editDecodeBtn').addEventListener('click', () => {
|
|
if (!decodedValues) return;
|
|
populateBuildForm(decodedValues);
|
|
// Switch to build tab
|
|
document.querySelectorAll('.tab').forEach(t => t.classList.remove('active'));
|
|
document.querySelectorAll('.tab-content').forEach(c => c.classList.remove('active'));
|
|
document.querySelector('[data-tab="build"]').classList.add('active');
|
|
document.getElementById('tab-build').classList.add('active');
|
|
});
|
|
|
|
function populateBuildForm(v) {
|
|
document.getElementById('b-omgid').value = v.OMGID || '';
|
|
document.getElementById('b-domain').value = v.Domain || '';
|
|
document.getElementById('b-subteam').value = v.Subteam || '';
|
|
document.getElementById('b-brand').value = v.Brand || '';
|
|
document.getElementById('b-event').value = v.Event || '';
|
|
document.getElementById('b-initiative').value = v.Initiative || '';
|
|
document.getElementById('b-yy').value = v.YY || '';
|
|
document.getElementById('b-seq').value = v.Sequence || '';
|
|
document.getElementById('b-assetname').value = v.AssetName || '';
|
|
document.getElementById('b-version').value = v.Version || '';
|
|
|
|
if (v.Domain === 'EVNT') {
|
|
rowSubteamBrand.classList.add('hidden');
|
|
rowEvent.classList.remove('hidden');
|
|
} else {
|
|
rowSubteamBrand.classList.remove('hidden');
|
|
rowEvent.classList.add('hidden');
|
|
}
|
|
updateBuildPreview();
|
|
}
|
|
|
|
// --- Push to Naming Tool ---
|
|
function pushToTool(v) {
|
|
const params = new URLSearchParams();
|
|
params.set('builder', '1');
|
|
Object.keys(v).forEach(key => {
|
|
if (v[key]) params.set(key, v[key]);
|
|
});
|
|
window.location.href = 'index.php?' + params.toString();
|
|
}
|
|
})();
|
|
</script>
|
|
</body>
|
|
</html>
|