package com.fxy.common;

import android.content.Context;
import android.os.Handler;
import android.os.Message;
import android.widget.Toast;

import com.alibaba.sdk.android.oss.ClientConfiguration;
import com.alibaba.sdk.android.oss.ClientException;
import com.alibaba.sdk.android.oss.OSS;
import com.alibaba.sdk.android.oss.OSSClient;
import com.alibaba.sdk.android.oss.ServiceException;
import com.alibaba.sdk.android.oss.callback.OSSCompletedCallback;
import com.alibaba.sdk.android.oss.callback.OSSProgressCallback;
import com.alibaba.sdk.android.oss.common.OSSConstants;
import com.alibaba.sdk.android.oss.common.auth.OSSCredentialProvider;
import com.alibaba.sdk.android.oss.common.auth.OSSFederationCredentialProvider;
import com.alibaba.sdk.android.oss.common.auth.OSSFederationToken;
import com.alibaba.sdk.android.oss.common.utils.IOUtils;
import com.alibaba.sdk.android.oss.internal.OSSAsyncTask;
import com.alibaba.sdk.android.oss.model.PutObjectRequest;
import com.alibaba.sdk.android.oss.model.PutObjectResult;
import com.elvishew.xlog.XLog;
import com.fxy.baselibrary.util.RxTimeTool;
import com.fxy.BuildConfig;
import com.fxy.constant.SPCache;
import com.fxy.net.Urls;

import org.json.JSONObject;

import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;

public class OssService {
    private Context mContext;
    private  String endpoint = ""; //上传节点 比如：http://oss-cn-shenzhen.aliyuncs.com
    private  String bucketName = "fhdr"; // bucket值
    private  String regionId = "cn-shenzhen"; //地区 比如：cn-shenzhen
    private  String filePath = "fxy/";
    protected OSS oss ;
    protected String ossHost="";
    OSSAsyncTask taskId = null;

    public String getBucketName(){
        return bucketName;
    }

    public String getFilePath(){
        return filePath;
    }

    public String getOssHost(){
        return ossHost;
    }

    public OSS getOSS(){
        return oss;
    }
    public OssService(Context context, String prefix){
        mContext = context;
        initData();
        prefix = prefix.isEmpty()?"default/":prefix+"/";
        filePath = filePath+prefix+RxTimeTool.getYestoryDate("yyyyMMd")+"/";

        creationOss();
    }

    //创建 OSS
    public OSS creationOss(){
        // 在移动端建议使用STS的方式初始化OSSClient。
        String stsServer = Urls.getServiceAddress(mContext)+ Urls.FMS_UPLOAD_SIGN;
        // 推荐使用OSSAuthCredentialsProvider。token过期可以及时更新。

        OSSCredentialProvider credentialProvider = new OSSFederationCredentialProvider() {
            @Override
            public OSSFederationToken getFederationToken() {
                try {
                    URL stsUrl = new URL(Urls.getServiceAddress(mContext)+ Urls.FMS_UPLOAD_SIGN);
                    HttpURLConnection conn = (HttpURLConnection) stsUrl.openConnection();
                    conn.setRequestProperty("warehouse-id", SPCache.getInstance(mContext).getWareHouseId());
                    conn.setRequestProperty("version", "999999");
                    conn.setRequestProperty("token", SPCache.getInstance(mContext).getToken());
                    InputStream input = conn.getInputStream();
                    String jsonText = IOUtils.readStreamAsString(input, OSSConstants.DEFAULT_CHARSET_NAME);
                    JSONObject response = new JSONObject(jsonText);
                    if (response.getInt("code")==1){
                        JSONObject jsonObjs = response.getJSONObject("data");
                        String ak = jsonObjs.getString("AccessKeyId");
                        String sk = jsonObjs.getString("AccessKeySecret");
                        String token = jsonObjs.getString("SecurityToken");
                        String expiration = jsonObjs.getString("Expiration");
                        SPCache spCache = SPCache.getInstance(mContext);
                        if (jsonObjs.has("resource_region") && !spCache.getResourceRegion().equals(jsonObjs.getString("resource_region")) ||
                                !spCache.getResourceBucket().equals(jsonObjs.getString("resource_bucket"))||
                                !spCache.getResourcePrefix().equals(jsonObjs.getString("resource_prefix"))){
                            spCache.setResourcePrefix(jsonObjs.getString("resource_prefix"));
                            spCache.setResourceRegion(jsonObjs.getString("resource_region"));
                            spCache.setResourceBucket(jsonObjs.getString("resource_bucket"));
                            initData();
                        }
                        return new OSSFederationToken(ak, sk, token, expiration);
                    }
                } catch (Exception e) {
                    e.printStackTrace();
                }
                return null;
            }
        };

        // 在移动端建议使用STS的方式初始化OSSClient。
        //OSSCredentialProvider credentialProvider = new OSSStsTokenCredentialProvider(accessKeyId, accessKeySecret, "");

        ClientConfiguration conf = new ClientConfiguration();
        conf.setConnectionTimeout(15 * 1000); // 连接超时，默认15秒。
        conf.setSocketTimeout(15 * 1000); // socket超时，默认15秒。
        conf.setMaxConcurrentRequest(5); // 最大并发请求书，默认5个。
        conf.setMaxErrorRetry(2); // 失败后最大重试次数，默认2次。
        oss = new OSSClient(mContext, endpoint, credentialProvider, conf);


        //开始日志
        //OSSLog.enableLog();
        return oss;
    }

    //初始化oss数据以及切换不同的oss账号
    private void initData(){
        SPCache spCache = SPCache.getInstance(mContext);
        ossHost = spCache.getResourceHost();
        filePath = spCache.getResourcePrefix()+"/android/";
        //匹配资源

        bucketName = spCache.getResourceBucket();
        regionId   = spCache.getResourceRegion();
        if (!regionId.isEmpty()){
            endpoint   = "https://oss-"+regionId+".aliyuncs.com";
        }

        if (regionId.isEmpty()){
            Toast.makeText(mContext, "资源路径异常", Toast.LENGTH_SHORT).show();
        }
    }

    public void ossUpload(String filePath, String uploadName , int num, Handler handler){
        new ossThread(filePath, uploadName , num,handler).start();
        // task.cancel(); // 可以取消任务
        // task.waitUntilFinished(); // 可以等待直到任务完成
    }

    //取消上传
    public void taskCancel(){
        if (taskId!=null && !taskId.isCanceled()){
            taskId.cancel();
        }
    }

    //阿里云oss上传
    class ossThread extends Thread {
        private String urlPath = "";
        private String objectKey = "";
        private int current = 0;
        private Handler uploadHandler ;
        public ossThread(String filePath, String fileName ,int num,Handler handler) {
            urlPath = filePath;
            objectKey = fileName;
            current = num;
            uploadHandler = handler;
        }
        public void run() {

            // 下面3个参数依次为bucket名，ObjectKey名，上传文件路径
            final PutObjectRequest put = new PutObjectRequest(getBucketName(), getFilePath()+objectKey, urlPath);
            // 设置进度回调
            put.setProgressCallback(new OSSProgressCallback<PutObjectRequest>() {
                @Override
                public void onProgress(PutObjectRequest request, long currentSize, long totalSize) {
                    // 进度逻辑
                    int progress = (int) ((double) currentSize / (double) totalSize * 100);
                    Message msg = new Message();
                    msg.arg1 = progress;
                    msg.what = 3;
                    uploadHandler.sendMessage(msg);
                }
            });
            // 异步上传
            taskId = oss.asyncPutObject(put, new OSSCompletedCallback<PutObjectRequest, PutObjectResult>() {
                @Override
                public void onSuccess(PutObjectRequest request, PutObjectResult result) {

                    if (BuildConfig.DEBUG){
                        XLog.e(request);
                    }
                    Message msg = new Message();
                    msg.arg1 = current;
                    msg.obj = "/"+request.getObjectKey();
                    msg.what = 2;
                    uploadHandler.sendMessage(msg);
                }

                @Override
                public void onFailure(PutObjectRequest request, ClientException clientExcepion, ServiceException serviceException) {
                    Message msg = new Message();
                    msg.what = 1;
                    if (clientExcepion != null) {
                        // 本地异常，如网络异常等。
                        msg.obj = "网络异常，请稍后...";
                        uploadHandler.sendMessage(msg);
                        XLog.e("RawMessage", clientExcepion.getMessage());
                    }
                    if (serviceException != null) {
                        msg.obj = "服务异常，请稍后...";
                        uploadHandler.sendMessage(msg);
                        if (BuildConfig.DEBUG){
                            // 服务异常。
                            XLog.e("ErrorCode", serviceException.getErrorCode());
                            XLog.e("RequestId", serviceException.getRequestId());
                            XLog.e("HostId", serviceException.getHostId());
                            XLog.e("RawMessage", serviceException.getRawMessage());
                        }
                    }
                }
            });
        }
    }




}
