import os import re import toon import json import requests from taskflow import get_logger import tos from dotenv import load_dotenv logger = get_logger("examples.video_create.utils.tools") def string_to_json(markdown_string): try: json_content = re.sub(r'^```json|\n```$', '', markdown_string, flags=re.MULTILINE).strip() if not json_content: json_content = markdown_string # raise ValueError("字符串中未找到有效的JSON内容") # 解析JSON内容 json_data = json.loads(json_content) return json_data except Exception as e: logger.error(f"生成结果解析失败:\n{markdown_string}") raise e def download_video(video_url, output_path): """ 根据视频URL下载视频到本地指定路径 参数: video_url (str): 视频的URL地址 output_path (str): 本地保存路径(包含文件名和扩展名) 返回: bool: 下载成功返回True,失败返回False """ try: # 创建目录(如果不存在) os.makedirs(os.path.dirname(output_path), exist_ok=True) # 发送HTTP GET请求 headers = { 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.3' } response = requests.get(video_url, headers=headers, stream=True) response.raise_for_status() # 检查请求是否成功 # 获取文件总大小(用于进度显示) total_size = int(response.headers.get('content-length', 0)) # 以二进制写入模式保存视频 with open(output_path, 'wb') as f: downloaded_size = 0 for chunk in response.iter_content(chunk_size=8192): if chunk: # 过滤掉保持连接的新块 f.write(chunk) downloaded_size += len(chunk) logger.info(f"\n视频已成功保存到: {output_path}") return True except requests.exceptions.RequestException as e: logger.info(f"下载视频时出错: {e}") except IOError as e: logger.info(f"保存视频时出错: {e}") except Exception as e: logger.info(f"发生未知错误: {e}") return False def download_image(image_url, output_path): """ 根据图片URL下载图片到本地指定路径 参数: image_url (str): 图片的URL地址 output_path (str): 本地保存路径(包含文件名和扩展名) """ try: # 创建目录(如果不存在) os.makedirs(os.path.dirname(output_path), exist_ok=True) # 发送HTTP GET请求 headers = { 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.3' } response = requests.get(image_url, headers=headers, stream=True) response.raise_for_status() # 检查请求是否成功 # 以二进制写入模式保存图片 with open(output_path, 'wb') as f: for chunk in response.iter_content(chunk_size=8192): if chunk: # 过滤掉保持连接的新块 f.write(chunk) logger.info(f"\n图片已成功保存到: {output_path}") return True except requests.exceptions.RequestException as e: logger.info(f"下载图片时出错: {e}") except IOError as e: logger.info(f"保存图片时出错: {e}") except Exception as e: logger.info(f"发生未知错误: {e}") return False def efficient_sort(a, b): """ 高效排序算法,通过贪心策略 """ n = len(a) selected = [False] * n result = [] available = set() # 统计每个元素的依赖 dependencies = [] for i in range(n): # 如果a[i]在b[i]中,它可以立即被处理 immediate = a[i] in b[i] dependencies.append((immediate, i)) # 先处理可以立即处理的元素 for immediate, i in dependencies: if immediate and not selected[i]: result.append(i) selected[i] = True available.update(b[i]) # 然后处理其他元素 while len(result) < n: progress = False for i in range(n): if not selected[i] and a[i] in available: result.append(i) selected[i] = True available.update(b[i]) progress = True # 如果没有进展,选择第一个未处理的元素 if not progress: for i in range(n): if not selected[i]: result.append(i) selected[i] = True available.update(b[i]) break return result # 加载环境变量 load_dotenv() # 从环境变量获取 AK 和 SK 信息 ak = os.getenv('TOS_ACCESS_KEY') sk = os.getenv('TOS_SECRET_KEY') # 存储桶配置信息 endpoint = "https://tos-cn-guangzhou.volces.com" region = "cn-guangzhou" bucket_name = "guide-material" def upload_file_to_tos(file_name: str) -> str: """ 上传文件到TOS存储桶并返回访问URL Args: file_name (str): 本地文件的完整路径 Returns: str: 上传文件的访问URL Raises: Exception: 上传过程中的任何错误 """ try: # 检查文件是否存在 if not os.path.exists(file_name): raise FileNotFoundError(f"文件不存在: {file_name}") # 从文件路径中提取文件名作为object_key,确保使用正斜杠 filename = os.path.basename(file_name) object_key = f"video-create/{filename}".replace("\\", "/") logger.info(f'开始上传文件: {file_name}') logger.info(f'文件将保存为: {object_key}') # 创建客户端并上传文件 client = tos.TosClientV2(ak, sk, endpoint, region) client.put_object_from_file(bucket_name, object_key, file_name) # 验证上传是否成功 - 尝试获取对象元数据 try: head_response = client.head_object(bucket_name, object_key) if head_response is None: raise Exception("无法验证文件是否上传成功:head_object返回None") logger.info(f'文件上传验证成功,ETag: {getattr(head_response, "etag", "N/A")}') except Exception as verify_error: logger.warning(f'验证上传状态时出现警告: {str(verify_error)}') # 不抛出异常,因为上传可能已经成功,只是验证失败 # 生成访问URL,确保object_key使用正斜杠 object_key_normalized = object_key.replace("\\", "/") object_url = f"https://testdgxcx-oss.gloria.com.cn/{object_key_normalized}" logger.info(f'文件上传成功,访问URL: {object_url}') logger.info(f'Object Key (用于调试): {object_key_normalized}') return object_url except tos.exceptions.TosClientError as e: error_msg = f'上传失败,客户端错误: message={e.message}, cause={e.cause}' logger.error(error_msg) raise Exception(error_msg) except tos.exceptions.TosServerError as e: error_msg = f'上传失败,服务端错误: code={e.code}, request_id={e.request_id}, message={e.message}, status_code={e.status_code}, ec={e.ec}, request_url={e.request_url}' logger.error(error_msg) raise Exception(error_msg) except Exception as e: error_msg = f'上传失败,未知错误: {str(e)}' logger.error(error_msg) raise Exception(error_msg) if __name__ == "__main__": # data = { # "name": "John", # "age": 30, # "city": "New York" # } # toon_str = toon.encode(data) # print(type(toon_str), toon_str) # decoded_data = toon.decode(toon_str) # print(type(decoded_data), decoded_data) # python -m utils.upload test_file = "./image.jpg" try: url = upload_file_to_tos(test_file) print(f"文件上传成功,访问URL: {url}") except Exception as e: print(f"上传失败: {str(e)}")