From bdc8af0efb28203d7d7b147e1196601a2472eaeb Mon Sep 17 00:00:00 2001 From: jean-baptiste-perez-bib Date: Thu, 5 Dec 2024 15:51:30 +0100 Subject: [PATCH 1/4] Allow showing processing timeline events (backend) The POST /sketches/{sketchId}/explore/ endpoint can now be parameterized to include processing timeline indices. --- timesketch/api/v1/resources/aggregation.py | 2 +- timesketch/api/v1/resources/explore.py | 8 ++++++-- timesketch/lib/utils.py | 10 ++++++++-- timesketch/models/sketch.py | 4 ++-- 4 files changed, 17 insertions(+), 7 deletions(-) diff --git a/timesketch/api/v1/resources/aggregation.py b/timesketch/api/v1/resources/aggregation.py index 1b25827e34..de3d13064a 100644 --- a/timesketch/api/v1/resources/aggregation.py +++ b/timesketch/api/v1/resources/aggregation.py @@ -468,7 +468,7 @@ def post(self, sketch_id): sketch_indices = { t.searchindex.index_name for t in sketch.timelines - if t.get_status.status.lower() == "ready" + if t.get_status.status.lower() in ["ready", "processing"] } aggregation_dsl = form.aggregation_dsl.data diff --git a/timesketch/api/v1/resources/explore.py b/timesketch/api/v1/resources/explore.py index c45a917f87..f2b38a4149 100644 --- a/timesketch/api/v1/resources/explore.py +++ b/timesketch/api/v1/resources/explore.py @@ -142,7 +142,9 @@ def post(self, sketch_id): query_filter = request.json.get("filter", {}) parent = request.json.get("parent", None) incognito = request.json.get("incognito", False) - + include_processing_timelines = request.json.get( + "includeProcessingTimelines", False + ) return_field_string = form.fields.data if return_field_string: return_fields = [x.strip() for x in return_field_string.split(",")] @@ -163,7 +165,9 @@ def post(self, sketch_id): # Make sure that the indices in the filter are part of the sketch. # This will also remove any deleted timeline from the search result. - indices, timeline_ids = get_validated_indices(indices, sketch) + indices, timeline_ids = get_validated_indices( + indices, sketch, include_processing_timelines + ) # Remove indices that don't exist from search. indices = utils.validate_indices(indices, self.datastore) diff --git a/timesketch/lib/utils.py b/timesketch/lib/utils.py index 43bb552766..9cb39c091b 100644 --- a/timesketch/lib/utils.py +++ b/timesketch/lib/utils.py @@ -526,21 +526,27 @@ def read_and_validate_jsonl( ) -def get_validated_indices(indices, sketch): +def get_validated_indices(indices, sketch, include_processing_timelines=False): """Exclude any deleted search index references. Args: indices: List of indices from the user sketch: A sketch object (instance of models.sketch.Sketch). + include_processing_timelines: True to include processing + timelines, Flase otherwise. Returns: Tuple of two items: List of indices with those removed that is not in the sketch List of timeline IDs that should be part of the output. """ + allowed_statuses = ["ready"] + if include_processing_timelines: + allowed_statuses.append("processing") + sketch_structure = {} for timeline in sketch.timelines: - if timeline.get_status.status.lower() != "ready": + if timeline.get_status.status.lower() not in allowed_statuses: continue index_ = timeline.searchindex.index_name sketch_structure.setdefault(index_, []) diff --git a/timesketch/models/sketch.py b/timesketch/models/sketch.py index cda99d7bf0..f41350ca06 100644 --- a/timesketch/models/sketch.py +++ b/timesketch/models/sketch.py @@ -135,7 +135,7 @@ def get_view_urls(self): @property def active_timelines(self): - """List timelines that are ready for analysis. + """List timelines that are being processed or ready for analysis. Returns: List of instances of timesketch.models.sketch.Timeline @@ -144,7 +144,7 @@ def active_timelines(self): for timeline in self.timelines: timeline_status = timeline.get_status.status index_status = timeline.searchindex.get_status.status - if (timeline_status or index_status) in ("processing", "fail", "archived"): + if (timeline_status or index_status) in ("fail", "archived"): continue _timelines.append(timeline) return _timelines From 28045746be6e8ded0e9a6280d12516f1b021a265 Mon Sep 17 00:00:00 2001 From: jean-baptiste-perez-bib Date: Mon, 23 Dec 2024 15:51:29 +0100 Subject: [PATCH 2/4] Add a user setting to enable processing timeline events Default value is "false" (legacy behaviour). --- .../frontend-ng/src/components/SettingsDialog.vue | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/timesketch/frontend-ng/src/components/SettingsDialog.vue b/timesketch/frontend-ng/src/components/SettingsDialog.vue index ca7e789dd2..719fd313a9 100644 --- a/timesketch/frontend-ng/src/components/SettingsDialog.vue +++ b/timesketch/frontend-ng/src/components/SettingsDialog.vue @@ -40,6 +40,17 @@ limitations under the License. > + + + + + + Show processing timeline events + Select to include events from timelines in processing state + + @@ -49,6 +60,7 @@ import ApiClient from '../utils/RestApiClient' const DEFAULT_SETTINGS = { showLeftPanel: true, + showProcessingTimelineEvents: false, } export default { @@ -57,6 +69,7 @@ export default { settings: { showLeftPanel: true, generateQuery: true, + showProcessingTimelineEvents: false, }, } }, From 86f6b7ef7cbf56795c2feeb664db5676c1832d31 Mon Sep 17 00:00:00 2001 From: jean-baptiste-perez-bib Date: Mon, 23 Dec 2024 14:26:06 +0100 Subject: [PATCH 3/4] Allow showing processing timeline events (frontend) --- .../src/components/Explore/EventList.vue | 5 +++++ .../src/components/Explore/TimelineChip.vue | 4 ++-- .../components/Explore/TimelineComponent.vue | 14 ++++++++---- .../components/LeftPanel/TimelinesTable.vue | 22 +++++++++++++++---- 4 files changed, 35 insertions(+), 10 deletions(-) diff --git a/timesketch/frontend-ng/src/components/Explore/EventList.vue b/timesketch/frontend-ng/src/components/Explore/EventList.vue index 53918775e7..caa5824be9 100644 --- a/timesketch/frontend-ng/src/components/Explore/EventList.vue +++ b/timesketch/frontend-ng/src/components/Explore/EventList.vue @@ -681,6 +681,9 @@ export default { activeContext() { return this.$store.state.activeContext }, + settings() { + return this.$store.state.settings + }, filterChips: function () { return this.currentQueryFilter.chips.filter((chip) => chip.type === 'label' || chip.type === 'term') }, @@ -864,6 +867,8 @@ export default { formData['facet'] = this.activeContext.facetId formData['question'] = this.activeContext.questionId + formData['includeProcessingTimelines'] = this.settings.showProcessingTimelineEvents + ApiClient.search(this.sketch.id, formData) .then((response) => { this.eventList.objects = response.data.objects diff --git a/timesketch/frontend-ng/src/components/Explore/TimelineChip.vue b/timesketch/frontend-ng/src/components/Explore/TimelineChip.vue index aeafed1ce7..e99a444ca8 100644 --- a/timesketch/frontend-ng/src/components/Explore/TimelineChip.vue +++ b/timesketch/frontend-ng/src/components/Explore/TimelineChip.vue @@ -50,7 +50,7 @@ limitations under the License.