1
-from enum import Enum
2
-from typing import Any
3
-from typing import Dict
4
-from typing import List
5
-from typing import Optional
6
-
7
-from fastapi import HTTPException
8
-from pydantic import BaseModel
9
-from pydantic import Extra
10
-from pydantic import Field
11
-from pydantic import validator
12
-
13
-from app.integrations.alert_creation.general.schema.alert import IrisAsset
14
-from app.integrations.alert_creation.general.schema.alert import IrisIoc
15
-
16
-
17
-class WazuhSourceFieldsToRemove(Enum):
18
- GL2 = "gl2"
19
- RULE_MITRE_TACTIC = "rule_mitre_tactic"
20
- RULE_MITRE_ID = "rule_mitre_id"
21
- RULE_MITRE_TECHNIQUE = "rule_mitre_technique"
22
- RULE_ID = "rule_id"
23
- MESSAGE = "message"
24
- # Add more fields as needed
25
-
26
-
27
-class MonitoringAlertsRequestModel(BaseModel):
28
- id: Optional[int] = None
29
- alert_id: str
30
- alert_index: str
31
- customer_code: str
32
- alert_source: str
33
-
34
- class Config:
35
- orm_mode = True
36
-
37
-
38
-class MonitoringAlertsResponseModel(BaseModel):
39
- success: bool
40
- message: str
41
- monitoring_alerts: List[MonitoringAlertsRequestModel]
42
-
43
-
44
-class MonitoringWazuhAlertsRequestModel(BaseModel):
45
- customer_code: str
46
-
47
-
48
-class GraylogEventFields(BaseModel):
49
- ALERT_ID: str = Field(
50
- ...,
51
- description="Unique identifier for the alert",
52
- example="65f6a260-c1f3-11ee-93bc-86000046278a",
53
- )
54
- ALERT_SOURCE: str = Field(..., description="Source of the alert", example="WAZUH")
55
- CUSTOMER_CODE: str = Field(
56
- ...,
57
- description="Customer code associated with the alert",
58
- example="00002",
59
- )
60
-
61
-
62
-class GraylogEvent(BaseModel):
63
- id: str = Field(
64
- ...,
65
- description="Unique identifier for the event",
66
- example="01HNNF2YCM5SSV3KDQJSRK0EV0",
67
- )
68
- event_definition_type: str = Field(
69
- ...,
70
- description="Type of event definition",
71
- example="aggregation-v1",
72
- )
73
- event_definition_id: str = Field(
74
- ...,
75
- description="Identifier for the event definition",
76
- example="65bd28505e9a2d550cf521e7",
77
- )
78
- origin_context: str = Field(
79
- ...,
80
- description="Context from which the event originated",
81
- example="urn:graylog:message:es:wazuh_00002_290:65f6a260-c1f3-11ee-93bc-86000046278a",
82
- )
83
- timestamp: str = Field(
84
- ...,
85
- description="Timestamp when the event occurred",
86
- example="2024-02-02T17:49:22.694Z",
87
- )
88
- timestamp_processing: str = Field(
89
- ...,
90
- description="Timestamp when the event was processed",
91
- example="2024-02-02T17:50:26.708Z",
92
- )
93
- timerange_start: Optional[str] = Field(
94
- None,
95
- description="Start of the timerange for the event",
96
- example=None,
97
- )
98
- timerange_end: Optional[str] = Field(
99
- None,
100
- description="End of the timerange for the event",
101
- example=None,
102
- )
103
- streams: List[str] = Field(
104
- ...,
105
- description="List of streams associated with the event",
106
- example=[],
107
- )
108
- source_streams: List[str] = Field(
109
- ...,
110
- description="List of source streams for the event",
111
- example=["645a3a6123e5cc30bbc0e5dc"],
112
- )
113
- message: str = Field(
114
- ...,
115
- description="Message associated with the event",
116
- example="COPILOT TESTING WAZUH",
117
- )
118
- source: str = Field(..., description="Source of the event", example="ASHGRL02")
119
- key_tuple: List[str] = Field(
120
- ...,
121
- description="Tuple keys associated with the event",
122
- example=[],
123
- )
124
- key: str = Field(..., description="Key associated with the event", example="")
125
- priority: int = Field(..., description="Priority of the event", example=2)
126
- alert: bool = Field(
127
- ...,
128
- description="Indicates if the event is an alert",
129
- example=True,
130
- )
131
- # fields: GraylogEventFields = Field(..., description="Custom fields for the event")
132
- fields: Dict[str, Any] = Field(..., description="Custom fields for the event")
133
- group_by_fields: Dict[str, Any] = Field(
134
- ...,
135
- description="Fields used to group events",
136
- example={},
137
- )
138
-
139
- @property
140
- def alert_index(self) -> str:
141
- return self.origin_context.split(":")[4]
142
-
143
- @property
144
- def alert_id(self) -> str:
145
- return self.origin_context.split(":")[5]
146
-
147
- @validator("fields")
148
- def check_customer_code(cls, fields):
149
- if "CUSTOMER_CODE" not in fields:
150
- raise HTTPException(
151
- status_code=400,
152
- detail="CUSTOMER_CODE is required in the fields",
153
- )
154
- return fields
155
-
156
-
157
-class GraylogPostRequest(BaseModel):
158
- event_definition_id: str = Field(
159
- ...,
160
- description="Identifier for the event definition",
161
- example="65bd28505e9a2d550cf521e7",
162
- )
163
- event_definition_type: str = Field(
164
- ...,
165
- description="Type of the event definition",
166
- example="aggregation-v1",
167
- )
168
- event_definition_title: str = Field(
169
- ...,
170
- description="Title of the event definition",
171
- example="COPILOT TESTING WAZUH",
172
- )
173
- event_definition_description: Optional[str] = Field(
174
- None,
175
- description="Description of the event definition",
176
- example="",
177
- )
178
- job_definition_id: str = Field(
179
- ...,
180
- description="Identifier for the job definition",
181
- example="65bd284b5e9a2d550cf521dc",
182
- )
183
- job_trigger_id: str = Field(
184
- ...,
185
- description="Identifier for the job trigger",
186
- example="65bd2b625e9a2d550cf528e4",
187
- )
188
- event: GraylogEvent = Field(..., description="Event details")
189
- backlog: List[str] = Field(
190
- ...,
191
- description="List of backlog items associated with the event",
192
- example=[],
193
- )
194
-
195
-
196
-class GraylogPostResponse(BaseModel):
197
- success: bool = Field(
198
- ...,
199
- description="Indicates if the request was successful",
200
- example=True,
201
- )
202
- message: str = Field(
203
- ...,
204
- description="Message associated with the response",
205
- example="Event processed successfully",
206
- )
207
-
208
-
209
-class AlertAnalysisResponse(BaseModel):
210
- success: bool = Field(
211
- ...,
212
- description="Indicates if the request was successful",
213
- example=True,
214
- )
215
- message: str = Field(
216
- ...,
217
- description="Message associated with the response",
218
- example="Analysis completed successfully",
219
- )
220
-
221
-
222
-# ! Wazuh Indexer Schema ! #
223
-class WazuhSourceModel(BaseModel):
224
- agent_name: str = Field(..., description="The name of the agent.")
225
- agent_id: str = Field(..., description="The id of the agent.")
226
- agent_labels_customer: str = Field(..., description="The customer of the agent.")
227
- rule_id: str = Field(..., description="The id of the rule.")
228
- rule_level: int = Field(..., description="The level of the rule.")
229
- rule_description: str = Field(..., description="The description of the rule.")
230
- timestamp: str = Field(..., description="The timestamp of the alert.")
231
- process_id: Optional[str] = Field(
232
- "n/a",
233
- description="The process id of the alert.",
234
- )
235
- timestamp_utc: Optional[str] = Field(
236
- None,
237
- description="The UTC timestamp of the alert.",
238
- )
239
- process_image: Optional[str] = Field(
240
- "n/a",
241
- description="The process image of the alert.",
242
- )
243
- data_win_eventdata_image: Optional[str] = Field(
244
- "n/a",
245
- description="The image of the event data.",
246
- )
247
-
248
- class Config:
249
- extra = Extra.allow
250
-
251
-
252
-class WazuhAlertModel(BaseModel):
253
- _index: str
254
- _id: str
255
- _version: int
256
- _source: WazuhSourceModel
257
- asset_type_id: Optional[int] = Field(
258
- None,
259
- description="The asset type id of the alert which is needed for when we add the asset to IRIS.",
260
- )
261
- ioc_value: Optional[str] = Field(
262
- None,
263
- description="The IoC value of the alert which is needed for when we add the IoC to IRIS.",
264
- )
265
- ioc_type: Optional[str] = Field(
266
- None,
267
- description="The IoC type of the alert which is needed for when we add the IoC to IRIS.",
268
- )
269
-
270
- class Config:
271
- extra = Extra.allow
272
-
273
- def to_dict(self):
274
- return self.dict(exclude_none=True)
275
-
276
-
277
-class SortOrder(Enum):
278
- desc = "desc"
279
- asc = "asc"
280
-
281
-
282
-class FilterAlertsRequest(BaseModel):
283
- per_page: int = Field(1000, description="The number of alerts to return per page.")
284
- page: int = Field(1, description="The page number to return.")
285
- sort: SortOrder = Field(
286
- SortOrder.desc,
287
- description="The sort order for the alerts.",
288
- )
289
- alert_tags: str = Field(..., description="The tags of the alert.")
290
- alert_status_id: int = Field(
291
- 3,
292
- description="The status of the alert. Default to assigned.",
293
- example=3,
294
- )
295
- alert_customer_id: int = Field(
296
- ...,
297
- description="The customer id of the alert.",
298
- example=1,
299
- )
300
-
301
-
302
-class WazuhIrisAlertContext(BaseModel):
303
- customer_iris_id: int = Field(
304
- ...,
305
- description="IRIS ID of the customer",
306
- example=1,
307
- )
308
- customer_name: str = Field(
309
- ...,
310
- description="Name of the customer",
311
- example="SOCFortress",
312
- )
313
- customer_cases_index: str = Field(
314
- ...,
315
- description="IRIS case index name in the Wazuh-Indexer",
316
- example="dfir_iris_00001",
317
- )
318
- alert_name: str = Field(
319
- ...,
320
- description="Name of the alert",
321
- example="Intrusion Detected",
322
- )
323
- alert_level: int = Field(..., description="Severity level of the alert", example=3)
324
- rule_id: str = Field(
325
- ...,
326
- description="ID of the rule that triggered the alert",
327
- example="2001",
328
- )
329
- rule_mitre_id: Optional[str] = Field(
330
- "n/a",
331
- description="MITRE ATT&CK ID of the rule",
332
- example="T1234",
333
- )
334
- rule_mitre_tactic: Optional[str] = Field(
335
- "n/a",
336
- description="MITRE ATT&CK Tactic",
337
- example="Execution",
338
- )
339
- rule_mitre_technique: Optional[str] = Field(
340
- "n/a",
341
- description="MITRE ATT&CK Technique",
342
- example="Scripting",
343
- )
344
- process_name: Optional[List[str]] = Field(
345
- example=["No process name found"],
346
- description="Name of the process",
347
- )
348
-
349
- class Config:
350
- extra = Extra.allow
351
-
352
-
353
-class WazuhIrisAlertPayload(BaseModel):
354
- alert_title: str = Field(
355
- ...,
356
- description="Title of the alert",
357
- example="Intrusion Detected",
358
- )
359
- alert_description: str = Field(
360
- ...,
361
- description="Description of the alert",
362
- example="Intrusion Detected by Firewall",
363
- )
364
- alert_source: str = Field(..., description="Source of the alert", example="Wazuh")
365
- assets: List[IrisAsset] = Field(..., description="List of affected assets")
366
- alert_status_id: int = Field(..., description="Status ID of the alert", example=3)
367
- alert_severity_id: int = Field(
368
- ...,
369
- description="Severity ID of the alert",
370
- example=5,
371
- )
372
- alert_customer_id: int = Field(
373
- ...,
374
- description="Customer ID related to the alert",
375
- example=1,
376
- )
377
- alert_source_content: Dict[str, Any] = Field(
378
- ...,
379
- description="Original content from the alert source",
380
- )
381
- alert_context: WazuhIrisAlertContext = Field(
382
- ...,
383
- description="Contextual information about the alert",
384
- )
385
- alert_iocs: Optional[List[IrisIoc]] = Field(
386
- None,
387
- description="List of IoCs related to the alert",
388
- )
389
- alert_source_event_time: str = Field(
390
- ...,
391
- description="Timestamp of the alert",
392
- example="2021-01-01T00:00:00.000Z",
393
- )
394
-
395
- def to_dict(self):
396
- return self.dict(exclude_none=True)
397
-
398
-
399
-########### ! CUSTOM ALERTS SCHEMA ! ###########
400
-class CustomSourceModel(BaseModel):
401
- timestamp: str = Field(..., description="The timestamp of the alert.")
402
- timestamp_utc: Optional[str] = Field(
403
- ...,
404
- description="The UTC timestamp of the alert.",
405
- )
406
- time_field: Optional[str] = Field(
407
- "timestamp",
408
- description="The timefield of the alert to be used when creating the IRIS alert.",
409
- )
410
- date: Optional[float] = Field(
411
- None,
412
- description="Date of the alert in Unix timestamp",
413
- )
414
- alert_metadata_tag: Optional[str] = Field(
415
- None,
416
- description="Metadata tag for the alert",
417
- )
418
- alert_gid: Optional[int] = Field(None, description="Alert group ID")
419
-
420
- class Config:
421
- allow_population_by_field_name = True
422
- extra = Extra.allow
423
-
424
- def to_dict(self):
425
- return self.dict(exclude_none=True)
426
-
427
-
428
-class CustomAlertModel(BaseModel):
429
- _index: str
430
- _id: str
431
- _version: int
432
- _source: CustomSourceModel
433
- asset_type_id: Optional[int] = Field(
434
- None,
435
- description="The asset type id of the alert which is needed for when we add the asset to IRIS.",
436
- )
437
- ioc_value: Optional[str] = Field(
438
- None,
439
- description="The IoC value of the alert which is needed for when we add the IoC to IRIS.",
440
- )
441
- ioc_type: Optional[str] = Field(
442
- None,
443
- description="The IoC type of the alert which is needed for when we add the IoC to IRIS.",
444
- )
445
-
446
- class Config:
447
- extra = Extra.allow
448
-
449
- def to_dict(self):
450
- return self.dict(exclude_none=True)
451
-
452
-
453
-########### ! Create Custom Alerts In IRIS Schemas ! ###########
454
-class CustomIrisAsset(BaseModel):
455
- asset_name: Optional[str] = Field(
456
- "Asset Does Not Apply to Custom Alerts",
457
- description="Name of the asset",
458
- example="Server01",
459
- )
460
- asset_ip: Optional[str] = Field(
461
- "Asset Does Not Apply to Custom Alerts",
462
- description="IP address of the asset",
463
- example="192.168.1.1",
464
- )
465
- asset_description: Optional[str] = Field(
466
- "Asset Does Not Apply to Custom Alerts",
467
- description="Description of the asset",
468
- example="Windows Server",
469
- )
470
- asset_type_id: Optional[int] = Field(
471
- 9,
472
- description="Type ID of the asset",
473
- example=1,
474
- )
475
-
476
- def to_dict(self):
477
- return self.dict(exclude_none=True)
478
-
479
-
480
-class CustomIrisIoc(BaseModel):
481
- ioc_value: str = Field(
482
- ...,
483
- description="Value of the IoC",
484
- example="www.google.com",
485
- )
486
- ioc_description: str = Field(
487
- ...,
488
- description="Description of the IoC",
489
- example="Google",
490
- )
491
- ioc_tlp_id: int = Field(1, description="TLP ID of the IoC", example=1)
492
- ioc_type_id: int = Field(20, description="Type ID of the IoC", example=20)
493
-
494
-
495
-class CustomIrisAlertContext(Dict[str, Any]):
496
- _source: CustomSourceModel
497
- alert_id: str = Field(..., description="ID of the alert", example="123")
498
- alert_name: str = Field(
499
- ...,
500
- description="Name of the alert",
501
- example="Intrusion Detected",
502
- )
503
- customer_iris_id: Optional[int] = Field(
504
- None,
505
- description="IRIS ID of the customer",
506
- )
507
- customer_name: Optional[str] = Field(
508
- None,
509
- description="Name of the customer",
510
- )
511
- customer_cases_index: Optional[str] = Field(
512
- None,
513
- description="IRIS case index name in the Wazuh-Indexer",
514
- )
515
- time_field: Optional[str] = Field(
516
- "timestamp_utc",
517
- description="The timefield of the alert to be used when creating the IRIS alert.",
518
- )
519
-
520
- def to_dict(self):
521
- return self.dict(exclude_none=True)
522
-
523
-
524
-class CustomIrisAlertPayload(BaseModel):
525
- alert_title: str = Field(
526
- ...,
527
- description="Title of the alert",
528
- example="Intrusion Detected",
529
- )
530
- alert_description: str = Field(
531
- ...,
532
- description="Description of the alert",
533
- example="Intrusion Detected by Firewall",
534
- )
535
- alert_source: str = Field(..., description="Source of the alert", example="Suricata")
536
- assets: List[CustomIrisAsset] = Field(..., description="List of affected assets")
537
- alert_status_id: int = Field(..., description="Status ID of the alert", example=3)
538
- alert_severity_id: int = Field(
539
- ...,
540
- description="Severity ID of the alert",
541
- example=5,
542
- )
543
- alert_customer_id: int = Field(
544
- ...,
545
- description="Customer ID related to the alert",
546
- example=1,
547
- )
548
- alert_source_content: Dict[str, Any] = Field(
549
- ...,
550
- description="Original content from the alert source",
551
- )
552
- alert_context: CustomIrisAlertContext = Field(
553
- ...,
554
- description="Contextual information about the alert",
555
- )
556
- alert_iocs: Optional[List[IrisIoc]] = Field(
557
- None,
558
- description="List of IoCs related to the alert",
559
- )
560
- alert_source_event_time: str = Field(
561
- ...,
562
- description="Timestamp of the alert",
563
- example="2021-01-01T00:00:00.000Z",
564
- )
565
-
566
- def to_dict(self):
567
- return self.dict(exclude_none=True)
568
-
569
-
570
-########### ! SURICATA ALERTS SCHEMA ! ###########
571
-class SuricataSourceModel(BaseModel):
572
- alert_signature: str = Field(..., description="Signature of the alert")
573
- alert_severity: int = Field(..., description="Severity level of the alert")
574
- alert_signature_id: int = Field(..., description="Signature ID of the alert")
575
- src_ip: str = Field(..., description="Source IP address")
576
- dest_ip: str = Field(..., description="Destination IP address")
577
- app_proto: str = Field(..., description="Application protocol")
578
- agent_labels_customer: str = Field(..., description="Customer of the agent")
579
- timestamp: str = Field(..., description="The timestamp of the alert.")
580
- timestamp_utc: Optional[str] = Field(
581
- ...,
582
- description="The UTC timestamp of the alert.",
583
- )
584
- time_field: Optional[str] = Field(
585
- "timestamp",
586
- description="The timefield of the alert to be used when creating the IRIS alert.",
587
- )
588
- date: Optional[float] = Field(
589
- None,
590
- description="Date of the alert in Unix timestamp",
591
- )
592
- alert_metadata_tag: Optional[str] = Field(
593
- None,
594
- description="Metadata tag for the alert",
595
- )
596
- alert_gid: Optional[int] = Field(None, description="Alert group ID")
597
-
598
- class Config:
599
- allow_population_by_field_name = True
600
- extra = Extra.allow
601
-
602
- def to_dict(self):
603
- return self.dict(exclude_none=True)
604
-
605
-
606
-class SuricataAlertModel(BaseModel):
607
- _index: str
608
- _id: str
609
- _version: int
610
- _source: SuricataSourceModel
611
- asset_type_id: Optional[int] = Field(
612
- None,
613
- description="The asset type id of the alert which is needed for when we add the asset to IRIS.",
614
- )
615
- ioc_value: Optional[str] = Field(
616
- None,
617
- description="The IoC value of the alert which is needed for when we add the IoC to IRIS.",
618
- )
619
- ioc_type: Optional[str] = Field(
620
- None,
621
- description="The IoC type of the alert which is needed for when we add the IoC to IRIS.",
622
- )
623
-
624
- class Config:
625
- extra = Extra.allow
626
-
627
-
628
-########### ! Create Suricata Alerts In IRIS Schemas ! ###########
629
-class SuricataIrisAsset(BaseModel):
630
- asset_name: Optional[str] = Field(
631
- "Asset Does Not Apply to Suricata Alerts",
632
- description="Name of the asset",
633
- example="Server01",
634
- )
635
- asset_ip: Optional[str] = Field(
636
- "Asset Does Not Apply to Suricata Alerts",
637
- description="IP address of the asset",
638
- example="192.168.1.1",
639
- )
640
- asset_description: Optional[str] = Field(
641
- "Asset Does Not Apply to Suricata Alerts",
642
- description="Description of the asset",
643
- example="Windows Server",
644
- )
645
- asset_type_id: Optional[int] = Field(
646
- 9,
647
- description="Type ID of the asset",
648
- example=1,
649
- )
650
-
651
- def to_dict(self):
652
- return self.dict(exclude_none=True)
653
-
654
-
655
-class SuricataIrisIoc(BaseModel):
656
- ioc_value: str = Field(
657
- ...,
658
- description="Value of the IoC",
659
- example="www.google.com",
660
- )
661
- ioc_description: str = Field(
662
- ...,
663
- description="Description of the IoC",
664
- example="Google",
665
- )
666
- ioc_tlp_id: int = Field(1, description="TLP ID of the IoC", example=1)
667
- ioc_type_id: int = Field(20, description="Type ID of the IoC", example=20)
668
-
669
-
670
-class SuricataIrisAlertContext(BaseModel):
671
- _source: SuricataSourceModel
672
- alert_id: str = Field(..., description="ID of the alert", example="123")
673
- alert_name: str = Field(
674
- ...,
675
- description="Name of the alert",
676
- example="Intrusion Detected",
677
- )
678
- alert_level: int = Field(..., description="Severity level of the alert", example=3)
679
- rule_id: int = Field(
680
- ...,
681
- description="ID of the Suricata rule that triggered the alert",
682
- example="2001",
683
- )
684
- src_ip: str = Field(
685
- ...,
686
- description="Source IP address of the alert",
687
- example="1.1.1.1",
688
- )
689
- dest_ip: str = Field(
690
- ...,
691
- description="Destination IP address of the alert",
692
- example="8.8.8.8",
693
- )
694
- app_proto: str = Field(
695
- ...,
696
- description="Application protocol of the alert",
697
- example="TCP",
698
- )
699
- agent_labels_customer: str = Field(
700
- ...,
701
- description="Customer of the endpoint",
702
- example="SOCFortress",
703
- )
704
- customer_iris_id: Optional[int] = Field(
705
- None,
706
- description="IRIS ID of the customer",
707
- )
708
- customer_name: Optional[str] = Field(
709
- None,
710
- description="Name of the customer",
711
- )
712
- customer_cases_index: Optional[str] = Field(
713
- None,
714
- description="IRIS case index name in the Wazuh-Indexer",
715
- )
716
- time_field: Optional[str] = Field(
717
- "timestamp_utc",
718
- description="The timefield of the alert to be used when creating the IRIS alert.",
719
- )
720
-
721
- def to_dict(self):
722
- return self.dict(exclude_none=True)
723
-
724
-
725
-class SuricataIrisAlertPayload(BaseModel):
726
- alert_title: str = Field(
727
- ...,
728
- description="Title of the alert",
729
- example="Intrusion Detected",
730
- )
731
- alert_description: str = Field(
732
- ...,
733
- description="Description of the alert",
734
- example="Intrusion Detected by Firewall",
735
- )
736
- alert_source: str = Field(..., description="Source of the alert", example="Suricata")
737
- assets: List[SuricataIrisAsset] = Field(..., description="List of affected assets")
738
- alert_status_id: int = Field(..., description="Status ID of the alert", example=3)
739
- alert_severity_id: int = Field(
740
- ...,
741
- description="Severity ID of the alert",
742
- example=5,
743
- )
744
- alert_customer_id: int = Field(
745
- ...,
746
- description="Customer ID related to the alert",
747
- example=1,
748
- )
749
- alert_source_content: Dict[str, Any] = Field(
750
- ...,
751
- description="Original content from the alert source",
752
- )
753
- alert_context: SuricataIrisAlertContext = Field(
754
- ...,
755
- description="Contextual information about the alert",
756
- )
757
- alert_iocs: Optional[List[IrisIoc]] = Field(
758
- None,
759
- description="List of IoCs related to the alert",
760
- )
761
- alert_source_event_time: str = Field(
762
- ...,
763
- description="Timestamp of the alert",
764
- example="2021-01-01T00:00:00.000Z",
765
- )
766
-
767
- def to_dict(self):
768
- return self.dict(exclude_none=True)
769
-
770
-
771
-########### ! Office365 Exchange ALERTS SCHEMA ! ###########
772
-class Office365ExchangeSourceModel(BaseModel):
773
- client_ip: Optional[str] = Field("Not found", description="Client IP address")
774
- operation: Optional[str] = Field("Not found", description="Operation")
775
- creation_time: Optional[str] = Field("Not found", description="Creation time")
776
- office365_id: str = Field(..., description="Office365 ID")
777
- organization_name: str = Field(..., description="Organization name")
778
- user_id: str = Field(..., description="User ID")
779
- workload: str = Field(..., description="Workload")
780
- organization_id: str = Field(..., description="Organization ID")
781
- timestamp: str = Field(..., description="The timestamp of the alert.")
782
- timestamp_utc: Optional[str] = Field(
783
- ...,
784
- description="The UTC timestamp of the alert.",
785
- )
786
- time_field: Optional[str] = Field(
787
- "timestamp",
788
- description="The timefield of the alert to be used when creating the IRIS alert.",
789
- )
790
- date: Optional[float] = Field(
791
- None,
792
- description="Date of the alert in Unix timestamp",
793
- )
794
- rule_description: str = Field(
795
- ...,
796
- description="Description of the rule",
797
- )
798
-
799
- class Config:
800
- allow_population_by_field_name = True
801
- extra = Extra.allow
802
-
803
- def to_dict(self):
804
- return self.dict(exclude_none=True)
805
-
806
-
807
-class Office365ExchangeAlertModel(BaseModel):
808
- _index: str
809
- _id: str
810
- _version: int
811
- _source: Office365ExchangeSourceModel
812
- asset_type_id: Optional[int] = Field(
813
- None,
814
- description="The asset type id of the alert which is needed for when we add the asset to IRIS.",
815
- )
816
- ioc_value: Optional[str] = Field(
817
- None,
818
- description="The IoC value of the alert which is needed for when we add the IoC to IRIS.",
819
- )
820
- ioc_type: Optional[str] = Field(
821
- None,
822
- description="The IoC type of the alert which is needed for when we add the IoC to IRIS.",
823
- )
824
-
825
- class Config:
826
- extra = Extra.allow
827
-
828
-
829
-########### ! Create Office365 Exchange Alerts In IRIS Schemas ! ###########
830
-class Office365ExchangeIrisAsset(BaseModel):
831
- asset_name: Optional[str] = Field(
832
- "Asset Does Not Apply to Office365 Exchange Alerts",
833
- description="Name of the asset",
834
- example="test@socfortress.co",
835
- )
836
- asset_description: Optional[str] = Field(
837
- "Asset Does Not Apply to Office365 Exchange Alerts",
838
- description="Description of the asset",
839
- example="Windows Server",
840
- )
841
- asset_type_id: Optional[int] = Field(
842
- 1,
843
- description="Type ID of the asset",
844
- example=1,
845
- )
846
-
847
- def to_dict(self):
848
- return self.dict(exclude_none=True)
849
-
850
-
851
-class Office365ExchangeIrisAlertContext(BaseModel):
852
- _source: Office365ExchangeSourceModel = Field(..., description="Source of the alert")
853
- client_ip: Optional[str] = Field("Not found", description="Client IP address")
854
- operation: Optional[str] = Field("Not found", description="Operation")
855
- creation_time: Optional[str] = Field("Not found", description="Creation time")
856
- office365_id: str = Field(..., description="Office365 ID")
857
- organization_name: str = Field(..., description="Organization name")
858
- user_id: str = Field(..., description="User ID")
859
- workload: str = Field(..., description="Workload")
860
- organization_id: str = Field(..., description="Organization ID")
861
- customer_iris_id: Optional[int] = Field(
862
- None,
863
- description="IRIS ID of the customer",
864
- )
865
- customer_name: Optional[str] = Field(
866
- None,
867
- description="Name of the customer",
868
- )
869
- customer_cases_index: Optional[str] = Field(
870
- None,
871
- description="IRIS case index name in the Wazuh-Indexer",
872
- )
873
- time_field: Optional[str] = Field(
874
- "timestamp_utc",
875
- description="The timefield of the alert to be used when creating the IRIS alert.",
876
- )
877
- rule_description: str = Field(
878
- ...,
879
- description="Description of the rule",
880
- )
881
- rule_id: str = Field(
882
- ...,
883
- description="ID of the rule that triggered the alert",
884
- example="2001",
885
- )
886
-
887
- def to_dict(self):
888
- return self.dict(exclude_none=True)
889
-
890
-
891
-class Office365ExchangeIrisAlertPayload(BaseModel):
892
- alert_title: str = Field(
893
- ...,
894
- description="Title of the alert",
895
- example="Intrusion Detected",
896
- )
897
- alert_description: str = Field(
898
- ...,
899
- description="Description of the alert",
900
- example="Intrusion Detected by Firewall",
901
- )
902
- alert_source: str = Field(..., description="Source of the alert", example="Suricata")
903
- assets: List[Office365ExchangeIrisAsset] = Field(..., description="List of affected assets")
904
- alert_status_id: int = Field(..., description="Status ID of the alert", example=3)
905
- alert_severity_id: int = Field(
906
- ...,
907
- description="Severity ID of the alert",
908
- example=5,
909
- )
910
- alert_customer_id: int = Field(
911
- ...,
912
- description="Customer ID related to the alert",
913
- example=1,
914
- )
915
- alert_source_content: Dict[str, Any] = Field(
916
- ...,
917
- description="Original content from the alert source",
918
- )
919
- alert_context: Office365ExchangeIrisAlertContext = Field(
920
- ...,
921
- description="Contextual information about the alert",
922
- )
923
- alert_iocs: Optional[List[IrisIoc]] = Field(
924
- None,
925
- description="List of IoCs related to the alert",
926
- )
927
- alert_source_event_time: str = Field(
928
- ...,
929
- description="Timestamp of the alert",
930
- example="2021-01-01T00:00:00.000Z",
931
- )
932
-
933
- def to_dict(self):
934
- return self.dict(exclude_none=True)
935
-
936
-
937
-########### ! Office365 Threat Intel ALERTS SCHEMA ! ###########
938
-class Office365ThreatIntelSourceModel(BaseModel):
939
- sender_ip: Optional[str] = Field("Not found", description="Sender IP address")
940
- operation: Optional[str] = Field("Not found", description="Operation")
941
- creation_time: Optional[str] = Field("Not found", description="Creation time")
942
- office365_id: str = Field(..., description="Office365 ID")
943
- recipients: str = Field(..., description="Recipients")
944
- workload: str = Field(..., description="Workload")
945
- organization_id: str = Field(..., description="Organization ID")
946
- timestamp: str = Field(..., description="The timestamp of the alert.")
947
- timestamp_utc: Optional[str] = Field(
948
- ...,
949
- description="The UTC timestamp of the alert.",
950
- )
951
- time_field: Optional[str] = Field(
952
- "timestamp",
953
- description="The timefield of the alert to be used when creating the IRIS alert.",
954
- )
955
- date: Optional[float] = Field(
956
- None,
957
- description="Date of the alert in Unix timestamp",
958
- )
959
- rule_description: str = Field(
960
- ...,
961
- description="Description of the rule",
962
- )
963
-
964
- class Config:
965
- allow_population_by_field_name = True
966
- extra = Extra.allow
967
-
968
- def to_dict(self):
969
- return self.dict(exclude_none=True)
970
-
971
-
972
-class Office365ThreatIntelAlertModel(BaseModel):
973
- _index: str
974
- _id: str
975
- _version: int
976
- _source: Office365ThreatIntelSourceModel
977
- asset_type_id: Optional[int] = Field(
978
- None,
979
- description="The asset type id of the alert which is needed for when we add the asset to IRIS.",
980
- )
981
- ioc_value: Optional[str] = Field(
982
- None,
983
- description="The IoC value of the alert which is needed for when we add the IoC to IRIS.",
984
- )
985
- ioc_type: Optional[str] = Field(
986
- None,
987
- description="The IoC type of the alert which is needed for when we add the IoC to IRIS.",
988
- )
989
-
990
- class Config:
991
- extra = Extra.allow
992
-
993
-
994
-########### ! Create Office365 Threat Intel Alerts In IRIS Schemas ! ###########
995
-class Office365ThreatIntelIrisAsset(BaseModel):
996
- asset_name: Optional[str] = Field(
997
- "Asset Does Not Apply to Office365 Exchange Alerts",
998
- description="Name of the asset",
999
- example="test@socfortress.co",
1000
- )
1001
- asset_description: Optional[str] = Field(
1002
- "Asset Does Not Apply to Office365 Exchange Alerts",
1003
- description="Description of the asset",
1004
- example="Windows Server",
1005
- )
1006
- asset_type_id: Optional[int] = Field(
1007
- 1,
1008
- description="Type ID of the asset",
1009
- example=1,
1010
- )
1011
-
1012
- def to_dict(self):
1013
- return self.dict(exclude_none=True)
1014
-
1015
-
1016
-class Office365ThreatIntelIrisAlertContext(BaseModel):
1017
- _source: Office365ThreatIntelSourceModel = Field(..., description="Source of the alert")
1018
- sender_ip: Optional[str] = Field("Not found", description="Sender IP address")
1019
- operation: Optional[str] = Field("Not found", description="Operation")
1020
- creation_time: Optional[str] = Field("Not found", description="Creation time")
1021
- office365_id: str = Field(..., description="Office365 ID")
1022
- recipients: str = Field(..., description="Recipients")
1023
- workload: str = Field(..., description="Workload")
1024
- organization_id: str = Field(..., description="Organization ID")
1025
- customer_iris_id: Optional[int] = Field(
1026
- None,
1027
- description="IRIS ID of the customer",
1028
- )
1029
- customer_name: Optional[str] = Field(
1030
- None,
1031
- description="Name of the customer",
1032
- )
1033
- customer_cases_index: Optional[str] = Field(
1034
- None,
1035
- description="IRIS case index name in the Wazuh-Indexer",
1036
- )
1037
- time_field: Optional[str] = Field(
1038
- "timestamp_utc",
1039
- description="The timefield of the alert to be used when creating the IRIS alert.",
1040
- )
1041
- rule_description: str = Field(
1042
- ...,
1043
- description="Description of the rule",
1044
- )
1045
- rule_id: str = Field(
1046
- ...,
1047
- description="ID of the rule that triggered the alert",
1048
- example="2001",
1049
- )
1050
-
1051
- def to_dict(self):
1052
- return self.dict(exclude_none=True)
1053
-
1054
-
1055
-class Office365ThreatIntelIrisAlertPayload(BaseModel):
1056
- alert_title: str = Field(
1057
- ...,
1058
- description="Title of the alert",
1059
- example="Intrusion Detected",
1060
- )
1061
- alert_description: str = Field(
1062
- ...,
1063
- description="Description of the alert",
1064
- example="Intrusion Detected by Firewall",
1065
- )
1066
- alert_source: str = Field(..., description="Source of the alert", example="Suricata")
1067
- assets: List[Office365ThreatIntelIrisAsset] = Field(..., description="List of affected assets")
1068
- alert_status_id: int = Field(..., description="Status ID of the alert", example=3)
1069
- alert_severity_id: int = Field(
1070
- ...,
1071
- description="Severity ID of the alert",
1072
- example=5,
1073
- )
1074
- alert_customer_id: int = Field(
1075
- ...,
1076
- description="Customer ID related to the alert",
1077
- example=1,
1078
- )
1079
- alert_source_content: Dict[str, Any] = Field(
1080
- ...,
1081
- description="Original content from the alert source",
1082
- )
1083
- alert_context: Office365ThreatIntelIrisAlertContext = Field(
1084
- ...,
1085
- description="Contextual information about the alert",
1086
- )
1087
- alert_iocs: Optional[List[IrisIoc]] = Field(
1088
- None,
1089
- description="List of IoCs related to the alert",
1090
- )
1091
- alert_source_event_time: str = Field(
1092
- ...,
1093
- description="Timestamp of the alert",
1094
- example="2021-01-01T00:00:00.000Z",
1095
- )
1096
-
1097
- def to_dict(self):
1098
- return self.dict(exclude_none=True)