@tantainnovative/ndpr-toolkit
Version:
Nigeria Data Protection Toolkit — enterprise-grade compliance components for the Nigeria Data Protection Act (NDPA) 2023
607 lines (579 loc) • 17.6 kB
TypeScript
import * as React_2 from 'react';
import React__default from 'react';
/**
* Assesses the risk level of a DPIA based on the identified risks
* @param dpiaResult The DPIA result containing risks to assess
* @returns Assessment result with overall risk level and recommendations
*/
export declare function assessDPIARisk(dpiaResult: DPIAResult): {
overallRiskLevel: 'low' | 'medium' | 'high' | 'critical';
requiresConsultation: boolean;
canProceed: boolean;
recommendations: string[];
};
export declare const DPIA: {
Provider: React_2.FC<DPIAProviderProps>;
Questionnaire: React_2.FC<DPIAQuestionnaireProps>;
Report: React_2.FC<DPIAReportProps>;
StepIndicator: React_2.FC<StepIndicatorProps>;
};
/** A map of question IDs to their answer values */
declare type DPIAAnswerMap = Record<string, DPIAAnswerValue>;
/** Possible value types for a DPIA answer */
declare type DPIAAnswerValue = string | number | boolean | string[];
declare interface DPIAContextValue extends UseDPIAReturn {
sections: DPIASection[];
}
export declare const DPIAProvider: React__default.FC<DPIAProviderProps>;
export declare interface DPIAProviderProps {
sections: DPIASection[];
initialAnswers?: DPIAAnswerMap;
adapter?: StorageAdapter<DPIAAnswerMap>;
storageKey?: string;
useLocalStorage?: boolean;
onComplete?: (result: DPIAResult) => void;
children: React__default.ReactNode;
}
/**
* Data Protection Impact Assessment types aligned with NDPA 2023 Section 28
* A DPIA is required when processing is likely to result in high risk to data subjects
*/
/**
* Represents a question in the DPIA questionnaire
*/
export declare interface DPIAQuestion {
/** Unique identifier for the question */
id: string;
/** The text of the question */
text: string;
/** Additional guidance for answering the question */
guidance?: string;
/** Type of input required for the answer */
type: 'text' | 'textarea' | 'select' | 'radio' | 'checkbox' | 'scale';
/** Options for select, radio, or checkbox questions */
options?: Array<{
value: string;
label: string;
riskLevel?: 'low' | 'medium' | 'high';
}>;
/** For scale questions, the minimum value */
minValue?: number;
/** For scale questions, the maximum value */
maxValue?: number;
/** For scale questions, labels for the scale points */
scaleLabels?: Record<number, string>;
/** Whether the question is required */
required: boolean;
/** Risk level associated with this question */
riskLevel?: 'low' | 'medium' | 'high';
/** Whether this question triggers additional questions based on the answer */
hasDependentQuestions?: boolean;
/** Conditions that determine when this question should be shown */
showWhen?: Array<{
questionId: string;
operator: 'equals' | 'contains' | 'greaterThan' | 'lessThan';
value: string | number | boolean;
}>;
}
/**
* DPIA questionnaire component. Implements NDPA Section 28 requirements
* for conducting Data Privacy Impact Assessments on high-risk processing activities.
*/
export declare const DPIAQuestionnaire: React__default.FC<DPIAQuestionnaireProps>;
export declare interface DPIAQuestionnaireClassNames {
/** Outermost wrapper */
root?: string;
/** Header area containing progress indicator */
header?: string;
/** Section title */
title?: string;
/** Section container */
section?: string;
/** Section title heading */
sectionTitle?: string;
/** Individual question wrapper */
question?: string;
/** Question label text */
questionText?: string;
/** Guidance / help text below a question */
guidance?: string;
/** Text / textarea / select inputs */
input?: string;
/** Radio option group container */
radioGroup?: string;
/** Individual radio option row */
radioOption?: string;
/** Navigation button container */
navigation?: string;
/** Next / submit button */
nextButton?: string;
/** Previous button */
prevButton?: string;
/** Alias for nextButton */
primaryButton?: string;
/** Alias for prevButton */
secondaryButton?: string;
/** Progress bar wrapper */
progressBar?: string;
}
declare interface DPIAQuestionnaireProps {
/**
* Sections of the DPIA questionnaire
*/
sections: DPIASection[];
/**
* Current answers to the questionnaire
*/
answers: Record<string, string | number | boolean | string[]>;
/**
* Callback function called when an answer is updated
*/
onAnswerChange: (questionId: string, value: string | number | boolean | string[]) => void;
/**
* Current section index
*/
currentSectionIndex: number;
/**
* Callback function called when user navigates to the next section
*/
onNextSection?: () => void;
/**
* Callback function called when user navigates to the previous section
*/
onPrevSection?: () => void;
/**
* Validation errors for the current section
*/
validationErrors?: Record<string, string>;
/**
* Whether the questionnaire is in read-only mode
* @default false
*/
readOnly?: boolean;
/**
* Custom CSS class for the questionnaire
*/
className?: string;
/**
* Custom CSS class for the buttons
*/
buttonClassName?: string;
/**
* Text for the next button
* @default "Next"
*/
nextButtonText?: string;
/**
* Text for the previous button
* @default "Previous"
*/
prevButtonText?: string;
/**
* Text for the submit button (shown on the last section)
* @default "Submit"
*/
submitButtonText?: string;
/**
* Whether to show a progress indicator
* @default true
*/
showProgress?: boolean;
/**
* Current progress percentage (0-100)
*/
progress?: number;
/**
* Per-section class name overrides
*/
classNames?: DPIAQuestionnaireClassNames;
/**
* When true, all default classes are stripped.
* Only explicit overrides from `classNames` are applied.
* @default false
*/
unstyled?: boolean;
}
/**
* DPIA report component. Implements NDPA Section 28 requirements for documenting
* and presenting Data Protection Impact Assessment findings, risks, and recommendations.
*/
export declare const DPIAReport: React__default.FC<DPIAReportProps>;
export declare interface DPIAReportClassNames {
/** Outermost wrapper */
root?: string;
/** Report header area */
header?: string;
/** Main report title */
title?: string;
/** Executive summary section */
summary?: string;
/** Risk level badge */
riskBadge?: string;
/** Risks table element */
riskTable?: string;
/** Individual risk row */
riskRow?: string;
/** Recommendation list item */
recommendation?: string;
/** Conclusion text */
conclusion?: string;
/** Print button */
printButton?: string;
/** Alias for printButton */
primaryButton?: string;
}
declare interface DPIAReportProps {
/**
* The DPIA result to display
*/
result: DPIAResult;
/**
* The sections of the DPIA questionnaire
*/
sections: DPIASection[];
/**
* Whether to show the full report or just a summary
* @default true
*/
showFullReport?: boolean;
/**
* Whether to allow printing the report
* @default true
*/
allowPrint?: boolean;
/**
* Whether to allow exporting the report as PDF
* @default true
*/
allowExport?: boolean;
/**
* Callback function called when the report is exported
*/
onExport?: (format: 'pdf' | 'docx' | 'html') => void;
/**
* Custom CSS class for the report container
*/
className?: string;
/**
* Custom CSS class for the buttons
*/
buttonClassName?: string;
/**
* Per-section class name overrides
*/
classNames?: DPIAReportClassNames;
/**
* When true, all default classes are stripped.
* Only explicit overrides from `classNames` are applied.
* @default false
*/
unstyled?: boolean;
}
/**
* Represents the result of a completed DPIA
*/
export declare interface DPIAResult {
/** Unique identifier for the DPIA */
id: string;
/** Title of the DPIA */
title: string;
/** Description of the processing activity being assessed */
processingDescription: string;
/** Timestamp when the DPIA was started */
startedAt: number;
/** Timestamp when the DPIA was completed */
completedAt?: number;
/** Person responsible for conducting the DPIA */
assessor: {
name: string;
role: string;
email: string;
};
/** Answers to all questions in the DPIA */
answers: Record<string, string | number | boolean | string[]>;
/** Risks identified in the DPIA */
risks: DPIARisk[];
/** Overall risk level of the processing activity */
overallRiskLevel: 'low' | 'medium' | 'high' | 'critical';
/** Whether the DPIA concluded that the processing can proceed */
canProceed: boolean;
/** Reasons why the processing can or cannot proceed */
conclusion: string;
/** Recommendations for the processing activity */
recommendations?: string[];
/** Next review date for the DPIA */
reviewDate?: number;
/** Version of the DPIA questionnaire used */
version: string;
/**
* Whether prior consultation with NDPC is required
* Per NDPA Section 28(2), consultation is required when DPIA indicates high residual risk
*/
ndpcConsultationRequired?: boolean;
/** Date when NDPC consultation was initiated */
ndpcConsultationDate?: number;
/** Reference number from NDPC consultation */
ndpcConsultationReference?: string;
/**
* The lawful basis for the processing activity being assessed
*/
lawfulBasis?: string;
/**
* Whether this DPIA involves cross-border data transfers
*/
involvesCrossBorderTransfer?: boolean;
}
/**
* Represents a risk identified in the DPIA
*/
export declare interface DPIARisk {
/** Unique identifier for the risk */
id: string;
/** Description of the risk */
description: string;
/** Likelihood of the risk occurring (1-5) */
likelihood: number;
/** Impact if the risk occurs (1-5) */
impact: number;
/** Overall risk score (likelihood * impact) */
score: number;
/** Risk level based on the score */
level: 'low' | 'medium' | 'high' | 'critical';
/** Measures to mitigate the risk */
mitigationMeasures?: string[];
/** Whether the risk has been mitigated */
mitigated: boolean;
/** Residual risk score after mitigation */
residualScore?: number;
/** Questions that identified this risk */
relatedQuestionIds: string[];
}
/**
* Represents a section in the DPIA questionnaire
*/
export declare interface DPIASection {
/** Unique identifier for the section */
id: string;
/** Title of the section */
title: string;
/** Description of the section */
description?: string;
/** Questions in this section */
questions: DPIAQuestion[];
/** Order of the section in the questionnaire */
order: number;
}
declare interface Step {
/**
* Unique identifier for the step
*/
id: string;
/**
* Display label for the step
*/
label: string;
/**
* Optional description for the step
*/
description?: string;
/**
* Whether the step is completed
*/
completed: boolean;
/**
* Whether the step is the current active step
*/
active: boolean;
/**
* Optional icon for the step
*/
icon?: React__default.ReactNode;
}
export declare const StepIndicator: React__default.FC<StepIndicatorProps>;
export declare interface StepIndicatorClassNames {
/** Outermost wrapper */
root?: string;
/** Individual step wrapper */
step?: string;
/** Active step circle / indicator */
stepActive?: string;
/** Completed step circle / indicator */
stepCompleted?: string;
/** Pending (incomplete, inactive) step circle / indicator */
stepPending?: string;
/** Connector line between steps */
connector?: string;
/** Step label text */
label?: string;
}
declare interface StepIndicatorProps {
/**
* Array of steps to display
*/
steps: Step[];
/**
* Callback function called when a step is clicked
*/
onStepClick?: (stepId: string) => void;
/**
* Whether the steps are clickable
* @default true
*/
clickable?: boolean;
/**
* Orientation of the step indicator
* @default "horizontal"
*/
orientation?: 'horizontal' | 'vertical';
/**
* Custom CSS class for the container
*/
className?: string;
/**
* Custom CSS class for the active step
*/
activeStepClassName?: string;
/**
* Custom CSS class for completed steps
*/
completedStepClassName?: string;
/**
* Custom CSS class for incomplete steps
*/
incompleteStepClassName?: string;
/**
* Per-section class name overrides
*/
classNames?: StepIndicatorClassNames;
/**
* When true, all default classes are stripped.
* Only explicit overrides from `classNames` are applied.
* @default false
*/
unstyled?: boolean;
}
export declare interface StorageAdapter<T = unknown> {
/** Load persisted data. Called once on hook mount. */
load(): T | null | Promise<T | null>;
/** Persist data. Called on every state change. */
save(data: T): void | Promise<void>;
/** Clear persisted data. Called on reset. */
remove(): void | Promise<void>;
}
/**
* Hook for conducting Data Protection Impact Assessments in compliance with the NDPA 2023.
*
* @example
* ```tsx
* import { useDPIA } from '@tantainnovative/ndpr-toolkit/hooks';
*
* function DPIAWizard({ sections }) {
* const { currentSection, progress, updateAnswer, nextSection } = useDPIA({ sections });
* return (
* <div>
* <h2>{currentSection?.title} ({progress}%)</h2>
* <button onClick={nextSection}>Next</button>
* </div>
* );
* }
* ```
*/
export declare function useDPIA({ sections, initialAnswers, adapter, storageKey, useLocalStorage, onComplete, }: UseDPIAOptions): UseDPIAReturn;
export declare function useDPIACompound(): DPIAContextValue;
declare interface UseDPIAOptions {
/**
* Sections of the DPIA questionnaire
*/
sections: DPIASection[];
/**
* Initial answers (if resuming a DPIA)
*/
initialAnswers?: DPIAAnswerMap;
/**
* Pluggable storage adapter. When provided, takes precedence over storageKey/useLocalStorage.
*/
adapter?: StorageAdapter<DPIAAnswerMap>;
/**
* Storage key for DPIA data
* @default "ndpr_dpia_data"
* @deprecated Use adapter instead
*/
storageKey?: string;
/**
* Whether to use local storage to persist DPIA data
* @default true
* @deprecated Use adapter instead
*/
useLocalStorage?: boolean;
/**
* Callback function called when the DPIA is completed
*/
onComplete?: (result: DPIAResult) => void;
}
declare interface UseDPIAReturn {
/**
* Current section index
*/
currentSectionIndex: number;
/**
* Current section
*/
currentSection: DPIASection | null;
/**
* All answers
*/
answers: DPIAAnswerMap;
/**
* Update an answer
*/
updateAnswer: (questionId: string, value: DPIAAnswerValue) => void;
/**
* Go to the next section
*/
nextSection: () => boolean;
/**
* Go to the previous section
*/
prevSection: () => boolean;
/**
* Go to a specific section
*/
goToSection: (index: number) => boolean;
/**
* Check if the current section is valid
*/
isCurrentSectionValid: () => boolean;
/**
* Get validation errors for the current section
*/
getCurrentSectionErrors: () => Record<string, string>;
/**
* Check if the DPIA is complete
*/
isComplete: () => boolean;
/**
* Complete the DPIA and generate a result
*/
completeDPIA: (assessorInfo: {
name: string;
role: string;
email: string;
}, title: string, processingDescription: string) => DPIAResult;
/**
* Get the visible questions for the current section
*/
getVisibleQuestions: () => DPIAQuestion[];
/**
* Reset the DPIA
*/
resetDPIA: () => void;
/**
* Progress percentage
*/
progress: number;
/**
* Whether the adapter is still loading data (relevant for async adapters)
*/
isLoading: boolean;
}
export { }