134 lines
4.6 KiB
Python
134 lines
4.6 KiB
Python
from ftplib import FTP
|
|
import os
|
|
import time
|
|
|
|
class FTPManager:
|
|
def __init__(self, siteFTP, userFTP, passwordFTP, postFTP):
|
|
self.server = siteFTP
|
|
self.user = userFTP
|
|
self.password = passwordFTP
|
|
self.port = postFTP # Puerto por defecto: 21
|
|
self.ftp_client = None
|
|
self.list_failed_uploads = []
|
|
#def __init__(self, **kwargs):
|
|
# self.server = kwargs.get('server')
|
|
# self.user = kwargs.get('user')
|
|
# self.password = kwargs.get('password')
|
|
# self.port = kwargs.get('port', 21) # Puerto por defecto: 21
|
|
# self.ftp_client = None
|
|
# self.list_failed_uploads = []
|
|
|
|
def connect(self):
|
|
"""Conecta al servidor FTP"""
|
|
try:
|
|
self.ftp_client = FTP()
|
|
self.ftp_client.connect(self.server, self.port)
|
|
self.ftp_client.login(self.user, self.password)
|
|
self.ftp_client.encoding = 'latin-1'
|
|
#print(f"Conexión exitosa al servidor FTP: {self.server}")
|
|
except Exception as e:
|
|
#print(f"Error al conectar al servidor FTP: {e}")
|
|
raise
|
|
|
|
def disconnect(self):
|
|
"""Cierra la conexión FTP"""
|
|
if self.ftp_client:
|
|
self.ftp_client.quit()
|
|
#print("Conexión cerrada con éxito")
|
|
|
|
def upload_photos(self, local_folder, remote_folder, batch_size=100):
|
|
"""
|
|
Sube archivos en lotes de 100. Si hay un error, omite el archivo y lo guarda para intentarlo al final.
|
|
"""
|
|
try:
|
|
self.ftp_client.cwd(remote_folder)
|
|
except:
|
|
# if not exit create folder
|
|
self.ftp_client.mkd(remote_folder)
|
|
self.ftp_client.cwd(remote_folder)
|
|
|
|
files = [f for f in os.listdir(local_folder) if os.path.isfile(os.path.join(local_folder, f))]
|
|
total_files = len(files)
|
|
print(f"Total de archivos a subir: {total_files}")
|
|
|
|
for i in range(0, total_files, batch_size):
|
|
batch = files[i:i+batch_size]
|
|
print(f"Subiendo lote {i//batch_size + 1}: {len(batch)} archivos")
|
|
|
|
for file in batch:
|
|
local_path = os.path.join(local_folder, file)
|
|
try:
|
|
with open(local_path, 'rb') as local_file:
|
|
self.ftp_client.storbinary(f"STOR {file}", local_file)
|
|
print(f"Subido: {file}")
|
|
except Exception as e:
|
|
print(f"Error al subir {file}: {e}")
|
|
self.list_failed_uploads.append(file)
|
|
|
|
time.sleep(2) # Pequeña pausa entre lotes para estabilidad
|
|
|
|
# Intentar subir nuevamente los fallidos
|
|
if self.list_failed_uploads:
|
|
print("Reintentando archivos fallidos...")
|
|
for file in self.list_failed_uploads:
|
|
local_path = os.path.join(local_folder, file)
|
|
try:
|
|
with open(local_path, 'rb') as local_file:
|
|
self.ftp_client.storbinary(f"STOR {file}", local_file)
|
|
print(f"Subido en reintento: {file}")
|
|
except Exception as e:
|
|
print(f"Fallo definitivo en {file}: {e}")
|
|
|
|
print("Proceso de subida finalizado.")
|
|
|
|
|
|
def uploadFile(self, remote_folder, local_file_path):
|
|
self.connect()
|
|
|
|
try:
|
|
self.ftp_client.cwd("/") # 👈 IMPORTANTE
|
|
self.ensure_remote_path(remote_folder)
|
|
|
|
with open(local_file_path, "rb") as f:
|
|
file_name = os.path.basename(local_file_path)
|
|
self.ftp_client.storbinary(f"STOR {file_name}", f)
|
|
|
|
finally:
|
|
self.disconnect()
|
|
|
|
|
|
def ensure_remote_path(self, remote_folder):
|
|
folders = remote_folder.strip("/").split("/")
|
|
|
|
# SIEMPRE empezar desde raíz
|
|
self.ftp_client.cwd("/")
|
|
|
|
for folder in folders:
|
|
if folder == "":
|
|
continue
|
|
try:
|
|
self.ftp_client.cwd(folder)
|
|
except:
|
|
self.ftp_client.mkd(folder)
|
|
|
|
#print(f"Creando/navegando carpeta: {folder}")
|
|
self.ftp_client.cwd(folder)
|
|
|
|
|
|
# Ejemplo de uso
|
|
if __name__ == "__main__":
|
|
config = {
|
|
"server": "glmservice.com",
|
|
"user": "ftpeleaderuser",
|
|
"password": "AdAw#BaAjwQdc4B",
|
|
"port": 21
|
|
}
|
|
|
|
ftp_manager = FTPManager(**config)
|
|
|
|
try:
|
|
ftp_manager.connect()
|
|
ftp_manager.upload_photos("C:\\Users\\emili\\Downloads\\sfotos", "/imglm/test/glmpg01/")
|
|
finally:
|
|
ftp_manager.disconnect()
|