package com.yd.oss.api.service.impl;

import com.aliyun.oss.OSS;
import com.aliyuncs.DefaultAcsClient;
import com.aliyuncs.IAcsClient;
import com.aliyuncs.exceptions.ClientException;
import com.aliyuncs.profile.DefaultProfile;
import com.aliyuncs.sts.model.v20150401.AssumeRoleRequest;
import com.aliyuncs.sts.model.v20150401.AssumeRoleResponse;
import com.yd.auth.core.dto.AuthUserDto;
import com.yd.auth.core.utils.SecurityUtil;
import com.yd.common.enums.CommonEnum;
import com.yd.common.result.Result;
import com.yd.common.utils.RandomStringGenerator;
import com.yd.oss.api.service.ApiOssStsService;
import com.yd.oss.feign.dto.ApiOssFileDto;
import com.yd.oss.feign.request.ApiBatchSaveFilesRequest;
import com.yd.oss.feign.response.ApiBatchSaveFilesResponse;
import com.yd.oss.feign.response.ApiGetStsTokenResponse;
import com.yd.oss.feign.response.ApiOssFileResponse;
import com.yd.oss.service.model.OssFile;
import com.yd.oss.service.model.OssProvider;
import com.yd.oss.service.service.IOssFileService;
import com.yd.oss.service.service.OssService;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.io.FilenameUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import java.net.MalformedURLException;
import java.net.URL;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

@Slf4j
@Service
public class ApiOssStsServiceImpl implements ApiOssStsService {

//    @Value("${aliyun.oss.access-key-id:LTAI5tFNiaUM3B4vC2bjqvtB}")
//    private String accessKeyId;
//
//    @Value("${aliyun.oss.access-key-secret:yH2L5YYmUayBYpQXhYevJ6Ghba349D}")
//    private String accessKeySecret;
//
    @Value("${aliyun.oss.role-arn:acs:ram::1939592679479894:role/oss-upload-role}")
    private String roleArn;
//
//    @Value("${aliyun.oss.region:cn-shanghai}")
//    private String region;
//
//    @Value("${aliyun.oss.bucket:yd-ali-oss}")
//    private String bucket;
//
//    @Value("${aliyun.oss.endpoint:oss-cn-shanghai-finance-1-pub.aliyuncs.com}")
//    private String endpoint;
//
    // 注入最大文件大小配置，默认100MB
    @Value("${aliyun.oss.max-size:104857600}")
    private Long maxSize;

    @Autowired
    private OssService ossService;

    // 动态代理的 OSS 客户端，会自动切换到当前服务商
    @Autowired
    private OSS ossClient;

    @Autowired
    private IOssFileService iOssFileService;

    /**
     * getStsToken如何根据传入的projectBizId查询对应服务商然后切换对应OSS服务商
     * @param projectBizId
     * @return
     */
    @Override
    public Result<ApiGetStsTokenResponse> getStsToken(String projectBizId) {
        // 切换服务商
        ossService.switchProviderByProjectId(projectBizId);

        // 获取切换后的服务商信息
        OssProvider currentProvider = ossService.getCurrentProvider();
        String region = currentProvider.getRegion();
        String accessKeyId = currentProvider.getAccessKey();
        String accessKeySecret = currentProvider.getSecretKey();
        // 或 ossService.getDefaultBucket()
        String bucket = currentProvider.getBucketName();
        // 或 ossService.getDefaultEndpoint()
        String endpoint = currentProvider.getEndpoint();

        //现在 ossClient 已经指向了切换后的服务商，可以直接使用
        if (!ossClient.doesBucketExist(bucket)) {
            log.warn("当前服务商的桶 {} 不存在，将尝试创建", bucket);
            // 可以创建桶，但通常桶应提前准备好
        }

        // 构建STS客户端
        DefaultProfile profile = DefaultProfile.getProfile(region, accessKeyId, accessKeySecret);
        IAcsClient client = new DefaultAcsClient(profile);

        // 构建请求
        AssumeRoleRequest request = new AssumeRoleRequest();
        request.setRoleArn(roleArn);
        request.setRoleSessionName("vue-upload-session");
        request.setDurationSeconds(3600L);

        try {
            AssumeRoleResponse response = client.getAcsResponse(request);
            if (response == null || response.getCredentials() == null) {
                return Result.fail("获取STS凭证失败：返回凭证为空");
            }

            AssumeRoleResponse.Credentials credentials = response.getCredentials();

            ApiGetStsTokenResponse tokenResponse = new ApiGetStsTokenResponse();
            tokenResponse.setAccessKeyId(credentials.getAccessKeyId());
            tokenResponse.setAccessKeySecret(credentials.getAccessKeySecret());
            tokenResponse.setStsToken(credentials.getSecurityToken());
            tokenResponse.setRegion(region);
            tokenResponse.setBucket(bucket);
            tokenResponse.setEndpoint(endpoint);
            tokenResponse.setMaxSize(maxSize);

            return Result.success(tokenResponse);
        } catch (ClientException e) {
            log.error("获取STS凭证失败", e);
            return Result.fail("获取STS凭证失败: " + e.getMessage());
        }
    }

    /**
     * 批量保存文件列表
     *
     * @return
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public Result<ApiBatchSaveFilesResponse> batchSaveFiles(ApiBatchSaveFilesRequest request) {

        // 根据 projectBizId 切换服务商，获取当前服务商信息
        ossService.switchProviderByProjectId(request.getProjectBizId());
        OssProvider currentProvider = ossService.getCurrentProvider();
        String providerBizId = currentProvider.getProviderBizId();
        String bucketName = currentProvider.getBucketName();

        // 获取当前登录用户信息
        AuthUserDto authUserDto = SecurityUtil.getCurrentLoginUser();
        String userId = authUserDto.getUserBizId();
        String userName = authUserDto.getUsername();

        List<OssFile> saveOssFileList = new ArrayList<>();
        List<ApiOssFileResponse> fileResponses = new ArrayList<>();

        // 遍历处理文件列表
        for (ApiOssFileDto fileDto : request.getApiOssFileDtoList()) {
            try {
                // 从完整 URL 中提取 fileKey（相对路径）
                String fileUrl = fileDto.getFileUrl();
                if (StringUtils.isBlank(fileUrl)) {
                    log.warn("文件URL为空，跳过：{}", fileDto);
                    continue;
                }
                URL url = new URL(fileUrl);
                String path = url.getPath();
                String fileKey = path.startsWith("/") ? path.substring(1) : path;

                // 生成文件业务ID
                String fileBizId = RandomStringGenerator.generateBizId16(CommonEnum.UID_TYPE_OSS_FILE.getCode());

                // 获取文件类型（扩展名）
                String originalName = fileDto.getFileName();
                String fileType = FilenameUtils.getExtension(originalName);
                if (StringUtils.isBlank(fileType)) {
                    fileType = FilenameUtils.getExtension(fileKey);
                }

                // 构建实体
                OssFile file = new OssFile();
                file.setTenantBizId(request.getTenantBizId());
                file.setProjectBizId(request.getProjectBizId());
                file.setFileBizId(fileBizId);
                file.setObjectType(request.getObjectType());
                file.setObjectTableName(request.getObjectTableName());
                file.setObjectName(request.getObjectName());
                file.setObjectBizId(request.getObjectBizId());
                file.setFileKey(fileKey);
                file.setOriginalName(originalName);
                file.setFileSize(fileDto.getFileSize());
                file.setFileType(fileType);
                file.setProviderBizId(providerBizId);
                file.setBucketName(bucketName);
                file.setUploadTime(LocalDateTime.now());
                file.setUploadUser(userId);
                file.setCreatorId(userId);
                file.setCreatorName(userName);
                file.setUpdaterId(userId);
                file.setCreateTime(LocalDateTime.now());
                file.setUpdateTime(LocalDateTime.now());
                file.setIsDeleted(0);
                saveOssFileList.add(file);

                // 构建响应对象（直接使用传入的完整URL）
                ApiOssFileResponse ossFileResponse = new ApiOssFileResponse();
                ossFileResponse.setFileBizId(file.getFileBizId());
                ossFileResponse.setFileName(file.getOriginalName());
                ossFileResponse.setFileSize(file.getFileSize());
                ossFileResponse.setFileUrl(fileDto.getFileUrl()); // 设置完整URL
                fileResponses.add(ossFileResponse);

            } catch (MalformedURLException e) {
                log.error("文件URL格式错误: {}", fileDto.getFileUrl(), e);
                return Result.fail("文件URL格式错误: " + fileDto.getFileUrl());
            } catch (Exception e) {
                log.error("保存文件记录失败: {}", fileDto, e);
                return Result.fail("保存文件记录失败: " + e.getMessage());
            }
        }

        // 批量保存（修复条件判断：列表不为空时才保存）
        if (CollectionUtils.isNotEmpty(saveOssFileList)) {
            iOssFileService.saveOrUpdateBatch(saveOssFileList);
            // 构建响应
            ApiBatchSaveFilesResponse response = new ApiBatchSaveFilesResponse();
            response.setFileResponses(fileResponses);
            return Result.success(response);
        }
        return Result.success();
    }
}