|
28 | 28 |
|
29 | 29 | import requests |
30 | 30 |
|
31 | | -misperrors = {'error': 'Error'} |
| 31 | +misperrors = {"error": "Error"} |
32 | 32 |
|
33 | 33 | mispattributes = { |
34 | | - 'input': [ |
35 | | - 'ip-src', 'ip-dst', |
36 | | - 'domain', 'hostname', |
37 | | - 'url', |
38 | | - 'md5', 'sha1', 'sha256', |
39 | | - 'email-src', 'email-dst', |
| 34 | + "input": [ |
| 35 | + "ip-src", |
| 36 | + "ip-dst", |
| 37 | + "domain", |
| 38 | + "hostname", |
| 39 | + "url", |
| 40 | + "md5", |
| 41 | + "sha1", |
| 42 | + "sha256", |
| 43 | + "email-src", |
| 44 | + "email-dst", |
40 | 45 | ], |
41 | | - 'output': ['text'], |
42 | | - 'format': 'misp_standard', |
| 46 | + "output": ["text"], |
| 47 | + "format": "misp_standard", |
43 | 48 | } |
44 | 49 |
|
45 | 50 | moduleinfo = { |
46 | | - 'version': '1.0', |
47 | | - 'author': 'SOCRadar', |
48 | | - 'description': 'Enrich MISP attributes with SOCRadar threat intelligence. ' |
49 | | - 'Queries SOCRadar IoC Enrichment API for categorization, ' |
50 | | - 'malware families, threat actors, confidence scores, ' |
51 | | - 'feed source history, and geographic attribution.', |
52 | | - 'module-type': ['expansion', 'hover'], |
53 | | - 'name': 'SOCRadar Threat Intelligence', |
54 | | - 'logo': 'socradar.png', |
55 | | - 'requirements': ['requests'], |
56 | | - 'features': ( |
57 | | - 'Query SOCRadar IoC Enrichment API to enrich MISP attributes with ' |
58 | | - 'threat intelligence context. Supports IP, domain, URL, hash, and ' |
59 | | - 'email lookups. Two modes: STIX (fast) and Full (detailed with ' |
60 | | - 'categorization, history, and optional AI insight). ' |
61 | | - 'Requires a SOCRadar Advanced Threat Intelligence API key.' |
| 51 | + "version": "1.0", |
| 52 | + "author": "SOCRadar", |
| 53 | + "description": ( |
| 54 | + "Enrich MISP attributes with SOCRadar threat intelligence. " |
| 55 | + "Queries SOCRadar IoC Enrichment API for categorization, " |
| 56 | + "malware families, threat actors, confidence scores, " |
| 57 | + "feed source history, and geographic attribution." |
62 | 58 | ), |
63 | | - 'references': [ |
64 | | - 'https://socradar.io', |
65 | | - 'https://platform.socradar.com', |
| 59 | + "module-type": ["expansion", "hover"], |
| 60 | + "name": "SOCRadar Threat Intelligence", |
| 61 | + "logo": "socradar.png", |
| 62 | + "requirements": ["requests"], |
| 63 | + "features": ( |
| 64 | + "Query SOCRadar IoC Enrichment API to enrich MISP attributes with " |
| 65 | + "threat intelligence context. Supports IP, domain, URL, hash, and " |
| 66 | + "email lookups. Two modes: STIX (fast) and Full (detailed with " |
| 67 | + "categorization, history, and optional AI insight). " |
| 68 | + "Requires a SOCRadar Advanced Threat Intelligence API key." |
| 69 | + ), |
| 70 | + "references": [ |
| 71 | + "https://socradar.io", |
| 72 | + "https://platform.socradar.com", |
66 | 73 | ], |
67 | | - 'input': 'A MISP attribute of type ip-src, ip-dst, domain, hostname, ' |
68 | | - 'url, md5, sha1, sha256, email-src, or email-dst.', |
69 | | - 'output': 'Enrichment data including categorization, malware families, ' |
70 | | - 'threat actors, confidence score, SOCRadar threat score, ' |
71 | | - 'feed source history, and country attribution.', |
| 74 | + "input": ( |
| 75 | + "A MISP attribute of type ip-src, ip-dst, domain, hostname, url, md5, sha1, sha256, email-src, or email-dst." |
| 76 | + ), |
| 77 | + "output": ( |
| 78 | + "Enrichment data including categorization, malware families, " |
| 79 | + "threat actors, confidence score, SOCRadar threat score, " |
| 80 | + "feed source history, and country attribution." |
| 81 | + ), |
72 | 82 | } |
73 | 83 |
|
74 | 84 | moduleconfig = [ |
75 | | - 'socradar_api_key', |
76 | | - 'socradar_api_url', |
77 | | - 'socradar_mode', |
78 | | - 'socradar_ai_insight', |
| 85 | + "socradar_api_key", |
| 86 | + "socradar_api_url", |
| 87 | + "socradar_mode", |
| 88 | + "socradar_ai_insight", |
79 | 89 | ] |
80 | 90 |
|
81 | 91 | # ═══════════════════════════════════════════════════════════════════════════ |
@@ -386,85 +396,84 @@ def handler(q=False): |
386 | 396 | return False |
387 | 397 |
|
388 | 398 | request = json.loads(q) |
389 | | - config = request.get('config', {}) |
| 399 | + config = request.get("config", {}) |
390 | 400 |
|
391 | 401 | # --- Validate API key --- |
392 | | - api_key = config.get('socradar_api_key', '').strip() |
| 402 | + api_key = config.get("socradar_api_key", "").strip() |
393 | 403 | if not api_key: |
394 | | - misperrors['error'] = ( |
395 | | - 'SOCRadar API key is required. ' |
396 | | - 'Get your Advanced Threat Intelligence API key at ' |
397 | | - 'https://platform.socradar.com → API Management' |
| 404 | + misperrors["error"] = ( |
| 405 | + "SOCRadar API key is required. " |
| 406 | + "Get your Advanced Threat Intelligence API key at " |
| 407 | + "https://platform.socradar.com → API Management" |
398 | 408 | ) |
399 | 409 | return misperrors |
400 | 410 |
|
401 | | - api_url = config.get('socradar_api_url', DEFAULT_API_URL).rstrip('/') |
402 | | - mode = config.get('socradar_mode', 'full').strip().lower() |
403 | | - include_ai = config.get('socradar_ai_insight', 'false').strip().lower() in ('true', '1', 'yes') |
| 411 | + api_url = config.get("socradar_api_url", DEFAULT_API_URL).rstrip("/") |
| 412 | + mode = config.get("socradar_mode", "full").strip().lower() |
| 413 | + include_ai = config.get("socradar_ai_insight", "false").strip().lower() in ("true", "1", "yes") |
404 | 414 |
|
405 | 415 | # --- Extract attribute value --- |
406 | | - attribute = request.get('attribute', {}) |
407 | | - search_value = attribute.get('value', '') |
| 416 | + attribute = request.get("attribute", {}) |
| 417 | + search_value = attribute.get("value", "") |
408 | 418 |
|
409 | 419 | if not search_value: |
410 | | - for attr_type in mispattributes['input']: |
| 420 | + for attr_type in mispattributes["input"]: |
411 | 421 | if attr_type in request: |
412 | 422 | search_value = request[attr_type] |
413 | 423 | break |
414 | 424 |
|
415 | 425 | if not search_value: |
416 | | - misperrors['error'] = 'No attribute value provided for enrichment' |
| 426 | + misperrors["error"] = "No attribute value provided for enrichment" |
417 | 427 | return misperrors |
418 | 428 |
|
419 | 429 | # --- Query SOCRadar API --- |
420 | 430 | try: |
421 | | - if mode == 'stix': |
| 431 | + if mode == "stix": |
422 | 432 | data = _call_indicator_details_stix(api_url, api_key, search_value) |
423 | 433 | enrichment_text, tags = _format_stix_result(data, search_value) |
424 | 434 | else: |
425 | 435 | data = _call_indicator_details(api_url, api_key, search_value, include_ai) |
426 | 436 | enrichment_text, tags = _format_full_result(data, search_value) |
427 | 437 |
|
428 | 438 | except requests.exceptions.HTTPError as e: |
429 | | - status = e.response.status_code if e.response else 'unknown' |
| 439 | + status = e.response.status_code if e.response else "unknown" |
430 | 440 | if status == 401: |
431 | | - misperrors['error'] = ( |
432 | | - 'SOCRadar API authentication failed. ' |
433 | | - 'Please check your API key. ' |
434 | | - 'A valid Advanced Threat Intelligence API key is required. ' |
435 | | - 'Get yours at https://platform.socradar.com → API Management' |
| 441 | + misperrors["error"] = ( |
| 442 | + "SOCRadar API authentication failed. " |
| 443 | + "Please check your API key. " |
| 444 | + "A valid Advanced Threat Intelligence API key is required. " |
| 445 | + "Get yours at https://platform.socradar.com → API Management" |
436 | 446 | ) |
437 | 447 | elif status == 400: |
438 | | - misperrors['error'] = f'SOCRadar API bad request for indicator: {search_value}' |
| 448 | + misperrors["error"] = f"SOCRadar API bad request for indicator: {search_value}" |
439 | 449 | else: |
440 | | - misperrors['error'] = f'SOCRadar API error (HTTP {status}): {str(e)}' |
| 450 | + misperrors["error"] = f"SOCRadar API error (HTTP {status}): {str(e)}" |
441 | 451 | return misperrors |
442 | 452 |
|
443 | 453 | except requests.exceptions.Timeout: |
444 | | - misperrors['error'] = ( |
445 | | - 'SOCRadar API request timed out. ' |
446 | | - 'If using AI insight mode, try disabling it for faster results.' |
| 454 | + misperrors["error"] = ( |
| 455 | + "SOCRadar API request timed out. If using AI insight mode, try disabling it for faster results." |
447 | 456 | ) |
448 | 457 | return misperrors |
449 | 458 |
|
450 | 459 | except Exception as e: |
451 | | - misperrors['error'] = f'SOCRadar API query failed: {str(e)}' |
| 460 | + misperrors["error"] = f"SOCRadar API query failed: {str(e)}" |
452 | 461 | return misperrors |
453 | 462 |
|
454 | 463 | # --- Return results --- |
455 | 464 | result = { |
456 | | - 'types': ['text'], |
457 | | - 'values': [enrichment_text], |
458 | | - 'tags': tags, |
| 465 | + "types": ["text"], |
| 466 | + "values": [enrichment_text], |
| 467 | + "tags": tags, |
459 | 468 | } |
460 | 469 |
|
461 | | - return {'results': [result]} |
| 470 | + return {"results": [result]} |
462 | 471 |
|
463 | 472 |
|
464 | 473 | def introspection(): |
465 | 474 | return mispattributes |
466 | 475 |
|
467 | 476 |
|
468 | 477 | def version(): |
469 | | - moduleinfo['config'] = moduleconfig |
| 478 | + moduleinfo["config"] = moduleconfig |
470 | 479 | return moduleinfo |
0 commit comments