在一点云打包中勾选 QQ 移动应用登录 并填写 AppID 后,APK 会集成 QQ 互联 OpenSDK。用户在 APP 内点击 QQ 登录时,原生唤起 QQ 客户端完成授权,回到 WebView 后由网站 H5 将 access_tokenopenid 提交到您的网站建立会话。

重要:打包仅写入移动应用 AppIDAppKey 必须在您网站服务器.env 或自有后端)配置,不会出现在 APK 内。

一、QQ 互联控制台(connect.qq.com)

  1. 登录 QQ 互联,创建 移动应用,获取 AppID(填到打包表单的「QQ 移动应用 AppID」)。
  2. 在移动应用详情中填写 Android 包名:须与打包时填写的「应用包名」完全一致(如 com.example.myapp)。
  3. 填写 应用签名:QQ 要求证书 MD5 指纹,格式为去冒号、全小写(例如 a1b2c3d4e5f6...)。须与本次打包实际使用的签名证书一致,否则无法唤起 QQ。
  4. 若网站仍需 浏览器 / 网页 QQ 登录,另建「网站应用」,配置回调地址,并在服务器配置对应 AppKey(见下文)。

二、如何获取应用签名 MD5

正式打包(Release 签名)

使用您在控制台上传或在线生成的 Release Keystore 签名。打包页勾选 QQ 登录后,会在参数区显示当前所选证书的 MD5,可直接复制到 QQ 互联。

也可在本地用 keytool 查看(将路径、别名、密码替换为您的证书信息):

keytool -list -v -keystore your-release.jks -alias your_alias

在输出中找到 MD5: 一行,去掉冒号并转为小写即为 QQ 互联所需格式。

试用打包(Debug 签名)

试用包使用云端编译服务器的 Android Debug 签名。打包页会显示对应的 Debug MD5;若未显示,可在试用包编译完成后,用以下方式从 APK 提取:

三、打包表单填写项

四、网站服务端配置

在网站 .env 中配置 QQ 互联「网站应用」凭证(用于校验 token / 网页授权):

OAUTH_QQ_ENABLED=true
OAUTH_QQ_APP_ID=你的网站应用AppID
OAUTH_QQ_APP_KEY=你的网站应用AppKey
# 可选:与 QQ 互联控制台一致;默认 https://你的域名/qqlogin.html
OAUTH_QQ_REDIRECT_URI=https://你的域名/qqlogin.html

原生登录接口(APP 内 H5 调用,POST JSON):

POST /auth/qq/native
Content-Type: application/json
X-CSRF-TOKEN: (页面 csrf_token)

{
  "access_token": "由 QWNative.loginQQ() 返回",
  "openid": "由 QWNative.loginQQ() 返回",
  "app_id": "与打包时填写的移动应用 AppID 一致"
}

网页授权入口:/auth/qq(浏览器打开;APP 内一般走原生流程)。

五、APP 内 H5 集成(推荐)

登录页放置 QQ 按钮;在 APP 内拦截点击并调用原生登录,成功后提交到 /auth/qq/native

<a href="/auth/qq" id="qqLoginBtn"
   data-qq-native-url="/auth/qq/native">QQ 登录</a>

<script>
document.getElementById('qqLoginBtn').addEventListener('click', function (e) {
  var native = window.QWNative;
  if (!native || !native.isInApp || !native.isInApp()) return;
  if (!native.isQQNativeLoginEnabled || !native.isQQNativeLoginEnabled()) return;
  if (!native.loginQQ) return;

  e.preventDefault();
  native.loginQQ()
    .then(function (data) {
      return fetch(e.currentTarget.getAttribute('data-qq-native-url'), {
        method: 'POST',
        headers: {
          'Content-Type': 'application/json',
          'Accept': 'application/json',
          'X-CSRF-TOKEN': '您的CSRF令牌',
          'X-Requested-With': 'XMLHttpRequest'
        },
        credentials: 'same-origin',
        body: JSON.stringify({
          access_token: data.access_token,
          openid: data.openid,
          app_id: native.getQQAppId ? native.getQQAppId() : ''
        })
      });
    })
    .then(function (r) { return r.json(); })
    .then(function (res) {
      if (res.ok && res.redirect) {
        window.location.href = res.redirect;
        return;
      }
      throw new Error(res.message || 'QQ 登录失败');
    })
    .catch(function (err) {
      if (err && err.message !== 'cancelled') {
        alert(err.message || 'QQ 登录失败');
      }
    });
});
</script>

本站登录/注册页已内置类似逻辑。若您使用自有登录页,请复制上述代码或引用相同接口。

六、QWNative 方法

方法说明
QWNative.isInApp()是否在打包 APP 的 WebView 内
QWNative.isQQNativeLoginEnabled()当前 APK 是否已开启 QQ 原生登录
QWNative.getQQAppId()返回打包时写入的移动应用 AppID
QWNative.loginQQ()Promise,成功返回 { access_token, openid };用户取消则 reject cancelled

无需在网站单独引入 JS 文件;APP 启动后会自动注入 QWNative

七、网页 QQ 登录与回调

  1. 浏览器访问 /auth/qq 跳转 QQ 授权。
  2. 授权后 QQ 回调至 /qqlogin.html(或您填写的自定义地址)。
  3. 在 APP 内打开时,qqlogin.html 会转回站内 /auth/qq/callback 完成登录。

八、常见问题

配置完成后,可在控制台提交打包任务。勾选 QQ 登录后,参数区会实时显示当前包名与签名 MD5,便于复制到 QQ 互联。