-
Notifications
You must be signed in to change notification settings - Fork 18
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge branch 'master' into sms-message
- Loading branch information
Showing
12 changed files
with
475 additions
and
3 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,3 +1,6 @@ | ||
## 2.5.0 (2019-9-3) | ||
- [A] 支持百度小程序 | ||
|
||
## 2.4.0 (2019-8-21) | ||
- [A] QQ SDK 支持 QQ 小程序支付 | ||
- [A] web 端支持 QQ 扫码支付 | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,160 @@ | ||
const constants = require('core-module/constants') | ||
const HError = require('core-module/HError') | ||
const storage = require('core-module/storage') | ||
const utils = require('core-module/utils') | ||
const commonAuth = require('core-module/auth') | ||
|
||
module.exports = BaaS => { | ||
const API = BaaS._config.API | ||
|
||
const getLoginCode = () => { | ||
return new Promise((resolve, reject) => { | ||
swan.login({ | ||
success: res => { | ||
resolve(res.code) | ||
}, | ||
fail: (err) => { | ||
BaaS.request.swanRequestFail(reject) | ||
}, | ||
}) | ||
}) | ||
} | ||
|
||
// 获取登录凭证 code, 进而换取用户登录态信息 | ||
const auth = ({createUser = true} = {}) => { | ||
return new Promise((resolve, reject) => { | ||
getLoginCode().then(code => { | ||
sessionInit({code, createUser}, resolve, reject) | ||
}, reject) | ||
}) | ||
} | ||
|
||
// code 换取 session_key,生成并获取 3rd_session 即 token | ||
const sessionInit = ({code, createUser}, resolve, reject) => { | ||
return BaaS.request({ | ||
url: API.BAIDU.SILENT_LOGIN, | ||
method: 'POST', | ||
data: { | ||
create_user: createUser, | ||
code: code | ||
} | ||
}).then(utils.validateStatusCode).then(res => { | ||
BaaS._polyfill.handleLoginSuccess(res) | ||
resolve(res) | ||
}, reject) | ||
} | ||
|
||
const silentLogin = utils.rateLimit(function (...args) { | ||
if (storage.get(constants.STORAGE_KEY.AUTH_TOKEN) && !utils.isSessionExpired()) { | ||
return Promise.resolve() | ||
} | ||
return auth(...args) | ||
}) | ||
|
||
const getSensitiveData = (data) => { | ||
return BaaS.request({ | ||
url: API.BAIDU.AUTHENTICATE, | ||
method: 'POST', | ||
data, | ||
}).then(utils.validateStatusCode) | ||
} | ||
|
||
const getUserInfo = ({lang} = {}) => { | ||
return new Promise((resolve, reject) => { | ||
swan.getUserInfo({ | ||
lang, | ||
success: resolve, fail: reject | ||
}) | ||
}) | ||
} | ||
|
||
// 提供给开发者在 button (open-type="getUserInfo") 的回调中调用,对加密数据进行解密,同时将 userinfo 存入 storage 中 | ||
const handleUserInfo = res => { | ||
if (!res || !res.detail) { | ||
throw new HError(603) | ||
} | ||
|
||
let detail = res.detail | ||
let createUser = !!res.createUser | ||
let syncUserProfile = res.syncUserProfile | ||
|
||
// 用户拒绝授权,仅返回 uid, openid | ||
if (!detail.userInfo) { | ||
return Promise.reject(Object.assign(new HError(603), { | ||
id: storage.get(constants.STORAGE_KEY.UID), | ||
openid: storage.get(constants.STORAGE_KEY.OPENID), | ||
})) | ||
} | ||
|
||
return getLoginCode().then(code => { | ||
return getUserInfo({lang: detail.userInfo.language}).then(detail => { | ||
let payload = { | ||
code, | ||
create_user: createUser, | ||
data: detail.data, | ||
iv: detail.iv, | ||
update_userprofile: utils.getUpdateUserProfileParam(syncUserProfile), | ||
} | ||
return getSensitiveData(payload) | ||
}) | ||
}).then(res => { | ||
BaaS._polyfill.handleLoginSuccess(res) | ||
}) | ||
} | ||
|
||
|
||
const linkBaidu = (res, { | ||
syncUserProfile = constants.UPDATE_USERPROFILE_VALUE.SETNX, | ||
} = {}) => { | ||
let refreshUserInfo = false | ||
if (res && res.detail && res.detail.userInfo) { | ||
refreshUserInfo = true | ||
} | ||
|
||
return getLoginCode().then(code => { | ||
// 如果用户传递了授权信息,则重新获取一次 userInfo, 避免因为重新获取 code 导致 session 失效而解密失败 | ||
let getUserInfoPromise = refreshUserInfo | ||
? getUserInfo({lang: res.detail.userInfo.language}) | ||
: Promise.resolve(null) | ||
|
||
return getUserInfoPromise.then(res => { | ||
let payload = res ? { | ||
rawData: res.rawData, | ||
signature: res.signature, | ||
encryptedData: res.encryptedData, | ||
iv: res.iv, | ||
update_userprofile: utils.getUpdateUserProfileParam(syncUserProfile), | ||
code | ||
} : {code} | ||
|
||
return BaaS._baasRequest({ | ||
method: 'POST', | ||
url: API.BAIDU.USER_ASSOCIATE, | ||
data: payload, | ||
}) | ||
}) | ||
}) | ||
} | ||
|
||
const loginWithBaidu = (authData, { | ||
createUser = true, | ||
syncUserProfile = constants.UPDATE_USERPROFILE_VALUE.SETNX, | ||
} = {}) => { | ||
let loginPromise = null | ||
if (authData && authData.detail) { | ||
// handleUserInfo 流程 | ||
loginPromise = handleUserInfo(Object.assign(authData, {createUser, syncUserProfile})) | ||
} else { | ||
// 静默登录流程 | ||
loginPromise = silentLogin({createUser}) | ||
} | ||
|
||
return loginPromise.then(() => commonAuth.getCurrentUser()) | ||
} | ||
|
||
Object.assign(BaaS.auth, { | ||
silentLogin, | ||
loginWithBaidu: utils.rateLimit(loginWithBaidu), | ||
linkBaidu: utils.rateLimit(linkBaidu), | ||
}) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,40 @@ | ||
const utils = require('core-module/utils') | ||
const BaaS = require('core-module/baas') | ||
const constants = require('core-module/constants') | ||
const storage = require('core-module/storage') | ||
|
||
/** | ||
* | ||
* @param {object} payload | ||
*/ | ||
function tryResendRequest(payload) { | ||
// 情景1:若是第一次出现 401 错误,此时的缓存一定是过期的。 | ||
// 情景2:假设有 a,b 两个 401 错误的请求,a请求 300ms 后返回,走情景 1 的逻辑。b 在 pending 10 秒后返回,此时缓存实际上是没过期的,但是仍然会重新清空缓存,走情景 1 逻辑。 | ||
// 情景3:假设有 a,b,c 3 个并发请求,a 先返回,走了情景 1 的逻辑,此时 bc 请求在 silentLogin 请求返回前返回了,这时候他们会等待 silentLogin , 即多个请求只会发送一次 silentLogin 请求 | ||
if (storage.get(constants.STORAGE_KEY.AUTH_TOKEN)) { | ||
// 缓存被清空,silentLogin 一定会发起 session init 请求 | ||
BaaS.clearSession() | ||
} | ||
|
||
BaaS.auth.silentLogin().then(() => { | ||
return BaaS.request(payload).then(utils.validateStatusCode) | ||
}) | ||
} | ||
|
||
// BaaS 网络请求,此方法能保证在已登录 BaaS 后再发起请求 | ||
// eslint-disable-next-line no-unused-vars | ||
const baasRequest = function ({url, method = 'GET', data = {}, header = {}, dataType = 'json'}) { | ||
let beforeRequestPromise = BaaS._config.AUTO_LOGIN ? BaaS.auth.silentLogin() : Promise.resolve() | ||
|
||
return beforeRequestPromise.then(() => { | ||
return BaaS.request.apply(null, arguments) | ||
}).then(res => { | ||
if (res.statusCode === constants.STATUS_CODE.UNAUTHORIZED && BaaS._config.AUTO_LOGIN) { | ||
return tryResendRequest({header, method, url, data, dataType}) | ||
} else { | ||
return utils.validateStatusCode(res) | ||
} | ||
}) | ||
} | ||
|
||
module.exports = baasRequest |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,20 @@ | ||
const BaaS = require('core-module/baas') | ||
const core = require('core-module/index') | ||
const polyfill = require('./polyfill') | ||
const auth = require('./auth') | ||
|
||
BaaS._config.VERSION = __VERSION_BAIDU__ | ||
|
||
BaaS.use(core) | ||
BaaS.use(polyfill) | ||
BaaS.use(auth) | ||
BaaS.request = require('./request') | ||
BaaS._baasRequest = require('./baasRequest') | ||
BaaS.uploadFile = require('./uploadFile') | ||
BaaS._createRequestMethod() | ||
// 暴露 BaaS 到小程序环境 | ||
if (typeof swan !== 'undefined') { | ||
swan.BaaS = BaaS | ||
} | ||
|
||
module.exports = BaaS |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,44 @@ | ||
const constants = require('core-module/constants') | ||
module.exports = BaaS => { | ||
Object.assign(BaaS._polyfill, { | ||
CLIENT_PLATFORM: 'BAIDU', | ||
setStorageSync(k, v) { | ||
return swan.setStorageSync(k, v) | ||
}, | ||
getStorageSync(k) { | ||
return swan.getStorageSync(k) | ||
}, | ||
getSystemInfoSync() { | ||
return swan.getSystemInfoSync() | ||
}, | ||
checkLatestVersion() { | ||
let info = swan.getSystemInfoSync() | ||
if (info.platform === 'devtools') { | ||
BaaS.checkVersion({platform: 'baidu_miniapp'}) | ||
} | ||
}, | ||
linkBaidu(...args) { | ||
return BaaS.auth.linkBaidu(...args) | ||
}, | ||
handleLoginSuccess(res, isAnonymous) { | ||
// 登录成功的 hook (login、loginWithWechat、register)调用成功后触发 | ||
BaaS.storage.set(constants.STORAGE_KEY.UID, res.data.user_id) | ||
BaaS.storage.set(constants.STORAGE_KEY.OPENID, res.data.openid || '') | ||
BaaS.storage.set(constants.STORAGE_KEY.AUTH_TOKEN, res.data.token) | ||
BaaS.storage.set(constants.STORAGE_KEY.UNIONID, res.data.unionid || '') | ||
if (res.data.openid) { | ||
BaaS.storage.set(constants.STORAGE_KEY.USERINFO, { | ||
id: res.data.user_id, | ||
openid: res.data.openid, | ||
unionid: res.data.unionid, | ||
}) | ||
} | ||
BaaS.storage.set(constants.STORAGE_KEY.EXPIRES_AT, Math.floor(Date.now() / 1000) + res.data.expires_in - 30) | ||
if (isAnonymous) { | ||
BaaS.storage.set(constants.STORAGE_KEY.IS_ANONYMOUS_USER, 1) | ||
} else { | ||
BaaS.storage.set(constants.STORAGE_KEY.IS_ANONYMOUS_USER, 0) | ||
} | ||
}, | ||
}) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
const BaaS = require('core-module/baas') | ||
const HError = require('core-module/HError') | ||
const utils = require('core-module/utils') | ||
const constants = require('core-module/constants') | ||
|
||
const swanRequestFail = function (reject) { | ||
swan.getNetworkType({ | ||
success: function (res) { | ||
if (res.networkType === 'none') { | ||
reject(new HError(600)) // 断网 | ||
} else { | ||
reject(new HError(601)) // 网络超时 | ||
} | ||
} | ||
}) | ||
} | ||
|
||
const request = ({url, method = 'GET', data = {}, header = {}, dataType = 'json'}) => { | ||
return new Promise((resolve, reject) => { | ||
|
||
if (!BaaS._config.CLIENT_ID) { | ||
return reject(new HError(602)) | ||
} | ||
|
||
let headers = utils.mergeRequestHeader(header) | ||
|
||
if (!/https?:\/\//.test(url)) { | ||
const API_HOST = BaaS._config.DEBUG ? BaaS._config.API_HOST : BaaS._polyfill.getAPIHost() | ||
url = API_HOST.replace(/\/$/, '') + '/' + url.replace(/^\//, '') | ||
} | ||
|
||
swan.request({ | ||
method: method, | ||
url: url, | ||
data: data, | ||
header: headers, | ||
dataType: dataType, | ||
success: resolve, | ||
fail: (err) => { | ||
swanRequestFail(reject) | ||
} | ||
}) | ||
|
||
utils.log(constants.LOG_LEVEL.INFO, 'Request => ' + url) | ||
}) | ||
} | ||
|
||
module.exports = request | ||
module.exports.swanRequestFail = swanRequestFail |
Oops, something went wrong.