# AUTOGENERATED! DO NOT EDIT! File to edit: ../../nbs/classes/50_DomoDataflow.ipynb.

# %% ../../nbs/classes/50_DomoDataflow.ipynb 2
from __future__ import annotations

import domolibrary.utils.DictDot as util_dd
import domolibrary.utils.chunk_execution as dmce

from domolibrary.client.DomoEntity import DomoEntity_w_Lineage
import domolibrary.client.DomoError as dmde
import domolibrary.client.DomoAuth as dmda

import domolibrary.routes.dataflow as dataflow_routes

import domolibrary.classes.DomoLineage as dmdl
import domolibrary.classes.DomoJupyter as dmdj

from dataclasses import dataclass, field
from typing import List


import httpx

from nbdev.showdoc import patch_to

# %% auto 0
__all__ = ['DomoDataflow', 'DomoDataflows']

# %% ../../nbs/classes/50_DomoDataflow.ipynb 3
from .DomoDataflow_Action import DomoDataflow_Action
from domolibrary.classes.DomoDataflow_History import (
    DomoDataflow_History,
    DomoDataflow_ActionResult,
)

# %% ../../nbs/classes/50_DomoDataflow.ipynb 6
@dataclass
class DomoDataflow(DomoEntity_w_Lineage):
    id: str
    auth: dmda.DomoAuth = field( repr=False)
    Lineage : dmdl.DomoLineage = field(repr= False)
    
    name: str = None
    owner: str = None
    description: str = None
    tags: list[str] = None
    actions: list[DomoDataflow_Action] = None

    version_id: int = None
    version_number: int = None
    versions: List[dict] = None  # list of DomoDataflow Versions

    jupyter_workspace_config : dict = None

    History: DomoDataflow_History = None  # class for managing the history of a dataflow

    JupyterWorkspace : dmdj.DomoJupyterWorkspace = None


    def __post_init__(self):
        self.History = DomoDataflow_History(
            dataflow=self, dataflow_id=self.id, auth=self.auth
        )

        self.Lineage = dmdl.DomoLineage._from_parent(
            auth = self.auth,
            parent = self
        )

    @classmethod
    def _from_json(cls, obj, auth, version_id=None, version_number=None):
        dd = util_dd.DictDot(obj)

        domo_dataflow = cls(
            auth=auth,
            id=dd.id,
            raw = obj,
            name=dd.name,
            description=dd.description,
            owner=dd.owner or dd.responsibleUserId,
            tags=dd.tags,
            version_id=version_id,
            version_number=version_number,
            Lineage = None
        )

        if dd.actions:
            domo_dataflow.actions = [
                DomoDataflow_Action._from_json(action) for action in dd.actions
            ]

            [
                domo_action.get_parents(domo_dataflow.actions)
                for domo_action in domo_dataflow.actions
            ]

        return domo_dataflow


    def display_url(self):
        return f"https://{self.auth.domo_instance}.domo.com/datacenter/dataflows/{self.id}/details"
    
    @classmethod
    async def get_by_id(
        cls: DomoDataflow,
        dataflow_id: int,
        auth: dmda.DomoAuth,
        return_raw: bool = False,
        session: httpx.AsyncClient = None,
        debug_api: bool = False,
        debug_num_stacks_to_drop=2,
        id = None
    ):
        dataflow_id = dataflow_id or id
        res = await dataflow_routes.get_dataflow_by_id(
            auth=auth,
            dataflow_id=dataflow_id,
            debug_api=debug_api,
            debug_num_stacks_to_drop=debug_num_stacks_to_drop,
            parent_class=cls.__name__,
            session=session,
        )

        if return_raw:
            return res

        if not res.is_success:
            return None
            

        return cls._from_json(res.response, auth=auth)
    
    @classmethod
    async def _get_entity_by_id(cls, auth, entity_id, **kwargs):
        return await cls.get_by_id(
            dataflow_id=entity_id,
            auth=auth,
            return_raw=False,
            **kwargs
        )

# %% ../../nbs/classes/50_DomoDataflow.ipynb 9
@patch_to(DomoDataflow)
async def get_definition(
    self,
    debug_api: bool = False,
    return_raw: bool = False,
    session: httpx.AsyncClient = None,
):
    res = await self.get_by_id(
        auth=self.auth, 
        dataflow_id=self.id, 
        return_raw=return_raw,
        session=session,
        debug_api = debug_api,
    )

    if return_raw:
        return res


    new_obj = res.__dict__

    # Update attributes of ClassB instance
    for key, value in new_obj.items():
        if hasattr(self, key):
            setattr(self, key, value)

    return self


@patch_to(DomoDataflow)
async def update_dataflow_definition(
    self,
    new_dataflow_definition,
    debug_api: bool = False,
    debug_num_stacks_to_drop=2,
    session: httpx.AsyncClient = None,
):
    await dataflow_routes.update_dataflow_definition(
        auth=self.auth,
        dataflow_id = self.id,
        dataflow_definition=new_dataflow_definition,
        debug_api=debug_api,
        debug_num_stacks_to_drop=debug_num_stacks_to_drop,
        session=session,
    )

    return await self.get_definition(return_raw=False)

# %% ../../nbs/classes/50_DomoDataflow.ipynb 15
@patch_to(DomoDataflow)
async def get_jupyter_config(
    self,
    return_raw: bool = False,
    debug_api: bool = False,
    debug_num_stacks_to_drop : int = 2,
    session : httpx.AsyncClient = None,
):
    import domolibrary.classes.DomoJupyter as dmdj
    
    res = await dataflow_routes.search_dataflows_to_jupyter_workspaces(
        auth=self.auth,
        dataflow_id = self.id,
        debug_api = debug_api,
        debug_num_stacks_to_drop = debug_num_stacks_to_drop,
        session = session,
        parent_class = self.__class__.__name__,
        return_raw = return_raw
    )

    if return_raw:
        return res
    
    self.jupyter_workspace = await dmdj.DomoJupyterWorkspace.get_by_id(auth = self.auth, workspace_id = res.response['workspaceId'])
    
    self.jupyter_workspace_config = res.response
    self.jupyter_workspace_config['workspace_name'] = self.jupyter_workspace.name

    return self.jupyter_workspace

# %% ../../nbs/classes/50_DomoDataflow.ipynb 17
@patch_to(DomoDataflow)
async def execute(
    self: DomoDataflow,
    auth: dmda.DomoAuth = None,
    debug_api: bool = False,
    debug_num_stacks_to_drop=2,
):
    return await dataflow_routes.execute_dataflow(
        auth=auth or self.auth,
        dataflow_id=self.id,
        parent_class=self.__class__.__name__,
        debug_api=debug_api,
        debug_num_stacks_to_drop=debug_num_stacks_to_drop,
    )

# %% ../../nbs/classes/50_DomoDataflow.ipynb 21
@patch_to(DomoDataflow, cls_method=True)
async def get_by_version_id(
    cls: DomoDataflow,
    auth: dmda.DomoAuth,
    dataflow_id: int,
    version_id: int,
    debug_api: bool = False,
    debug_num_stacks_to_drop=2,
    session: httpx.AsyncClient = None,
    return_raw: bool = False,
):
    res = await dataflow_routes.get_dataflow_by_id_and_version(
        auth=auth,
        dataflow_id=dataflow_id,
        version_id=version_id,
        debug_api=debug_api,
        debug_num_stacks_to_drop=debug_num_stacks_to_drop,
        parent_class=cls.__name__,
        session=session,
    )

    if return_raw:
        return res

    domo_dataflow = cls._from_json(
        res.response["dataFlow"],
        version_id=res.response["id"],
        version_number=res.response["versionNumber"],
        auth=auth,
    )

    return domo_dataflow

# %% ../../nbs/classes/50_DomoDataflow.ipynb 23
@patch_to(DomoDataflow)
async def get_versions(
    self: DomoDataflow,
    debug_api: bool = False,
    debug_num_stacks_to_drop=2,
    session: httpx.AsyncClient = None,
    return_raw: bool = False,
):
    res = await dataflow_routes.get_dataflow_versions(
        auth=self.auth,
        dataflow_id=self.id,
        debug_api=debug_api,
        session=session,
        debug_num_stacks_to_drop=debug_num_stacks_to_drop,
        parent_class=self.__class__.__name__,
    )

    if return_raw:
        return res

    version_ids = [df_obj["id"] for df_obj in res.response]

    self.versions = await dmce.gather_with_concurrency(
        *[
            DomoDataflow.get_by_version_id(
                dataflow_id=self.id,
                version_id=version_id,
                auth=self.auth,
                session=session,
                debug_api=debug_api,
                debug_num_stacks_to_drop=debug_num_stacks_to_drop,
            )
            for version_id in version_ids
        ],
        n=10
    )

    return self.versions

# %% ../../nbs/classes/50_DomoDataflow.ipynb 25
@dataclass
class DomoDataflows:
    auth: dmda.DomoAuth = field(repr = False)
    dataflows : List[DomoDataflow] = None

    async def get(self, return_raw: bool = False, debug_api : bool = False, session : httpx.AsyncClient = None, ):
        res = await dataflow_routes.get_dataflows(
            debug_api = debug_api,
            auth = self.auth,
            session = session,
            
        )

        if return_raw:
            return res
        
        return await dmce.gather_with_concurrency(*[
            DomoDataflow.get_by_id(auth = self.auth, dataflow_id = obj['id']) for obj in res.response], n = 10
        )
        
