Files
MailUI4Agents/client/electron/test/manual/addr-verify.mjs

99 lines
3.9 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/**
* 邮件详情页地址行的真实渲染验收。
*
* 锁的是那次事故:发件行显示成 `jianf.<会话别名>` —— 别名拼给了发件人,
* 而且 path 为空时拼出了 ParseAddress 会整串当成名字的非法形态。
*/
import { openApp, WIDE } from './narrow-probe-helper.mjs';
const { browser, page } = await openApp(WIDE);
let fail = 0;
const check = (name, ok, detail = '') => {
if (ok) console.log(` 通过 ${name}`);
else { fail++; console.log(` 失败 ${name}${detail ? ' — ' + detail : ''}`); }
};
// 走**发件**箱:报这个 bug 的那封信是人发出去的jianf → pi抄送 pi@….new
// 收件箱里只有 Agent 的回信 —— 而回信没有抄送、也不带 `.new`
// 探不到要验的那三处。
await page.waitForSelector('button', { timeout: 20000 });
await page.click('button:has-text("发件")');
await page.waitForTimeout(2000);
// 收件箱/发件箱按会话分组:先点组头展开,再点里面的邮件行。
// 两者 className 都含 `w-full text-left`,靠「点完有没有出现含『发件』的 dl」区分。
let opened = false;
for (let round = 0; round < 3 && !opened; round++) {
const btns = await page.$$('button.w-full.text-left');
for (const b of btns) {
const t = await b.innerText().catch(() => '');
if (!t) continue;
await b.click().catch(() => {});
await page.waitForTimeout(350);
const hasMeta = await page.evaluate(() =>
[...document.querySelectorAll('dl')].some(dl => dl.textContent.includes('发件')));
if (hasMeta) { opened = true; break; }
}
}
check('打开了一封邮件', opened);
await page.waitForTimeout(800);
// 读元信息 dl
const meta = await page.evaluate(() => {
const dls = [...document.querySelectorAll('dl')];
for (const dl of dls) {
const pairs = [];
const kids = [...dl.children];
for (const div of kids) {
const dt = div.querySelector('dt'), dd = div.querySelector('dd');
if (dt && dd) pairs.push([dt.textContent.trim(), dd.textContent.trim()]);
}
if (pairs.some(([k]) => k === '发件')) return Object.fromEntries(pairs);
}
return null;
});
if (!meta) {
check('找到元信息区', false, '没有含「发件」的 dl');
} else {
console.log(' 元信息:', JSON.stringify(meta));
const from = meta['发件'] || '';
const to = meta['收件'] || '';
const cc = meta['抄送'] || '';
// 判「哪一方是人」:人的地址里既无 @ 也无 .
const isHuman = a => a && !a.includes('@') && !a.includes('.');
const human = isHuman(from) ? from : (isHuman(to) ? to : '');
const agent = isHuman(from) ? to : from;
check('有一方是人(裸名字,无 @ 无 .', !!human, `发件=${from} 收件=${to}`);
check('人的地址不含会话位', !human || !/[@.]/.test(human), `人=${human}`);
// Agent 必须三段齐全name@path.session
const threeSeg = /^[^@]+@\/[^@]*\.[^.@]+$/.test(agent);
check('Agent 带完整三段 name@path.session', threeSeg, `agent=${agent}`);
// path 不能是 Agent 名(`dsh@dsh` 那个 bug
if (agent.includes('@')) {
const [n, rest] = [agent.slice(0, agent.indexOf('@')), agent.slice(agent.indexOf('@') + 1)];
check('Agent 的 path 是真路径而不是 Agent 名',
rest.startsWith('/'), `${n}@${rest}`);
}
// 别名不能挂在人身上
check('会话别名跟着 Agent 而不是人',
!human || !agent || agent.includes('.'), `人=${human} agent=${agent}`);
// 抄送里不能残留 .new
check('抄送里没有 .new',
!cc.split('、').some(a => a.trim().endsWith('.new')), `抄送=${cc}`);
if (cc) console.log(` 抄送实际值: ${cc}`);
// 不该再有独立的「会话」行(别名已在 Agent 地址里)
check('没有多余的「会话」行', !('会话' in meta), `会话=${meta['会话']}`);
}
await browser.close();
console.log(fail ? `\n!! ${fail} 项不达标` : '\n全部达标');
process.exit(fail ? 1 : 0);