Download index.html from getreadystack/outlook-email-html-lint: direct link, hf CLI and curl.
- Browser
- Download file 39.7 kB
-
https://huggingface.co/spaces/getreadystack/outlook-email-html-lint/resolve/main/index.html
- Command line
-
hf download hf://spaces/getreadystack/outlook-email-html-lint/index.html
-
curl -L -o index.html https://huggingface.co/spaces/getreadystack/outlook-email-html-lint/resolve/main/index.html
39.7 kB
| <html lang="en"><meta charset="utf-8"> | |
| <meta name="viewport" content="width=device-width,initial-scale=1"> | |
| <title>Outlook Email HTML Lint - Classic vs New</title> | |
| <meta name="description" content="Classic Outlook renders with the Word engine, the new Outlook with WebView2. Lint one email file against both at once, line by line, before you send."> | |
| <style> | |
| :root{color-scheme:light dark} | |
| body{margin:0;font:16px/1.6 system-ui,-apple-system,"Segoe UI",sans-serif; | |
| background:#fbfbfa;color:#16161d} | |
| @media(prefers-color-scheme:dark){body{background:#14141a;color:#e8e8ea}} | |
| .wrap{max-width:880px;margin:0 auto;padding:28px 20px 64px} | |
| h1{font-size:1.7rem;line-height:1.25;margin:.2em 0 .3em} | |
| p.sub{margin:0 0 1.4em;opacity:.8} | |
| textarea{width:100%;min-height:230px;font:13px/1.5 ui-monospace,Menlo,Consolas,monospace; | |
| padding:12px;border:1px solid #c9c9d1;border-radius:10px;background:transparent;color:inherit; | |
| box-sizing:border-box} | |
| button{font:600 15px/1 inherit;padding:12px 22px;border:0;border-radius:10px; | |
| background:#1d4ed8;color:#fff;cursor:pointer;margin:12px 0} | |
| button:hover{background:#1a43bd} | |
| table{border-collapse:collapse;width:100%;margin-top:14px;font-size:14px} | |
| th,td{border-bottom:1px solid #d8d8e0;padding:8px 6px;text-align:left;vertical-align:top} | |
| th{font-weight:600;opacity:.75} | |
| td.n{width:64px;font:13px ui-monospace,monospace;opacity:.7} | |
| .ok{padding:14px;border-radius:10px;background:#e8f5ec;color:#14532d;margin-top:14px} | |
| @media(prefers-color-scheme:dark){.ok{background:#15321f;color:#bbf7d0}} | |
| .next{margin-top:30px;padding:18px;border:1px solid #d8d8e0;border-radius:12px} | |
| .next h2{font-size:1.05rem;margin:0 0 .5em} | |
| .next ul{margin:.3em 0 1em 1.1em;padding:0} | |
| </style> | |
| <div class="wrap"> | |
| <h1>Outlook Email HTML Lint - Classic vs New</h1> | |
| <p class="sub">Classic Outlook renders with the Word engine, the new Outlook with WebView2. Lint one email file against both at once, line by line, before you send.</p> | |
| <textarea id="src" placeholder="Paste the file here"></textarea> | |
| <button id="go">Check</button> | |
| <div id="out"></div> | |
| <div class="next"><h2>In the full version</h2><ul><li>Scan the whole template library</li><li>Export a report you can hand over</li><li>CI output</li><li><a href="https://getreadystack.com/api/buy/cl/polar_cl_0zZyRdFLtRxDC42FwytNvrE9IKgRLFcSm8ED044gS16">Get the full version - $29 once, not $99/month</a></li></ul></div> | |
| </div> | |
| <script> | |
| var RULES=[{"pattern": "display\\s*:\\s*flex", "flags": "i", "message": "classic Outlook: classic Outlook (Word engine) ignores display:flex - the row collapses into stacked blocks.", "fix": "Lay the row out with <table role=\"presentation\"><tr><td>.", "sev": "error"}, {"pattern": "(flex-direction|justify-content|align-items|flex-wrap)\\s*:", "flags": "i", "message": "classic Outlook: flexbox property is ignored by the Word engine in classic Outlook.", "fix": "Use table cells with align/valign attributes.", "sev": "error"}, {"pattern": "display\\s*:\\s*(inline-)?grid|grid-template", "flags": "i", "message": "classic Outlook: CSS grid is not supported by classic Outlook (Word engine).", "fix": "Rebuild the grid as nested tables.", "sev": "error"}, {"pattern": "(^|[;\"\\x27\\s])gap\\s*:", "flags": "i", "message": "classic Outlook: gap is ignored by the Word engine - your columns will touch.", "fix": "Add a spacer <td width=\"20\"> between columns.", "sev": "warn"}, {"pattern": "max-width\\s*:", "flags": "i", "message": "classic Outlook: classic Outlook ignores max-width and renders the element at full width.", "fix": "Set width=\"600\" as an HTML attribute on the table.", "sev": "error"}, {"pattern": "<div[^>]*style=\"[^\"]*padding", "flags": "i", "message": "classic Outlook: padding on a <div> is dropped by the Word engine.", "fix": "Move the padding onto the surrounding <td>.", "sev": "error"}, {"pattern": "border-radius\\s*:", "flags": "i", "message": "classic Outlook: border-radius is ignored in classic Outlook - the corners render square.", "fix": "Accept square corners there, or draw the button with VML.", "sev": "warn"}, {"pattern": "box-shadow\\s*:|text-shadow\\s*:", "flags": "i", "message": "classic Outlook: shadows are not rendered by the Word engine.", "fix": "Use a solid border instead.", "sev": "warn"}, {"pattern": "position\\s*:\\s*(absolute|fixed|sticky)", "flags": "i", "message": "classic Outlook: CSS positioning is not supported by classic Outlook.", "fix": "Use table layout - overlap is not achievable there.", "sev": "error"}, {"pattern": "float\\s*:\\s*(left|right)", "flags": "i", "message": "classic Outlook: float is unreliable in the Word engine.", "fix": "Use table cells side by side.", "sev": "warn"}, {"pattern": "background(-image)?\\s*:\\s*(url\\(|linear-gradient|radial-gradient)", "flags": "i", "message": "classic Outlook: CSS background images and gradients do not render in classic Outlook.", "fix": "Add a VML v:rect fallback, and set a solid bgcolor.", "sev": "error"}, {"pattern": "opacity\\s*:|transform\\s*:|filter\\s*:", "flags": "i", "message": "classic Outlook: opacity/transform/filter are not supported by the Word engine.", "fix": "Bake the effect into the image instead.", "sev": "warn"}, {"pattern": "object-fit\\s*:", "flags": "i", "message": "classic Outlook: object-fit is ignored - the image will stretch in classic Outlook.", "fix": "Crop the image to its final ratio before export.", "sev": "warn"}, {"pattern": "<svg", "flags": "i", "message": "classic Outlook: classic Outlook does not render inline SVG - the graphic disappears.", "fix": "Export the SVG to PNG and reference it with <img>.", "sev": "error"}, {"pattern": "<(video|audio|iframe|canvas|form|script)\\b", "flags": "i", "message": "classic Outlook: this element is stripped by Outlook and most other mail clients.", "fix": "Link out to a hosted page instead.", "sev": "error"}, {"pattern": "@media", "flags": "i", "message": "classic Outlook: classic Outlook ignores media queries - it always sees the desktop rules.", "fix": "Make the desktop rules the safe default and let media queries only enhance.", "sev": "warn"}, {"pattern": ":\\s*-?[\\d.]+(vh|vw|rem|ch)\\b", "flags": "i", "message": "classic Outlook: viewport and root-relative units are not supported by the Word engine.", "fix": "Use px.", "sev": "error"}, {"pattern": "(color|background-color)\\s*:\\s*(rgba|hsla?)\\(", "flags": "i", "message": "classic Outlook: rgba/hsl colours (and alpha) are not understood by classic Outlook.", "fix": "Use a 6-digit hex colour.", "sev": "warn"}, {"pattern": "<(section|article|header|footer|main|aside|nav|figure)\\b", "flags": "i", "message": "classic Outlook: semantic HTML5 elements get no layout from the Word engine.", "fix": "Wrap the content in a table instead.", "sev": "warn"}, {"pattern": "<img(?![^>]*\\swidth\\s*=)[^>]*>", "flags": "i", "message": "classic Outlook: an <img> with no width attribute is scaled unpredictably by classic Outlook.", "fix": "Add width=\"...\" as an HTML attribute, not only in CSS.", "sev": "error"}, {"pattern": "<img(?![^>]*\\salt\\s*=)[^>]*>", "flags": "i", "message": "classic Outlook: an <img> with no alt text shows nothing - Outlook blocks images by default.", "fix": "Add alt=\"...\" describing the image.", "sev": "error"}, {"pattern": "line-height\\s*:(?![^;]*mso-line-height-rule)", "flags": "i", "message": "classic Outlook: the Word engine inflates line-height unless mso-line-height-rule is set.", "fix": "Add mso-line-height-rule:exactly; alongside it.", "sev": "warn"}, {"pattern": "<script data-grow-initializer="">!(function(){window.growMe||((window.growMe=function(e){window.growMe._.push(e);}),(window.growMe._=[]));var e=document.createElement("script");(e.type="text/javascript"),(e.src="https://faves.grow.me/main.js"),(e.defer=!0),e.setAttribute("data-grow-faves-site-id","U2l0ZTphZjljMzgyMC0yMmU5LTRhYjgtYTIxNS03OTRhMGY1N2ExYzM=");var t=document.getElementsByTagName("script")[0];t.parentNode.insertBefore(e,t);})();</script> | |
| <!--yj-canon-s101--><link rel="canonical" href="https://getreadystack.com/tools/outlook-email-html-lint"><body[^>]*style=\"[^\"]*background", "flags": "i", "message": "classic Outlook: classic Outlook ignores a background set on <body>.", "fix": "Wrap everything in a width=\"100%\" table carrying bgcolor.", "sev": "warn"}, {"pattern": "<table(?![^>]*role\\s*=)", "flags": "i", "message": "classic Outlook: a layout <table> without role=\"presentation\" is announced as a data table by screen readers.", "fix": "Add role=\"presentation\".", "sev": "warn"}, {"pattern": "<v:(roundrect|rect|shape|fill|textbox|image|background)", "flags": "i", "message": "new Outlook: VML is NOT rendered by the new Outlook (WebView2) - this button or background silently disappears there.", "fix": "Keep the VML for classic, but put a real HTML/CSS version outside the mso conditional.", "sev": "error"}, {"pattern": "xmlns:(v|o|w)\\s*=", "flags": "i", "message": "new Outlook: VML namespaces declared - this file targets classic Outlook only; check the new Outlook path too.", "fix": "Verify the non-VML fallback renders on its own.", "sev": "warn"}, {"pattern": "<!--\\s*\\[if\\s+(gte\\s+|lte\\s+|lt\\s+|gt\\s+|!)?mso", "flags": "i", "message": "new Outlook: mso conditional comments are not processed by the new Outlook - anything living only inside this block will not appear.", "fix": "Make sure the content also exists outside the conditional.", "sev": "error"}, {"pattern": "mso-[a-z-]+\\s*:", "flags": "i", "message": "new Outlook: mso- properties are inert in the new Outlook (WebView2).", "fix": "Ensure a standard CSS equivalent is present as well.", "sev": "warn"}, {"pattern": "(?=[^<]*unsubscribe)(?=.*mailto:)", "flags": "i", "message": "before you send: a mailto-only unsubscribe does not satisfy the Gmail/Yahoo one-click unsubscribe requirement (RFC 8058) for bulk senders.", "fix": "Add an https List-Unsubscribe URL plus the List-Unsubscribe-Post header.", "sev": "error"}, {"pattern": "href\\s*=\\s*[\"\\x27]#[\"\\x27]", "flags": "i", "message": "before you send: placeholder href=\"#\" left in - if this is the unsubscribe or preference link, the opt-out is dead.", "fix": "Point it at the real URL before sending.", "sev": "error"}, {"pattern": "\\{\\{[^}]+\\}\\}|%%[A-Z_]+%%|\\*\\|[A-Z_]+\\|\\*|\\[\\[[A-Z_]+\\]\\]", "flags": "i", "message": "before you send: an unresolved merge tag would be sent literally to the whole list.", "fix": "Confirm your ESP replaces this token, or remove it.", "sev": "error"}, {"pattern": "(src|href)\\s*=\\s*[\"\\x27]http://", "flags": "i", "message": "before you send: a non-TLS http:// asset or link - images get blocked and the link is flagged.", "fix": "Serve it over https://.", "sev": "error"}, {"pattern": "(localhost|127\\.0\\.0\\.1|staging\\.|\\.local/|file:///|example\\.com)", "flags": "i", "message": "before you send: a development URL is still in the file - it will be broken for every recipient.", "fix": "Swap in the production URL.", "sev": "error"}]; | |
| function scan(t){var L=String(t).split(/\r?\n/),h=[],i,r,re; | |
| for(i=0;i<L.length;i++){for(var k=0;k<RULES.length;k++){r=RULES[k]; | |
| try{re=new RegExp(r.pattern,r.flags||'')}catch(e){continue} | |
| if(re.test(L[i]))h.push({line:i+1,msg:r.message})}} | |
| return h} | |
| document.getElementById('go').onclick=function(){ | |
| var t=document.getElementById('src').value,o=document.getElementById('out'); | |
| if(!t.trim()){o.innerHTML='';return} | |
| var h=scan(t); | |
| if(!h.length){o.innerHTML='<div class="ok">Nothing found - this file is clean for both Outlook engines</div>';return} | |
| var s='<table><tr><th>Line</th><th>Finding</th></tr>'; | |
| for(var i=0;i<h.length;i++){s+='<tr><td class="n">'+h[i].line+'</td><td>'+ | |
| String(h[i].msg).replace(/&/g,'&').replace(/</g,'<')+'</td></tr>'} | |
| o.innerHTML=s+'</table>'}; | |
| </script> | |
| </html> | |
| <section data-yj-install="free" style="margin:2rem auto 1rem;max-width:46rem;padding:1.25rem 1.25rem;border:1px solid #cfe3d6;border-radius:12px;background:#f6fbf8;font:16px/1.6 system-ui,-apple-system,Segoe UI,sans-serif"><h2 style="margin:0 0 .4rem;font-size:1.2rem">Install free</h2><p style="margin:0 0 .8rem;color:#41505f">Free for the file open in your editor - no key, no limit. The workspace sweep and the report ask for a key.</p><a href="https://www.npmjs.com/package/@readystack/outlook-email-html-lint" rel="noopener" data-yj-install-door="npm" onclick="try{navigator.sendBeacon('/api/ev',new Blob([JSON.stringify({t:'install',slug:'outlook-email-html-lint',src:'npm',path:location.pathname})],{type:'application/json'}))}catch(e){}" style="display:inline-block;margin:0 .5rem .5rem 0;padding:.6rem 1rem;border-radius:8px;background:#0f7b3f;color:#fff;text-decoration:none;font-weight:600">npm</a><a href="https://www.npmjs.com/package/@readystack/outlook-email-html-lint" rel="noopener" data-yj-install-door="mcp" onclick="try{navigator.sendBeacon('/api/ev',new Blob([JSON.stringify({t:'install',slug:'outlook-email-html-lint',src:'mcp',path:location.pathname})],{type:'application/json'}))}catch(e){}" style="display:inline-block;margin:0 .5rem .5rem 0;padding:.6rem 1rem;border-radius:8px;background:#0f7b3f;color:#fff;text-decoration:none;font-weight:600">MCP server (npx)</a><a href="https://hub.docker.com/r/getreadystack/outlook-email-html-lint" rel="noopener" data-yj-install-door="docker" onclick="try{navigator.sendBeacon('/api/ev',new Blob([JSON.stringify({t:'install',slug:'outlook-email-html-lint',src:'docker',path:location.pathname})],{type:'application/json'}))}catch(e){}" style="display:inline-block;margin:0 .5rem .5rem 0;padding:.6rem 1rem;border-radius:8px;background:#0f7b3f;color:#fff;text-decoration:none;font-weight:600">Docker Hub</a><pre style="margin:.5rem 0 0;padding:.6rem .8rem;background:#f3f5f8;border-radius:8px;font-size:.9rem;overflow:auto">npx @readystack/outlook-email-html-lint <file> | |
| npx @readystack/outlook-email-html-lint --mcp | |
| docker run --rm -v "$PWD:/w" getreadystack/outlook-email-html-lint /w</pre><p style="margin:.6rem 0 0;font-size:.92rem;color:#41505f"><a href="https://getreadystack.com/api/buy/cl/polar_cl_l6iN1uWt0FwWu7tBsczD0jWpP2vxFM54Wdwqb3KPi1G" rel="nofollow" style="color:#0f7b3f;text-decoration:underline">Team? One key for every ReadyStack linter, 5 seats, $149 once</a></p></section> | |
| <section data-yj-alert="rule" style="margin:1rem auto 1.5rem;max-width:46rem;padding:1.1rem 1.25rem;border:1px solid #d9dee6;border-radius:12px;background:#fbfcfd;font:15px/1.55 system-ui,-apple-system,Segoe UI,sans-serif"><b style="font-size:1.05rem">Get the full rule table as a PDF</b><div style="opacity:.78;margin:.35rem 0 .8rem">All 33 rules Outlook Email HTML Lint - Classic vs New checks, each with its source and date, on printable pages you can hand to your team or auditor. We email it now, and once more only if a rule changes. No newsletter.</div><div style="display:flex;gap:8px;flex-wrap:wrap"><input id="yjae" type="email" placeholder="you@example.com" style="flex:1;min-width:210px;padding:11px 13px;border:1px solid rgba(140,150,165,.34);border-radius:8px;background:#fff;color:inherit"><button id="yjab" style="padding:11px 18px;border-radius:8px;border:0;cursor:pointer;background:#0f7b3f;color:#fff;font:600 15px system-ui,sans-serif">Email me the PDF</button></div><div id="yjao" hidden style="margin-top:.6rem;color:#0f7b3f">Sent. It arrives within the hour - check spam too.</div><script>(function(){var b=document.getElementById("yjab"),e=document.getElementById("yjae");if(!b||!e)return;b.addEventListener("click",function(){var v=e.value.trim();if(!/.+@.+\..+/.test(v))return;try{localStorage.setItem("yj_em","1");}catch(_){}fetch(location.origin+"/api/subscribe",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({email:v,slug:"outlook-email-html-lint",lang:"en",source:"rule_table"+((b.closest&&b.closest("section")&&b.closest("section").getAttribute("data-yj-moved"))?"_at_result":"")})}).then(function(r){var o=document.getElementById("yjao");o.hidden=false;if(!r.ok){o.textContent="Could not save - please try again.";}}).catch(function(){var o=document.getElementById("yjao");o.hidden=false;o.textContent="Could not save - please try again.";});});})();</script><script>(function(){var e=document.getElementById("yjae"),s=e&&e.closest?e.closest("section"):null,o=document.getElementById("out");if(!s||!o)return;var d=false;function mv(ev){if(d)return;if(ev&&ev.target&&s.contains(ev.target))return;d=true;var b=o;while(b.parentNode&&b.parentNode!==document.body&&b.parentNode.tagName!=="MAIN"&&b.parentNode.tagName!=="ARTICLE")b=b.parentNode;if(!b.parentNode||b===s||b.contains(s))return;try{b.parentNode.insertBefore(s,b.nextSibling);s.setAttribute("data-yj-moved","1");}catch(_){}}document.addEventListener("input",mv,true);document.addEventListener("change",mv,true);})();</script></section> | |
| <section data-yj-cta="paid" style="margin:3rem auto;max-width:46rem;padding:1.5rem 1.25rem;border:1px solid #d8dee9;border-radius:12px;background:#fbfcfe;font:16px/1.6 system-ui,-apple-system,Segoe UI,sans-serif"><h2 style="margin:0 0 .5rem;font-size:1.25rem">Get the complete version <span class="yj-price">$29</span></h2><p style="margin:.25rem 0 1rem;color:#41505f">This page is the working piece. The full pack has everything below.</p><p style="margin:0 0 1rem;color:#41505f">Classic Outlook renders with the Word engine, the new Outlook with WebView2. Lint one email file against both at once, line by line, before you send.</p><p style="margin:0 0 1rem;color:#5b6b7c;font-size:.94rem">Email on Acid Basics is $99/month and Litmus Core starts at $500/month (checked 2026-09-07).</p><a href="https://getreadystack.com/api/buy/cl/polar_cl_0zZyRdFLtRxDC42FwytNvrE9IKgRLFcSm8ED044gS16" rel="nofollow" style="display:inline-block;padding:.7rem 1.3rem;border-radius:8px;background:#1b64f2;color:#fff;text-decoration:none;font-weight:600">Buy the full version — $29</a></section> | |
| <!--yj-share-s101--><div style="margin:28px 0 8px;text-align:center"><button id="yjcp" type="button" style="font:inherit;padding:10px 18px;border:1px solid #8884;border-radius:10px;background:transparent;cursor:pointer">Copy link</button><button id="yjimg" type="button" style="font:inherit;padding:10px 18px;margin-left:8px;border:1px solid #8884;border-radius:10px;background:transparent;cursor:pointer">Save result as image</button></div><script>(function(){var b=document.getElementById("yjimg");if(!b)return;b.addEventListener("click",function(){var o=document.getElementById("out");var txt=(o&&(o.innerText||o.textContent)||"").trim();if(!txt){b.textContent="(no result yet)";setTimeout(function(){b.textContent="Save result as image";},1500);return;}var lines=txt.split(String.fromCharCode(10)).filter(function(x){return x.trim();}).slice(0,10);var W=1200,P=56,c=document.createElement("canvas");c.width=W;var lh=38,H=P*2+70+lines.length*lh+60;c.height=H;var x=c.getContext("2d");x.fillStyle="#1a1512";x.fillRect(0,0,W,H);x.fillStyle="#f3e9d2";x.font="600 34px system-ui,Segoe UI,Arial";var t=(document.title||"").split("|")[0].trim();x.fillText(t.slice(0,54),P,P+34);x.font="22px ui-monospace,Menlo,Consolas,monospace";x.fillStyle="#e8dcc4";for(var i=0;i<lines.length;i++){x.fillText(lines[i].slice(0,88),P,P+70+i*lh+22);}x.font="600 22px system-ui,Segoe UI,Arial";x.fillStyle="#c9a227";var d=location.hostname.replace("www.","");x.fillText(d,W-P-x.measureText(d).width,H-P+6);c.toBlob(function(bl){var u=URL.createObjectURL(bl),a=document.createElement("a");a.href=u;a.download=(t||"result").replace(/[^a-z0-9]+/gi,"-").toLowerCase()+"-"+d+".png";document.body.appendChild(a);a.click();setTimeout(function(){URL.revokeObjectURL(u);a.remove();},2000);},"image/png");});})();</script><script>(function(){var b=document.getElementById("yjcp");if(!b)return;var t=b.textContent;b.addEventListener("click",function(){var u=location.href.split("#")[0];function d(){b.textContent="Link copied";setTimeout(function(){b.textContent=t;},1800);}if(navigator.clipboard&&navigator.clipboard.writeText){navigator.clipboard.writeText(u).then(d,function(){prompt("",u);});}else{prompt("",u);}});})();</script><div class="yj-home-find"><div class="yj-lgbar"><a href="/" class="yj-lg on">EN</a><a href="/de/" class="yj-lg">DE</a><a href="/ja/" class="yj-lg">JA</a><a href="/es/" class="yj-lg">ES</a><a href="/pt/" class="yj-lg">PT</a></div><section class="yj-find"><h2>Find a tool</h2><input id="yjq" type="search" autocomplete="off" placeholder="Type a product name, format or task"><div id="yjr"></div></section><style>.yj-lgbar{position:absolute;top:14px;right:18px;display:flex;gap:6px;z-index:60}.yj-lg{font:600 12px/1 system-ui,sans-serif;padding:6px 9px;border-radius:4px;text-decoration:none;color:#8b96a3;border:1px solid rgba(140,150,165,.28)}.yj-lg:hover{color:#e8eaed;border-color:rgba(160,175,195,.6)}.yj-lg.on{color:#0e1116;background:#cfd6de;border-color:#cfd6de}.yj-find{max-width:760px;margin:34px auto 8px;padding:0 20px}.yj-find h2{font:600 20px/1.3 system-ui,sans-serif;margin:0 0 10px}#yjq{width:100%;box-sizing:border-box;padding:13px 15px;font:400 15.5px system-ui,sans-serif;border:1px solid rgba(140,150,165,.34);border-radius:8px;background:rgba(255,255,255,.04);color:inherit}#yjq:focus{outline:none;border-color:#7FD1C4}#yjr{margin-top:10px;display:flex;flex-direction:column;gap:6px}#yjr a{display:flex;justify-content:space-between;gap:12px;padding:11px 14px;border:1px solid rgba(140,150,165,.22);border-radius:6px;text-decoration:none;font:400 14.5px/1.4 system-ui,sans-serif;color:inherit}#yjr a:hover{border-color:#7FD1C4}#yjr .pr{font:600 13px system-ui,sans-serif;color:#5fbf9a;white-space:nowrap}</style><script>(function(){var q=document.getElementById("yjq"),r=document.getElementById("yjr"),D=null;function load(){if(D)return Promise.resolve(D);return fetch("/search-index.json").then(function(x){return x.json();}).then(function(j){D=j;return j;}).catch(function(){D=[];return D;});}function esc(t){return String(t).replace(/[&<>"]/g,function(c){return {"&":"&","<":"<",">":">",'"':"""}[c];});}function run(){var v=q.value.trim().toLowerCase();if(v.length<2){r.innerHTML="";return;}load().then(function(j){var w=v.split(/\s+/),o=[];for(var i=0;i<j.length&&o.length<12;i++){var t=j[i].t.toLowerCase();var ok=true;for(var k=0;k<w.length;k++){if(t.indexOf(w[k])<0){ok=false;break;}}if(ok)o.push(j[i]);}r.innerHTML=o.length?o.map(function(x){return "<a href=\""+esc(x.u)+"\">"+"<span>"+esc(x.t)+"</span>"+(x.p?"<span class=\"pr\">$"+x.p+"</span>":"")+"</a>";}).join(""):"";});}q.addEventListener("input",run);q.addEventListener("focus",load);})();</script></div> | |
| <script data-yj="yj-view-beacon">(function(){try{var p=location.pathname;var k='yjv:'+p;if(sessionStorage.getItem(k))return;sessionStorage.setItem(k,'1');fetch('/api/ev',{method:'POST',keepalive:true,headers:{'Content-Type':'application/json'},body:JSON.stringify({path:p,lang:"en",ref:(document.referrer||''),src:(function(){try{return (new URLSearchParams(location.search).get('ref')||'').replace(/[^a-z_]/g,'').slice(0,12)}catch(e){return ''}})()})}).catch(function(){});}catch(e){}})();</script> | |
| <script data-yj="yj-use-beacon">(function(){try{var o=document.getElementById('out');if(!o)return;var p=location.pathname,k='yju:'+p,sent=false;function fire(){if(sent||sessionStorage.getItem(k))return;if(!(o.textContent||'').replace(/\s+/g,'').length)return;sent=true;sessionStorage.setItem(k,'1');fetch('/api/ev',{method:'POST',keepalive:true,headers:{'Content-Type':'application/json'},body:JSON.stringify({path:p,lang:"en",t:'use',src:(function(){try{return (new URLSearchParams(location.search).get('ref')||'').replace(/[^a-z_]/g,'').slice(0,12)}catch(e){return ''}})()})}).catch(function(){});}var mo=new MutationObserver(function(){fire();if(sent)mo.disconnect();});mo.observe(o,{childList:true,characterData:true,subtree:true});}catch(e){}})();</script> | |
| <section data-yj="yj-facts-v1" style="max-width:920px;margin:48px auto 0;padding:0 20px;font-family:system-ui,sans-serif"><style>.yj-article p{font:400 15.5px/1.7 system-ui,sans-serif;color:#26313b;margin:0 0 12px;max-width:72ch}.yj-article h2,.yj-article h3,.yj-article h4{font:600 17px/1.35 system-ui,sans-serif;color:#1b1f24;margin:22px 0 8px}.yj-article table{border-collapse:collapse;margin:10px 0 16px;font:14px/1.45 system-ui,sans-serif}.yj-article th,.yj-article td{border:1px solid #e2e6ea;padding:6px 10px;text-align:left}.yj-article th{background:#f4f6f8}.yj-article pre{background:#0f1720;color:#e6edf3;padding:12px 14px;border-radius:8px;overflow:auto;font:13px/1.5 ui-monospace,Menlo,monospace}.yj-article code{font:13px ui-monospace,Menlo,monospace;background:#f1f3f5;padding:1px 4px;border-radius:3px}.yj-article pre code{background:none;padding:0}.yj-article ul,.yj-article ol{font:15px/1.6 system-ui,sans-serif;color:#26313b}</style><p style="font:400 13px/1.5 system-ui,sans-serif;color:#6b7680;margin:0 0 14px"><time datetime="2026-09-07">Updated 2026-09-07</time> · ReadyStack</p><script type="application/ld+json">{"@context":"https://schema.org","@type":"WebPage","dateModified":"2026-09-07","author":{"@type":"Organization","name":"ReadyStack"}}</script><h2 style="font:600 21px/1.3 system-ui,sans-serif;margin:0 0 6px;color:#1b1f24">Worked example</h2><p style="font:400 14.5px/1.5 system-ui,sans-serif;margin:0 0 16px;color:#5b6570">Real numbers from this tool, line by line.</p><div class="yj-article"><p><img src="https://getreadystack.com/img/promo/sku8261_result_card.jpg" alt="Outlook Email HTML Lint - Classic vs New" loading="lazy" style="max-width:100%;border-radius:6px"></p> | |
| <h3>There are two Outlooks now, and they disagree</h3> | |
| <pre><code> 12 classic Outlook: display:flex is ignored by the Word engine - the row collapses | |
| 12 classic Outlook: max-width is ignored - the element renders at full width | |
| 13 classic Outlook: an <img> with no width attribute is scaled unpredictably | |
| 14 before you send: an unresolved merge tag would be sent literally to the whole list | |
| 31 new Outlook: VML is NOT rendered by WebView2 - this button disappears there | |
| 38 before you send: a mailto-only unsubscribe fails the Gmail and Yahoo one-click rule</code></pre> | |
| <p>That is one campaign template, checked in the editor before it went out: six findings — three from classic Outlook, one from the new Outlook, and two that would have gone out to the whole list. Every one of them renders clean in a browser preview.</p> | |
| <p>Here is the block those first findings point at:</p> | |
| <pre><code><div style="display:flex; gap:16px; max-width:600px"> | |
| <img src="https://cdn.acme.org/logo.png"> | |
| <p style="border-radius:8px">Hi {{first_name}}</p> | |
| </div></code></pre> | |
| <p>VS Code's Live Preview, your browser, and every free HTML validator render that with one modern engine, and it looks right. Classic Outlook for Windows does not use a modern engine. It renders your email with <strong>Microsoft Word</strong>, which has no flexbox, no grid, no <code>gap</code>, no <code>max-width</code>, and which throws away padding you put on a <code><div></code>. So it arrives as a full-width stack of blocks, with square corners, an image scaled to something you did not choose — and, if your ESP did not fill it, the literal text <code>{{first_name}}</code> in front of everyone on the list.</p> | |
| <h4>The half nobody lints</h4> | |
| <p>Here is the part that is new in 2026. The *new* Outlook for Windows does not use the Word engine either. It uses Edge <strong>WebView2</strong>, so modern CSS mostly works. Good news — except that everything you added to survive classic Outlook now becomes the bug.</p> | |
| <p><strong>VML is not rendered by WebView2.</strong> The <code><v:roundrect></code> you used to get a rounded button in classic Outlook is simply not drawn in the new Outlook. If your real button lives only inside <code><!--[if mso]>...<![endif]--></code>, new-Outlook readers see a gap where your call to action used to be. No error, no warning. Just a missing button. That is line 31 above.</p> | |
| <p>Microsoft ends support for the Word-engine Outlook in <strong>October 2026</strong>. But classic remains the enterprise default into 2027 — which means for this stretch you are not migrating from one engine to the other, you are shipping to <strong>both at the same time</strong>.</p> | |
| <p>That is the awkward window, and it is exactly where an AI assistant will steer you wrong. Ask one whether Outlook supports flexbox and you will get a confident answer that is either two years stale ("use tables, Outlook uses Word") or two years early ("new Outlook uses WebView2, modern CSS is fine"). Today, both answers ship a broken email — and an email is the one artifact you cannot recall after you press send.</p> | |
| <h4>What this does</h4> | |
| <p>Outlook Split Lint reads the file you have open and marks every line, saying which engine breaks on it and what to do instead. 33 rules in three groups: classic Outlook (Word engine), new Outlook (WebView2), and before-you-send checks — a dead <code>href="#"</code> opt-out, a mailto-only unsubscribe that fails the Gmail and Yahoo one-click requirement under RFC 8058, unresolved merge tags, <code>http://</code> assets, staging URLs.</p> | |
| <p>Opening a file and checking it is free, with no key and no limit — every rule, every finding, every suggested fix. That job finishes on its own.</p> | |
| <p>What it does not do for free is the *next* job: you have a whole template library, not one file, and a client who wants the sign-off in writing. The licence scans the whole library in a pass, exports the report as CSV, JSON or HTML, and gives CI machine-readable output so a broken template never reaches the send window. That is $29, once. Email on Acid Basics is $99/month and Litmus Core starts at $500/month (checked 2026-09-07).</p></div><h2 style="font:600 19px/1.3 system-ui,sans-serif;margin:30px 0 10px;color:#1b1f24">15 seconds — what it actually does</h2><video controls muted playsinline preload="none" poster="/img/promo/sku8261_result_card.jpg" style="width:100%;max-width:360px;border-radius:10px;display:block;margin:0 auto"><source src="/media/sku8261_short.mp4" type="video/mp4"></video><h2 style="font:600 21px/1.3 system-ui,sans-serif;margin:34px 0 6px;color:#1b1f24">Questions people ask</h2><details style="border-bottom:1px solid #e6e9ed;padding:10px 0"><summary style="cursor:pointer;font:600 15px/1.4 system-ui,sans-serif;color:#1b1f24">What does Outlook Split Lint actually do?</summary><p style="margin:8px 0 2px;font:400 14.5px/1.6 system-ui,sans-serif;color:#33404b">It reads an HTML email file and marks every line that breaks in Outlook, saying which of the two Outlooks breaks on it. Classic Outlook for Windows renders with the Microsoft Word engine; the new Outlook renders with Edge WebView2. Thirty-three rules cover both engines plus before-you-send checks, each with a suggested fix.</p></details><details style="border-bottom:1px solid #e6e9ed;padding:10px 0"><summary style="cursor:pointer;font:600 15px/1.4 system-ui,sans-serif;color:#1b1f24">Who is this for?</summary><p style="margin:8px 0 2px;font:400 14.5px/1.6 system-ui,sans-serif;color:#33404b">Email developers and agencies who hand-write or hand-fix HTML email and must support Outlook on Windows. It is most useful to anyone maintaining a template library through the 2026 to 2027 changeover, when classic Outlook and the new Outlook are both in the field and disagree with each other about the same markup.</p></details><details style="border-bottom:1px solid #e6e9ed;padding:10px 0"><summary style="cursor:pointer;font:600 15px/1.4 system-ui,sans-serif;color:#1b1f24">Why can't I just use a browser preview or a free HTML validator?</summary><p style="margin:8px 0 2px;font:400 14.5px/1.6 system-ui,sans-serif;color:#33404b">A browser preview and a free validator both render with one modern engine, so a table-less flexbox layout passes cleanly. Classic Outlook uses the Word engine and will destroy that exact file. Nothing that renders in a browser can show you the Word engine, and none of them know that VML is invisible in the new Outlook.</p></details><details style="border-bottom:1px solid #e6e9ed;padding:10px 0"><summary style="cursor:pointer;font:600 15px/1.4 system-ui,sans-serif;color:#1b1f24">What is free and what needs a licence?</summary><p style="margin:8px 0 2px;font:400 14.5px/1.6 system-ui,sans-serif;color:#33404b">Opening a file and checking it is free with no key and no limit: every rule, every finding, every suggested fix, plus checking a selection and reopening the report. The licence covers a different job, not a bigger one: scanning the whole template library at once, exporting a report as CSV, JSON or HTML, and machine-readable output for CI.</p></details><details style="border-bottom:1px solid #e6e9ed;padding:10px 0"><summary style="cursor:pointer;font:600 15px/1.4 system-ui,sans-serif;color:#1b1f24">How much does this cost compared with the alternatives?</summary><p style="margin:8px 0 2px;font:400 14.5px/1.6 system-ui,sans-serif;color:#33404b">The licence is twenty-nine dollars, paid once,. Hosted email rendering services are priced per month instead: Email on Acid Basics is ninety-nine dollars a month and Litmus Core starts at five hundred dollars a month, both checked on the seventh of September 2026. Those render screenshots; this reads your source.</p></details><script type="application/ld+json" data-yj="yj-faq-ld">{"@context": "https://schema.org", "@type": "FAQPage", "mainEntity": [{"@type": "Question", "name": "What does Outlook Split Lint actually do?", "acceptedAnswer": {"@type": "Answer", "text": "It reads an HTML email file and marks every line that breaks in Outlook, saying which of the two Outlooks breaks on it. Classic Outlook for Windows renders with the Microsoft Word engine; the new Outlook renders with Edge WebView2. Thirty-three rules cover both engines plus before-you-send checks, each with a suggested fix."}}, {"@type": "Question", "name": "Who is this for?", "acceptedAnswer": {"@type": "Answer", "text": "Email developers and agencies who hand-write or hand-fix HTML email and must support Outlook on Windows. It is most useful to anyone maintaining a template library through the 2026 to 2027 changeover, when classic Outlook and the new Outlook are both in the field and disagree with each other about the same markup."}}, {"@type": "Question", "name": "Why can't I just use a browser preview or a free HTML validator?", "acceptedAnswer": {"@type": "Answer", "text": "A browser preview and a free validator both render with one modern engine, so a table-less flexbox layout passes cleanly. Classic Outlook uses the Word engine and will destroy that exact file. Nothing that renders in a browser can show you the Word engine, and none of them know that VML is invisible in the new Outlook."}}, {"@type": "Question", "name": "What is free and what needs a licence?", "acceptedAnswer": {"@type": "Answer", "text": "Opening a file and checking it is free with no key and no limit: every rule, every finding, every suggested fix, plus checking a selection and reopening the report. The licence covers a different job, not a bigger one: scanning the whole template library at once, exporting a report as CSV, JSON or HTML, and machine-readable output for CI."}}, {"@type": "Question", "name": "How much does this cost compared with the alternatives?", "acceptedAnswer": {"@type": "Answer", "text": "The licence is twenty-nine dollars, paid once,. Hosted email rendering services are priced per month instead: Email on Acid Basics is ninety-nine dollars a month and Litmus Core starts at five hundred dollars a month, both checked on the seventh of September 2026. Those render screenshots; this reads your source."}}]}</script><div id="yj-ask" style="margin:36px 0 0;padding:18px 18px 16px;border:1px solid #e2e6ea;border-radius:10px;background:#fbfbfc"><h2 style="font:600 19px/1.3 system-ui,sans-serif;margin:0 0 4px;color:#1b1f24">Ask about this tool</h2><p style="font:400 13.5px/1.5 system-ui,sans-serif;margin:0 0 12px;color:#5b6570">One question, answered by the person who built it. Your email only if you want the answer sent.</p><form onsubmit="return yjAsk(event)" style="display:grid;gap:8px"><textarea name="question" required minlength="10" maxlength="2000" rows="3" placeholder="Your question" style="font:14px/1.5 system-ui,sans-serif;padding:10px;border:1px solid #cfd6dd;border-radius:6px"></textarea><div style="display:flex;gap:8px;flex-wrap:wrap"><input type="email" name="email" placeholder="Email (optional)" style="flex:1;min-width:200px;font:14px system-ui,sans-serif;padding:9px 10px;border:1px solid #cfd6dd;border-radius:6px"><button type="submit" style="font:600 14px system-ui,sans-serif;padding:9px 18px;border:0;border-radius:6px;background:#1b1f24;color:#fff;cursor:pointer">Send</button></div><p id="yj-ask-msg" style="font:13px system-ui,sans-serif;margin:2px 0 0;color:#0a6238;min-height:1em"></p></form><script>function yjAsk(e){e.preventDefault();var f=e.target,m=document.getElementById("yj-ask-msg");m.style.color="#0a6238";fetch(location.origin+"/api/ask",{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({sku:8261,slug:"outlook-email-html-lint",lang:"en",question:f.question.value,email:f.email.value,page:location.pathname})}).then(function(r){if(!r.ok)throw 0;m.textContent="Thanks \u2014 noted. Answers land on this page and, if you left an email, in your inbox.";f.question.value="";}).catch(function(){m.style.color="#a8551f";m.textContent="Could not send. Please try again in a minute.";});return false;}</script></div></section><section class="yj-related" style="max-width:920px;margin:56px auto 40px;padding:0 20px"><h2 style="font:600 21px/1.3 system-ui,sans-serif;margin:0 0 6px;color:#1b1f24">Same job, next tool</h2><p style="font:400 14.5px/1.5 system-ui,sans-serif;margin:0 0 20px;color:#5b6570">Free in the browser. The full version is a one-time licence.</p><div style="display:grid;grid-template-columns:repeat(auto-fill,minmax(250px,1fr));gap:14px"><a class="yj-rel-c" href="https://getreadystack.com/tools/bem-class-extractor-html"><span class="yj-rel-t">BEM Class Auditor for HTML and SCSS</span><span class="yj-rel-p">$29</span></a><a class="yj-rel-c" href="https://getreadystack.com/tools/bulk-sender-lint"><span class="yj-rel-t">Bulk Sender Lint - the Gmail, Yahoo and Outlook.com rules, checked in your mai</span><span class="yj-rel-p">$29</span></a><a class="yj-rel-c" href="https://getreadystack.com/tools/eaa-form-lint-wcag22"><span class="yj-rel-t">EAA Form Lint: WCAG 2.2 AA for HTML</span><span class="yj-rel-p">$29</span></a><a class="yj-rel-c" href="https://getreadystack.com/tools/email-footer-law-lint"><span class="yj-rel-t">Email Footer Law Lint</span><span class="yj-rel-p">$29</span></a><a class="yj-rel-c" href="https://getreadystack.com/tools/view-in-browser-leak-audit"><span class="yj-rel-t">View in Browser — Publish Leak Audit (HTML)</span><span class="yj-rel-p">$29</span></a><a class="yj-rel-c" href="https://getreadystack.com/tools/wcag21-aa-legal-baseline-audit"><span class="yj-rel-t">WCAG 2.1 AA Legal Baseline Audit for templates</span><span class="yj-rel-p">$29</span></a></div><style>.yj-rel-c{display:flex;flex-direction:column;gap:8px;padding:15px 16px;border:1px solid #e2e6ea;border-radius:6px;text-decoration:none;background:#fff}.yj-rel-c:hover{border-color:#b9c2cb;background:#fafbfc}.yj-rel-t{font:500 14.5px/1.42 system-ui,sans-serif;color:#1b1f24}.yj-rel-p{font:600 13px system-ui,sans-serif;color:#0a6238}</style></section> |