export function vendorComplianceSurvey(form: FormTs) {
// Vendor Compliance Assessment - Security and compliance questionnaire
// Demonstrates: Pages (multi-page), MatrixQuestion, CheckboxList, RatingScale, ThumbRating, dynamic styling
// ============================================
// HEADER
// ============================================
form.addRow(row => {
row.addTextPanel('header', {
label: 'Vendor Compliance Assessment',
computedValue: () => 'Complete this assessment to evaluate vendor security, compliance, and operational readiness. All responses will be reviewed by our compliance team.',
customStyles: {
backgroundColor: '#7c3aed',
color: 'white',
padding: '24px',
borderRadius: '12px',
textAlign: 'center'
}
});
});
// ============================================
// MULTI-PAGE WIZARD
// ============================================
const pages = form.addPages('assessmentPages', {
heightMode: 'current-page'
});
// ============================================
// PAGE 1: Company Information
// ============================================
const page1 = pages.addPage('companyInfo');
page1.setTitle(() => 'Step 1: Company Information');
page1.addRow(row => {
row.addTextbox('companyName', {
label: 'Company legal name',
placeholder: 'Enter legal entity name',
isRequired: true
}, '1fr');
row.addTextbox('dba', {
label: 'DBA / Trading name (if different)',
placeholder: 'Enter DBA name'
}, '1fr');
});
page1.addRow(row => {
row.addTextbox('headquarters', {
label: 'Headquarters location',
placeholder: 'City, Country',
isRequired: true
}, '1fr');
row.addDropdown('companySize', {
label: 'Company size',
options: [
{ id: '1-50', name: '1-50 employees' },
{ id: '51-200', name: '51-200 employees' },
{ id: '201-1000', name: '201-1000 employees' },
{ id: '1001-5000', name: '1001-5000 employees' },
{ id: '5000+', name: '5000+ employees' }
],
placeholder: 'Select size...',
isRequired: true
}, '1fr');
});
page1.addRow(row => {
row.addDropdown('vendorType', {
label: 'Type of services provided',
options: [
{ id: 'saas', name: 'SaaS / Cloud Software' },
{ id: 'consulting', name: 'Consulting / Professional Services' },
{ id: 'infrastructure', name: 'Infrastructure / Hosting' },
{ id: 'data-processing', name: 'Data Processing' },
{ id: 'marketing', name: 'Marketing / Advertising' },
{ id: 'hr-services', name: 'HR / Payroll Services' },
{ id: 'financial', name: 'Financial Services' },
{ id: 'other', name: 'Other' }
],
placeholder: 'Select type...',
isRequired: true
}, '1fr');
row.addDropdown('dataAccess', {
label: 'Level of data access required',
options: [
{ id: 'none', name: 'No access to our data' },
{ id: 'public', name: 'Public data only' },
{ id: 'internal', name: 'Internal/confidential data' },
{ id: 'sensitive', name: 'Sensitive/PII data' },
{ id: 'critical', name: 'Critical/regulated data' }
],
placeholder: 'Select access level...',
isRequired: true
}, '1fr');
});
page1.addRow(row => {
row.addTextbox('primaryContact', {
label: 'Primary security contact name',
placeholder: 'Name of security/compliance contact',
isRequired: true
}, '1fr');
row.addEmail('contactEmail', {
label: 'Security contact email',
placeholder: 'security@vendor.com',
isRequired: true
}, '1fr');
});
// ============================================
// PAGE 2: Security Certifications
// ============================================
const page2 = pages.addPage('securityCerts');
page2.setTitle(() => 'Step 2: Security Certifications');
page2.addRow(row => {
row.addCheckboxList('certifications', {
label: 'Which security certifications does your organization hold?',
options: [
{ id: 'soc2-1', name: 'SOC 2 Type I' },
{ id: 'soc2-2', name: 'SOC 2 Type II' },
{ id: 'iso27001', name: 'ISO 27001' },
{ id: 'iso27017', name: 'ISO 27017 (Cloud Security)' },
{ id: 'iso27018', name: 'ISO 27018 (PII Protection)' },
{ id: 'pci-dss', name: 'PCI DSS' },
{ id: 'hipaa', name: 'HIPAA Compliance' },
{ id: 'fedramp', name: 'FedRAMP' },
{ id: 'gdpr', name: 'GDPR Compliant' },
{ id: 'ccpa', name: 'CCPA Compliant' },
{ id: 'none', name: 'No certifications currently' }
],
orientation: 'vertical'
});
});
page2.addRow(row => {
row.addTextarea('certificationDetails', {
label: 'Certification details and expiration dates',
placeholder: 'List certification dates and any relevant details...',
rows: 3,
isVisible: () => {
const certs = page2.checkboxList('certifications')?.value() ?? [];
return certs.length > 0 && !certs.includes('none');
}
});
});
page2.addRow(row => {
row.addThumbRating('independentAudits', {
label: 'Do you undergo regular independent security audits?',
showLabels: true,
upLabel: 'Yes',
downLabel: 'No',
alignment: 'left'
});
});
page2.addRow(row => {
row.addDropdown('auditFrequency', {
label: 'How often are security audits conducted?',
options: [
{ id: 'annual', name: 'Annually' },
{ id: 'biannual', name: 'Twice per year' },
{ id: 'quarterly', name: 'Quarterly' },
{ id: 'continuous', name: 'Continuous monitoring' }
],
placeholder: 'Select frequency...',
isVisible: () => page2.thumbRating('independentAudits')?.value() === 'up'
});
});
// ============================================
// PAGE 3: Data Security Practices
// ============================================
const page3 = pages.addPage('dataSecurity');
page3.setTitle(() => 'Step 3: Data Security Practices');
page3.addRow(row => {
row.addMatrixQuestion('securityPractices', {
label: 'Rate your implementation of the following security controls:',
rows: [
{ id: 'encryption-transit', label: 'Data encryption in transit', isRequired: true },
{ id: 'encryption-rest', label: 'Data encryption at rest', isRequired: true },
{ id: 'access-control', label: 'Role-based access control', isRequired: true },
{ id: 'mfa', label: 'Multi-factor authentication', isRequired: true },
{ id: 'logging', label: 'Security logging & monitoring', isRequired: false },
{ id: 'vuln-mgmt', label: 'Vulnerability management', isRequired: false },
{ id: 'patch-mgmt', label: 'Patch management', isRequired: false }
],
columns: [
{ id: 'not-implemented', label: 'Not Implemented' },
{ id: 'partial', label: 'Partially' },
{ id: 'implemented', label: 'Implemented' },
{ id: 'mature', label: 'Mature/Documented' }
],
striped: true,
fullWidth: true
});
});
page3.addRow(row => {
row.addRadioButton('dataLocation', {
label: 'Where is customer data stored?',
options: [
{ id: 'us-only', name: 'United States only' },
{ id: 'eu-only', name: 'European Union only' },
{ id: 'customer-choice', name: 'Customer-specified region' },
{ id: 'multiple', name: 'Multiple regions/global' }
],
orientation: 'vertical',
isRequired: true
});
});
page3.addRow(row => {
row.addCheckboxList('dataRetention', {
label: 'Data retention and deletion capabilities:',
options: [
{ id: 'custom-retention', name: 'Configurable retention periods' },
{ id: 'auto-delete', name: 'Automatic data deletion' },
{ id: 'on-request', name: 'Deletion on customer request' },
{ id: 'export', name: 'Data export capability' },
{ id: 'right-to-forget', name: 'Right to be forgotten support' }
],
orientation: 'vertical'
});
});
// ============================================
// PAGE 4: Incident Response & Business Continuity
// ============================================
const page4 = pages.addPage('incidentResponse');
page4.setTitle(() => 'Step 4: Incident Response & Business Continuity');
page4.addRow(row => {
row.addThumbRating('incidentPlan', {
label: 'Do you have a documented incident response plan?',
showLabels: true,
upLabel: 'Yes',
downLabel: 'No',
alignment: 'left'
});
});
page4.addRow(row => {
row.addDropdown('incidentNotification', {
label: 'How quickly do you notify customers of security incidents?',
options: [
{ id: '24h', name: 'Within 24 hours' },
{ id: '48h', name: 'Within 48 hours' },
{ id: '72h', name: 'Within 72 hours' },
{ id: 'asap', name: 'As soon as practical' },
{ id: 'varies', name: 'Depends on severity' }
],
placeholder: 'Select timeframe...',
isRequired: true
});
});
page4.addRow(row => {
row.addThumbRating('bcpDrp', {
label: 'Do you have Business Continuity (BCP) and Disaster Recovery (DRP) plans?',
showLabels: true,
upLabel: 'Yes',
downLabel: 'No',
alignment: 'left'
});
});
page4.addRow(row => {
row.addMatrixQuestion('continuityMetrics', {
label: 'Business continuity capabilities:',
rows: [
{ id: 'rto', label: 'Recovery Time Objective (RTO)', isRequired: false },
{ id: 'rpo', label: 'Recovery Point Objective (RPO)', isRequired: false },
{ id: 'uptime', label: 'Uptime SLA commitment', isRequired: false },
{ id: 'testing', label: 'DR testing frequency', isRequired: false }
],
columns: [
{ id: 'none', label: 'Not Defined' },
{ id: 'basic', label: 'Basic' },
{ id: 'good', label: 'Good' },
{ id: 'excellent', label: 'Excellent' }
],
striped: true,
fullWidth: true,
isVisible: () => page4.thumbRating('bcpDrp')?.value() === 'up'
});
});
page4.addRow(row => {
row.addCheckboxList('insurance', {
label: 'Insurance coverage held:',
options: [
{ id: 'cyber', name: 'Cyber liability insurance' },
{ id: 'errors', name: 'Errors & omissions (E&O)' },
{ id: 'general', name: 'General liability' },
{ id: 'professional', name: 'Professional liability' }
],
orientation: 'vertical'
});
});
// ============================================
// PAGE 5: Compliance & Review
// ============================================
const page5 = pages.addPage('complianceReview');
page5.setTitle(() => 'Step 5: Compliance Acknowledgment');
page5.addRow(row => {
row.addRatingScale('overallRisk', {
preset: 'likert-5',
label: 'How would you rate your organization\'s overall security maturity?',
lowLabel: 'Basic',
highLabel: 'Advanced',
alignment: 'center'
});
});
const riskLevel = form.computedValue(() => {
const dataAccess = page1.dropdown('dataAccess')?.value();
const certs = page2.checkboxList('certifications')?.value() ?? [];
const hasAudits = page2.thumbRating('independentAudits')?.value() === 'up';
const hasBcp = page4.thumbRating('bcpDrp')?.value() === 'up';
let risk = 'medium';
// High risk factors
if (dataAccess === 'sensitive' || dataAccess === 'critical') {
if (certs.includes('none') || certs.length === 0) {
risk = 'high';
}
}
// Low risk factors
if ((certs.includes('soc2-2') || certs.includes('iso27001')) && hasAudits && hasBcp) {
risk = 'low';
}
return risk;
});
page5.addRow(row => {
row.addTextPanel('riskAssessment', {
label: 'Preliminary Risk Assessment',
computedValue: () => {
const risk = riskLevel();
const dataAccess = page1.dropdown('dataAccess')?.value();
const certs = page2.checkboxList('certifications')?.value() ?? [];
const accessLabels: Record<string, string> = {
'none': 'No data access',
'public': 'Public data only',
'internal': 'Internal/confidential data',
'sensitive': 'Sensitive/PII data',
'critical': 'Critical/regulated data'
};
let summary = 'Risk Profile Summary\n';
summary += '═'.repeat(25) + '\n\n';
summary += `Data Access Level: ${accessLabels[dataAccess ?? ''] || 'Not specified'}\n`;
summary += `Certifications: ${certs.length > 0 && !certs.includes('none') ? certs.length : 'None'}\n`;
summary += `\nPreliminary Risk Level: ${risk.toUpperCase()}`;
return summary;
},
customStyles: () => {
const risk = riskLevel();
const baseStyles = {
padding: '16px',
borderRadius: '8px',
whiteSpace: 'pre-wrap',
fontFamily: 'monospace',
fontSize: '14px'
};
if (risk === 'low') {
return { ...baseStyles, backgroundColor: '#d1fae5', borderLeft: '4px solid #10b981' };
} else if (risk === 'high') {
return { ...baseStyles, backgroundColor: '#fee2e2', borderLeft: '4px solid #ef4444' };
}
return { ...baseStyles, backgroundColor: '#fef3c7', borderLeft: '4px solid #f59e0b' };
}
});
});
page5.addSpacer();
page5.addRow(row => {
row.addTextarea('additionalInfo', {
label: 'Additional information or clarifications',
placeholder: 'Provide any additional context about your security practices...',
rows: 3
});
});
page5.addRow(row => {
row.addCheckbox('accuracyCertification', {
label: 'I certify that the information provided in this assessment is accurate and complete to the best of my knowledge',
isRequired: true
});
});
page5.addRow(row => {
row.addTextbox('certifierName', {
label: 'Certifier name and title',
placeholder: 'John Smith, Chief Security Officer',
isRequired: true
}, '1fr');
row.addDatepicker('certificationDate', {
label: 'Date',
isRequired: true
}, '200px');
});
// ============================================
// FORM CONFIGURATION
// ============================================
form.configureSubmitButton({
label: 'Submit Assessment',
isVisible: () => page5.checkbox('accuracyCertification')?.value() === true
});
form.configureCompletionScreen({
type: 'text',
title: 'Assessment Submitted',
message: 'Thank you for completing the vendor compliance assessment. Our compliance team will review your responses and may reach out for additional documentation or clarification. You will receive a risk assessment summary within 5 business days.'
});
}