Fix: CSS inline sans Tailwind (classes Tailwind non interpretes sans CDN)

This commit is contained in:
2026-08-14 13:58:52 +02:00
parent 5c31c2fb5f
commit 89da858568
+280 -369
View File
@@ -5,453 +5,364 @@
<meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>SysCmd — Command Reference</title> <title>SysCmd — Command Reference</title>
<style> <style>
*,*::before,*::after{box-sizing:border-box;margin:0;padding:0} *{box-sizing:border-box;margin:0;padding:0}
body{font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',Roboto,sans-serif;-webkit-font-smoothing:antialiased;line-height:1.5;background:#f8fafc;color:#0f172a} body{font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',Roboto,sans-serif;background:#f8fafc;color:#0f172a;line-height:1.5}
.flex{display:flex}.flex-col{flex-direction:column}.min-h-screen{min-height:100vh}.flex-1{flex:1}.overflow-y-auto{overflow-y:auto} .sbar{width:14rem;border-right:1px solid #e2e8f0;background:#fff;display:flex;flex-direction:column;min-height:100vh;padding:12px 0;overflow-y:auto;flex-shrink:0}
.w-56{width:14rem}.border-r{border-right:1px solid #e2e8f0}.py-3{padding-top:0.75rem;padding-bottom:0.75rem} .main{flex:1;padding:24px;max-width:960px}
.px-3{padding-left:0.75rem;padding-right:0.75rem}.pb-3{padding-bottom:0.75rem}.mb-2{margin-bottom:0.5rem} .tree{flex:1;overflow-y:auto}
.border-b{border-bottom:1px solid #f1f5f9}.bg-white{background:#fff} .grp{font-size:10px;font-weight:700;text-transform:uppercase;letter-spacing:.05em;color:#94a3b8;padding:8px 12px 4px}
.items-center{align-items:center}.gap-2{gap:0.5rem}.gap-2\\.5{gap:0.625rem} .slk{display:flex;align-items:center;gap:6px;padding:4px 10px;border-radius:6px;font-size:13px;font-weight:500;cursor:pointer;color:#475569;transition:all .12s;user-select:none}
.font-bold{font-weight:700}.text-sm{font-size:0.8125rem} .slk:hover{background:#f1f5f9;color:#0f172a}
.hidden{display:none}.lg\\:flex{display:flex} .slk.act{background:#0f172a;color:#fff}
.sidebar-link{display:flex;align-items:center;gap:6px;padding:4px 10px;border-radius:6px;font-size:0.8125rem;font-weight:500;cursor:pointer;user-select:none;transition:all 0.12s;color:#475569} .slk3{padding-left:48px;font-size:12px}
.sidebar-link:hover{background:#f1f5f9;color:#0f172a} .slk4{padding-left:64px;font-size:11px;font-weight:400}
.sidebar-link.active{background:#0f172a;color:#fff} .tgl{display:inline-flex;align-items:center;justify-content:center;width:16px;height:16px;flex-shrink:0;transition:transform .15s;color:#94a3b8}
.sidebar-link-3{padding-left:48px;font-size:0.75rem} .tgl.o{transform:rotate(90deg)}
.sidebar-link-4{padding-left:64px;font-size:0.6875rem;font-weight:400} .chd{display:none}
.tree-toggle{display:inline-flex;align-items:center;justify-content:center;width:16px;height:16px;flex-shrink:0;transition:transform 0.15s;color:#94a3b8} .chd.o{display:block}
.tree-toggle.open{transform:rotate(90deg)} .dg{width:6px;height:6px;border-radius:50%;background:#22c55e;flex-shrink:0}
.tree-children{display:none}.tree-children.open{display:block} .dgr{width:6px;height:6px;border-radius:50%;background:#cbd5e1;flex-shrink:0}
.group-label{font-size:0.625rem;font-weight:700;text-transform:uppercase;letter-spacing:0.05em;color:#94a3b8;padding:8px 12px 4px} .do{width:6px;height:6px;border-radius:50%;background:#f59e0b;flex-shrink:0}
.main{padding:1.5rem;max-width:64rem}.mb-4{margin-bottom:1rem}.mb-5{margin-bottom:1.25rem}.mb-6{margin-bottom:1.5rem}.mb-3{margin-bottom:0.75rem} .bd{font-size:11px;color:#94a3b8;display:flex;gap:6px;align-items:center;margin-bottom:2px}
.mt-4{margin-top:1rem} .bd .c{color:#0f172a;font-weight:500}
.breadcrumb{font-size:0.75rem;color:#94a3b8;display:flex;gap:6px;align-items:center;margin-bottom:2px} .scmd{display:grid;grid-template-columns:190px 1fr;align-items:start;padding:4px 12px;border-radius:5px;font-size:13px;gap:8px;transition:background .1s}
.breadcrumb .current{color:#0f172a;font-weight:500} .scmd:hover{background:#f1f5f9}
.text-xl{font-size:1.125rem}.font-bold{font-weight:700} .scmd .d{color:#475569;font-weight:500;line-height:1.4}
.text-xs{font-size:0.6875rem}.text-sm{font-size:0.8125rem} .scmd .t{font-family:Consolas,'Courier New',monospace;font-size:12px;color:#0f172a;cursor:pointer;display:inline-flex;align-items:center;gap:6px;line-height:1.4;word-break:break-all}
.text-center{text-align:center} .scmd .t:hover .cp{opacity:1}
.text-\\[\\#64748b\\]{color:#64748b}.text-\\[\\#94a3b8\\]{color:#94a3b8}.text-\\[\\#0f172a\\]{color:#0f172a} .cp{opacity:0;width:14px;height:14px;flex-shrink:0;color:#94a3b8;transition:opacity .12s}
.relative{position:relative} .alt{background:#fafbfc}
.search-input{width:100%;padding:7px 12px 7px 34px;border-radius:8px;font-size:0.8125rem;outline:none;border:1.5px solid #e2e8f0;background:#fff;transition:border-color 0.12s} .stab{padding:4px 10px;border-radius:5px;font-size:11px;font-weight:500;cursor:pointer;border:1px solid #e2e8f0;color:#64748b;white-space:nowrap;transition:all .12s}
.search-input:focus{border-color:#0f172a} .stab.a{background:#0f172a;color:#fff;border-color:#0f172a}
.section-tab{padding:4px 10px;border-radius:5px;font-size:0.6875rem;font-weight:500;cursor:pointer;transition:all 0.12s;border:1px solid #e2e8f0;color:#64748b;white-space:nowrap} .stab:hover:not(.a){background:#f1f5f9}
.section-tab.active{background:#0f172a;color:#fff;border-color:#0f172a} .si{width:100%;padding:7px 12px 7px 34px;border-radius:8px;font-size:13px;outline:none;border:1.5px solid #e2e8f0;background:#fff;transition:border-color .12s}
.section-tab:hover:not(.active){background:#f1f5f9} .si:focus{border-color:#0f172a}
.cmd-row{display:grid;grid-template-columns:190px 1fr;align-items:start;padding:4px 12px;border-radius:5px;font-size:0.8125rem;transition:background 0.1s;gap:8px} .oc{border-radius:10px;border:1px solid #e2e8f0;background:#fff;cursor:pointer;transition:all .15s;padding:16px}
.cmd-row:hover{background:#f1f5f9} .oc:hover{border-color:#0f172a;box-shadow:0 2px 12px rgba(0,0,0,.08)}
.cmd-row .cmd-desc{color:#475569;font-weight:500;line-height:1.4} .oc .ic{width:36px;height:36px;border-radius:8px;display:flex;align-items:center;justify-content:center;flex-shrink:0}
.cmd-row .cmd-text{font-family:'Cascadia Code','Fira Code','Consolas',monospace;font-size:0.75rem;color:#0f172a;cursor:pointer;display:inline-flex;align-items:center;gap:6px;line-height:1.4;word-break:break-all} .oc .sl{font-size:11px;color:#94a3b8}
.cmd-row .cmd-text:hover .copy-icon{opacity:1} .oc.ph{opacity:.6}
.copy-icon{opacity:0;width:14px;height:14px;flex-shrink:0;color:#94a3b8;transition:opacity 0.12s} .oc.ph:hover{opacity:.8}
.bg-\\[\\#fafbfc\\]{background:#fafbfc} .emp{padding:40px 16px;max-width:360px;margin:0 auto;text-align:center}
.dot-green{width:6px;height:6px;border-radius:50%;background:#22c55e;flex-shrink:0} .emp h3{font-weight:600;font-size:15px;margin-bottom:4px;color:#0f172a}
.dot-gray{width:6px;height:6px;border-radius:50%;background:#cbd5e1;flex-shrink:0} .emp p{font-size:13px;color:#94a3b8;line-height:1.5}
.dot-orange{width:6px;height:6px;border-radius:50%;background:#f59e0b;flex-shrink:0} .sb{border:1px solid #e2e8f0;border-radius:10px;background:#fff;text-align:center;padding:12px}
.flex-wrap{flex-wrap:wrap}.gap-1{gap:0.25rem}.gap-3{gap:0.75rem} .sb .n{font-size:20px;font-weight:700;color:#0f172a}
.items-center{align-items:center} .sb .l{font-size:11px;color:#94a3b8}
.justify-between{justify-content:space-between} .cl{font-size:11px;font-weight:700;text-transform:uppercase;letter-spacing:.05em;color:#94a3b8;margin-top:8px;margin-bottom:4px}
.grid{display:grid} .gp{display:flex;gap:4px;flex-wrap:wrap;margin-bottom:12px}
.grid-cols-1{grid-template-columns:repeat(1,1fr)} .lr{display:flex;gap:12px;align-items:center;margin-bottom:12px;font-size:11px;color:#64748b}
.os-card{border-radius:10px;border:1px solid #e2e8f0;background:#fff;cursor:pointer;transition:all 0.15s;padding:16px} .p8{padding:24px;font-size:13px;color:#94a3b8}
.os-card:hover{border-color:#0f172a;box-shadow:0 2px 12px rgba(0,0,0,0.08)} .cmdbox{background:#fff;border:1px solid #e2e8f0;border-radius:12px;overflow:hidden}
.os-card .icon{width:36px;height:36px;border-radius:8px;display:flex;align-items:center;justify-content:center;flex-shrink:0} .cmdbox .s{font-size:11px;color:#94a3b8;padding:8px 12px;border-bottom:1px solid #f1f5f9}
.os-card .sublabel{font-size:0.6875rem;color:#94a3b8}
.os-card .stat-value{font-size:1.25rem;font-weight:700;letter-spacing:-0.02em}
.placeholder-card{opacity:0.6}.placeholder-card:hover{opacity:0.8}
.empty-state{padding:40px 16px;max-width:360px;margin:0 auto;text-align:center}
.empty-state h3{font-weight:600;font-size:0.9375rem;margin-bottom:4px;color:#0f172a}
.empty-state p{font-size:0.8125rem;color:#94a3b8;line-height:1.5}
.stat-box{padding:12px;border:1px solid #e2e8f0;border-radius:10px;background:#fff;text-align:center}
.stat-box .num{font-size:1.25rem;font-weight:700;color:#0f172a}
.stat-box .lbl{font-size:0.6875rem;color:#94a3b8}
.category-label{font-size:0.6875rem;font-weight:700;text-transform:uppercase;letter-spacing:0.05em;color:#94a3b8;margin-top:8px;margin-bottom:4px;grid-column:1/-1}
.mt-auto{margin-top:auto}
.pt-3{padding-top:0.75rem}
.border-t{border-top:1px solid #f1f5f9}
.rounded-xl{border-radius:12px}
.overflow-hidden{overflow:hidden}
.border{border:1px solid #e2e8f0}
.divide-y>*+*{border-top:1px solid #f1f5f9}
.p-8{padding:2rem}
@media(min-width:640px){.sm\\:grid-cols-2{grid-template-columns:repeat(2,1fr)}}
@media(min-width:1024px){.lg\\:flex{display:flex}.lg\\:grid-cols-3{grid-template-columns:repeat(3,1fr)}}
</style> </style>
</head> </head>
<body> <body style="display:flex;min-height:100vh">
<div class="flex min-h-screen">
<!-- SIDEBAR --> <!-- SIDEBAR -->
<aside id="sidebar" class="w-56 border-r py-3 bg-white overflow-y-auto flex-col hidden lg:flex"> <div class="sbar">
<div class="flex items-center gap-2.5 px-3 pb-3 mb-2 border-b"> <div style="display:flex;align-items:center;gap:10px;padding:8px 12px 16px;border-bottom:1px solid #f1f5f9;flex-shrink:0">
<div style="width:28px;height:28px;background:#0f172a;border-radius:8px;display:flex;align-items:center;justify-content:center;flex-shrink:0"> <div style="width:28px;height:28px;background:#0f172a;border-radius:8px;display:flex;align-items:center;justify-content:center">
<svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="white" stroke-width="2.5"><path d="M10 20l4-16m4 4l4 4-4 4M6 16l-4-4 4-4"/></svg> <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="white" stroke-width="2.5"><path d="M10 20l4-16m4 4l4 4-4 4M6 16l-4-4 4-4"/></svg>
</div> </div>
<span class="font-bold text-sm">SysCmd</span> <span style="font-weight:700;font-size:14px">SysCmd</span>
</div>
<div class="tree" id="tree"></div>
<div style="padding-top:12px;border-top:1px solid #f1f5f9;flex-shrink:0">
<div style="display:flex;align-items:center;gap:8px;padding:8px 12px">
<div style="width:28px;height:28px;background:#e2e8f0;border-radius:50%;display:flex;align-items:center;justify-content:center;font-size:12px;font-weight:600;color:#64748b">LK</div>
<div style="font-size:12px"><div style="font-weight:500;color:#0f172a">Laurent</div><div style="color:#94a3b8">sysadmin</div></div>
</div> </div>
<div id="tree" class="flex-1 overflow-y-auto"></div>
<div class="pt-3 border-t mt-auto">
<div class="flex items-center gap-2 px-3 py-2">
<div style="width:28px;height:28px;background:#e2e8f0;border-radius:50%;display:flex;align-items:center;justify-content:center;font-size:0.75rem;font-weight:600;color:#64748b;flex-shrink:0">LK</div>
<div style="font-size:0.75rem"><div style="font-weight:500;color:#0f172a">Laurent</div><div style="color:#94a3b8">sysadmin</div></div>
</div> </div>
</div> </div>
</aside>
<!-- MAIN --> <!-- MAIN -->
<main class="flex-1 main"> <div class="main">
<!-- HEADER --> <div style="display:flex;justify-content:space-between;align-items:center;margin-bottom:20px">
<div class="flex items-center justify-between mb-5">
<div> <div>
<div class="breadcrumb" id="breadcrumb"></div> <div class="bd" id="bd"></div>
<h1 class="text-xl font-bold" id="os-title">SysCmd</h1> <h1 style="font-size:18px;font-weight:700" id="os-title">SysCmd</h1>
<p class="text-xs text-[#64748b] mt-0.5" id="os-sub"></p> <p style="font-size:11px;color:#64748b;margin-top:2px" id="os-sub"></p>
</div> </div>
<div class="relative"> <div style="position:relative">
<svg style="position:absolute;left:10px;top:50%;transform:translateY(-50%);width:14px;height:14px;color:#94a3b8" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M21 21l-6-6m2-5a7 7 0 11-14 0 7 7 0 0114 0z"/></svg> <svg style="position:absolute;left:10px;top:50%;transform:translateY(-50%);width:14px;height:14px;color:#94a3b8" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M21 21l-6-6m2-5a7 7 0 11-14 0 7 7 0 0114 0z"/></svg>
<input class="search-input" id="search" placeholder="Chercher une commande..." oninput="onSearch(this.value)"> <input class="si" id="search" placeholder="Chercher une commande..." oninput="onSearch(this.value)">
</div> </div>
</div> </div>
<!-- TABS --> <div class="gp" id="tabs"></div>
<div class="flex gap-1 flex-wrap mb-3" id="tabs"></div>
<!-- STATS BAR --> <div class="lr" id="stats-bar">
<div class="flex gap-3 items-center mb-3 text-xs text-[#64748b]" id="stats-bar">
<span id="shown">0</span> <span>commandes</span> <span id="shown">0</span> <span>commandes</span>
<span>·</span> <span>·</span>
<span id="filter-info">Aucun filtre</span> <span id="fi">Aucun filtre</span>
</div> </div>
<!-- COMMANDS --> <div class="cmdbox" id="cmd-box">
<div class="bg-white border border-[#e2e8f0] rounded-xl overflow-hidden" id="cmds-container">
<div id="cmds"></div> <div id="cmds"></div>
</div> </div>
<!-- HOME --> <!-- HOME -->
<div id="home-content"> <div id="home">
<div class="text-center mb-6" style="margin-top:2rem"> <div style="text-align:center;margin:32px 0 24px">
<h2 style="font-size:1.5rem;font-weight:700;margin-bottom:8px">SysCmd</h2> <h2 style="font-size:24px;font-weight:700;margin-bottom:8px">SysCmd</h2>
<p style="font-size:0.8125rem;color:#64748b;max-width:480px;margin:0 auto">Référence de commandes multi-plateforme. Cliquez sur un OS pour voir ses commandes.</p> <p style="font-size:13px;color:#64748b;max-width:480px;margin:0 auto">R&eacute;f&eacute;rence de commandes multi-plateforme. Cliquez sur un OS pour voir ses commandes.</p>
<div style="margin-top:12px;display:flex;justify-content:center;gap:12px;font-size:0.6875rem;color:#94a3b8"> <div style="margin-top:12px;display:flex;justify-content:center;gap:12px;font-size:11px;color:#94a3b8">
<span class="flex items-center gap-1"><span class="dot-green" style="display:inline-block;vertical-align:middle"></span> Données disponibles</span> <span style="display:flex;align-items:center;gap:4px"><span class="dg" style="display:inline-block;vertical-align:middle"></span> Donn&eacute;es disponibles</span>
<span class="flex items-center gap-1"><span class="dot-orange" style="display:inline-block;vertical-align:middle"></span> Catégorie</span> <span style="display:flex;align-items:center;gap:4px"><span class="do" style="display:inline-block;vertical-align:middle"></span> Cat&eacute;gorie</span>
<span class="flex items-center gap-1"><span class="dot-gray" style="display:inline-block;vertical-align:middle"></span> À venir</span> <span style="display:flex;align-items:center;gap:4px"><span class="dgr" style="display:inline-block;vertical-align:middle"></span> &Agrave; venir</span>
</div> </div>
</div> </div>
<div id="global-search-results" style="display:none;margin-bottom:1.5rem"></div> <div id="gs" style="display:none;margin-bottom:24px"></div>
<div class="grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-3 gap-3 mb-6 text-center" id="stats-row"></div> <div id="stats-row" style="display:grid;grid-template-columns:repeat(4,1fr);gap:12px;margin-bottom:24px"></div>
<div class="grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-3 gap-3" id="card-grid"></div> <div id="grid" style="display:grid;grid-template-columns:repeat(3,1fr);gap:12px"></div>
</div> </div>
<div class="mt-4 text-center text-xs text-[#94a3b8]" id="footer-hint">Cliquez sur un OS pour explorer ses commandes</div> <div style="margin-top:16px;text-align:center;font-size:11px;color:#94a3b8" id="fh">Cliquez sur un OS pour explorer ses commandes</div>
</main>
</div> </div>
<script> <script>
"use strict"; "use strict";
function t(fr,en){return{fr:fr,en:en}} function t(f,e){return{fr:f,en:e}}
var N=null,CS=null;
var currentNode=null,currentSection=null; var TREE={id:'r',children:[
{id:'os',label:t('OS','OS'),children:[
var TREE={id:'root',children:[ {id:'lnx',label:t('Linux','Linux'),children:[
{id:'os-cat',label:t('OS','OS'),children:[ {id:'ubu',label:t('Ubuntu','Ubuntu'),children:[
{id:'linux',label:t('Linux','Linux'),children:[ {id:'u20',label:t('20.04','20.04'),osKey:'u',secs:['sys','apt','users']},
{id:'ubuntu',label:t('Ubuntu','Ubuntu'),children:[ {id:'u22',label:t('22.04','22.04'),osKey:'u',secs:['sys','apt','users']},
{id:'ubuntu-2004',label:t('20.04','20.04'),osKey:'ubuntu',sectionIds:['sys','apt','users']}, {id:'u24',label:t('24.04','24.04'),osKey:'u',secs:['sys','apt','users','systemd']}]},
{id:'ubuntu-2204',label:t('22.04','22.04'),osKey:'ubuntu',sectionIds:['sys','apt','users']}, {id:'deb',label:t('Debian','Debian'),osKey:'d',secs:['sys','apt','users','systemd']},
{id:'ubuntu-2404',label:t('24.04','24.04'),osKey:'ubuntu',sectionIds:['sys','apt','users','systemd']}]}, {id:'ora',label:t('Oracle Linux','Oracle Linux'),osKey:'o',secs:['odnf','ospec','osel','ofw','systemd']},
{id:'debian',label:t('Debian','Debian'),osKey:'debian',sectionIds:['sys','apt','users','systemd']}, {id:'rhel',label:t('RHEL/CentOS','RHEL/CentOS')},{id:'fed',label:t('Fedora','Fedora')}]},
{id:'oracle',label:t('Oracle Linux','Oracle Linux'),osKey:'oracle',sectionIds:['oracle-dnf','oracle-spec','oracle-selinux','oracle-fw','systemd']}, {id:'win',label:t('Windows','Windows'),children:[
{id:'rhel',label:t('RHEL/CentOS','RHEL/CentOS')},{id:'fedora',label:t('Fedora','Fedora')}]}, {id:'wcl',label:t('Client','Client'),children:[
{id:'windows',label:t('Windows','Windows'),children:[ {id:'wxp',label:t('XP','XP')},{id:'w10',label:t('10','10'),osKey:'w',secs:['wsys','wfiles','wproc','wnet']},
{id:'win-client',label:t('Client','Client'),children:[ {id:'w11',label:t('11','11'),osKey:'w',secs:['wsys','wfiles','wproc','wnet']}]},
{id:'win-xp',label:t('XP','XP')},{id:'win-10',label:t('10','10'),osKey:'windows',sectionIds:['win-sys','win-files','win-process','win-network']}, {id:'wsrv',label:t('Server','Server'),children:[
{id:'win-11',label:t('11','11'),osKey:'windows',sectionIds:['win-sys','win-files','win-process','win-network']}]}, {id:'w16',label:t('2016','2016'),osKey:'ws',secs:['wsys','wfiles','wproc','wnet']},
{id:'win-server',label:t('Server','Server'),children:[ {id:'w19',label:t('2019','2019'),osKey:'ws',secs:['wsys','wfiles','wproc','wnet']}]}]},
{id:'win-2016',label:t('2016','2016'),osKey:'windows-server',sectionIds:['win-sys','win-files','win-process','win-network']}, {id:'sol',label:t('Solaris/illumos','Solaris/illumos'),osKey:'s',secs:['sips','ssmf','szfs','szones']},
{id:'win-2019',label:t('2019','2019'),osKey:'windows-server',sectionIds:['win-sys','win-files','win-process','win-network']}]}]}, {id:'mac',label:t('macOS','macOS')}]},
{id:'solaris',label:t('Solaris/illumos','Solaris/illumos'),osKey:'solaris',sectionIds:['solaris-ips','solaris-smf','solaris-zfs','solaris-zones']}, {id:'dck',label:t('Docker','Docker'),children:[
{id:'macos',label:t('macOS','macOS')}]}, {id:'dcc',label:t('Compose','Compose')},{id:'dcs',label:t('Swarm','Swarm')},{id:'dcf',label:t('Dockerfile','Dockerfile')}]},
{id:'docker-cat',label:t('Docker','Docker'),children:[ {id:'oth',label:t('Other','Other'),children:[
{id:'dc-compose',label:t('Compose','Compose')},{id:'dc-swarm',label:t('Swarm','Swarm')},{id:'dc-file',label:t('Dockerfile','Dockerfile')}]}, {id:'net',label:t('Reseau','Network'),children:[{id:'cis',label:t('Cisco','Cisco')},{id:'tpl',label:t('TP-Link','TP-Link')}]},
{id:'other-cat',label:t('Other','Other'),children:[ {id:'sql',label:t('SQL','SQL'),children:[{id:'my',label:t('MySQL/MariaDB','MySQL/MariaDB')},{id:'pg',label:t('PostgreSQL','PostgreSQL')}]},
{id:'net',label:t('Reseau','Network'),children:[{id:'cisco',label:t('Cisco','Cisco')},{id:'tplink',label:t('TP-Link','TP-Link')}]}, {id:'dev',label:t('DevOps','DevOps'),children:[{id:'ans',label:t('Ansible','Ansible')},{id:'tf',label:t('Terraform','Terraform')},{id:'k8',label:t('Kubernetes','Kubernetes')}]}]}]};
{id:'sql',label:t('SQL','SQL'),children:[{id:'mysql',label:t('MySQL/MariaDB','MySQL/MariaDB')},{id:'pg',label:t('PostgreSQL','PostgreSQL')}]},
{id:'devops',label:t('DevOps','DevOps'),children:[{id:'ansible',label:t('Ansible','Ansible')},{id:'tf',label:t('Terraform','Terraform')},{id:'k8s',label:t('Kubernetes','Kubernetes')}]}]}]};
var SEC={}; var SEC={};
SEC.sys={label:t('systeme','system'),commands:[ SEC.sys={label:t('systeme','system'),cmds:[
{d:t('Version noyau','Kernel version'),c:'uname -r'}, {d:t('Version noyau','Kernel'),c:'uname -r'},{d:t('Version OS','OS version'),c:'lsb_release -a'},
{d:t('Version OS','OS version'),c:'lsb_release -a'}, {d:t('Memoire','Memory'),c:'free -h'},{d:t('Hostname','Hostname'),c:'hostnamectl'},
{d:t('Memoire dispo','Memory available'),c:'free -h'}, {d:t('Uptime','Uptime'),c:'uptime'},{d:t('CPU','CPU'),c:'lscpu'},{d:t('Date','Date'),c:'timedatectl'}]};
{d:t("Nom d'hote",'Hostname'),c:'hostnamectl'}, SEC.apt={label:t('APT','APT'),cmds:[
{d:t('Uptime','Uptime'),c:'uptime'}, {d:t('Sync repos','Sync repos'),c:'sudo apt update'},{d:t('Mise a jour','Upgrade'),c:'sudo apt full-upgrade -y'},
{d:t('Infos CPU','CPU info'),c:'lscpu'}, {d:t('Installer','Install'),c:'sudo apt install [pkg]'},{d:t('Purge','Purge'),c:'sudo apt purge [pkg]'},
{d:t('Date/heure','Date/time'),c:'timedatectl'}]}; {d:t('Search','Search'),c:'apt search [kw]'},{d:t('Installed','Installed'),c:'apt list --installed'},
SEC.apt={label:t('APT','APT'),commands:[ {d:t('Fichiers','Package files'),c:'dpkg -L [pkg]'}]};
{d:t('Synchro depots','Sync repos'),c:'sudo apt update'}, SEC.users={label:t('utilisateurs','users'),cmds:[
{d:t('Mise a jour','Full upgrade'),c:'sudo apt full-upgrade -y'}, {d:t('Ajouter','Add'),c:'sudo adduser [n]'},{d:t('Supprimer','Delete'),c:'sudo deluser --remove-home [n]'},
{d:t('Installer','Install'),c:'sudo apt install [package]'}, {d:t('Groupe sudo','Sudo group'),c:'sudo usermod -aG sudo [n]'},{d:t('Permissions','Perms'),c:'chmod 755 [f]'},
{d:t('Purge','Purge'),c:'sudo apt purge [package]'}, {d:t('Root','Root'),c:'sudo -i'}]};
{d:t('Chercher','Search'),c:'apt search [keyword]'}, SEC.systemd={label:t('systemd','systemd'),cmds:[
{d:t('Paquets installes','Installed'),c:'apt list --installed'}, {d:t('Start/Stop','Start/Stop'),c:'sudo systemctl start|stop [s]'},{d:t('Restart','Restart'),c:'sudo systemctl restart [s]'},
{d:t('Fichiers fournis','Package files'),c:'dpkg -L [package]'}]}; {d:t('Enable','Enable'),c:'sudo systemctl enable [s]'},{d:t('Status','Status'),c:'systemctl status [s]'},
SEC.users={label:t('utilisateurs','users'),commands:[ {d:t('Logs','Logs'),c:'journalctl -u [s] -n 50'},{d:t('Purge logs','Purge logs'),c:'sudo journalctl --vacuum-time=7d'}]};
{d:t('Ajouter','Add user'),c:'sudo adduser [name]'}, SEC.wsys={label:t('systeme','system'),cmds:[
{d:t('Supprimer','Delete user'),c:'sudo deluser --remove-home [name]'}, {d:t('(CMD) Version','(CMD) Version'),c:'ver'},{d:t('(CMD) systeminfo','(CMD) systeminfo'),c:'systeminfo'},
{d:t('Groupe sudo','Sudo group'),c:'sudo usermod -aG sudo [name]'},
{d:t('Permissions','Permissions'),c:'chmod 755 [file]'},
{d:t('Root','Root shell'),c:'sudo -i'}]};
SEC.systemd={label:t('systemd','systemd'),commands:[
{d:t('Start/Stop','Start/Stop'),c:'sudo systemctl start|stop [service]'},
{d:t('Restart','Restart'),c:'sudo systemctl restart [service]'},
{d:t('Enable','Enable'),c:'sudo systemctl enable [service]'},
{d:t('Statut','Status'),c:'systemctl status [service]'},
{d:t('Logs','Logs'),c:'journalctl -u [service] -n 50'},
{d:t('Purger logs','Purge logs'),c:'sudo journalctl --vacuum-time=7d'}]};
SEC['win-sys']={label:t('systeme','system'),commands:[
{d:t('(CMD) Version','(CMD) Version'),c:'ver'},
{d:t('(CMD) systeminfo','(CMD) systeminfo'),c:'systeminfo'},
{d:t('(PS) Get-ComputerInfo','(PS) Get-ComputerInfo'),c:'Get-ComputerInfo'}]}; {d:t('(PS) Get-ComputerInfo','(PS) Get-ComputerInfo'),c:'Get-ComputerInfo'}]};
SEC['win-files']={label:t('fichiers','files'),commands:[ SEC.wfiles={label:t('fichiers','files'),cmds:[
{d:t('(CMD) dir','(CMD) dir'),c:'dir /s'}, {d:t('(CMD) dir','(CMD) dir'),c:'dir /s'},{d:t('(CMD) rmdir','(CMD) rmdir'),c:'rmdir /s [f]'},
{d:t('(CMD) rmdir','(CMD) rmdir'),c:'rmdir /s [folder]'},
{d:t('(PS) Get-ChildItem','(PS) Get-ChildItem'),c:'Get-ChildItem -Recurse -Filter *.txt'}]}; {d:t('(PS) Get-ChildItem','(PS) Get-ChildItem'),c:'Get-ChildItem -Recurse -Filter *.txt'}]};
SEC['win-process']={label:t('processus','processes'),commands:[ SEC.wproc={label:t('processus','processes'),cmds:[
{d:t('(CMD) tasklist','(CMD) tasklist'),c:'tasklist'}, {d:t('(CMD) tasklist','(CMD) tasklist'),c:'tasklist'},{d:t('(CMD) taskkill','(CMD) taskkill'),c:'taskkill /IM notepad.exe /F'},
{d:t('(CMD) taskkill','(CMD) taskkill'),c:'taskkill /IM notepad.exe /F'},
{d:t('(PS) Get-Process','(PS) Get-Process'),c:'Get-Process'}]}; {d:t('(PS) Get-Process','(PS) Get-Process'),c:'Get-Process'}]};
SEC['win-network']={label:t('reseau','network'),commands:[ SEC.wnet={label:t('reseau','network'),cmds:[
{d:t('(CMD) ipconfig','(CMD) ipconfig'),c:'ipconfig /all'}, {d:t('(CMD) ipconfig','(CMD) ipconfig'),c:'ipconfig /all'},{d:t('(CMD) netstat','(CMD) netstat'),c:'netstat -an | findstr LISTEN'},
{d:t('(CMD) netstat','(CMD) netstat'),c:'netstat -an | findstr LISTEN'}, {d:t('(PS) TNM','(PS) TNM'),c:'Test-NetConnection [ip] -Port [port]'}]};
{d:t('(PS) Test-NetConnection','(PS) Test-NetConnection'),c:'Test-NetConnection [ip] -Port [port]'}]}; SEC.odnf={label:t('DNF','DNF'),cmds:[
SEC['oracle-dnf']={label:t('DNF','DNF'),commands:[ {d:t('Sync','Sync'),c:'sudo dnf check-update'},{d:t('Upgrade','Upgrade'),c:'sudo dnf upgrade -y'},
{d:t('Synchro','Sync'),c:'sudo dnf check-update'}, {d:t('Install','Install'),c:'sudo dnf install [p]'},{d:t('Remove','Remove'),c:'sudo dnf remove [p]'}]};
{d:t('Upgrade','Upgrade'),c:'sudo dnf upgrade -y'}, SEC.ospec={label:t('Oracle spec.','Oracle spec.'),cmds:[
{d:t('Install','Install'),c:'sudo dnf install [package]'}, {d:t('Ksplice status','Ksplice status'),c:'sudo uptrack-status'},{d:t('Ksplice upgrade','Ksplice upgrade'),c:'sudo uptrack-upgrade'},
{d:t('Remove','Remove'),c:'sudo dnf remove [package]'}]}; {d:t('Switch kernel','Switch kernel'),c:'sudo grubby --set-default /boot/vmlinuz-[v]'}]};
SEC['oracle-spec']={label:t('Oracle spec.','Oracle spec.'),commands:[ SEC.osel={label:t('SELinux','SELinux'),cmds:[
{d:t('Ksplice status','Ksplice status'),c:'sudo uptrack-status'}, {d:t('Status','Status'),c:'getenforce'},{d:t('Permissive','Permissive'),c:'sudo setenforce 0'},
{d:t('Ksplice upgrade','Ksplice upgrade'),c:'sudo uptrack-upgrade'}, {d:t('AVC logs','AVC logs'),c:'sudo ausearch -m avc -ts recent'}]};
{d:t('Changer noyau','Switch kernel'),c:'sudo grubby --set-default /boot/vmlinuz-[ver]'}]}; SEC.ofw={label:t('firewalld','firewalld'),cmds:[
SEC['oracle-selinux']={label:t('SELinux','SELinux'),commands:[ {d:t('Status','Status'),c:'sudo firewall-cmd --state'},{d:t('Open port','Open port'),c:'sudo firewall-cmd --permanent --add-port=22/tcp'}]};
{d:t('Statut','Status'),c:'getenforce'}, SEC.sips={label:t('IPS','IPS'),cmds:[
{d:t('Permissif','Permissive'),c:'sudo setenforce 0'}, {d:t('Refresh','Refresh'),c:'sudo pkg refresh'},{d:t('Update','Update'),c:'sudo pkg update'},
{d:t('Logs AVC','AVC logs'),c:'sudo ausearch -m avc -ts recent'}]}; {d:t('Install','Install'),c:'sudo pkg install [p]'},{d:t('Remove','Remove'),c:'sudo pkg uninstall [p]'}]};
SEC['oracle-fw']={label:t('firewalld','firewalld'),commands:[ SEC.ssmf={label:t('SMF','SMF'),cmds:[
{d:t('Status','Status'),c:'sudo firewall-cmd --state'}, {d:t('List','List'),c:'svcs -a'},{d:t('Enable','Enable'),c:'sudo svcadm enable [s]'},
{d:t('Ouvrir port','Open port'),c:'sudo firewall-cmd --permanent --add-port=22/tcp'}]}; {d:t('Disable','Disable'),c:'sudo svcadm disable [s]'},{d:t('Restart','Restart'),c:'sudo svcadm restart [s]'}]};
SEC['solaris-ips']={label:t('IPS','IPS'),commands:[ SEC.szfs={label:t('ZFS','ZFS'),cmds:[
{d:t('Refresh','Refresh'),c:'sudo pkg refresh'}, {d:t('Pool status','Pool status'),c:'zpool status'},{d:t('Scrub','Scrub'),c:'sudo zpool scrub [p]'},
{d:t('Update','Update'),c:'sudo pkg update'}, {d:t('Snapshot','Snapshot'),c:'sudo zfs snapshot [p]/[ds]@[n]'},{d:t('Send/Receive','Send/Receive'),c:'zfs send [p]/[ds]@snap | zfs receive [d]'}]};
{d:t('Install','Install'),c:'sudo pkg install [package]'}, SEC.szones={label:t('Zones','Zones'),cmds:[
{d:t('Remove','Remove'),c:'sudo pkg uninstall [package]'}]}; {d:t('List','List'),c:'zoneadm list -cv'},{d:t('Boot','Boot'),c:'sudo zoneadm -z [z] boot'},
SEC['solaris-smf']={label:t('SMF','SMF'),commands:[ {d:t('Halt','Halt'),c:'sudo zoneadm -z [z] halt'},{d:t('Console','Console'),c:'sudo zlogin -C [z]'}]};
{d:t('Liste','List'),c:'svcs -a'},
{d:t('Enable','Enable'),c:'sudo svcadm enable [service]'},
{d:t('Disable','Disable'),c:'sudo svcadm disable [service]'},
{d:t('Restart','Restart'),c:'sudo svcadm restart [service]'}]};
SEC['solaris-zfs']={label:t('ZFS','ZFS'),commands:[
{d:t('Pool status','Pool status'),c:'zpool status'},
{d:t('Scrub','Scrub'),c:'sudo zpool scrub [pool]'},
{d:t('Snapshot','Snapshot'),c:'sudo zfs snapshot [pool]/[ds]@[name]'},
{d:t('Send/Receive','Send/Receive'),c:'zfs send [pool]/[ds]@snap | zfs receive [dest]'}]};
SEC['solaris-zones']={label:t('Zones','Zones'),commands:[
{d:t('Liste','List'),c:'zoneadm list -cv'},
{d:t('Boot','Boot'),c:'sudo zoneadm -z [zone] boot'},
{d:t('Halt','Halt'),c:'sudo zoneadm -z [zone] halt'},
{d:t('Console','Console'),c:'sudo zlogin -C [zone]'}]};
// ALL COMMANDS for global search var ALL=[];(function(){var seen={};for(var k in SEC)SEC[k].cmds.forEach(function(x){if(!seen[x.c]){seen[x.c]=1;ALL.push(x)}})})();
var ALL=[];
(function(){var seen={};for(var k in SEC)if(SEC.hasOwnProperty(k))SEC[k].commands.forEach(function(x){var key=x.c;if(!seen[key]){seen[key]=true;ALL.push(x)}})})();
// HELPERS function FN(t,i){if(t.id===i)return t;for(var j=0;j<(t.children||[]).length;j++){var r=FN(t.children[j],i);if(r)return r}return null}
function findNode(tree,id){if(tree.id===id)return tree;for(var i=0;i<(tree.children||[]).length;i++){var f=findNode(tree.children[i],id);if(f)return f}return null} function CL(n,o){if(n.children){for(var i=0;i<n.children.length;i++)CL(n.children[i],o)}else o.push(n);return o}
function collectLeaves(node,out){if(node.children){for(var i=0;i<node.children.length;i++)collectLeaves(node.children[i],out)}else{out.push(node)}return out} function CC(n){if(n.secs){var t=0;for(var i=0;i<n.secs.length;i++)if(SEC[n.secs[i]])t+=SEC[n.secs[i]].cmds.length;return t}return 0}
function countCmds(node){if(node.sectionIds){var n=0;for(var i=0;i<node.sectionIds.length;i++)if(SEC[node.sectionIds[i]])n+=SEC[node.sectionIds[i]].commands.length;return n}return 0} function $(i){return document.getElementById(i)}
function $(id){return document.getElementById(id)} function RT(){
var el=$('tree');el.innerHTML='';
// RENDER TREE function RN(c,n,d){
function renderTree(){var el=$('tree');el.innerHTML='';renderNode(el,TREE,0)} var br=n.children&&n.children.length>0,ver=!!n.secs;
function renderNode(container,node,depth){ var dv=document.createElement('div');
var isBranch=node.children&&node.children.length>0,isVersion=!!node.sectionIds; if(d===0){var lb=document.createElement('div');lb.className='grp';lb.textContent='Categories';dv.appendChild(lb)}
var div=document.createElement('div'); else{
if(depth===0){ var rw=document.createElement('div');
var label=document.createElement('div');label.className='group-label';label.textContent='Categories';div.appendChild(label) var c2='slk';if(d===2)c2+=' slk3';if(d===3)c2+=' slk4';if(n===N)c2+=' act';rw.className=c2;
}else{ if(br){var tg=document.createElement('span');tg.className='tgl o';
var row=document.createElement('div'); tg.innerHTML='<svg width="12" height="12" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2.5" d="M9 18l6-6-6-6"/></svg>';rw.appendChild(tg)
var cls='sidebar-link';if(depth===2)cls+=' sidebar-link-3';if(depth===3)cls+=' sidebar-link-4'; }else{var sp=document.createElement('span');sp.style.cssText='width:16px;flex-shrink:0;display:inline-block';rw.appendChild(sp)}
if(node===currentNode)cls+=' active';row.className=cls; var dt=document.createElement('span');
if(isBranch){var tgl=document.createElement('span');tgl.className='tree-toggle open'; if(ver||n._p)dt.className='dg';else if(br)dt.className='do';else dt.className='dgr';
tgl.innerHTML='<svg width="12" height="12" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2.5" d="M9 18l6-6-6-6"/></svg>';row.appendChild(tgl) rw.appendChild(dt);
}else{var sp=document.createElement('span');sp.style.cssText='width:16px;flex-shrink:0;display:inline-block';row.appendChild(sp)} var lb2=document.createElement('span');lb2.textContent=n.label.fr;rw.appendChild(lb2);
var dot=document.createElement('span'); var cnt=CC(n)||(n._p&&n._p.secs?SEC[n._sid]?SEC[n._sid].cmds.length:0:0);
if(isVersion||node._parent)dot.className='dot-green';else if(isBranch)dot.className='dot-orange';else dot.className='dot-gray'; if(cnt>0){var b2=document.createElement('span');b2.style.cssText='margin-left:auto;font-size:10px;color:#94a3b8';b2.textContent=''+cnt;rw.appendChild(b2)}
row.appendChild(dot); rw.onclick=function(e){
var lbl=document.createElement('span');lbl.textContent=node.label.fr;row.appendChild(lbl); if(br&&(e.target.closest('.tgl')||e.target.closest('[data-toggle]'))){var tg=rw.querySelector('.tgl');if(tg){tg.classList.toggle('o');rw.nextElementSibling.classList.toggle('o');e.stopPropagation()}return}
var cnt=countCmds(node)||(node._parent&&node._parent.sectionIds?SEC[node._sectionId]?SEC[node._sectionId].commands.length:0:0); if(br)return;S(n)
if(cnt>0){var b=document.createElement('span');b.className='ml-auto text-[0.625rem] text-[#94a3b8]';b.textContent=''+cnt;row.appendChild(b)}
row.onclick=function(e){
if(isBranch&&(e.target.closest('.tree-toggle')||e.target.closest('[data-toggle]'))){var tg=row.querySelector('.tree-toggle');if(tg){tg.classList.toggle('open');row.nextElementSibling.classList.toggle('open');e.stopPropagation()}return}
if(isBranch)return;selectNode(node)
}; };
div.appendChild(row) dv.appendChild(rw)
} }
if(isBranch){ if(br){var kd=document.createElement('div');kd.className='chd o';
var kids=document.createElement('div');kids.className='tree-children open'; for(var i=0;i<n.children.length;i++){n.children[i]._p=n;RN(kd,n.children[i],d+1)}
for(var i=0;i<node.children.length;i++){node.children[i]._parent=node;renderNode(kids,node.children[i],depth+1)} dv.appendChild(kd)
div.appendChild(kids)
} }
if(isVersion&&node.sectionIds){ if(ver&&n.secs){var kd=document.createElement('div');kd.className='chd';
var kids=document.createElement('div');kids.className='tree-children'; if(n===N||(N&&N._p===n))kd.className='chd o';
if(node===currentNode||(currentNode&&currentNode._parent===node))kids.className='tree-children open'; for(var j=0;j<n.secs.length;j++){var s=n.secs[j],sc=SEC[s];if(!sc)continue;
for(var j=0;j<node.sectionIds.length;j++){var sid=node.sectionIds[j],sec=SEC[sid];if(!sec)continue; var sn={id:n.id+'-'+s,label:sc.label,_sid:s,_p:n};RN(kd,sn,d+1)}
var sn={id:node.id+'-'+sid,label:sec.label,_sectionId:sid,_parent:node};renderNode(kids,sn,depth+1)} dv.appendChild(kd)
div.appendChild(kids)
} }
container.appendChild(div) c.appendChild(dv)
}
RN(el,TREE,0)
} }
// SELECT function S(n){
function selectNode(node){ N=n;CS=null;RT();$('search').value='';HI();$('bd').innerHTML='';
currentNode=node;currentSection=null;renderTree(); var t=$('os-title'),s=$('os-sub'),c=$('cmds');
$('search').value='';hideHome();$('breadcrumb').innerHTML=''; if(n._sid){var sc=SEC[n._sid];if(sc){t.textContent=(n._p.label.fr||'')+' > '+sc.label.fr;s.textContent=sc.cmds.length+' commandes';SC(sc.cmds)}return}
var title=$('os-title'),sub=$('os-sub'),cmds=$('cmds'); if(n.secs&&n.secs.length>0){var s0=n.secs[0],sc0=SEC[s0];if(sc0){t.textContent=n.label.fr;s.textContent=n.secs.length+' sections . '+CC(n)+' commandes';SC(sc0.cmds)}return}
if(node._sectionId){var sec=SEC[node._sectionId];if(sec){title.textContent=(node._parent.label.fr||'')+' > '+sec.label.fr;sub.textContent=sec.commands.length+' commandes';showCmds(sec.commands)}return} t.textContent=n.label.fr;s.textContent='Aucune donnee';c.innerHTML='<div class="emp"><h3>'+n.label.fr+'</h3><p>Pas encore de commandes</p></div>'
if(node.sectionIds&&node.sectionIds.length>0){
var sid=node.sectionIds[0],sec=SEC[sid];
if(sec){title.textContent=node.label.fr;sub.textContent=node.sectionIds.length+' sections . '+countCmds(node)+' commandes';showCmds(sec.commands)}return
}
title.textContent=node.label.fr;sub.textContent='Aucune donnee';cmds.innerHTML='<div class="empty-state"><h3>'+node.label.fr+'</h3><p>Pas encore de commandes pour cet OS.</p></div>'
} }
function showHome(){ function SH(){N=null;CS=null;RT();$('search').value='';
currentNode=null;currentSection=null;renderTree();$('search').value=''; $('home').style.display='block';$('tabs').style.display='none';$('stats-bar').style.display='none';$('cmd-box').style.display='none';
$('home-content').style.display='block';$('tabs').style.display='none';$('stats-bar').style.display='none'; $('bd').innerHTML='';$('os-title').textContent='SysCmd';$('os-sub').textContent='';$('fh').textContent='Cliquez sur un OS pour explorer ses commandes';
$('cmds-container').style.display='none';$('breadcrumb').innerHTML=''; RH()
$('os-title').textContent='SysCmd';$('os-sub').textContent='';$('footer-hint').textContent='Cliquez sur un OS pour explorer ses commandes';
renderHome()
} }
function hideHome(){$('home-content').style.display='none';$('tabs').style.display='flex';$('stats-bar').style.display='flex';$('cmds-container').style.display='block';$('footer-hint').textContent='Cliquez sur une commande pour la copier'} function HI(){$('home').style.display='none';$('tabs').style.display='flex';$('stats-bar').style.display='flex';$('cmd-box').style.display='block';$('fh').textContent='Cliquez sur une commande pour la copier'}
// HOME function RH(){RS();RCS()}
function renderHome(){renderStats();renderCards()} function RS(){
function renderStats(){ var tc=ALL.length,ts=0;for(var k in SEC)ts++;
var totalCmds=ALL.length,totalSections=0;for(var k in SEC)if(SEC.hasOwnProperty(k))totalSections++; var lv=CL(TREE,[]),tos=0;for(var i=0;i<lv.length;i++)if(lv[i].secs)tos++;
var leaves=collectLeaves(TREE,[]),totalOS=0;for(var i=0;i<leaves.length;i++)if(leaves[i].sectionIds)totalOS++; $('stats-row').innerHTML='<div class="sb"><div class="n">'+tc+'</div><div class="l">commandes</div></div><div class="sb"><div class="n">'+ts+'</div><div class="l">sections</div></div><div class="sb"><div class="n">'+tos+'</div><div class="l">OS renseignes</div></div><div class="sb"><div class="n" style="color:#94a3b8">'+(lv.length-tos)+'</div><div class="l">placeholders</div></div>'
$('stats-row').innerHTML=
'<div class="stat-box"><div class="num">'+totalCmds+'</div><div class="lbl">commandes</div></div>'+
'<div class="stat-box"><div class="num">'+totalSections+'</div><div class="lbl">sections</div></div>'+
'<div class="stat-box"><div class="num">'+totalOS+'</div><div class="lbl">OS renseignes</div></div>'+
'<div class="stat-box"><div class="num" style="color:#94a3b8">'+(leaves.length-totalOS)+'</div><div class="lbl">placeholders</div></div>'
} }
var CARDS=[ var CARDS=[
{id:'debian',label:'Debian',icon:'D',color:'#0f172a',desc:t('Distribution stable','Stable distribution'),cat:'os'}, {id:'deb',l:'Debian',i:'D',c:'#0f172a',d:t('Distribution stable','Stable'),cat:'os'},
{id:'ubuntu',label:'Ubuntu',icon:'U',color:'#dc2626',desc:t('Base Debian avec LTS','Debian-based LTS'),cat:'os',group:true}, {id:'ubu',l:'Ubuntu',i:'U',c:'#dc2626',d:t('Base Debian LTS','Debian LTS'),cat:'os',gr:true},
{id:'oracle',label:'Oracle Linux',icon:'O',color:'#b9141e',desc:t('Linux UEK+SELinux','Linux UEK+SELinux'),cat:'os'}, {id:'ora',l:'Oracle Linux',i:'O',c:'#b9141e',d:t('Linux UEK+SELinux','UEK+SELinux'),cat:'os'},
{id:'windows',label:'Windows',icon:'W',color:'#0078d4',desc:t('CMD+PS client/server','CMD+PS client/server'),cat:'os',group:true}, {id:'win',l:'Windows',i:'W',c:'#0078d4',d:t('CMD+PS','CMD+PS'),cat:'os',gr:true},
{id:'solaris',label:'Solaris',icon:'S',color:'#b46400',desc:t('Solaris+ZFS+DTrace','Solaris+ZFS+DTrace'),cat:'os'}, {id:'sol',l:'Solaris',i:'S',c:'#b46400',d:t('Solaris+ZFS+DTrace','Solaris'),cat:'os'},
{id:'rhel',label:'RHEL/CentOS',icon:'R',color:'#94a3b8',desc:t('Enterprise Linux','Enterprise Linux'),cat:'os',ph:true}, {id:'rhel',l:'RHEL/CentOS',i:'R',c:'#94a3b8',d:t('Enterprise Linux','Enterprise'),cat:'os',ph:1},
{id:'fedora',label:'Fedora',icon:'F',color:'#94a3b8',desc:t('RHEL-based','RHEL-based'),cat:'os',ph:true}, {id:'fed',l:'Fedora',i:'F',c:'#94a3b8',d:t('RHEL-based','RHEL-based'),cat:'os',ph:1},
{id:'macos',label:'macOS',icon:'M',color:'#94a3b8',desc:t('macOS','macOS'),cat:'os',ph:true}, {id:'mac',l:'macOS',i:'M',c:'#94a3b8',d:t('macOS','macOS'),cat:'os',ph:1},
{id:'dc-compose',label:'Docker Compose',icon:'D',color:'#0ea5e9',desc:t('Multi-conteneurs','Multi-container'),cat:'docker',ph:true}, {id:'dcc',l:'Docker Compose',i:'D',c:'#0ea5e9',d:t('Multi-conteneurs','Multi-container'),cat:'dk',ph:1},
{id:'dc-swarm',label:'Docker Swarm',icon:'S',color:'#0ea5e9',desc:t('Cluster natif','Native cluster'),cat:'docker',ph:true}, {id:'dcs',l:'Docker Swarm',i:'S',c:'#0ea5e9',d:t('Cluster natif','Cluster'),cat:'dk',ph:1},
{id:'dc-file',label:'Dockerfile',icon:'F',color:'#0ea5e9',desc:t('Build instructions','Build instructions'),cat:'docker',ph:true}, {id:'dcf',l:'Dockerfile',i:'F',c:'#0ea5e9',d:t('Build','Build'),cat:'dk',ph:1},
{id:'cisco',label:'Cisco IOS',icon:'C',color:'#8b5cf6',desc:t('Reseau Cisco','Cisco networking'),cat:'other',ph:true}, {id:'cis',l:'Cisco',i:'C',c:'#8b5cf6',d:t('Reseau Cisco','Cisco'),cat:'oth',ph:1},
{id:'mysql',label:'MySQL/MariaDB',icon:'S',color:'#8b5cf6',desc:t('Bases SQL','SQL databases'),cat:'other',ph:true}, {id:'my',l:'MySQL/MariaDB',i:'S',c:'#8b5cf6',d:t('Bases SQL','SQL'),cat:'oth',ph:1},
{id:'pg',label:'PostgreSQL',icon:'P',color:'#8b5cf6',desc:t('Base avancee','Advanced DB'),cat:'other',ph:true}, {id:'pg',l:'PostgreSQL',i:'P',c:'#8b5cf6',d:t('Base avancee','Advanced DB'),cat:'oth',ph:1},
{id:'ansible',label:'Ansible',icon:'A',color:'#8b5cf6',desc:t('Automatisation IT','IT automation'),cat:'other',ph:true}, {id:'ans',l:'Ansible',i:'A',c:'#8b5cf6',d:t('Automatisation','Automation'),cat:'oth',ph:1},
{id:'k8s',label:'Kubernetes',icon:'K',color:'#8b5cf6',desc:t('Orchestration','Orchestration'),cat:'other',ph:true}]; {id:'k8',l:'Kubernetes',i:'K',c:'#8b5cf6',d:t('Orchestration','Orchestration'),cat:'oth',ph:1}];
function renderCards(){ function RCS(){
var cats={os:{label:t('Systemes d exploitation','Operating Systems'),html:''},docker:{label:t('Docker/Conteneurs','Docker/Containers'),html:''},other:{label:t('Reseau, BDD, DevOps','Network, DB, DevOps'),html:''}}; var cats={os:{l:t('Systemes d exploitation','Operating Systems'),h:''},dk:{l:t('Docker/Conteneurs','Docker/Containers'),h:''},oth:{l:t('Reseau, BDD, DevOps','Network, DB, DevOps'),h:''}};
CARDS.forEach(function(card){ CARDS.forEach(function(cd){
var n=findNode(TREE,card.id),cnt=n?countCmds(n):0,ph=card.ph&&cnt===0; var nd=FN(TREE,cd.id),cnt=nd?CC(nd):0,ph=cd.ph&&cnt===0;
if(!cats[card.cat])cats[card.cat]={label:card.cat,html:''}; if(!cats[cd.cat])cats[cd.cat]={l:cd.cat,h:''};
var h='<div class="os-card'+(ph?' placeholder-card':'')+'">'+ var h='<div class="oc'+(ph?' ph':'')+'" data-card="'+cd.id+'">'+
'<div class="flex items-start gap-3 mb-3">'+ '<div style="display:flex;gap:12px;margin-bottom:12px">'+
'<div class="icon" style="background:'+(ph?'#e2e8f0':card.color)+(ph?';color:#94a3b8':';color:#fff')+'"><span style="font-weight:700;font-size:0.8125rem">'+card.icon+'</span></div>'+ '<div class="ic" style="background:'+(ph?'#e2e8f0':cd.c)+';color:'+(ph?'#94a3b8':'#fff')+'"><span style="font-weight:700;font-size:13px">'+cd.i+'</span></div>'+
'<div class="flex-1" style="min-width:0"><div style="font-weight:600;font-size:0.8125rem;overflow:hidden;text-overflow:ellipsis;white-space:nowrap">'+(card.group?card.label+' >':card.label)+'</div>'+ '<div style="flex:1;min-width:0"><div style="font-weight:600;font-size:13px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap">'+(cd.gr?cd.l+' >':cd.l)+'</div>'+
'<div class="sublabel">'+card.desc.fr+'</div></div></div>'+ '<div class="sl">'+cd.d.fr+'</div></div></div>'+
'<div class="flex items-center gap-2 text-xs">'+(cnt>0?'<span style="font-weight:600;color:#0f172a">'+cnt+'</span><span style="color:#94a3b8">commandes</span>':'<span style="color:#cbd5e1">'+(ph?'A venir':'via sidebar')+'</span>')+'</div></div>'; '<div style="display:flex;gap:8px;font-size:11px">'+(cnt>0?'<span style="font-weight:600;color:#0f172a">'+cnt+'</span><span style="color:#94a3b8">commandes</span>':'<span style="color:#cbd5e1">'+(ph?'A venir':'via sidebar')+'</span>')+'</div></div>';
cats[card.cat].html+=h cats[cd.cat].h+=h
}); });
var html=''; var html='';
Object.keys(cats).forEach(function(k){html+='<div class="category-label">'+cats[k].label.fr+'</div>'+cats[k].html}); Object.keys(cats).forEach(function(k){html+='<div class="cl">'+cats[k].l.fr+'</div>'+cats[k].h});
$('card-grid').innerHTML=html; $('grid').innerHTML=html;
// Bind clicks
// Click handlers $('grid').querySelectorAll('[data-card]').forEach(function(el){
$('card-grid').querySelectorAll('.os-card').forEach(function(el,i){
var card=CARDS[i%CARDS.length]; // simplified
});
// Re-bind properly
var idx=0;
$('card-grid').querySelectorAll('.os-card').forEach(function(el){
var card=CARDS[idx++];
if(!card)return;
el.onclick=function(){ el.onclick=function(){
var n=findNode(TREE,card.id); var id=el.dataset.card,cd=null;
if(card.group){if(n&&n.children&&n.children.length>0)selectNode(n.children[0])} for(var i=0;i<CARDS.length;i++)if(CARDS[i].id===id){cd=CARDS[i];break}
else if(n)selectNode(n) if(!cd)return;
var nd=FN(TREE,cd.id);
if(cd.gr&&nd&&nd.children&&nd.children.length>0)S(nd.children[0]);
else if(nd)S(nd)
} }
}) })
} }
function showCmds(commands){ function SC(cmds){
var el=$('cmds'),sv=$('search').value.trim().toLowerCase(); var el=$('cmds'),sv=$('search').value.trim().toLowerCase();
var cmds=sv?commands.filter(function(x){return x.d.fr.toLowerCase().indexOf(sv)!==-1||x.d.en.toLowerCase().indexOf(sv)!==-1||x.c.toLowerCase().indexOf(sv)!==-1}):commands; var c2=sv?cmds.filter(function(x){return x.d.fr.indexOf(sv)!==-1||x.d.en.indexOf(sv)!==-1||x.c.indexOf(sv)!==-1}):cmds;
$('shown').textContent=''+cmds.length; $('shown').textContent=''+c2.length;
if(cmds.length===0){el.innerHTML='<div class="p-8 text-center text-sm" style="color:#94a3b8">Aucune commande trouvee</div>';return} if(c2.length===0){el.innerHTML='<div class="p8">Aucune commande trouvee</div>';return}
el.innerHTML=''; el.innerHTML='';
cmds.forEach(function(x,i){ c2.forEach(function(x,i){
var row=document.createElement('div');row.className='cmd-row'+(i%2===0?' bg-[#fafbfc]':''); var r=document.createElement('div');r.className='scmd'+(i%2===0?' alt':'');
var cmdSafe=x.c.replace(/"/g,'&quot;'); r.innerHTML='<div class="d">'+x.d.fr+'</div><div class="t"><span class="cp"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" width="14" height="14"><rect x="9" y="9" width="13" height="13" rx="2" ry="2"/><path d="M5 15H4a2 2 0 01-2-2V4a2 2 0 012-2h9a2 2 0 012 2v1"/></svg></span><span>'+x.c+'</span></div>';
row.innerHTML='<div class="cmd-desc">'+x.d.fr+'</div><div class="cmd-text"><span class="copy-icon"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" width="14" height="14"><rect x="9" y="9" width="13" height="13" rx="2" ry="2"/><path d="M5 15H4a2 2 0 01-2-2V4a2 2 0 012-2h9a2 2 0 012 2v1"/></svg></span><span>'+x.c+'</span></div>'; r.querySelector('.t').onclick=function(){
row.querySelector('.cmd-text').onclick=function(){
navigator.clipboard.writeText(x.c).then(function(){ navigator.clipboard.writeText(x.c).then(function(){
var icon=row.querySelector('.copy-icon'); var ic=r.querySelector('.cp');
icon.innerHTML='<svg viewBox="0 0 24 24" fill="none" stroke="#22c55e" stroke-width="2.5" width="14" height="14"><polyline points="20 6 9 17 4 12"/></svg>'; ic.innerHTML='<svg viewBox="0 0 24 24" fill="none" stroke="#22c55e" stroke-width="2.5" width="14" height="14"><polyline points="20 6 9 17 4 12"/></svg>';
setTimeout(function(){icon.innerHTML='<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" width="14" height="14"><rect x="9" y="9" width="13" height="13" rx="2" ry="2"/><path d="M5 15H4a2 2 0 01-2-2V4a2 2 0 012-2h9a2 2 0 012 2v1"/></svg>'},1200) setTimeout(function(){ic.innerHTML='<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" width="14" height="14"><rect x="9" y="9" width="13" height="13" rx="2" ry="2"/><path d="M5 15H4a2 2 0 01-2-2V4a2 2 0 012-2h9a2 2 0 012 2v1"/></svg>'},1200)
}) })
}; };
el.appendChild(row) el.appendChild(r)
}) })
} }
function onSearch(val){ function onSearch(v){
var fi=$('filter-info'); $('fi').textContent=v.trim()?'Filtre: "'+v+'"':'Aucun filtre';
fi.textContent=val.trim()?'Filtre: "'+val+'"':'Aucun filtre'; if(N&&N._sid){SC(SEC[N._sid].cmds);return}
if(currentNode&&currentNode._sectionId){showCmds(SEC[currentNode._sectionId].commands);return} if(N&&N.secs&&N.secs.length>0){SC(SEC[N.secs[0]].cmds);return}
if(currentNode&&currentNode.sectionIds&&currentNode.sectionIds.length>0){showCmds(SEC[currentNode.sectionIds[0]].commands);return} if(!N&&v.trim()){
// Global search on home var r=ALL.filter(function(x){return x.d.fr.indexOf(v.trim().toLowerCase())!==-1||x.d.en.indexOf(v.trim().toLowerCase())!==-1||x.c.indexOf(v.trim().toLowerCase())!==-1});
if(!currentNode&&val.trim()){ $('gs').style.display='block';
var results=ALL.filter(function(x){return x.d.fr.toLowerCase().indexOf(val.trim().toLowerCase())!==-1||x.d.en.toLowerCase().indexOf(val.trim().toLowerCase())!==-1||x.c.toLowerCase().indexOf(val.trim().toLowerCase())!==-1}); var h='<div class="cmdbox"><div class="s">'+r.length+' resultat(s)</div>';
var el=$('global-search-results');el.style.display='block'; if(r.length===0)h+='<div class="p8">Aucun resultat</div>';
el.innerHTML='<div class="bg-white border border-[#e2e8f0] rounded-xl overflow-hidden">'; else{r.forEach(function(x,i){
if(results.length===0){el.innerHTML+='<div class="p-8 text-center text-sm" style="color:#94a3b8">Aucun resultat</div>'} h+='<div class="scmd'+(i%2===0?' alt':'')+'"><div class="d">'+x.d.fr+'</div><div class="t"><span class="cp"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" width="14" height="14"><rect x="9" y="9" width="13" height="13" rx="2" ry="2"/><path d="M5 15H4a2 2 0 01-2-2V4a2 2 0 012-2h9a2 2 0 012 2v1"/></svg></span><span>'+x.c+'</span></div></div>'
else{ })}
el.firstChild.innerHTML='<div style="padding:8px 12px;font-size:0.6875rem;color:#94a3b8;border-bottom:1px solid #f1f5f9">'+results.length+' resultat(s)</div><div id="gcmds"></div>'; h+='</div>';$('gs').innerHTML=h;$('grid').style.display='none';$('stats-row').style.display='none'
var g=$('gcmds')||el.querySelector('#gcmds'); }else if(!N){$('gs').style.display='none';$('grid').style.display='grid';$('stats-row').style.display='grid'}
results.forEach(function(x,i){
var row=document.createElement('div');row.className='cmd-row'+(i%2===0?' bg-[#fafbfc]':'');
row.innerHTML='<div class="cmd-desc">'+x.d.fr+'</div><div class="cmd-text"><span class="copy-icon"><svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" width="14" height="14"><rect x="9" y="9" width="13" height="13" rx="2" ry="2"/><path d="M5 15H4a2 2 0 01-2-2V4a2 2 0 012-2h9a2 2 0 012 2v1"/></svg></span><span>'+x.c+'</span></div>';
row.querySelector('.cmd-text').onclick=function(){navigator.clipboard.writeText(x.c)};
g.appendChild(row)
})
}
el.innerHTML+='</div>';$('card-grid').style.display='none';$('stats-row').style.display='none'
}else if(!currentNode){$('global-search-results').style.display='none';$('card-grid').style.display='grid';$('stats-row').style.display='grid'}
} }
renderTree(); RT();
showHome(); SH();
</script> </script>
</body> </body>
</html> </html>