package com.ycwl.basic.service.pc.impl;

import com.ycwl.basic.facebody.FaceBodyFactory;
import com.ycwl.basic.facebody.adapter.IFaceBodyAdapter;
import com.ycwl.basic.integration.scenic.dto.scenic.ScenicV2DTO;
import com.ycwl.basic.model.pc.scenic.entity.ScenicConfigEntity;
import com.ycwl.basic.model.pc.scenic.req.ScenicReqQuery;
import com.ycwl.basic.pay.PayFactory;
import com.ycwl.basic.pay.adapter.IPayAdapter;
import com.ycwl.basic.repository.ScenicRepository;
import com.ycwl.basic.service.pc.ScenicService;
import com.ycwl.basic.storage.StorageFactory;
import com.ycwl.basic.storage.adapters.IStorageAdapter;
import com.ycwl.basic.storage.exceptions.StorageUnsupportedException;
import com.ycwl.basic.utils.ApiResponse;
import com.ycwl.basic.utils.JacksonUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

/**
 * @Author：longbinbin
 * @Date：2024/12/3 15:25
 */
@Slf4j
@Service
public class ScenicServiceImpl implements ScenicService {
    @Autowired
    private ScenicRepository scenicRepository;

    @Override
    @Deprecated
    public ApiResponse<List<ScenicV2DTO>> list(ScenicReqQuery scenicReqQuery) {
        return ApiResponse.success(scenicRepository.list(scenicReqQuery));
    }

    private static final Map<Long, IStorageAdapter> scenicStorageAdapterMap = new ConcurrentHashMap<>();
    @Override
    public IStorageAdapter getScenicStorageAdapter(Long scenicId) {
        return scenicStorageAdapterMap.computeIfAbsent(scenicId, (key) -> {
            IStorageAdapter adapter;
            ScenicConfigEntity scenicConfig = scenicRepository.getScenicConfig(scenicId);
            if (scenicConfig != null && scenicConfig.getStoreType() != null) {
                try {
                    adapter = StorageFactory.get(scenicConfig.getStoreType());
                    adapter.loadConfig(JacksonUtil.parseObject(scenicConfig.getStoreConfigJson(), Map.class));
                } catch (StorageUnsupportedException ignored) {
                    return StorageFactory.use("video");
                }
            } else {
                adapter = StorageFactory.use("video");
            }
            return adapter;
        });
    }
    private static final Map<Long, IStorageAdapter> scenicTmpStorageAdapterMap = new ConcurrentHashMap<>();
    @Override
    public IStorageAdapter getScenicTmpStorageAdapter(Long scenicId) {
        return scenicTmpStorageAdapterMap.computeIfAbsent(scenicId, (key) -> {
            IStorageAdapter adapter;
            ScenicConfigEntity scenicConfig = scenicRepository.getScenicConfig(scenicId);
            if (scenicConfig != null && scenicConfig.getTmpStoreType() != null) {
                try {
                    adapter = StorageFactory.get(scenicConfig.getTmpStoreType());
                    adapter.loadConfig(JacksonUtil.parseObject(scenicConfig.getTmpStoreConfigJson(), Map.class));
                } catch (StorageUnsupportedException ignored) {
                    return getScenicStorageAdapter(scenicId);
                }
            } else {
                return getScenicStorageAdapter(scenicId);
            }
            return adapter;
        });
    }
    private static final Map<Long, IStorageAdapter> scenicLocalStorageAdapterMap = new ConcurrentHashMap<>();
    @Override
    public IStorageAdapter getScenicLocalStorageAdapter(Long scenicId) {
        return scenicLocalStorageAdapterMap.computeIfAbsent(scenicId, (key) -> {
            IStorageAdapter adapter;
            ScenicConfigEntity scenicConfig = scenicRepository.getScenicConfig(scenicId);
            if (scenicConfig != null && scenicConfig.getLocalStoreType() != null) {
                try {
                    adapter = StorageFactory.get(scenicConfig.getLocalStoreType());
                    adapter.loadConfig(JacksonUtil.parseObject(scenicConfig.getLocalStoreConfigJson(), Map.class));
                } catch (StorageUnsupportedException ignored) {
                    return getScenicStorageAdapter(scenicId);
                }
            } else {
                return getScenicStorageAdapter(scenicId);
            }
            return adapter;
        });
    }

    private static final Map<Long, IFaceBodyAdapter> scenicFaceBodyAdapterMap = new ConcurrentHashMap<>();
    @Override
    public IFaceBodyAdapter getScenicFaceBodyAdapter(Long scenicId) {
        return scenicFaceBodyAdapterMap.computeIfAbsent(scenicId, (key) -> {
            IFaceBodyAdapter adapter;
            ScenicConfigEntity scenicConfig = scenicRepository.getScenicConfig(scenicId);
            if (scenicConfig != null && scenicConfig.getFaceType() != null) {
                adapter = FaceBodyFactory.getAdapter(scenicConfig.getFaceType());
                adapter.loadConfig(JacksonUtil.parseObject(scenicConfig.getFaceConfigJson(), Map.class));
            } else {
                adapter = FaceBodyFactory.use();
            }
            return adapter;
        });
    }

    private static final Map<Long, IPayAdapter> scenicPayAdapterMap = new ConcurrentHashMap<>();
    @Override
    public IPayAdapter getScenicPayAdapter(Long scenicId) {
        return scenicPayAdapterMap.computeIfAbsent(scenicId, (key) -> {
            IPayAdapter adapter;
            ScenicConfigEntity scenicConfig = scenicRepository.getScenicConfig(scenicId);
            if (scenicConfig != null && scenicConfig.getPayType() != null) {
                adapter = PayFactory.getAdapter(scenicConfig.getPayType());
                adapter.loadConfig(JacksonUtil.parseObject(scenicConfig.getPayConfigJson(), Map.class));
            } else {
                adapter = PayFactory.use();
            }
            return adapter;
        });
    }
}
