@tantainnovative/ndpr-toolkit 1.0.3 → 1.0.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/next-env.d.ts +5 -0
- package/package.json +1 -1
- package/packages/ndpr-toolkit/dist/components/breach/BreachNotificationManager.d.ts +62 -0
- package/packages/ndpr-toolkit/dist/components/breach/BreachReportForm.d.ts +66 -0
- package/packages/ndpr-toolkit/dist/components/breach/BreachRiskAssessment.d.ts +50 -0
- package/packages/ndpr-toolkit/dist/components/breach/RegulatoryReportGenerator.d.ts +94 -0
- package/packages/ndpr-toolkit/dist/components/consent/ConsentBanner.d.ts +79 -0
- package/packages/ndpr-toolkit/dist/components/consent/ConsentManager.d.ts +73 -0
- package/packages/ndpr-toolkit/dist/components/consent/ConsentStorage.d.ts +41 -0
- package/packages/ndpr-toolkit/dist/components/dpia/DPIAQuestionnaire.d.ts +70 -0
- package/packages/ndpr-toolkit/dist/components/dpia/DPIAReport.d.ts +40 -0
- package/packages/ndpr-toolkit/dist/components/dpia/StepIndicator.d.ts +64 -0
- package/packages/ndpr-toolkit/dist/components/dsr/DSRDashboard.d.ts +58 -0
- package/packages/ndpr-toolkit/dist/components/dsr/DSRRequestForm.d.ts +74 -0
- package/packages/ndpr-toolkit/dist/components/dsr/DSRTracker.d.ts +56 -0
- package/packages/ndpr-toolkit/dist/components/policy/PolicyExporter.d.ts +65 -0
- package/packages/ndpr-toolkit/dist/components/policy/PolicyGenerator.d.ts +54 -0
- package/packages/ndpr-toolkit/dist/components/policy/PolicyPreview.d.ts +71 -0
- package/packages/ndpr-toolkit/dist/hooks/useBreach.d.ts +97 -0
- package/packages/ndpr-toolkit/dist/hooks/useConsent.d.ts +63 -0
- package/packages/ndpr-toolkit/dist/hooks/useDPIA.d.ts +92 -0
- package/packages/ndpr-toolkit/dist/hooks/useDSR.d.ts +72 -0
- package/packages/ndpr-toolkit/dist/hooks/usePrivacyPolicy.d.ts +87 -0
- package/packages/ndpr-toolkit/dist/index.d.ts +31 -0
- package/packages/ndpr-toolkit/dist/index.esm.js +2 -0
- package/packages/ndpr-toolkit/dist/index.esm.js.map +1 -0
- package/packages/ndpr-toolkit/dist/index.js +2 -0
- package/packages/ndpr-toolkit/dist/index.js.map +1 -0
- package/packages/ndpr-toolkit/dist/setupTests.d.ts +2 -0
- package/packages/ndpr-toolkit/dist/types/breach.d.ts +239 -0
- package/packages/ndpr-toolkit/dist/types/consent.d.ts +95 -0
- package/packages/ndpr-toolkit/dist/types/dpia.d.ts +196 -0
- package/packages/ndpr-toolkit/dist/types/dsr.d.ts +162 -0
- package/packages/ndpr-toolkit/dist/types/privacy.d.ts +204 -0
- package/packages/ndpr-toolkit/dist/utils/breach.d.ts +14 -0
- package/packages/ndpr-toolkit/dist/utils/consent.d.ts +10 -0
- package/packages/ndpr-toolkit/dist/utils/dpia.d.ts +12 -0
- package/packages/ndpr-toolkit/dist/utils/dsr.d.ts +11 -0
- package/packages/ndpr-toolkit/dist/utils/privacy.d.ts +12 -0
- package/src/components/consent/ConsentBanner.tsx +82 -48
- package/src/components/data-subject-rights/DataSubjectRequestForm.tsx +240 -129
- package/src/components/dpia/DPIAQuestionnaire.tsx +162 -122
- package/src/components/privacy-policy/PolicyGenerator.tsx +5 -5
- package/src/components/privacy-policy/steps/CustomSectionsStep.tsx +103 -77
- package/src/components/privacy-policy/steps/PolicyPreviewStep.tsx +117 -63
- package/src/hooks/useConsent.ts +16 -10
- package/src/lib/consentService.ts +44 -37
- package/src/lib/dpiaQuestions.ts +139 -99
- package/src/lib/requestService.ts +21 -17
- package/src/types/index.ts +13 -8
- package/.claude/settings.local.json +0 -20
- package/.eslintrc.json +0 -10
- package/.github/workflows/ci.yml +0 -36
- package/.github/workflows/nextjs.yml +0 -104
- package/.husky/commit-msg +0 -4
- package/.husky/pre-commit +0 -4
- package/.lintstagedrc.js +0 -4
- package/.nvmrc +0 -1
- package/.versionrc +0 -17
- package/CLAUDE.md +0 -90
- package/commitlint.config.js +0 -36
- package/jest.config.js +0 -31
- package/jest.setup.js +0 -15
- package/packages/ndpr-toolkit/jest.config.js +0 -23
- package/packages/ndpr-toolkit/src/__tests__/components/consent/ConsentBanner.test.tsx +0 -119
- package/packages/ndpr-toolkit/src/__tests__/components/consent/ConsentManager.test.tsx +0 -122
- package/packages/ndpr-toolkit/src/__tests__/components/consent/ConsentStorage.test.tsx +0 -270
- package/packages/ndpr-toolkit/src/__tests__/components/dsr/DSRDashboard.test.tsx +0 -199
- package/packages/ndpr-toolkit/src/__tests__/components/dsr/DSRRequestForm.test.tsx +0 -224
- package/packages/ndpr-toolkit/src/__tests__/components/dsr/DSRTracker.test.tsx +0 -104
- package/packages/ndpr-toolkit/src/__tests__/hooks/useConsent.test.tsx +0 -161
- package/packages/ndpr-toolkit/src/__tests__/hooks/useDSR.test.tsx +0 -330
- package/packages/ndpr-toolkit/src/__tests__/utils/breach.test.ts +0 -149
- package/packages/ndpr-toolkit/src/__tests__/utils/consent.test.ts +0 -88
- package/packages/ndpr-toolkit/src/__tests__/utils/dpia.test.ts +0 -160
- package/packages/ndpr-toolkit/src/__tests__/utils/dsr.test.ts +0 -110
- package/packages/ndpr-toolkit/src/__tests__/utils/privacy.test.ts +0 -97
- package/src/__tests__/example.test.ts +0 -13
- package/src/__tests__/requestService.test.ts +0 -57
- package/src/app/docs/components/DocLayout.tsx +0 -267
- package/src/app/docs/components/breach-notification/page.tsx +0 -797
- package/src/app/docs/components/consent-management/page.tsx +0 -576
- package/src/app/docs/components/data-subject-rights/page.tsx +0 -511
- package/src/app/docs/components/dpia-questionnaire/layout.tsx +0 -15
- package/src/app/docs/components/dpia-questionnaire/metadata.ts +0 -31
- package/src/app/docs/components/dpia-questionnaire/page.tsx +0 -666
- package/src/app/docs/components/hooks/page.tsx +0 -305
- package/src/app/docs/components/page.tsx +0 -84
- package/src/app/docs/components/privacy-policy-generator/page.tsx +0 -634
- package/src/app/docs/guides/breach-notification-process/components/BestPractices.tsx +0 -123
- package/src/app/docs/guides/breach-notification-process/components/ImplementationSteps.tsx +0 -328
- package/src/app/docs/guides/breach-notification-process/components/Introduction.tsx +0 -28
- package/src/app/docs/guides/breach-notification-process/components/NotificationTimeline.tsx +0 -91
- package/src/app/docs/guides/breach-notification-process/components/Resources.tsx +0 -118
- package/src/app/docs/guides/breach-notification-process/page.tsx +0 -39
- package/src/app/docs/guides/conducting-dpia/page.tsx +0 -593
- package/src/app/docs/guides/data-subject-requests/page.tsx +0 -666
- package/src/app/docs/guides/managing-consent/page.tsx +0 -738
- package/src/app/docs/guides/ndpr-compliance-checklist/components/ComplianceChecklist.tsx +0 -296
- package/src/app/docs/guides/ndpr-compliance-checklist/components/ImplementationTools.tsx +0 -145
- package/src/app/docs/guides/ndpr-compliance-checklist/components/Introduction.tsx +0 -33
- package/src/app/docs/guides/ndpr-compliance-checklist/components/KeyRequirements.tsx +0 -99
- package/src/app/docs/guides/ndpr-compliance-checklist/components/Resources.tsx +0 -159
- package/src/app/docs/guides/ndpr-compliance-checklist/page.tsx +0 -38
- package/src/app/docs/guides/page.tsx +0 -67
- package/src/app/docs/layout.tsx +0 -15
- package/src/app/docs/metadata.ts +0 -31
- package/src/app/docs/page.tsx +0 -572
- package/src/components/docs/DocLayout.tsx +0 -289
- package/src/components/docs/index.ts +0 -2
|
@@ -1,104 +0,0 @@
|
|
|
1
|
-
import React from 'react';
|
|
2
|
-
import { render, screen, fireEvent } from '@testing-library/react';
|
|
3
|
-
import { DSRTracker } from '../../../components/dsr/DSRTracker';
|
|
4
|
-
import { DSRRequest } from '../../../types/dsr';
|
|
5
|
-
|
|
6
|
-
describe('DSRTracker', () => {
|
|
7
|
-
const mockRequest: DSRRequest = {
|
|
8
|
-
id: 'dsr-123',
|
|
9
|
-
type: 'access',
|
|
10
|
-
status: 'inProgress',
|
|
11
|
-
createdAt: 1620000000000,
|
|
12
|
-
updatedAt: 1620100000000,
|
|
13
|
-
subject: {
|
|
14
|
-
name: 'John Doe',
|
|
15
|
-
email: 'john@example.com'
|
|
16
|
-
},
|
|
17
|
-
description: 'I want to access my personal data'
|
|
18
|
-
};
|
|
19
|
-
|
|
20
|
-
const mockTrackHandler = jest.fn();
|
|
21
|
-
|
|
22
|
-
beforeEach(() => {
|
|
23
|
-
mockTrackHandler.mockClear();
|
|
24
|
-
});
|
|
25
|
-
|
|
26
|
-
it('renders the tracking form correctly', () => {
|
|
27
|
-
render(
|
|
28
|
-
<DSRTracker
|
|
29
|
-
requests={[]}
|
|
30
|
-
onSelectRequest={mockTrackHandler}
|
|
31
|
-
/>
|
|
32
|
-
);
|
|
33
|
-
|
|
34
|
-
expect(screen.getByText(/DSR Request Tracker/i)).toBeInTheDocument();
|
|
35
|
-
expect(screen.getByText(/track the status and progress/i)).toBeInTheDocument();
|
|
36
|
-
expect(screen.getByText(/total requests/i)).toBeInTheDocument();
|
|
37
|
-
expect(screen.getByLabelText(/timeframe/i)).toBeInTheDocument();
|
|
38
|
-
});
|
|
39
|
-
|
|
40
|
-
// Note: The DSRTracker component doesn't have a form for tracking requests directly visible on initial render
|
|
41
|
-
// These tests are removed as they don't match the actual component implementation
|
|
42
|
-
|
|
43
|
-
it('displays request count when provided', () => {
|
|
44
|
-
// Render the component with a request
|
|
45
|
-
const { container } = render(
|
|
46
|
-
<DSRTracker
|
|
47
|
-
requests={[mockRequest]}
|
|
48
|
-
onSelectRequest={mockTrackHandler}
|
|
49
|
-
/>
|
|
50
|
-
);
|
|
51
|
-
|
|
52
|
-
// Check that the component renders without crashing
|
|
53
|
-
expect(container).toBeInTheDocument();
|
|
54
|
-
|
|
55
|
-
// Should show summary stats with the request count heading
|
|
56
|
-
expect(screen.getByText(/total requests/i)).toBeInTheDocument();
|
|
57
|
-
|
|
58
|
-
// Check that the component has rendered some content
|
|
59
|
-
const statsContainer = screen.getByText(/total requests/i).closest('div');
|
|
60
|
-
expect(statsContainer).toBeInTheDocument();
|
|
61
|
-
});
|
|
62
|
-
|
|
63
|
-
// Note: The DSRTracker component doesn't display a "Request not found" message directly on initial render
|
|
64
|
-
// This test is removed as it doesn't match the actual component implementation
|
|
65
|
-
|
|
66
|
-
it('handles custom title', () => {
|
|
67
|
-
const customTitle = 'Custom DSR Tracker Title';
|
|
68
|
-
|
|
69
|
-
render(
|
|
70
|
-
<DSRTracker
|
|
71
|
-
requests={[]}
|
|
72
|
-
onSelectRequest={mockTrackHandler}
|
|
73
|
-
title={customTitle}
|
|
74
|
-
/>
|
|
75
|
-
);
|
|
76
|
-
|
|
77
|
-
expect(screen.getByText(customTitle)).toBeInTheDocument();
|
|
78
|
-
});
|
|
79
|
-
|
|
80
|
-
it('shows request timeline chart when requests are provided', () => {
|
|
81
|
-
const requestWithDates: DSRRequest = {
|
|
82
|
-
...mockRequest,
|
|
83
|
-
verifiedAt: 1620050000000,
|
|
84
|
-
completedAt: 1620200000000
|
|
85
|
-
};
|
|
86
|
-
|
|
87
|
-
// Render the component with the request
|
|
88
|
-
const { container } = render(
|
|
89
|
-
<DSRTracker
|
|
90
|
-
requests={[requestWithDates]}
|
|
91
|
-
onSelectRequest={mockTrackHandler}
|
|
92
|
-
/>
|
|
93
|
-
);
|
|
94
|
-
|
|
95
|
-
// Check that the component renders without crashing
|
|
96
|
-
expect(container).toBeInTheDocument();
|
|
97
|
-
|
|
98
|
-
// Check for the title which should always be present
|
|
99
|
-
expect(screen.getByText(/DSR Request Tracker/i)).toBeInTheDocument();
|
|
100
|
-
|
|
101
|
-
// Check that the description is present
|
|
102
|
-
expect(screen.getByText(/Track the status and progress/i)).toBeInTheDocument();
|
|
103
|
-
});
|
|
104
|
-
});
|
|
@@ -1,161 +0,0 @@
|
|
|
1
|
-
import React from 'react';
|
|
2
|
-
import { renderHook, act } from '@testing-library/react';
|
|
3
|
-
import { useConsent } from '../../hooks/useConsent';
|
|
4
|
-
import { ConsentOption, ConsentSettings } from '../../types/consent';
|
|
5
|
-
|
|
6
|
-
// Mock localStorage
|
|
7
|
-
const mockLocalStorage = (() => {
|
|
8
|
-
let store: Record<string, string> = {};
|
|
9
|
-
return {
|
|
10
|
-
getItem: jest.fn((key: string) => store[key] || null),
|
|
11
|
-
setItem: jest.fn((key: string, value: string) => {
|
|
12
|
-
store[key] = value.toString();
|
|
13
|
-
}),
|
|
14
|
-
removeItem: jest.fn((key: string) => {
|
|
15
|
-
delete store[key];
|
|
16
|
-
}),
|
|
17
|
-
clear: jest.fn(() => {
|
|
18
|
-
store = {};
|
|
19
|
-
}),
|
|
20
|
-
};
|
|
21
|
-
})();
|
|
22
|
-
|
|
23
|
-
Object.defineProperty(window, 'localStorage', {
|
|
24
|
-
value: mockLocalStorage,
|
|
25
|
-
});
|
|
26
|
-
|
|
27
|
-
describe('useConsent', () => {
|
|
28
|
-
beforeEach(() => {
|
|
29
|
-
mockLocalStorage.clear();
|
|
30
|
-
jest.clearAllMocks();
|
|
31
|
-
});
|
|
32
|
-
|
|
33
|
-
const consentOptions: ConsentOption[] = [
|
|
34
|
-
{
|
|
35
|
-
id: 'necessary',
|
|
36
|
-
label: 'Necessary',
|
|
37
|
-
description: 'Essential cookies',
|
|
38
|
-
required: true,
|
|
39
|
-
},
|
|
40
|
-
{
|
|
41
|
-
id: 'analytics',
|
|
42
|
-
label: 'Analytics',
|
|
43
|
-
description: 'Analytics cookies',
|
|
44
|
-
required: false,
|
|
45
|
-
},
|
|
46
|
-
{
|
|
47
|
-
id: 'marketing',
|
|
48
|
-
label: 'Marketing',
|
|
49
|
-
description: 'Marketing cookies',
|
|
50
|
-
required: false,
|
|
51
|
-
},
|
|
52
|
-
];
|
|
53
|
-
|
|
54
|
-
it('should initialize with default consent settings', () => {
|
|
55
|
-
const { result } = renderHook(() => useConsent({
|
|
56
|
-
options: consentOptions,
|
|
57
|
-
storageOptions: { storageKey: 'test-consent' }
|
|
58
|
-
}));
|
|
59
|
-
|
|
60
|
-
expect(result.current.settings).toBe(null);
|
|
61
|
-
expect(result.current.shouldShowBanner).toBe(true);
|
|
62
|
-
expect(result.current.hasConsent('necessary')).toBe(false);
|
|
63
|
-
expect(result.current.hasConsent('analytics')).toBe(false);
|
|
64
|
-
});
|
|
65
|
-
|
|
66
|
-
it('should update consent settings', () => {
|
|
67
|
-
const { result } = renderHook(() => useConsent({
|
|
68
|
-
options: consentOptions,
|
|
69
|
-
storageOptions: { storageKey: 'test-consent' }
|
|
70
|
-
}));
|
|
71
|
-
|
|
72
|
-
act(() => {
|
|
73
|
-
result.current.updateConsent({
|
|
74
|
-
necessary: true,
|
|
75
|
-
analytics: true,
|
|
76
|
-
marketing: false
|
|
77
|
-
});
|
|
78
|
-
});
|
|
79
|
-
|
|
80
|
-
expect(result.current.settings?.consents.necessary).toBe(true);
|
|
81
|
-
expect(result.current.settings?.consents.analytics).toBe(true);
|
|
82
|
-
expect(result.current.settings?.consents.marketing).toBe(false);
|
|
83
|
-
expect(result.current.hasConsent('analytics')).toBe(true);
|
|
84
|
-
});
|
|
85
|
-
|
|
86
|
-
it('should accept all consent options', () => {
|
|
87
|
-
const { result } = renderHook(() => useConsent({
|
|
88
|
-
options: consentOptions,
|
|
89
|
-
storageOptions: { storageKey: 'test-consent' }
|
|
90
|
-
}));
|
|
91
|
-
|
|
92
|
-
act(() => {
|
|
93
|
-
result.current.acceptAll();
|
|
94
|
-
});
|
|
95
|
-
|
|
96
|
-
expect(result.current.settings?.consents.necessary).toBe(true);
|
|
97
|
-
expect(result.current.settings?.consents.analytics).toBe(true);
|
|
98
|
-
expect(result.current.settings?.consents.marketing).toBe(true);
|
|
99
|
-
});
|
|
100
|
-
|
|
101
|
-
it('should save and reset consent settings', () => {
|
|
102
|
-
const { result } = renderHook(() => useConsent({
|
|
103
|
-
options: consentOptions,
|
|
104
|
-
storageOptions: { storageKey: 'test-consent' }
|
|
105
|
-
}));
|
|
106
|
-
|
|
107
|
-
act(() => {
|
|
108
|
-
result.current.updateConsent({
|
|
109
|
-
necessary: true,
|
|
110
|
-
analytics: true,
|
|
111
|
-
marketing: false
|
|
112
|
-
});
|
|
113
|
-
});
|
|
114
|
-
|
|
115
|
-
expect(mockLocalStorage.setItem).toHaveBeenCalled();
|
|
116
|
-
expect(result.current.shouldShowBanner).toBe(false);
|
|
117
|
-
|
|
118
|
-
// Reset the consent settings
|
|
119
|
-
act(() => {
|
|
120
|
-
result.current.resetConsent();
|
|
121
|
-
});
|
|
122
|
-
|
|
123
|
-
expect(mockLocalStorage.removeItem).toHaveBeenCalledWith('test-consent');
|
|
124
|
-
expect(result.current.settings).toBe(null);
|
|
125
|
-
expect(result.current.shouldShowBanner).toBe(true);
|
|
126
|
-
});
|
|
127
|
-
|
|
128
|
-
it('should reject all non-required consent options', () => {
|
|
129
|
-
const { result } = renderHook(() => useConsent({
|
|
130
|
-
options: consentOptions,
|
|
131
|
-
storageOptions: { storageKey: 'test-consent' }
|
|
132
|
-
}));
|
|
133
|
-
|
|
134
|
-
act(() => {
|
|
135
|
-
result.current.rejectAll();
|
|
136
|
-
});
|
|
137
|
-
|
|
138
|
-
// Necessary is required, so it should be true
|
|
139
|
-
expect(result.current.settings?.consents.necessary).toBe(true);
|
|
140
|
-
// Non-required options should be false
|
|
141
|
-
expect(result.current.settings?.consents.analytics).toBe(false);
|
|
142
|
-
expect(result.current.settings?.consents.marketing).toBe(false);
|
|
143
|
-
});
|
|
144
|
-
|
|
145
|
-
it('should handle validation', () => {
|
|
146
|
-
const { result } = renderHook(() => useConsent({
|
|
147
|
-
options: consentOptions,
|
|
148
|
-
storageOptions: { storageKey: 'test-consent' }
|
|
149
|
-
}));
|
|
150
|
-
|
|
151
|
-
expect(result.current.isValid).toBe(false);
|
|
152
|
-
|
|
153
|
-
act(() => {
|
|
154
|
-
result.current.acceptAll();
|
|
155
|
-
});
|
|
156
|
-
|
|
157
|
-
// After accepting all, settings should be valid
|
|
158
|
-
expect(result.current.isValid).toBe(true);
|
|
159
|
-
expect(result.current.validationErrors).toEqual([]);
|
|
160
|
-
});
|
|
161
|
-
});
|
|
@@ -1,330 +0,0 @@
|
|
|
1
|
-
import { renderHook, act } from '@testing-library/react';
|
|
2
|
-
import { useDSR } from '../../hooks/useDSR';
|
|
3
|
-
import React from 'react';
|
|
4
|
-
import { DSRRequest, RequestType } from '../../types/dsr';
|
|
5
|
-
|
|
6
|
-
// Mock localStorage
|
|
7
|
-
const mockLocalStorage = (() => {
|
|
8
|
-
let store: Record<string, string> = {};
|
|
9
|
-
return {
|
|
10
|
-
getItem: jest.fn((key: string) => store[key] || null),
|
|
11
|
-
setItem: jest.fn((key: string, value: string) => {
|
|
12
|
-
store[key] = value.toString();
|
|
13
|
-
}),
|
|
14
|
-
removeItem: jest.fn((key: string) => {
|
|
15
|
-
delete store[key];
|
|
16
|
-
}),
|
|
17
|
-
clear: jest.fn(() => {
|
|
18
|
-
store = {};
|
|
19
|
-
}),
|
|
20
|
-
};
|
|
21
|
-
})();
|
|
22
|
-
|
|
23
|
-
Object.defineProperty(window, 'localStorage', {
|
|
24
|
-
value: mockLocalStorage,
|
|
25
|
-
});
|
|
26
|
-
|
|
27
|
-
describe('useDSR', () => {
|
|
28
|
-
beforeEach(() => {
|
|
29
|
-
mockLocalStorage.clear();
|
|
30
|
-
jest.clearAllMocks();
|
|
31
|
-
});
|
|
32
|
-
|
|
33
|
-
const mockRequestTypes: RequestType[] = [
|
|
34
|
-
{
|
|
35
|
-
id: 'access',
|
|
36
|
-
name: 'Access Request',
|
|
37
|
-
description: 'Request to access your personal data',
|
|
38
|
-
estimatedCompletionTime: 30,
|
|
39
|
-
requiresAdditionalInfo: false
|
|
40
|
-
},
|
|
41
|
-
{
|
|
42
|
-
id: 'erasure',
|
|
43
|
-
name: 'Erasure Request',
|
|
44
|
-
description: 'Request to delete your personal data',
|
|
45
|
-
estimatedCompletionTime: 45,
|
|
46
|
-
requiresAdditionalInfo: false
|
|
47
|
-
},
|
|
48
|
-
{
|
|
49
|
-
id: 'rectification',
|
|
50
|
-
name: 'Rectification Request',
|
|
51
|
-
description: 'Request to correct your personal data',
|
|
52
|
-
estimatedCompletionTime: 15,
|
|
53
|
-
requiresAdditionalInfo: true
|
|
54
|
-
}
|
|
55
|
-
];
|
|
56
|
-
|
|
57
|
-
it('should initialize with empty requests array', () => {
|
|
58
|
-
const { result } = renderHook(() => useDSR({
|
|
59
|
-
requestTypes: mockRequestTypes,
|
|
60
|
-
storageKey: 'test-dsr',
|
|
61
|
-
useLocalStorage: true
|
|
62
|
-
}));
|
|
63
|
-
|
|
64
|
-
expect(result.current.requests).toEqual([]);
|
|
65
|
-
});
|
|
66
|
-
|
|
67
|
-
it('should submit a new DSR request', () => {
|
|
68
|
-
const { result } = renderHook(() => useDSR({
|
|
69
|
-
requestTypes: mockRequestTypes,
|
|
70
|
-
storageKey: 'test-dsr',
|
|
71
|
-
useLocalStorage: true
|
|
72
|
-
}));
|
|
73
|
-
|
|
74
|
-
act(() => {
|
|
75
|
-
result.current.submitRequest({
|
|
76
|
-
type: 'access',
|
|
77
|
-
subject: {
|
|
78
|
-
name: 'John Doe',
|
|
79
|
-
email: 'john@example.com',
|
|
80
|
-
},
|
|
81
|
-
createdAt: Date.now(),
|
|
82
|
-
description: 'I want to access my data',
|
|
83
|
-
});
|
|
84
|
-
});
|
|
85
|
-
|
|
86
|
-
expect(result.current.requests.length).toBe(1);
|
|
87
|
-
expect(result.current.requests[0].type).toBe('access');
|
|
88
|
-
expect(result.current.requests[0].status).toBe('pending');
|
|
89
|
-
expect(result.current.requests[0].subject.name).toBe('John Doe');
|
|
90
|
-
expect(result.current.requests[0].id).toBeDefined();
|
|
91
|
-
expect(result.current.requests[0].createdAt).toBeDefined();
|
|
92
|
-
expect(result.current.requests[0].updatedAt).toBeDefined();
|
|
93
|
-
});
|
|
94
|
-
|
|
95
|
-
it('should get a request by ID', () => {
|
|
96
|
-
const { result } = renderHook(() => useDSR({
|
|
97
|
-
requestTypes: mockRequestTypes,
|
|
98
|
-
storageKey: 'test-dsr',
|
|
99
|
-
useLocalStorage: true
|
|
100
|
-
}));
|
|
101
|
-
|
|
102
|
-
// Initialize requestId with a default value
|
|
103
|
-
let requestId: string = '';
|
|
104
|
-
|
|
105
|
-
act(() => {
|
|
106
|
-
const request = result.current.submitRequest({
|
|
107
|
-
type: 'access',
|
|
108
|
-
subject: {
|
|
109
|
-
name: 'John Doe',
|
|
110
|
-
email: 'john@example.com',
|
|
111
|
-
},
|
|
112
|
-
createdAt: Date.now(),
|
|
113
|
-
});
|
|
114
|
-
requestId = request.id;
|
|
115
|
-
});
|
|
116
|
-
|
|
117
|
-
const retrievedRequest = result.current.getRequest(requestId);
|
|
118
|
-
expect(retrievedRequest).toBeDefined();
|
|
119
|
-
expect(retrievedRequest?.id).toBe(requestId);
|
|
120
|
-
});
|
|
121
|
-
|
|
122
|
-
it('should update a request', () => {
|
|
123
|
-
const { result } = renderHook(() => useDSR({
|
|
124
|
-
requestTypes: mockRequestTypes,
|
|
125
|
-
storageKey: 'test-dsr',
|
|
126
|
-
useLocalStorage: true
|
|
127
|
-
}));
|
|
128
|
-
|
|
129
|
-
let requestId = '';
|
|
130
|
-
|
|
131
|
-
act(() => {
|
|
132
|
-
const request = result.current.submitRequest({
|
|
133
|
-
type: 'access',
|
|
134
|
-
subject: {
|
|
135
|
-
name: 'John Doe',
|
|
136
|
-
email: 'john@example.com',
|
|
137
|
-
},
|
|
138
|
-
createdAt: Date.now(),
|
|
139
|
-
});
|
|
140
|
-
requestId = request.id;
|
|
141
|
-
});
|
|
142
|
-
|
|
143
|
-
act(() => {
|
|
144
|
-
result.current.updateRequest(requestId!, {
|
|
145
|
-
status: 'inProgress',
|
|
146
|
-
internalNotes: [
|
|
147
|
-
{
|
|
148
|
-
timestamp: Date.now(),
|
|
149
|
-
author: 'Admin',
|
|
150
|
-
note: 'Working on this request',
|
|
151
|
-
},
|
|
152
|
-
],
|
|
153
|
-
});
|
|
154
|
-
});
|
|
155
|
-
|
|
156
|
-
const updatedRequest = result.current.getRequest(requestId!);
|
|
157
|
-
expect(updatedRequest?.status).toBe('inProgress');
|
|
158
|
-
expect(updatedRequest?.internalNotes?.length).toBe(1);
|
|
159
|
-
expect(updatedRequest?.internalNotes?.[0].author).toBe('Admin');
|
|
160
|
-
});
|
|
161
|
-
|
|
162
|
-
it('should clear all requests', () => {
|
|
163
|
-
const { result } = renderHook(() => useDSR({
|
|
164
|
-
requestTypes: mockRequestTypes,
|
|
165
|
-
storageKey: 'test-dsr',
|
|
166
|
-
useLocalStorage: true
|
|
167
|
-
}));
|
|
168
|
-
|
|
169
|
-
act(() => {
|
|
170
|
-
result.current.submitRequest({
|
|
171
|
-
type: 'access',
|
|
172
|
-
subject: {
|
|
173
|
-
name: 'John Doe',
|
|
174
|
-
email: 'john@example.com',
|
|
175
|
-
},
|
|
176
|
-
createdAt: Date.now(),
|
|
177
|
-
});
|
|
178
|
-
});
|
|
179
|
-
|
|
180
|
-
expect(result.current.requests.length).toBe(1);
|
|
181
|
-
|
|
182
|
-
act(() => {
|
|
183
|
-
result.current.clearRequests();
|
|
184
|
-
});
|
|
185
|
-
|
|
186
|
-
expect(result.current.requests.length).toBe(0);
|
|
187
|
-
});
|
|
188
|
-
|
|
189
|
-
it('should filter requests by type', () => {
|
|
190
|
-
const { result } = renderHook(() => useDSR({
|
|
191
|
-
requestTypes: mockRequestTypes,
|
|
192
|
-
storageKey: 'test-dsr',
|
|
193
|
-
useLocalStorage: true
|
|
194
|
-
}));
|
|
195
|
-
|
|
196
|
-
act(() => {
|
|
197
|
-
result.current.submitRequest({
|
|
198
|
-
type: 'access',
|
|
199
|
-
subject: {
|
|
200
|
-
name: 'John Doe',
|
|
201
|
-
email: 'john@example.com',
|
|
202
|
-
},
|
|
203
|
-
createdAt: Date.now(),
|
|
204
|
-
});
|
|
205
|
-
|
|
206
|
-
result.current.submitRequest({
|
|
207
|
-
type: 'erasure',
|
|
208
|
-
subject: {
|
|
209
|
-
name: 'Jane Smith',
|
|
210
|
-
email: 'jane@example.com',
|
|
211
|
-
},
|
|
212
|
-
createdAt: Date.now(),
|
|
213
|
-
});
|
|
214
|
-
|
|
215
|
-
result.current.submitRequest({
|
|
216
|
-
type: 'access',
|
|
217
|
-
subject: {
|
|
218
|
-
name: 'Bob Johnson',
|
|
219
|
-
email: 'bob@example.com',
|
|
220
|
-
},
|
|
221
|
-
createdAt: Date.now(),
|
|
222
|
-
});
|
|
223
|
-
});
|
|
224
|
-
|
|
225
|
-
const accessRequests = result.current.getRequestsByType('access');
|
|
226
|
-
expect(accessRequests.length).toBe(2);
|
|
227
|
-
expect(accessRequests[0].subject.name).toBe('John Doe');
|
|
228
|
-
expect(accessRequests[1].subject.name).toBe('Bob Johnson');
|
|
229
|
-
|
|
230
|
-
const erasureRequests = result.current.getRequestsByType('erasure');
|
|
231
|
-
expect(erasureRequests.length).toBe(1);
|
|
232
|
-
expect(erasureRequests[0].subject.name).toBe('Jane Smith');
|
|
233
|
-
});
|
|
234
|
-
|
|
235
|
-
it('should filter requests by status', () => {
|
|
236
|
-
const { result } = renderHook(() => useDSR({
|
|
237
|
-
requestTypes: mockRequestTypes,
|
|
238
|
-
storageKey: 'test-dsr',
|
|
239
|
-
useLocalStorage: true
|
|
240
|
-
}));
|
|
241
|
-
|
|
242
|
-
let requestId: string = '';
|
|
243
|
-
|
|
244
|
-
act(() => {
|
|
245
|
-
result.current.submitRequest({
|
|
246
|
-
type: 'access',
|
|
247
|
-
subject: {
|
|
248
|
-
name: 'John Doe',
|
|
249
|
-
email: 'john@example.com',
|
|
250
|
-
},
|
|
251
|
-
createdAt: Date.now(),
|
|
252
|
-
});
|
|
253
|
-
|
|
254
|
-
const request = result.current.submitRequest({
|
|
255
|
-
type: 'erasure',
|
|
256
|
-
subject: {
|
|
257
|
-
name: 'Jane Smith',
|
|
258
|
-
email: 'jane@example.com',
|
|
259
|
-
},
|
|
260
|
-
createdAt: Date.now(),
|
|
261
|
-
});
|
|
262
|
-
requestId = request.id;
|
|
263
|
-
|
|
264
|
-
result.current.submitRequest({
|
|
265
|
-
type: 'rectification',
|
|
266
|
-
subject: {
|
|
267
|
-
name: 'Bob Johnson',
|
|
268
|
-
email: 'bob@example.com',
|
|
269
|
-
},
|
|
270
|
-
createdAt: Date.now(),
|
|
271
|
-
});
|
|
272
|
-
});
|
|
273
|
-
|
|
274
|
-
act(() => {
|
|
275
|
-
result.current.updateRequest(requestId!, {
|
|
276
|
-
status: 'completed',
|
|
277
|
-
});
|
|
278
|
-
});
|
|
279
|
-
|
|
280
|
-
const pendingRequests = result.current.getRequestsByStatus('pending');
|
|
281
|
-
expect(pendingRequests.length).toBe(2);
|
|
282
|
-
|
|
283
|
-
const completedRequests = result.current.getRequestsByStatus('completed');
|
|
284
|
-
expect(completedRequests.length).toBe(1);
|
|
285
|
-
expect(completedRequests[0].subject.name).toBe('Jane Smith');
|
|
286
|
-
});
|
|
287
|
-
|
|
288
|
-
it('should format a request', () => {
|
|
289
|
-
const { result } = renderHook(() => useDSR({
|
|
290
|
-
requestTypes: mockRequestTypes,
|
|
291
|
-
storageKey: 'test-dsr',
|
|
292
|
-
useLocalStorage: true
|
|
293
|
-
}));
|
|
294
|
-
|
|
295
|
-
let request: DSRRequest | null = null;
|
|
296
|
-
|
|
297
|
-
act(() => {
|
|
298
|
-
request = result.current.submitRequest({
|
|
299
|
-
type: 'access',
|
|
300
|
-
subject: {
|
|
301
|
-
name: 'John Doe',
|
|
302
|
-
email: 'john@example.com',
|
|
303
|
-
},
|
|
304
|
-
createdAt: Date.now(),
|
|
305
|
-
});
|
|
306
|
-
});
|
|
307
|
-
|
|
308
|
-
expect(request).not.toBeNull();
|
|
309
|
-
|
|
310
|
-
if (request) {
|
|
311
|
-
const formattedRequest = result.current.formatRequest(request);
|
|
312
|
-
expect(formattedRequest).toBeDefined();
|
|
313
|
-
expect(formattedRequest.requestType).toBe('access');
|
|
314
|
-
expect(formattedRequest.dataSubject.name).toBe('John Doe');
|
|
315
|
-
}
|
|
316
|
-
});
|
|
317
|
-
|
|
318
|
-
it('should get request type by ID', () => {
|
|
319
|
-
const { result } = renderHook(() => useDSR({
|
|
320
|
-
requestTypes: mockRequestTypes,
|
|
321
|
-
storageKey: 'test-dsr',
|
|
322
|
-
useLocalStorage: true
|
|
323
|
-
}));
|
|
324
|
-
|
|
325
|
-
const requestType = result.current.getRequestType('access');
|
|
326
|
-
expect(requestType).toBeDefined();
|
|
327
|
-
expect(requestType?.name).toBe('Access Request');
|
|
328
|
-
expect(requestType?.estimatedCompletionTime).toBe(30);
|
|
329
|
-
});
|
|
330
|
-
});
|