`URLSearchParams` is absent from the App-Plus JS core, and
`toLocaleDateString('sv-SE', { timeZone: 'Asia/Shanghai' })` depends on full
ICU data that the App runtime does not ship, so the work-result pages built
either a broken query string or the device-local date.
Build query strings with `encodeURIComponent`, and centralise the business day
in `currentShanghaiDate()`, which shifts the epoch by a fixed UTC+8 offset
before slicing the ISO date. Asia/Shanghai has no DST, so the fixed offset is
exact rather than an approximation.
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
121 lines
5.6 KiB
JavaScript
121 lines
5.6 KiB
JavaScript
import assert from 'node:assert/strict';
|
|
import { readFile } from 'node:fs/promises';
|
|
import test from 'node:test';
|
|
|
|
const read = (path) => readFile(new URL(path, import.meta.url), 'utf8');
|
|
|
|
test('员工与主管成果页只允许推进待跟进或处理中记录', async () => {
|
|
const [employeePage, supervisorPage] = await Promise.all([
|
|
read('../src/pages/user/work-results/index.vue'),
|
|
read('../src/pages/supervisor/work-results/index.vue')
|
|
]);
|
|
|
|
const actionableStatuses = /\['PENDING',\s*'IN_PROGRESS'\]\.includes\(item\.businessStatus\)/;
|
|
assert.match(employeePage, actionableStatuses);
|
|
assert.match(supervisorPage, /\['PENDING','IN_PROGRESS'\]\.includes\(item\.businessStatus\)/);
|
|
assert.doesNotMatch(employeePage, /!\['COMPLETED',\s*'VOID'\]\.includes\(item\.businessStatus\)/);
|
|
assert.doesNotMatch(supervisorPage, /!\['COMPLETED','VOID'\]\.includes\(item\.businessStatus\)/);
|
|
});
|
|
|
|
test('员工成果页与主管成果页复用真实项目成果接口', async () => {
|
|
const [employeePage, supervisorPage, service] = await Promise.all([
|
|
read('../src/pages/user/work-results/index.vue'),
|
|
read('../src/pages/supervisor/work-results/index.vue'),
|
|
read('../src/services/work-results.ts')
|
|
]);
|
|
|
|
assert.match(employeePage, /generateMyWorkResult/);
|
|
assert.match(supervisorPage, /getProjectWorkResult/);
|
|
assert.match(service, /\/api\/aihr\/work-results\/mine\/generate/);
|
|
assert.match(service, /\/api\/aihr\/work-results\/project/);
|
|
assert.match(service, /pageNum/);
|
|
assert.match(service, /pageSize/);
|
|
});
|
|
|
|
test('App-Plus 查询参数不依赖 URLSearchParams', async () => {
|
|
const [service, supervisorReview] = await Promise.all([
|
|
read('../src/services/work-results.ts'),
|
|
read('../src/pages/supervisor/review/index.vue')
|
|
]);
|
|
|
|
assert.doesNotMatch(`${service}\n${supervisorReview}`, /URLSearchParams/);
|
|
assert.match(service, /encodeURIComponent\(projectCode\)/);
|
|
assert.match(supervisorReview, /encodeURIComponent\(assignedScenario\)/);
|
|
});
|
|
|
|
test('App-Plus 工作成果日期固定为上海 yyyy-MM-dd', async () => {
|
|
const [dateUtil, selector, employeePage, supervisorPage] = await Promise.all([
|
|
read('../src/utils/date.ts'),
|
|
read('../src/components/WorkDateSelector.vue'),
|
|
read('../src/pages/user/work-results/index.vue'),
|
|
read('../src/pages/supervisor/work-results/index.vue')
|
|
]);
|
|
|
|
assert.match(dateUtil, /Date\.now\(\) \+ 8 \* 60 \* 60 \* 1000/);
|
|
assert.match(dateUtil, /toISOString\(\)\.slice\(0, 10\)/);
|
|
assert.doesNotMatch(`${selector}\n${employeePage}\n${supervisorPage}`, /toLocaleDateString/);
|
|
for (const source of [selector, employeePage, supervisorPage]) {
|
|
assert.match(source, /currentShanghaiDate/);
|
|
}
|
|
});
|
|
|
|
test('主管成果页显式分页,避免把接口上限误当作完整团队', async () => {
|
|
const [supervisorPage, service, types] = await Promise.all([
|
|
read('../src/pages/supervisor/work-results/index.vue'),
|
|
read('../src/services/work-results.ts'),
|
|
read('../src/types/api.ts')
|
|
]);
|
|
|
|
assert.match(supervisorPage, /getProjectWorkResult\(currentProject\.value\.projectCode, workDate\.value, pageNum\.value, pageSize\)/);
|
|
assert.match(supervisorPage, /第 \{\{ result\.pageNum \}\} \/ \{\{ totalPages \}\} 页/);
|
|
assert.match(supervisorPage, /上一页/);
|
|
assert.match(supervisorPage, /下一页/);
|
|
assert.match(supervisorPage, /const changePage =/);
|
|
assert.match(service, /pageNum = 1, pageSize = 20/);
|
|
assert.match(types, /pageNum: number;/);
|
|
assert.match(types, /pageSize: number;/);
|
|
});
|
|
|
|
test('员工与主管成果页都能追溯非文字原始来源', async () => {
|
|
const [employeePage, supervisorPage, preview] = await Promise.all([
|
|
read('../src/pages/user/work-results/index.vue'),
|
|
read('../src/pages/supervisor/work-results/index.vue'),
|
|
read('../src/services/source-preview.ts')
|
|
]);
|
|
|
|
assert.match(employeePage, /openProtectedSource/);
|
|
assert.match(supervisorPage, /原始来源/);
|
|
assert.match(supervisorPage, /openProtectedSource/);
|
|
assert.match(preview, /createInnerAudioContext/);
|
|
assert.match(preview, /previewMedia/);
|
|
assert.doesNotMatch(employeePage, /openDocument/);
|
|
});
|
|
|
|
test('员工与主管成果页复用日期选择器查看历史成果且禁止未来日期', async () => {
|
|
const [employeePage, supervisorPage, dateSelector, pages] = await Promise.all([
|
|
read('../src/pages/user/work-results/index.vue'),
|
|
read('../src/pages/supervisor/work-results/index.vue'),
|
|
read('../src/components/WorkDateSelector.vue'),
|
|
read('../src/pages.json')
|
|
]);
|
|
|
|
assert.match(employeePage, /WorkDateSelector/);
|
|
assert.match(supervisorPage, /WorkDateSelector/);
|
|
assert.match(employeePage, /:max-date="today"/);
|
|
assert.match(supervisorPage, /:max-date="today"/);
|
|
assert.match(employeePage, /generateMyWorkResult\(currentProject\.value\.projectCode, workDate\.value\)/);
|
|
assert.match(supervisorPage, /getProjectWorkResult\(currentProject\.value\.projectCode, workDate\.value, pageNum\.value, pageSize\)/);
|
|
assert.match(dateSelector, /mode="date"/);
|
|
assert.match(dateSelector, /:end="today"/);
|
|
assert.match(dateSelector, /props\.maxDate \|\| currentShanghaiDate\(\)/);
|
|
assert.match(dateSelector, /nextDate > today\.value/);
|
|
assert.match(employeePage, /这一天没有已确认的工作记录/);
|
|
assert.match(employeePage, /回到今天/);
|
|
assert.match(employeePage, /completed: '当日已完成'/);
|
|
assert.match(supervisorPage, /当前项目这一天没有已确认的工作记录/);
|
|
assert.match(supervisorPage, />记录人数</);
|
|
assert.doesNotMatch(supervisorPage, /今日记录人数/);
|
|
assert.match(pages, /"navigationBarTitleText": "工作成果"/);
|
|
assert.match(pages, /"navigationBarTitleText": "团队工作成果"/);
|
|
});
|