from jh_utils.data.sql.connection import create_connection, create_string_connection
from jh_utils.data.sql.manipulate_db import create_table_structure, get_tables, drop_table, delete_table, get_top_rows, get_schemas, create_schema, drop_schema, apply_delete_to_schema
from dotenv import dotenv_values
from sqlalchemy import inspect

doc = """
    env: db, user, pass, host, port
    ----------------------------
    example .env
    host=weather
    host1=weather
    db=weather
    user=weather
    pass=weather12
    port=5400
    schema=raw
    """

class DB():
    __doc__ = doc
    def __init__(self,db,user,password,host,port):
        self.db = db
        self.user = user
        self.password = password
        self.host = host
        self.port = port
        
    def engine(self):
        return create_connection(database=self.db,
                            user=self.user,
                            password=self.password,
                            host=self.host,
                            port=self.port)

    def uri(self):
        return create_string_connection(database=self.db,
                            user=self.user,
                            password=self.password,
                            host=self.host,
                            port=self.port)

    def __repr__(self) -> str:
        return f"""host: {self.host}\ndb:{self.db}"""


    ## ! table
    def drop_table(self, table,schema):
        return drop_table(table,schema=schema,engine=self.engine)
    
    def delete_table(self,table_name,schema):
        delete_table(table_name, schema, self.engine, close_connection = True)

    def get_schemas(self):
        return get_schemas(self.engine)
    
    def get_tables(self,schema):
        return get_tables(schema,self.engine)
    
    def get_top_rows(self, table, schema, n=5):
        return get_top_rows(table = table, schema = schema, engine = self.engine, n=n)

    ## ! schema
    def drop_schema(self, schema):
        drop_schema(schema=schema,engine = self.engine)
    
    def create_schema(self, schema_nema):
        create_schema(schema_nema, self.engine)
        
    def run_sql(self, sql):
        conn = self.engine.connect()
        conn.execute(sql)

##
## ? Second form to create the object
## 

def create_object_DB(env_dict):
    __docstring__ = doc
    db_object = DB(db = env_dict['db'],
            user = env_dict['user'],
            password = env_dict['pass'],
            host = env_dict['host'],
            port = env_dict['port'])
    return db_object
        
def create_object_DB_by_envfile(path='.env'):
    __docstring__ = doc
    env = dotenv_values(path)
    db_obect_created = create_object_DB(env)
    return db_obect_created

