/* eslint-disable no-restricted-syntax */
'use strict';
import { auth } from '@cloudbase/weda-client';
const { checkAnonymous, __internal__ = {}} = auth;
const { getAuthConfig, redirectToLogin: _redirectToLogin, getAccessPermission, findLoginPage, cleanAccessPermissionCache } = __internal__
import { getWedaAPI } from '@cloudbase/weda-client'

export let LOGIN_CONFIG = <%= customLoginConfig %>

export function findStatusPage() {
  const { app } = getWedaAPI();
  const { pages = [] } = app.__internal__.getConfig();
  return pages.find((item) => item.type === 'status');
}

export function formatErrorMsg(e) {
  let msg = e?.errMsg || e?.error_description || e?.message;
  const uri = e?.error_uri;
  msg = `${msg}${uri ? `-${uri}` : ''}`;
  if (msg.startsWith('request:fail')) {
    msg = `网络故障, 请检查本地网络连接是否正常(${msg})`;
  }
  return msg;
}

export async function redirectToLogin($page) {
  const { app } = getWedaAPI();
	const loginConfig = await getLoginConfig();

  // 开启了多种登录模式，跳入登录页面让用户选择登录方式
  if (loginConfig?.miniprogram?.length > 1) {
    await _redirectToLogin($page);
    return null;
  }

  const AUTO_LOGIN = {
    openid_login: app.cloud.openIdLoginInWxApp,
    unionid_login: app.cloud.unionIdLoginInWxApp
  }
  const loginType = loginConfig?.miniprogram?.[0]?.type;

  if(AUTO_LOGIN[loginType]){
    await AUTO_LOGIN[loginType]();
    cleanAccessPermissionCache?.();

    const { avatarUrl, nickName } = app.auth.currentUser;
    // 信息不全，去登录页面补全信息
    if (!avatarUrl || !nickName) {
      await _redirectToLogin($page, { baseInfoShow: 'true', currentLoginType: loginType });
      return null
    }

    return { refreshAccess: true };
  }

  await _redirectToLogin($page);
  return null
}

/**
 * 检查页面权限
 **/
export async function checkAuth(app, appId, $page) {
  <% if(skipCheckAuth){ %> return true <% } %>

  const { publicPage } = app.__internal__?.getConfig() || {};

  // 是否处于公开访问页面
  const isInPublicPage = publicPage?.includes(`${$page.__internal__.packageName}/${$page.id}`.replace(/^\/|\/$/g, ''));

	const loginConfig = await getLoginConfig();

  const loginPage = findLoginPage(app);
  const loginPageUUID = loginPage?.uuid || loginPage?.id
  const currentUUID = $page.uuid || $page.id
  if (loginPageUUID === currentUUID) {
    return true;
  }
  const status = findStatusPage(app);
  if (status?.id === $page.id) {
    return true;
  }
  wx.showNavigationBarLoading();
  const requestList = [getAccessPermission(appId, $page.__internal__.packageName, $page.id, <%= !!isAdminPortal %>)];
  // 暂时先认为有登录页则自定义登录功能开启且生效
  if (loginConfig) {
    requestList.push(getAuthConfig(<%= !!isAdminPortal %>));
  }
  try {
    const [accessData, authConfig] = await Promise.all(requestList);

    const isAnonymousUser = await checkAnonymous();
    // 如果当前页面匿名用户无权限访问
    if (!accessData?.isAccess) {
      // 当前匿名情况下，且需要登录后访问应用
      if (isAnonymousUser && (authConfig?.NeedLogin || authConfig?.RejectStrategy == 'to_login')) {
        if (loginPage && !isInPublicPage) {
          // 开启了手机号授权登录，则判断是否跳转到登录页面
          const res = await redirectToLogin($page, loginConfig);
          if(res?.refreshAccess) {
            const accessData = await getAccessPermission(appId, $page.__internal__.packageName, $page.id, <%= !!isAdminPortal %>)
            return  accessData?.isAccess
          }
        }
      } else {
        app.showToast({
          title: ['-2', '-4'].includes(accessData?.roleId) ? '默认访客无权限' : '页面无访问权限',
          icon: 'error',
        });
      }
    } else if (authConfig?.NeedLogin && isAnonymousUser) {
      // 此分支逻辑本不应该前端判断是否登录，历史原因后端短期内搞不定，后续后端优化后删除
      // 如果当前页面匿名用户有权限访问，且需要登录后访问应用，则按配置进行登录
      if (loginPage && !isInPublicPage) {
        try {
          const res = await redirectToLogin($page, loginConfig);
          if(res?.refreshAccess) {
            const accessData = await getAccessPermission(appId, $page.__internal__.packageName, $page.id, <%= !!isAdminPortal %>)
            return  accessData?.isAccess
          }
          return false;
        } catch (e) {
          const res = await redirectToLogin($page, loginConfig);
          if(res?.refreshAccess) {
            const accessData = await getAccessPermission(appId, $page.__internal__.packageName, $page.id, <%= !!isAdminPortal %>)
            return  accessData?.isAccess
          }
          return false;
        }
      }
    }

    if (<%= !!ensureUserInfo %>) {
      await app.auth.getUserInfo()
    }

    return accessData?.isAccess;
  } catch (e) {
    if(app?.__internal__?.activePage?.id === $page.id) {
      throw new Error(formatErrorMsg(e))
    }
    return false;
  } finally {
    wx.hideNavigationBarLoading();
  }
}

<% if(expirationStartTimesnap){ %>
function formatLifecycle(time) {
  let str = '';
  const times = [time / 1000, 0, 0, 0];
  const unit = ['秒', '分', '小时', '天'];
  const delta = [1, 60, 60, 24];
  for (let i = 1; i < times.length; i++) {
    if (times[i - 1]) {
      times[i] = Math.floor(times[i - 1] / delta[i]);
      times[i - 1] = times[i - 1] % delta[i];
    }
  }
  for (let i = times.length - 1; i >= 0; i--) {
    if (times[i]) {
      str += times[i]+unit[i];
    }
  }
  return str;
}

const PROMISE = new Promise((resolve, reject)=>{
  wx.request({
    url: '<%= RUNTIME_CONFIG_URL %>',
    success: res => resolve(res.data),
    fail: e => {
      resolve(<%= JSON.stringify(runtimeDynamicConfig)%>)
    }
  })
})
<% } %>

export async function getExpiredMessage(createdTime = 0) {
  if (wx.getSystemInfoSync().platform === 'devtools') {
    return ;
  }
<% if(expirationStartTimesnap){ %>
  try {
    if (createdTime) {
      const json = await PROMISE;
      const { expLifeTime = Infinity } = json;
      const releaseTime = wx.getAccountInfoSync()?.miniProgram?.releaseTime;
      if(releaseTime) {
        let date = new Date(releaseTime);
        createdTime = date.getTime()
      }
      if (Date.now() - createdTime > expLifeTime) {
        return `该版本为微搭免费套餐（长期免费，按月续期），需要再次发布激活，每次发布应用活跃时间为${formatLifecycle(
          expLifeTime,
        )}，可多次发布。您也可以升级为付费套餐，无应用活跃时间限制。`;
      }
    }
  } catch (e) {
    console.error('检查应用存活周期失败', e);
  }
<% } %>
}

export async function getLoginConfig() {
  const { app } = getWedaAPI()
  <% if(loginConfigPathname){ %>
  const { staticResourceDomain, loginConfigVersion, id } = app.__internal__?.getConfig() || {};
  if (staticResourceDomain && loginConfigVersion && id) {
    const url = app.__internal__?.resolveStaticResourceUrl?.(`<%= loginConfigPathname %>`)
    if (!LOGIN_CONFIG) {
      LOGIN_CONFIG = await new Promise((resolve, reject) => {
        wx.request({
          url,
          success: res => {
            if(String(res.statusCode).startsWith('2')){
              resolve(res.data)
            } else {
              reject(new Error(`statusCode: ${res.statusCode} 获取${url}失败`))
            }
          },
          fail: e => {
            const error = new Error(e.errMsg)
            error.code = e.errno
            reject(error)
          }
        })
      })
    }
    return LOGIN_CONFIG
  } else {
    throw new Error('缺少登录配置');
  }
  <% } %>
}
