package com.duben.microtribe.ui.service;

import android.app.Notification;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.app.Service;
import android.content.Context;
import android.content.Intent;
import android.net.Uri;
import android.os.Binder;
import android.os.Build;
import android.os.Handler;
import android.os.IBinder;
import android.os.Message;
import androidx.core.app.NotificationCompat;
import androidx.core.content.FileProvider;
import android.widget.RemoteViews;

import com.duben.microtribe.R;
import com.duben.microtribe.common.Constant;
import com.duben.microtribe.ui.activitys.MainActivity;

import java.io.File;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;

public class UpdateService extends Service {
    static final int DOWN_OK = 1;
    static final int DOWN_ERROR = 2;
    static final int DOWN_PROGRESS = 3;
    static final int TIMEOUT = 5000;

    String down_url = null;
    static String tempFilename = "position_Android";

    static File updateFile;

    private UpdateNotification updateNotification;


    @Override
    public IBinder onBind(Intent intent) {
        //开启服务时有可能intent或者里面的Extras为空，这里要判断一下，以后如此
        if (intent != null && intent.getExtras() != null) {
            // 创建文件
            down_url = intent.getExtras().getString("path");
            tempFilename = intent.getExtras().getString("app_name");
//            updateFile = FileUtils.createAttachFile(tempFilepath, tempFilename + ".apk");// 创建文件
            updateFile = new File(this.getCacheDir().getPath() + "/" + tempFilename + ".apk");// 创建文件
            //创建的file不为空的话
            if (updateFile != null) {
                createNotification();// 首次创建
                createThread();// 线程下载
            }
        } else {
            stopService();
        }

        // 返回一个Binder对象 为了service通讯
        return new UpdateBinder();
    }

    /**
     * 获取更新的service
     */
    public class UpdateBinder extends Binder {
        public UpdateService getService() {
            return UpdateService.this;
        }
    }

    public void setUpdateNotification(UpdateNotification updateNotification) {
        this.updateNotification = updateNotification;
    }

    /**
     * 创建通知栏 Notification的进度条数值
     */
    RemoteViews contentView;
    NotificationManager notificationManager;
    Notification notification;
    NotificationCompat.Builder mBuilder;
    Intent updateIntent;
    PendingIntent pendingIntent;
    int notification_id = 11;

    /**
     * 创建通知栏
     */
    public void createNotification() {
        notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
        mBuilder = new NotificationCompat.Builder(this);

        updateIntent = new Intent(this, MainActivity.class);
        updateIntent.addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP);
        if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.S) {
            pendingIntent = PendingIntent.getActivity(this, 0, updateIntent, PendingIntent.FLAG_IMMUTABLE);
        } else {
            pendingIntent = PendingIntent.getActivity(this, 0, updateIntent, PendingIntent.FLAG_ONE_SHOT);
        }

        mBuilder.setWhen(System.currentTimeMillis())// 通知产生的时间，会在通知信息里显示
                .setContentIntent(pendingIntent)
                // .setNumber(number)//显示数量
                .setPriority(Notification.PRIORITY_DEFAULT)// 设置该通知优先级
                // .setAutoCancel(true)//设置这个标志当用户单击面板就可以让通知将自动取消
                .setOngoing(true)// ture，设置他为一个正在进行的通知。他们通常是用来表示一个后台任务,用户积极参与(如播放音乐)或以某种方式正在等待,因此占用设备(如一个文件下载,同步操作,主动网络连接)
                .setDefaults(Notification.FLAG_FOREGROUND_SERVICE)// 向通知添加声音、闪灯和振动效果的最简单、最一致的方式是使用当前的用户默认设置，使用defaults属性，可以组合：
                // Notification.DEFAULT_ALL Notification.DEFAULT_SOUND 添加声音 //
                // requires VIBRATE permission
                .setSmallIcon(R.mipmap.ic_launcher_main);

        contentView = new RemoteViews(getPackageName(), R.layout.notification_item);
        contentView.setImageViewResource(R.id.image, R.mipmap.ic_launcher_main);
        contentView.setTextViewText(R.id.notificationTitle, getString(R.string.update_load));
        contentView.setTextViewText(R.id.notificationPercent, "0%");
        contentView.setProgressBar(R.id.notificationProgress, 100, 0, false);

//        mBuilder.setContent(contentView)
        mBuilder.setTicker(getString(R.string.update_app));

        notification = mBuilder.build();
        notification.contentView = contentView;
        notificationManager.notify(notification_id, notification);

    }

    /***
     * 开线程下载
     */
    public void createThread() {
        /***
         * 更新UI
         */
        final Handler handler = new Handler() {
            @Override
            public void handleMessage(Message msg) {
                switch (msg.what) {
                    case DOWN_OK:
//                        // 下载完成，点击安装
//                        Intent intent = new Intent();
//                        // context以外启动时，必须要有该flag
//                        if (Build.VERSION.SDK_INT > Build.VERSION_CODES.M) {
//                            intent.setData(Uri.parse(Constant.YINGYONGBAO_URL));
//                        } else {
//                            intent.setDataAndType(Uri.fromFile(updateFile),
//                                    "application/vnd.android.package-archive");
//                        }
//                        intent.setAction(Intent.ACTION_VIEW);
//                        intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
//                        startActivity(intent);
                        if (updateNotification != null) {
                            updateNotification.finishProgress();
                        }
                        autoInstallApk(updateFile);
                        stopService();
                        break;
                    case DOWN_ERROR:
                        contentView.setTextViewText(R.id.notificationPercent, "下载错误");
                        contentView.setProgressBar(R.id.notificationProgress, 0,
                                0, false);
                        // show_view
                        notificationManager.notify(notification_id, notification);

                        stopService();
                        break;
                    case DOWN_PROGRESS:

                        contentView.setTextViewText(R.id.notificationPercent,
                                msg.arg1 + "%");
                        contentView.setProgressBar(R.id.notificationProgress, 100,
                                msg.arg1, false);
                        notificationManager.notify(notification_id, notification);

                        if (updateNotification != null) {
                            updateNotification.updateProgress(msg.arg1);
                        }
                        break;
                    default:
                        stopService();
                        break;
                }
            }
        };
        final Message message = new Message();
        new Thread(new Runnable() {
            public void run() {
                try {
                    long downloadSize = downloadUpdateFile(handler, down_url,
                            updateFile.toString());
                    if (downloadSize > 0) {
                        // 下载成功
                        message.what = DOWN_OK;
                        handler.sendMessage(message);
                    }
                } catch (Exception e) {
                    e.printStackTrace();
                    message.what = DOWN_ERROR;
                    handler.sendMessage(message);
                }
            }
        }).start();
    }

    /**
     * 安装 apk 文件
     */
    private void autoInstallApk(File file) {
        Intent intent = new Intent(Intent.ACTION_VIEW);
        if (Build.VERSION.SDK_INT < Build.VERSION_CODES.N) {
            intent.setDataAndType(Uri.fromFile(file), "application/vnd.android.package-archive");
        } else {//Android7.0之后获取uri要用contentProvider
            Uri contentUri = FileProvider.getUriForFile(getApplicationContext(), Constant.MINTS_PKG_NAME+".fileprovider", file);
            intent.setDataAndType(contentUri, "application/vnd.android.package-archive");
            intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
        }
        intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
        startActivity(intent);
    }

    /***
     * 下载文件
     *
     * @return
     * @throws MalformedURLException
     */
    private long downloadUpdateFile(Handler handler, String down_url, String file)
            throws Exception {
        int down_step = 1;// 提示step
        int totalSize;// 文件总大小
        int downloadCount = 0;// 已经下载好的大小
        int updateCount = 0;// 已经上传的文件大小
        Message message;
        InputStream inputStream;
        OutputStream outputStream;
        URL url = new URL(down_url);
        HttpURLConnection httpURLConnection = (HttpURLConnection) url
                .openConnection();
        httpURLConnection.setConnectTimeout(TIMEOUT);
        httpURLConnection.setReadTimeout(TIMEOUT);
        // 获取下载文件的size
        totalSize = httpURLConnection.getContentLength();
        if (httpURLConnection.getResponseCode() == 404) {
            throw new Exception("fail!");
        }
        inputStream = httpURLConnection.getInputStream();
        outputStream = new FileOutputStream(file, false);// 文件存在则覆盖掉
        byte buffer[] = new byte[1024];
        int readsize = 0;
        while ((readsize = inputStream.read(buffer)) != -1) {
            outputStream.write(buffer, 0, readsize);
            downloadCount += readsize;// 时时获取下载到的大小
            /**
             * 每次增张5%
             */
            if (updateCount == 0
                    || (downloadCount * 100 / totalSize - down_step) >= updateCount) {
                updateCount += down_step;
                message = new Message();
                message.what = DOWN_PROGRESS;
                message.arg1 = updateCount;
                handler.sendMessage(message);
            }
        }
        if (httpURLConnection != null) {
            httpURLConnection.disconnect();
        }
        inputStream.close();
        outputStream.close();
        return downloadCount;
    }

    /**
     * 关闭service
     */
    private void stopService() {
        new Handler().postDelayed(new Runnable() {
            @Override
            public void run() {
                notificationManager.cancel(notification_id);
                stopSelf();
            }
        }, 3000);
    }

    /**
     * apk更新进度通知
     */
    public interface UpdateNotification {
        public void updateProgress(int progress);

        void finishProgress();
    }

}
