VulnCheck - Open Source Vulnerability Management for Wazuh Features: - Vulnerability management with Wazuh integration - AI-powered CVE analysis (OpenAI, Anthropic, Google, DeepSeek, Ollama, Infomaniak) - SLA policy enforcement with automated email alerts - Automated patch verification via Wazuh Syscollector - Role-based access control (Admin, Editor, Readonly) - PDF/CSV reporting for compliance workflows - Full audit trail https://gitea.isuit.ch/vulncheck/vulncheck
77 lines
3.7 KiB
TypeScript
77 lines
3.7 KiB
TypeScript
|
|
import { SparklesIcon } from '@heroicons/react/24/outline';
|
|
import { Recommendation } from '../types';
|
|
|
|
interface AIRecommendationsProps {
|
|
recommendations: Recommendation[];
|
|
strategy?: string;
|
|
loading?: boolean;
|
|
error?: string | null;
|
|
}
|
|
|
|
export default function AIRecommendations({ recommendations, strategy, loading, error }: AIRecommendationsProps) {
|
|
if (loading) {
|
|
return (
|
|
<div className="bg-gradient-to-br from-indigo-50 to-blue-50 border border-indigo-100 p-6 rounded-sm shadow-sm mb-8 animate-pulse">
|
|
<div className="h-4 w-48 bg-indigo-200 rounded mb-4"></div>
|
|
<div className="space-y-3">
|
|
<div className="h-8 bg-white rounded"></div>
|
|
<div className="h-8 bg-white rounded"></div>
|
|
</div>
|
|
</div>
|
|
);
|
|
}
|
|
|
|
if (error) {
|
|
return (
|
|
<div className="bg-red-50 border border-red-200 p-4 rounded-sm shadow-sm mb-8">
|
|
<div className="flex items-center">
|
|
<SparklesIcon className="h-4 w-4 text-red-500 mr-2" />
|
|
<p className="text-sm text-red-700 font-bold">AI Analysis Error</p>
|
|
</div>
|
|
<p className="text-xs text-red-600 mt-1">{error}</p>
|
|
<p className="text-[10px] text-red-400 mt-2 italic">Note: Ensure your Infomaniak AI settings are correct and the model is set to 'llama3'.</p>
|
|
</div>
|
|
);
|
|
}
|
|
|
|
if (!recommendations || recommendations.length === 0) {
|
|
return (
|
|
<div className="bg-gray-50 border border-gray-200 p-4 rounded-sm shadow-sm mb-8 text-center text-gray-500 hover:bg-gray-100 transition-colors cursor-pointer" onClick={() => window.location.reload()}>
|
|
<p className="text-sm italic">No AI recommendations available yet. Try running an "AI Audit" above.</p>
|
|
</div>
|
|
);
|
|
}
|
|
|
|
return (
|
|
<div className="bg-gradient-to-br from-indigo-50 to-blue-50 border border-indigo-200 p-6 rounded-sm shadow-sm mb-8">
|
|
<div className="flex items-center mb-4">
|
|
<SparklesIcon className="h-5 w-5 text-indigo-600 mr-2" />
|
|
<h3 className="text-lg font-bold text-indigo-900 font-mono italic">AI-Engine: Priority Recommendations</h3>
|
|
</div>
|
|
|
|
{strategy && (
|
|
<p className="text-sm text-indigo-800 mb-6 bg-white/50 p-3 rounded border border-indigo-100 italic">
|
|
"{strategy}"
|
|
</p>
|
|
)}
|
|
|
|
<div className="grid gap-4 md:grid-cols-2 lg:grid-cols-3">
|
|
{recommendations.map((rec, index) => (
|
|
<div key={index} className="bg-white p-4 rounded border border-indigo-100 shadow-sm hover:shadow-md transition-shadow">
|
|
<div className="flex justify-between items-start mb-2">
|
|
<span className="text-xs font-bold text-indigo-600 uppercase tracking-wider font-mono">Priority #{rec.priority}</span>
|
|
<span className="text-xs px-2 py-0.5 bg-indigo-100 text-indigo-700 rounded-full font-bold">{rec.cve_id}</span>
|
|
</div>
|
|
<p className="text-sm font-bold text-gray-900 mb-1">{rec.asset_hostname}</p>
|
|
<p className="text-xs text-gray-600 mb-3 line-clamp-2">{rec.justification}</p>
|
|
<div className="text-[10px] text-indigo-500 font-mono border-t border-indigo-50 pt-2">
|
|
<span className="font-bold">Next Step:</span> {rec.remediation_hint}
|
|
</div>
|
|
</div>
|
|
))}
|
|
</div>
|
|
</div>
|
|
);
|
|
}
|