(
            self, es_index_name, name, index_name='', description='',
            provider='Manually added to OpenSearch',
            context='Added via API client', data_label='OpenSearch',
            status='ready')
return timeline_obj
Creates and returns a Timeline from OpenSearch data.

        This function can be used to import data into a sketch that was
        ingested via different mechanism, such as ELK, etc.

        The function creates the necessary structures (SearchIndex and a
        Timeline) for Timesketch to be able to properly support it.

        Args:
            es_index_name: name of the index in OpenSearch.
            name: string with the name of the timeline.
            index_name: optional string for the SearchIndex name, defaults
                to the same as the es_index_name.
            description: optional string with a description of the timeline.
            provider: optional string with the provider name for the data
                source of the imported data. Defaults to "Manually added
                to OpenSearch".
            context: optional string with the context for the data upload,
                defaults to "Added via API client".
            data_label: optional string with the data label of the OpenSearch
                data, defaults to "OpenSearch".
            status: Optional string, if provided will be used as a status
                for the searchindex, valid options are: "ready", "fail",
                "processing", "timeout". Defaults to "ready".

        Raises:
            ValueError: If there are errors in the generation of the
            timeline.

        Returns:
            Instance of a Timeline object.
Creates and returns a Timeline from OpenSearch data.
Creates and returns a Timeline from OpenSearch data .
def generate_timeline_from_es_index(
            self, es_index_name, name, index_name='', description='',
            provider='Manually added to OpenSearch',
            context='Added via API client', data_label='OpenSearch',
            status='ready'):
        """Creates and returns a Timeline from OpenSearch data.

        This function can be used to import data into a sketch that was
        ingested via different mechanism, such as ELK, etc.

        The function creates the necessary structures (SearchIndex and a
        Timeline) for Timesketch to be able to properly support it.

        Args:
            es_index_name: name of the index in OpenSearch.
            name: string with the name of the timeline.
            index_name: optional string for the SearchIndex name, defaults
                to the same as the es_index_name.
            description: optional string with a description of the timeline.
            provider: optional string with the provider name for the data
                source of the imported data. Defaults to "Manually added
                to OpenSearch".
            context: optional string with the context for the data upload,
                defaults to "Added via API client".
            data_label: optional string with the data label of the OpenSearch
                data, defaults to "OpenSearch".
            status: Optional string, if provided will be used as a status
                for the searchindex, valid options are: "ready", "fail",
                "processing", "timeout". Defaults to "ready".

        Raises:
            ValueError: If there are errors in the generation of the
            timeline.

        Returns:
            Instance of a Timeline object.
        """
        if not es_index_name:
            raise ValueError('ES index needs to be provided.')

        if not name:
            raise ValueError('Timeline name needs to be provided.')

        # Step 1: Make sure the index doesn't exist already.
        for index_obj in self.api.list_searchindices():
            if index_obj is None:
                continue
            if index_obj.index_name == es_index_name:
                raise ValueError(
                    'Unable to add the ES index, since it already exists.')

        # Step 2: Create a SearchIndex.
        resource_url = f'{self.api.api_root}/searchindices/'
        form_data = {
            'searchindex_name': index_name or es_index_name,
            'es_index_name': es_index_name,
        }
        response = self.api.session.post(resource_url, json=form_data)

        if response.status_code not in definitions.HTTP_STATUS_CODE_20X:
            error.error_message(
                response, message='Error creating searchindex',
                error=ValueError)

        response_dict = error.get_response_json(response, logger)
        objects = response_dict.get('objects')
        if not objects:
            raise ValueError(
                'Unable to create a SearchIndex, try again or file an '
                'issue on GitHub.')

        searchindex_id = objects[0].get('id')

        # Step 3: Verify mappings to make sure data conforms.
        index_obj = api_index.SearchIndex(searchindex_id, api=self.api)
        index_fields = set(index_obj.fields)

        if not self._NECESSARY_DATA_FIELDS.issubset(index_fields):
            index_obj.status = 'fail'
            raise ValueError(
                'Unable to ingest data since it is missing required '
                'fields: {0:s} [ingested data contains these fields: '
                '{1:s}]'.format(
                    ', '.join(self._NECESSARY_DATA_FIELDS.difference(
                        index_fields)), '|'.join(index_fields)))

        if status:
            index_obj.status = status

        # Step 4: Create the Timeline.
        resource_url = f'{self.api.api_root}/sketches/{self.id}/timelines/'
        form_data = {'timeline': searchindex_id, 'timeline_name': name}
        response = self.api.session.post(resource_url, json=form_data)

        if response.status_code not in definitions.HTTP_STATUS_CODE_20X:
            error.error_message(
                response, message='Error creating a timeline object',
                error=ValueError)

        response_dict = error.get_response_json(response, logger)
        objects = response_dict.get('objects')
        if not objects:
            raise ValueError(
                'Unable to create a Timeline, try again or file an '
                'issue on GitHub.')

        timeline_dict = objects[0]

        timeline_obj = timeline.Timeline(
            timeline_id=timeline_dict['id'],
            sketch_id=self.id,
            api=self.api,
            name=timeline_dict['name'],
            searchindex=timeline_dict['searchindex']['index_name'])

        # Step 5: Add the timeline ID into the dataset.
        resource_url = (
            f'{self.api.api_root}/sketches/{self.id}/event/add_timeline_id/')
        form_data = {
            'searchindex_id': searchindex_id,
            'timeline_id': timeline_dict['id'],
        }
        response = self.api.session.post(resource_url, json=form_data)

        if response.status_code not in definitions.HTTP_STATUS_CODE_20X:
            error.error_message(
                response, message='Unable to add timeline identifier to data',
                error=ValueError)

        # Step 6: Add a DataSource object.
        resource_url = f'{self.api.api_root}/sketches/{self.id}/datasource/'
        form_data = {
            'timeline_id': timeline_dict['id'],
            'provider': provider,
            'context': context,
            'data_label': data_label,
        }
        response = self.api.session.post(resource_url, json=form_data)
        if response.status_code not in definitions.HTTP_STATUS_CODE_20X:
            error.error_message(
                response, message='Error creating a datasource object',
                error=ValueError)

        _ = error.get_response_json(response, logger)

        return timeline_obj
def generate_timeline_from_es_index ( self , es_index_name , name , index_name = '' , description = '' , provider = 'Manually added to OpenSearch' , context = 'Added via API client' , data_label = 'OpenSearch' , status = 'ready' ) : if not es_index_name : raise ValueError ( 'ES index needs to be provided.' ) if not name : raise ValueError ( 'Timeline name needs to be provided.' ) # Step 1: Make sure the index doesn't exist already. for index_obj in self . api . list_searchindices ( ) : if index_obj is None : continue if index_obj . index_name == es_index_name : raise ValueError ( 'Unable to add the ES index, since it already exists.' ) # Step 2: Create a SearchIndex. resource_url = f'{self.api.api_root}/searchindices/' form_data = { 'searchindex_name' : index_name or es_index_name , 'es_index_name' : es_index_name , } response = self . api . session . post ( resource_url , json = form_data ) if response . status_code not in definitions . HTTP_STATUS_CODE_20X : error . error_message ( response , message = 'Error creating searchindex' , error = ValueError ) response_dict = error . get_response_json ( response , logger ) objects = response_dict . get ( 'objects' ) if not objects : raise ValueError ( 'Unable to create a SearchIndex, try again or file an ' 'issue on GitHub.' ) searchindex_id = objects [ 0 ] . get ( 'id' ) # Step 3: Verify mappings to make sure data conforms. index_obj = api_index . SearchIndex ( searchindex_id , api = self . api ) index_fields = set ( index_obj . fields ) if not self . _NECESSARY_DATA_FIELDS . issubset ( index_fields ) : index_obj . status = 'fail' raise ValueError ( 'Unable to ingest data since it is missing required ' 'fields: {0:s} [ingested data contains these fields: ' '{1:s}]' . format ( ', ' . join ( self . _NECESSARY_DATA_FIELDS . difference ( index_fields ) ) , '|' . join ( index_fields ) ) ) if status : index_obj . status = status # Step 4: Create the Timeline. resource_url = f'{self.api.api_root}/sketches/{self.id}/timelines/' form_data = { 'timeline' : searchindex_id , 'timeline_name' : name } response = self . api . session . post ( resource_url , json = form_data ) if response . status_code not in definitions . HTTP_STATUS_CODE_20X : error . error_message ( response , message = 'Error creating a timeline object' , error = ValueError ) response_dict = error . get_response_json ( response , logger ) objects = response_dict . get ( 'objects' ) if not objects : raise ValueError ( 'Unable to create a Timeline, try again or file an ' 'issue on GitHub.' ) timeline_dict = objects [ 0 ] timeline_obj = timeline . Timeline ( timeline_id = timeline_dict [ 'id' ] , sketch_id = self . id , api = self . api , name = timeline_dict [ 'name' ] , searchindex = timeline_dict [ 'searchindex' ] [ 'index_name' ] ) # Step 5: Add the timeline ID into the dataset. resource_url = ( f'{self.api.api_root}/sketches/{self.id}/event/add_timeline_id/' ) form_data = { 'searchindex_id' : searchindex_id , 'timeline_id' : timeline_dict [ 'id' ] , } response = self . api . session . post ( resource_url , json = form_data ) if response . status_code not in definitions . HTTP_STATUS_CODE_20X : error . error_message ( response , message = 'Unable to add timeline identifier to data' , error = ValueError ) # Step 6: Add a DataSource object. resource_url = f'{self.api.api_root}/sketches/{self.id}/datasource/' form_data = { 'timeline_id' : timeline_dict [ 'id' ] , 'provider' : provider , 'context' : context , 'data_label' : data_label , } response = self . api . session . post ( resource_url , json = form_data ) if response . status_code not in definitions . HTTP_STATUS_CODE_20X : error . error_message ( response , message = 'Error creating a datasource object' , error = ValueError ) _ = error . get_response_json ( response , logger ) return timeline_obj