Import normalizer: offline tool to normalize the raw archive spreadsheets #663
@@ -45,8 +45,39 @@ function runAction(
|
||||
} as any);
|
||||
}
|
||||
|
||||
describe('persons/review confirm action — WRITE_ALL guard', () => {
|
||||
it('returns fail(403) when the user lacks WRITE_ALL', async () => {
|
||||
describe('persons/review confirm action', () => {
|
||||
it('returns { success: true } on backend 200', async () => {
|
||||
const apiCall = mockApi({ ok: true, status: 200 });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
|
||||
const result = await runAction(actions.confirm, fd, writer);
|
||||
|
||||
expect(apiCall).toHaveBeenCalledOnce();
|
||||
expect(result).toEqual({ success: true });
|
||||
});
|
||||
|
||||
it('returns fail(403) on backend 403', async () => {
|
||||
mockApi({ ok: false, status: 403, error: { code: 'FORBIDDEN' } });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
|
||||
const result = await runAction(actions.confirm, fd, writer);
|
||||
|
||||
expect(result).toMatchObject({ status: 403 });
|
||||
});
|
||||
|
||||
it('returns fail(404) on backend 404', async () => {
|
||||
mockApi({ ok: false, status: 404, error: { code: 'NOT_FOUND' } });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-missing');
|
||||
|
||||
const result = await runAction(actions.confirm, fd, writer);
|
||||
|
||||
expect(result).toMatchObject({ status: 404 });
|
||||
});
|
||||
|
||||
it('returns fail(403) when the user lacks WRITE_ALL (server-side guard)', async () => {
|
||||
const apiCall = mockApi({ ok: true, status: 200 });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
@@ -58,8 +89,39 @@ describe('persons/review confirm action — WRITE_ALL guard', () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe('persons/review delete action — WRITE_ALL guard', () => {
|
||||
it('returns fail(403) when the user lacks WRITE_ALL', async () => {
|
||||
describe('persons/review delete action', () => {
|
||||
it('returns { success: true } on backend 200', async () => {
|
||||
const apiCall = mockApi({ ok: true, status: 200 });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
|
||||
const result = await runAction(actions.delete, fd, writer);
|
||||
|
||||
expect(apiCall).toHaveBeenCalledOnce();
|
||||
expect(result).toEqual({ success: true });
|
||||
});
|
||||
|
||||
it('returns fail(403) on backend 403', async () => {
|
||||
mockApi({ ok: false, status: 403, error: { code: 'FORBIDDEN' } });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
|
||||
const result = await runAction(actions.delete, fd, writer);
|
||||
|
||||
expect(result).toMatchObject({ status: 403 });
|
||||
});
|
||||
|
||||
it('returns fail(404) on backend 404', async () => {
|
||||
mockApi({ ok: false, status: 404, error: { code: 'NOT_FOUND' } });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-missing');
|
||||
|
||||
const result = await runAction(actions.delete, fd, writer);
|
||||
|
||||
expect(result).toMatchObject({ status: 404 });
|
||||
});
|
||||
|
||||
it('returns fail(403) when the user lacks WRITE_ALL (server-side guard)', async () => {
|
||||
const apiCall = mockApi({ ok: true, status: 200 });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
@@ -71,8 +133,53 @@ describe('persons/review delete action — WRITE_ALL guard', () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe('persons/review merge action — WRITE_ALL guard', () => {
|
||||
it('returns fail(403) when the user lacks WRITE_ALL', async () => {
|
||||
describe('persons/review merge action', () => {
|
||||
it('returns { success: true } on backend 200', async () => {
|
||||
const apiCall = mockApi({ ok: true, status: 200 });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
fd.append('targetPersonId', 'p-2');
|
||||
|
||||
const result = await runAction(actions.merge, fd, writer);
|
||||
|
||||
expect(apiCall).toHaveBeenCalledOnce();
|
||||
expect(result).toEqual({ success: true });
|
||||
});
|
||||
|
||||
it('returns fail(400) when targetPersonId is missing', async () => {
|
||||
const apiCall = mockApi({ ok: true, status: 200 });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
|
||||
const result = await runAction(actions.merge, fd, writer);
|
||||
|
||||
expect(apiCall).not.toHaveBeenCalled();
|
||||
expect(result).toMatchObject({ status: 400 });
|
||||
});
|
||||
|
||||
it('returns fail(403) on backend 403', async () => {
|
||||
mockApi({ ok: false, status: 403, error: { code: 'FORBIDDEN' } });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
fd.append('targetPersonId', 'p-2');
|
||||
|
||||
const result = await runAction(actions.merge, fd, writer);
|
||||
|
||||
expect(result).toMatchObject({ status: 403 });
|
||||
});
|
||||
|
||||
it('returns fail(404) on backend 404', async () => {
|
||||
mockApi({ ok: false, status: 404, error: { code: 'NOT_FOUND' } });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
fd.append('targetPersonId', 'p-missing');
|
||||
|
||||
const result = await runAction(actions.merge, fd, writer);
|
||||
|
||||
expect(result).toMatchObject({ status: 404 });
|
||||
});
|
||||
|
||||
it('returns fail(403) when the user lacks WRITE_ALL (server-side guard)', async () => {
|
||||
const apiCall = mockApi({ ok: true, status: 200 });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
@@ -85,8 +192,53 @@ describe('persons/review merge action — WRITE_ALL guard', () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe('persons/review rename action — WRITE_ALL guard', () => {
|
||||
it('returns fail(403) when the user lacks WRITE_ALL', async () => {
|
||||
describe('persons/review rename action', () => {
|
||||
it('returns { success: true } on backend 200', async () => {
|
||||
const apiCall = mockApi({ ok: true, status: 200 });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
fd.append('lastName', 'Smith');
|
||||
|
||||
const result = await runAction(actions.rename, fd, writer);
|
||||
|
||||
expect(apiCall).toHaveBeenCalledOnce();
|
||||
expect(result).toEqual({ success: true });
|
||||
});
|
||||
|
||||
it('returns fail(400) when lastName is missing', async () => {
|
||||
const apiCall = mockApi({ ok: true, status: 200 });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
|
||||
const result = await runAction(actions.rename, fd, writer);
|
||||
|
||||
expect(apiCall).not.toHaveBeenCalled();
|
||||
expect(result).toMatchObject({ status: 400 });
|
||||
});
|
||||
|
||||
it('returns fail(403) on backend 403', async () => {
|
||||
mockApi({ ok: false, status: 403, error: { code: 'FORBIDDEN' } });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
fd.append('lastName', 'Smith');
|
||||
|
||||
const result = await runAction(actions.rename, fd, writer);
|
||||
|
||||
expect(result).toMatchObject({ status: 403 });
|
||||
});
|
||||
|
||||
it('returns fail(404) on backend 404', async () => {
|
||||
mockApi({ ok: false, status: 404, error: { code: 'NOT_FOUND' } });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-missing');
|
||||
fd.append('lastName', 'Smith');
|
||||
|
||||
const result = await runAction(actions.rename, fd, writer);
|
||||
|
||||
expect(result).toMatchObject({ status: 404 });
|
||||
});
|
||||
|
||||
it('returns fail(403) when the user lacks WRITE_ALL (server-side guard)', async () => {
|
||||
const apiCall = mockApi({ ok: true, status: 200 });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
@@ -98,18 +250,3 @@ describe('persons/review rename action — WRITE_ALL guard', () => {
|
||||
expect(result).toMatchObject({ status: 403 });
|
||||
});
|
||||
});
|
||||
|
||||
// Sanity: writers still pass through (no 403 from the guard). Full happy-path coverage lives
|
||||
// in the action-by-action describe blocks added later.
|
||||
describe('persons/review confirm action — writer passes guard', () => {
|
||||
it('does NOT short-circuit with 403 when the user has WRITE_ALL', async () => {
|
||||
const apiCall = mockApi({ ok: true, status: 200 });
|
||||
const fd = new FormData();
|
||||
fd.append('id', 'p-1');
|
||||
|
||||
const result = await runAction(actions.confirm, fd, writer);
|
||||
|
||||
expect(apiCall).toHaveBeenCalled();
|
||||
expect(result).toEqual({ success: true });
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user