import logging from uuid import uuid4 from config import load_config from utils import hashPassword def sync_dealers(conn_factuges, conn_mysql, last_execution_date): config = load_config() consulta_factuges = ( f"select V_CONTACTOS.ID as ID, V_CONTACTOS.NOMBRE, V_CONTACTOS.IDIOMA_ISO, " f"CLIENTES_DATOS.DIST_EMAIL, CLIENTES_DATOS.DIST_PASSWORD, CLIENTES_DATOS.BLOQUEADO " f"from V_CONTACTOS " f"left OUTER JOIN CLIENTES_DATOS on (V_CONTACTOS.ID = CLIENTES_DATOS.ID_CLIENTE) " f"where (V_CONTACTOS.ID_CATEGORIA = 1) " f"and (V_CONTACTOS.ID_EMPRESA = '{config['FACTUGES_ID_EMPRESA']}') " f"and (CLIENTES_DATOS.TIENDA_WEB = 1) " f"and (V_CONTACTOS.FECHA_MODIFICACION is not null) " f"and (V_CONTACTOS.FECHA_MODIFICACION > '{last_execution_date}')" ) consulta_dealer_uecko = ( "SELECT dealers.id, dealers.id_contact, dealers.user_id, dealers.status, dealers.updated_at " "FROM dealers " "WHERE dealers.id_contact = %s" ) cursor_FactuGES = None try: cursor_FactuGES = conn_factuges.cursor() # Ejecutar la consulta cursor_FactuGES.execute(consulta_factuges) contactos = cursor_FactuGES.fetchall() except Exception as e: if cursor_FactuGES is not None: cursor_FactuGES.close() logging.error(f"(ERROR) Failed to fetch from database:{ config['FACTUGES_DATABASE']} - using user:{config['FACTUGES_USER']}") logging.error(e) raise e columnas_contacto = [desc[0] for desc in cursor_FactuGES.description] cursor_FactuGES.close() contactos_seleccionados = [] for contacto in contactos: tupla = dict(zip(columnas_contacto, contacto)) contactos_seleccionados.append(tupla) logging.info(f"Contacts rows to be processed: { len(contactos_seleccionados)}") if contactos_seleccionados: for contacto in contactos_seleccionados: cursor_MySQL = None try: cursor_MySQL = conn_mysql.cursor() cursor_MySQL.execute(consulta_dealer_uecko, (contacto['ID'],)) dealer = cursor_MySQL.fetchone() if (dealer is None): user_id = insert_user(conn_mysql, contacto, config) insert_dealer(conn_mysql, user_id, contacto, config) logging.info(f"Inserted user and dealer from contact { contacto['ID']} {contacto['NOMBRE']}") else: # 0 => 'ID' # 2 => 'USER_ID' # Casos: # - Cambio en el nombre del distribuidor # - Distribuidor bloqueado / desbloqueado # - Usuario con baja lógica id = dealer[0] user_id = dealer[2] update_dealer(conn_mysql, id, contacto, config) update_user(conn_mysql, user_id, contacto, config) except Exception as e: # Escribir el error en el archivo de errores logging.error(str(e)) raise e # Re-lanzar la excepción para detener el procesamiento finally: # Cerrar la conexión if cursor_MySQL is not None: cursor_MySQL.close() else: logging.info( "There are no new or modified contacts rows since the last run.") # Revisar todos los distribuidores dados de alta y # comprobar si en FactuGES siguen estando activos (tienda_web = 1) # # - USUARIO DISABLED dealers = fetch_all_dealers(conn_mysql, config) for dealer in dealers: # dealer[1] => id_contact if (dealer[1] is not None) and (not is_valid_dealer(conn_factuges, dealer[1], config)): user_id = dealer[7] # 7 => user_id # Desactivar el distribuidor disable_dealer(conn_mysql, dealer[0], config) # 0 => id # Baja lógica del usuario del dealer soft_delete_user(conn_mysql, user_id, config) logging.info(f"Deleted dealer and user from contact {dealer[1]}") def fetch_all_dealers(conn_mysql, config): consulta = ( f"SELECT dealers.id, dealers.id_contact, dealers.default_payment_method, dealers.default_notes, " f"dealers.default_legal_terms, dealers.default_quote_validity, dealers.status, dealers.user_id " f"FROM dealers " ) cursor_MySQL = None try: cursor_MySQL = conn_mysql.cursor() cursor_MySQL.execute(consulta) return cursor_MySQL.fetchall() except Exception as e: # Escribir el error en el archivo de errores logging.error(str(e)) raise e # Re-lanzar la excepción para detener el procesamiento finally: if cursor_MySQL is not None: cursor_MySQL.close() def is_valid_dealer(conn_factuges, id_contact, config): consulta = ( f"select CLIENTES_DATOS.ID_CLIENTE from CLIENTES_DATOS where CLIENTES_DATOS.ID_CLIENTE = { id_contact} and CLIENTES_DATOS.TIENDA_WEB = 1" ) cursor_FactuGES = None try: cursor_FactuGES = conn_factuges.cursor() cursor_FactuGES.execute(consulta) exists = cursor_FactuGES.fetchone() return exists is not None except Exception as e: # Escribir el error en el archivo de errores logging.error(str(e)) raise e # Re-lanzar la excepción para detener el procesamiento finally: if cursor_FactuGES is not None: cursor_FactuGES.close() def insert_user(conn_mysql, data, config): cursor_MySQL = None try: cursor_MySQL = conn_mysql.cursor() id = str(uuid4()) name = str(data['NOMBRE']) email = str(data['DIST_EMAIL']) password = hashPassword(str(data['DIST_PASSWORD'])) lang_code = str(data['IDIOMA_ISO']) insert_data = ( "INSERT INTO users (id, name, email, password, lang_code, roles, created_at, updated_at) VALUES (" "%s, %s, %s, %s, %s, 'ROLE_USER', Now(), Now()" ")" ) cursor_MySQL.execute( insert_data, (id, name, email, password, lang_code)) return id except Exception as e: # Escribir el error en el archivo de errores logging.error(str(e)) raise e # Re-lanzar la excepción para detener el procesamiento finally: if cursor_MySQL is not None: cursor_MySQL.close() def update_user(conn_mysql, user_id, data, config): cursor_MySQL = None try: cursor_MySQL = conn_mysql.cursor() name = str(data['NOMBRE']) email = str(data['DIST_EMAIL']) password = hashPassword(str(data['DIST_PASSWORD'])) lang_code = str(data['IDIOMA_ISO']) update_data = ( "UPDATE users set " "name = %s, " "email = %s, " "password = %s, " "lang_code = %s, " "updated_at = Now(), " "deleted_at = NULL " "WHERE id = %s" ) cursor_MySQL.execute( update_data, (name, email, password, lang_code, user_id)) logging.info(f"Updated user from contact {data['ID']} {name}") except Exception as e: # Escribir el error en el archivo de errores logging.error(str(e)) raise e # Re-lanzar la excepción para detener el procesamiento finally: if cursor_MySQL is not None: cursor_MySQL.close() def insert_dealer(conn_mysql, user_id, data, config): cursor_MySQL = None try: cursor_MySQL = conn_mysql.cursor() id = str(uuid4()) id_contact = str(data['ID']) name = str(data['NOMBRE']) default_payment_method = str(config['UECKO_DEFAULT_FORMA_PAGO']) default_notes = str(config['UECKO_DEFAULT_NOTAS']) default_legal_terms = str(config['UECKO_DEFAULT_LOPD']) default_quote_validity = str(config['UECKO_DEFAULT_VALIDEZ']) default_tax = str(config["UECKO_DEFAULT_IVA"]) lang_code = str(data['IDIOMA_ISO']) currency_code = str(config["UECKO_DEFAULT_CURRENCY_CODE"]) insert_data = ( "INSERT INTO dealers (id, id_contact, name, default_payment_method, default_notes, " "default_legal_terms, default_quote_validity, default_tax, lang_code, " "currency_code, user_id, status, created_at, updated_at ) values (" "%s, %s, %s, %s, %s, %s, %s, %s, %s, %s, %s, 'actived', Now(), Now()" ")" ) cursor_MySQL.execute(insert_data, (id, id_contact, name, default_payment_method, default_notes, default_legal_terms, default_quote_validity, default_tax, lang_code, currency_code, user_id)) return id except Exception as e: # Escribir el error en el archivo de errores logging.error(str(e)) raise e # Re-lanzar la excepción para detener el procesamiento finally: if cursor_MySQL is not None: cursor_MySQL.close() def update_dealer(conn_mysql, dealer_id, data, config): cursor_MySQL = None try: cursor_MySQL = conn_mysql.cursor() name = str(data['NOMBRE']) status = 'disabled' if data['BLOQUEADO'] == 1 else 'actived' insert_data = ( "UPDATE dealers SET name = %s, status = %s WHERE dealers.id = %s" ) cursor_MySQL.execute(insert_data, (name, status, dealer_id)) logging.info(f"Dealer with id = {dealer_id} name = {name} updated") except Exception as e: # Escribir el error en el archivo de errores logging.error(str(e)) raise e # Re-lanzar la excepción para detener el procesamiento finally: if cursor_MySQL is not None: cursor_MySQL.close() def soft_delete_user(conn_mysql, user_id, config): consulta_sql = "UPDATE users SET users.deleted_at = NOW() WHERE users.id = %s AND users.roles = 'ROLE_USER'" cursor_MySQL = None try: cursor_MySQL = conn_mysql.cursor() cursor_MySQL.execute(consulta_sql, (user_id, )) logging.info(f"User with id = {id} soft delete") except Exception as e: # Escribir el error en el archivo de errores logging.error(str(e)) raise e # Re-lanzar la excepción para detener el procesamiento finally: if cursor_MySQL is not None: cursor_MySQL.close() def active_dealer(conn_mysql, id, config): consulta_sql = "UPDATE dealers SET status = 'actived' WHERE dealers.id = %s" cursor_MySQL = None try: cursor_MySQL = conn_mysql.cursor() cursor_MySQL.execute(consulta_sql, (id, )) logging.info(f"Dealer with id = {id} actived") except Exception as e: # Escribir el error en el archivo de errores logging.error(str(e)) raise e # Re-lanzar la excepción para detener el procesamiento finally: if cursor_MySQL is not None: cursor_MySQL.close() def disable_dealer(conn_mysql, id, config): consulta_sql = "UPDATE dealers SET status = 'disabled' WHERE dealers.id = %s" cursor_MySQL = None try: cursor_MySQL = conn_mysql.cursor() cursor_MySQL.execute(consulta_sql, (id, )) logging.info(f"Dealer with id = {id} disabled") except Exception as e: # Escribir el error en el archivo de errores logging.error(str(e)) raise e # Re-lanzar la excepción para detener el procesamiento finally: if cursor_MySQL is not None: cursor_MySQL.close()