fylgja/src/blocks/sigma/sigma_conversion_block.js
2025-04-16 18:01:35 -04:00

124 lines
No EOL
3.1 KiB
JavaScript

/**
* sigma_conversion_block.js
*
* Provides block templates for displaying Sigma rule conversion results in Slack
*/
const logger = require('../../utils/logger');
const { getFileName } = require('../../utils/file_utils');
const FILE_NAME = getFileName(__filename);
/**
* Generate blocks for displaying a Sigma rule conversion result
*
* @param {Object} conversionResult - The result of the conversion operation
* @returns {Array} Array of blocks for Slack message
*/
function getConversionResultBlocks(conversionResult) {
logger.debug(`${FILE_NAME}: Generating blocks for conversion result`);
if (!conversionResult || !conversionResult.success) {
logger.warn(`${FILE_NAME}: Invalid conversion result provided for block generation`);
return [{
type: 'section',
text: {
type: 'mrkdwn',
text: 'Error: Failed to generate conversion result blocks'
}
}];
}
const rule = conversionResult.rule || {
id: 'unknown',
title: 'Unknown Rule',
description: 'No rule metadata available'
};
const details = conversionResult.conversionDetails || {
backend: 'lucene',
target: 'ecs_windows',
format: 'siem_rule_ndjson'
};
// Truncate output if it's too long for Slack
let output = conversionResult.output || '';
const maxOutputLength = 2900; // Slack has a limit of ~3000 chars in a code block
const isTruncated = output.length > maxOutputLength;
if (isTruncated) {
output = output.substring(0, maxOutputLength) + '... [truncated]';
}
// Create the blocks
const blocks = [
{
type: 'header',
text: {
type: 'plain_text',
text: `Converted Rule: ${rule.title}`,
emoji: true
}
},
{
type: 'section',
text: {
type: 'mrkdwn',
text: `*Rule ID:* ${rule.id}\n*Description:* ${rule.description}`
}
},
{
type: 'section',
text: {
type: 'mrkdwn',
text: `*Conversion Settings:*\nBackend: \`${details.backend}\` | Target: \`${details.target}\` | Format: \`${details.format}\``
}
},
{
type: 'divider'
},
{
type: 'section',
text: {
type: 'mrkdwn',
text: `*Converted Output:*${isTruncated ? ' (truncated for display)' : ''}\n\`\`\`\n${output}\n\`\`\``
}
}
];
// Action buttons
blocks.push({
type: 'actions',
elements: [
{
type: 'button',
text: {
type: 'plain_text',
text: '🚀 Send to Elasticsearch',
emoji: true
},
value: `select_space_for_rule_${rule.id}`,
action_id: 'select_space_for_rule'
},
]
});
// Warning if output was truncated
if (isTruncated) {
blocks.push({
type: 'context',
elements: [
{
type: 'mrkdwn',
text: ':warning: The output was truncated for display in Slack. Use the copy button to get the full content.'
}
]
});
}
logger.debug(`${FILE_NAME}: Generated ${blocks.length} blocks for conversion result`);
return blocks;
}
module.exports = {
getConversionResultBlocks
};