main
John Lauer web-control handoff: correct per ab#964 — no allowlist, works today; Quick Actions is a forum curation 9e5d46f 1mo ago
<!doctype html><html><head><meta charset="utf-8"><title>Altium web-control test</title>
<style>
body{font:14px system-ui;background:#0d1117;color:#e6edf3;max-width:760px;margin:40px auto;padding:0 16px}
h1{font-size:20px} code{background:#161b22;padding:2px 5px;border-radius:4px}
.row{display:flex;gap:10px;align-items:center;margin:14px 0}
button{background:#238636;color:#fff;border:0;border-radius:6px;padding:9px 18px;font-size:14px;cursor:pointer}
button:disabled{opacity:.5}
#log{background:#161b22;border:1px solid #30363d;border-radius:8px;padding:12px;white-space:pre-wrap;font:12px ui-monospace,monospace;min-height:120px}
#proof{max-width:100%;border:1px solid #30363d;border-radius:8px;margin-top:12px;display:none}
.dot{width:10px;height:10px;border-radius:50%;background:#6e7681;display:inline-block}
.dot.up{background:#3fb950}.dot.warn{background:#d29922}.dot.down{background:#f85149}
</style></head><body>
<h1>Altium web-control acceptance test</h1>
<p>Mirrors <code>AdomWebControl.installLibraryBundle</code> for the <b>altium</b> bridge: detect ab →
fetch a bundle → stage via <code>write_file_chunk</code> → call
<code>altium_install_library_bundle</code> → render the proof frame. Works <b>today</b> — ab has no per-verb allowlist (adom/adom-bridge#964): click the button,
then <b>Allow</b> on ab's consent prompt, and the LAN7800 bundle installs with a proof frame.</p>
<div class="row"><span id="dot" class="dot"></span><span id="st">Checking for Adom Bridge…</span></div>
<div class="row">
  <label>Bundle URL: <input id="zip" size="52" value="https://wiki.adom.inc/download/adom/altium-bridge/LAN7800-bundle.zip"></label>
  <label>Library: <input id="lib" size="10" value="LAN7800"></label>
</div>
<div class="row"><button id="go" disabled>Add to Altium library</button></div>
<div id="log">—</div>
<img id="proof" alt="proof frame">
<script src="https://wiki.adom.inc/static/webcontrol.js"></script>
<script>
const $=id=>document.getElementById(id), log=m=>{$('log').textContent+='\n'+m};
const W=window.AdomWebControl;
function say(m){log('· '+m)}
W.detect().then(s=>{
  $('dot').className='dot '+(s.ready?'up':s.running?'warn':'down');
  $('st').textContent=s.ready?('Adom Bridge connected'+(s.machine?' on '+s.machine:'')):
    s.running?'ab running, web control off (enable in ab Settings)':'ab not detected';
  $('go').disabled=!s.running;
  $('log').textContent='detect: '+JSON.stringify({running:s.running,ready:s.ready,port:s.port});
});
$('go').onclick=async()=>{
  $('go').disabled=true;$('proof').style.display='none';
  try{
    // identical to webcontrol.js Le(), with the altium verb
    log('fetching bundle…');
    const buf=await fetch($('zip').value,{credentials:'same-origin'}).then(r=>{if(!r.ok)throw new Error('bundle fetch '+r.status);return r.arrayBuffer()});
    log('staging '+buf.byteLength+' bytes via write_file (approve in ab)…');
    const b64=btoa(new Uint8Array(buf).reduce((a,b)=>a+String.fromCharCode(b),''));
    const st=await W.run('write_file',{path:'~/adom-wiki-libs/'+$('lib').value+'.zip',content:b64,encoding:'base64'});
    if(!st.ok)throw Object.assign(new Error(st.error),{code:st.code});
    const staged=(st.data&&st.data.path)||('~/adom-wiki-libs/'+$('lib').value+'.zip');
    log('staged: '+staged+'\ninstalling into Altium…');
    const r=await W.run('altium_install_library_bundle',{zipPath:staged,libraryName:$('lib').value,capture:true,captureMaxWidth:480});
    if(!r.ok)throw Object.assign(new Error(r.error),{code:r.code});
    const d=r.data||{};
    log('RESULT: '+JSON.stringify({success:d.success,symbols:d.symbols,footprints:d.footprints,installed:d.installed,restartNeeded:d.restartNeeded,proofSkipped:d.proofSkipped}));
    if(d.restartNeeded)log('Altium is open — it needs a restart to see the new library (the verb never closes it).');
    if(d.thumbnailDataUrl){$('proof').src=d.thumbnailDataUrl;$('proof').style.display='block';log('proof frame rendered ✓')}
  }catch(e){
    log('BLOCKED/FAILED: '+(e.code||'')+' '+e.message);
  }finally{$('go').disabled=false}
};
</script></body></html>