@szmg-fe/tarco
Version:
function library in Taro
136 lines (111 loc) • 4.05 kB
text/typescript
/*
* @Description: wx login
* @Date: 2021-03-24 11:18:17
* @Author: Lemon
* @LastEditTime: 2021-04-30 08:56:58
*/
import { BaseEventOrig, ButtonProps } from "@tarojs/components";
import chain from "@szmg-fe/funba/chain";
import id from "@szmg-fe/funba/id";
import { compose, map } from "@szmg-fe/funba/ramda";
import isArray from 'lodash/isArray';
import isFunction from 'lodash/isFunction';
import getOpenIdByConfig from "./getOpenId";
import loginForPhone from "./phoneLogin";
import { getWxCode } from "./getWxCode";
import applyFuncs from "@szmg-fe/funba/applyFunction";
import fork from "@szmg-fe/funba/fork";
import Task from '@szmg-fe/funba/Task';
import { useCallback, useRef, useEffect } from "react";
import useHandler from '@szmg-fe/hooks/useHandler';
import hideLoading from '@szmg-fe/tarco/hideLoading';
import showMessage from '@szmg-fe/tarco/showMessage';
import useRefCallback from '@szmg-fe/hooks/useRefCallback';
import showLoading from '@szmg-fe/tarco/showLoading';
import bringFunction from '@szmg-fe/funba/bringFunction'
import Taro from './Taro';
/**
* @appid:小程序appid
* @api配置:getOpenid -> 获取openid的api task
* @api配置:getToken -> 获取token的api task
*/
export default function useWxLogin(
appid: string,
api: {
getOpenid: Task,
getToken: Task
},
onLogin: (res: {
openid: string
token: string
}) => void
) {
const { getOpenid, getToken } = api; // function for task
const getWxOpenId = useCallback(getOpenIdByConfig(getOpenid, appid), []); // function for getting openId task
const middlewares = useRef([onLogin || id]); // 成功登录的中间件
// hooks里的登录信息
const loginData = useRef({
openid: '',
token: ''
});
// 错误处理的hook
const { handler: errorHandler, addHandler: addErrorHandler } = useHandler(id);
// 保存open id
const saveOpenid = compose(() => loginData.current.openid, id => loginData.current.openid = id);
// 保存token
const saveToken = token => loginData.current.token = token;
// 登录完触发middlewares
const afterLogin = compose(hideLoading, applyFuncs(middlewares.current), () => loginData.current);
// 批量返回backArgs函数
const createFs = map(f => {
const _f = res => {
f(res);
return res;
}
return _f
});
const use = fs => {
const _ifFunction = isFunction(fs);
const _isArr = isArray(fs);
if (_ifFunction || _isArr) {
middlewares.current.unshift(...createFs(_ifFunction ? [fs] : fs));
} else {
console.error('参数不符合预期');
}
return login;
}; // 插入中间件
const getLoginData = () => loginData;
const login = (e: BaseEventOrig<ButtonProps.onGetUserInfoEventDetail>) => {
const getPhone = loginForPhone(getToken, appid, e.detail.encryptedData, e.detail.iv);
compose(fork(i => errorHandler.current(i), afterLogin), map(saveToken), chain(getPhone), map(saveOpenid), chain(getWxOpenId), getWxCode)();
}
// 注入登录失败的回调
useEffect(() => {
const loginFail = () => {
hideLoading();
showMessage('登录失败,请稍后重试');
}
addErrorHandler(loginFail);
}, []);
// 手机号授权
const onGetPhoneNumber = useRefCallback((e: BaseEventOrig<ButtonProps.onGetUserInfoEventDetail>) => {
if (e.detail.errMsg.includes('deny')) return;
showLoading('登录中');
const _login = bringFunction(login)(e);
// 先check session
Taro.checkSession({
success: (i) => {
console.log('check session\'s res', i);
login(e);
},
fail: compose(fork(_login, i => console.error(i)), getWxCode)
});
});
return {
onGetPhoneNumber,
getLoginData,
use,
addErrorHandler,
login
};
};