jverify 0.6.3

  • Readme
  • Changelog
  • Example
  • Installing
  • 81

QQ Group

JVerify Flutter Plugin #

安装 #

在工程 pubspec.yaml 中加入 dependencies

  • github 集成
dependencies:
  jverify:
    git:
      url: git://github.com/jpush/jverify-flutter-plugin.git
      ref: master
  • pub 集成
dependencies:
  jverify: 0.6.3

配置 #

Android:

/android/app/build.gradle 中添加下列代码:

android: {
  ....
  defaultConfig {
    applicationId "替换成自己应用 ID"
    ...
    ndk {
	//选择要添加的对应 cpu 类型的 .so 库。
	abiFilters 'armeabi', 'armeabi-v7a', 'x86', 'x86_64', 'mips', 'mips64', 'arm64-v8a',        
    }

    manifestPlaceholders = [
        JPUSH_PKGNAME : applicationId,
        JPUSH_APPKEY : "appkey", // NOTE: JPush 上注册的包名对应的 Appkey.
        JPUSH_CHANNEL : "developer-default", //暂时填写默认值即可.
    ]
  }    
}

使用 #

import 'package:jverify/jverify.dart';

APIs #

注意 : 需要先调用 Jverify.setup 来初始化插件,才能保证其他功能正常工作。

参考

0.6.3 #

  • 修改文档

0.6.2 #

  • 同步 JVerification SDK 版本
  • 内部安全策略优化

0.6.1 #

  • 优化:Android 回调 flutter 的回调函数
  • 优化重复请求逻辑

0.6.0 #

  • 新增:SDK 初始化回调监听
  • 新增:授权页弹窗模式
  • 修复:授权页无法唤起问题
  • 同步 JVerification SDK 2.5.2 版本

0.5.2 #

  • 修复:授权登录回调通知 bug

0.5.1 #

  • 修复:iOS 授权页 loading 框位置偏移问题
  • 修复:iOS 授权页监听点击事件 bug
  • 同步 JVerification SDK 2.5.0 版本

0.5.0 #

  • 新增:一键登录的同步接口 [loginAuthSyncApi]

0.4.0 #

  • 新增:一键登录接口(loginAuth)返回数据支持添加监听获取 [addLoginAuthCallBackListener],具体使用查看 API 文档或者 demo 样例;

0.3.0 #

  • 新增:关闭授权页面接口

0.2.0 #

  • 新增:设置授权页背景图片
  • 新增:支持隐藏导航栏、返回按钮

0.1.0 #

  • 新增:SDK 清除预取号缓存接口
  • 新增:可设置横竖屏授权页接口
  • 新增:授权页点击事件监听
  • sdk 适配到 v2.4.8

0.0.5 #

  • fix 1、修复:自定义 UI 时传入无资源的图片导致错误问题; 2、修复:自定义 UI 时不传 widgets 导致错误问题; 3、SDK 适配到 v2.3.6

0.0.4 #

  • fix 1、新增:添加自定义 Textview 控件; 2、新增:添加自定义 Button 控件; 3、新增:设置协议勾选框默认状态属性; 4、变更:自定义 UI 界面接口将使用新接口 [setCustomAuthViewAllWidgets],具体使用查看 API 文档或者 demo 样例;

0.0.3 #

  • fix 1、修复与微信插件 fluwx 命名冲突问题;

0.0.2 #

  • fix 1、适配最新版本的认证 SDK; 2、修复 bug;

0.0.1 #

official release.

example/lib/main.dart

import 'dart:async';

import 'dart:io';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:modal_progress_hud/modal_progress_hud.dart';
import 'package:jverify/jverify.dart';




void main() => runApp(
    new MaterialApp(
      title: "demo",
      theme: new ThemeData(primaryColor: Colors.white),
      home: MyApp(),
    )
);

class MyApp extends StatefulWidget {
  @override
  _MyAppState createState() => _MyAppState();
}

class _MyAppState extends State<MyApp> {


  /// 统一 key
  final String f_result_key = "result";
  /// 错误码
  final  String  f_code_key = "code";
  /// 回调的提示信息,统一返回 flutter 为 message
  final  String  f_msg_key  = "message";
  /// 运营商信息
  final  String  f_opr_key  = "operator";


  String _platformVersion = 'Unknown';
  String _result = "token=";
  var controllerPHone = new TextEditingController();
  final Jverify jverify = new Jverify();
  bool _loading = false;
  String _token;


  @override
  void initState() {
    super.initState();
    initPlatformState();
  }

  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(
          title: const Text('JVerify example'),
        ),
        body: ModalProgressHUD(child: _buildContent(), inAsyncCall: _loading),
      ),
    );
  }

  Widget _buildContent() {
    return Center(
      widthFactor: 2,
      child: new Column(
        children: <Widget>[
          Container(
            margin: EdgeInsets.all(20),
            color: Colors.brown,
            child: Text(_result),
            width: 300,
            height: 100,
          ),
          new Container(
            margin: EdgeInsets.fromLTRB(40, 5, 40, 5),
            child: new Row(
              mainAxisAlignment: MainAxisAlignment.center,
              children: <Widget>[
                new CustomButton(
                    onPressed: (){
                      isInitSuccess();
                    },
                    title: "初始化状态"
                ),
                new Text("   "),
                new CustomButton(
                  onPressed: (){
                    checkVerifyEnable();
                  },
                  title: "网络环境是否支持",
                ),
              ],
            ),
          ),
          new Container(
            child: SizedBox(
              child: new CustomButton(
                onPressed: () {
                  getToken();
                },
                title: "获取号码认证 Token",
              ),
              width: double.infinity,
            ),
            margin: EdgeInsets.fromLTRB(40, 5, 40, 5),
          ),
          new Container(
            child: TextField(
              autofocus: false,
              style: TextStyle(color: Colors.black),
              decoration: InputDecoration(
                  hintText: "手机号码", hintStyle: TextStyle(color: Colors.black)),
              controller: controllerPHone,
            ),
            margin: EdgeInsets.fromLTRB(40, 5, 40, 5),
          ),
          new Container(
            child: SizedBox(
              child: new CustomButton(
                onPressed: () {
                  preLogin();
                },
                title: "预取号",
              ),
              width: double.infinity,
            ),
            margin: EdgeInsets.fromLTRB(40, 5, 40, 5),
          ),
          new Container(
            child: SizedBox(
              child: new CustomButton(
                onPressed: () {
                  loginAuth();
                },
                title: "一键登录",
              ),
              width: double.infinity,
            ),
            margin: EdgeInsets.fromLTRB(40, 5, 40, 5),
          )
        ],
        mainAxisAlignment: MainAxisAlignment.start,
      ),
    );
  }

  /// sdk 初始化是否完成
  void isInitSuccess() {
    jverify.isInitSuccess().then((map) {
      bool result = map[f_result_key];
      setState(() {
        if (result) {
          _result = "sdk 初始换成功";
        }else {
          _result = "sdk 初始换失败";
        }
      });
    });
  }

  /// 判断当前网络环境是否可以发起认证
  void checkVerifyEnable() {
    jverify.checkVerifyEnable().then((map) {
      bool result = map[f_result_key];
      setState(() {
        if (result) {
          _result = "当前网络环境【支持认证】!";
        }else {
          _result = "当前网络环境【不支持认证】!";
        }
      });
    });
  }


  /// 获取号码认证token
  void getToken() {
    setState(() {
      _loading = true;
    });
    jverify.checkVerifyEnable().then((map) {
      bool result = map[f_result_key];
      if (result) {
        jverify.getToken().then((map) {
          int code = map[f_code_key];
          _token = map[f_msg_key];
          String operator = map[f_opr_key];
          setState(() {
            _loading = false;
            _result = "[$code] message = $_token, operator = $operator";
          });
        });
      } else {
        setState(() {
          _loading = false;
          _result = "[2016],msg = 当前网络环境不支持认证";
        });
      }
    });
  }


  /// 登录预取号
  void preLogin(){
    setState(() {
      _loading = true;
    });

    jverify.checkVerifyEnable().then((map) {
      bool result = map[f_result_key];
      if (result) {
        jverify.preLogin().then((map) {
          print("预取号接口回调:${map.toString()}");
          int code = map[f_code_key];
          String message = map[f_msg_key];
          setState(() {
            _loading = false;
            _result = "[$code] message = $message";
          });
        });
      }else {
        setState(() {
          _loading = false;
          _result = "[2016],msg = 当前网络环境不支持认证";
        });
      }
    });
  }

  /// SDK 请求授权一键登录
  void loginAuth() {
    setState(() {
      _loading = true;
    });

    jverify.checkVerifyEnable().then((map) {
      bool result = map[f_result_key];
      if (result) {

        final screenSize = MediaQuery.of(context).size;
        final screenWidth = screenSize.width;
        final screenHeight = screenSize.height;
        bool isiOS = Platform.isIOS;

        /// 自定义授权的 UI 界面,以下设置的图片必须添加到资源文件里,
        /// android项目将图片存放至drawable文件夹下,可使用图片选择器的文件名,例如:btn_login.xml,入参为"btn_login"。
        /// ios项目存放在 Assets.xcassets。
        /// 
        JVUIConfig uiConfig = JVUIConfig();
        //uiConfig.authBackgroundImage = ;

        //uiConfig.navHidden = true;
        uiConfig.navColor = Colors.red.value;
        uiConfig.navText = "登录";
        uiConfig.navTextColor = Colors.blue.value;
        uiConfig.navReturnImgPath = "return_bg";//图片必须存在

        uiConfig.logoWidth = 100;
        uiConfig.logoHeight = 100;
        //uiConfig.logoOffsetX = isiOS ? 0 : null;//(screenWidth/2 - uiConfig.logoWidth/2).toInt();
        uiConfig.logoOffsetY = 10;
        uiConfig.logoVerticalLayoutItem = JVIOSLayoutItem.ItemSuper;
        uiConfig.logoHidden = false;
        uiConfig.logoImgPath = "logo";

        uiConfig.numberFieldWidth = 200;
        uiConfig.numberFieldHeight = 40 ;
        //uiConfig.numFieldOffsetX = isiOS ? 0 : null;//(screenWidth/2 - uiConfig.numberFieldWidth/2).toInt();
        uiConfig.numFieldOffsetY = isiOS ? 20 : 120;
        uiConfig.numberVerticalLayoutItem = JVIOSLayoutItem.ItemLogo;
        uiConfig.numberColor = Colors.blue.value;
        uiConfig.numberSize = 18;

        uiConfig.sloganOffsetY = isiOS ? 20 : 160;
        uiConfig.sloganVerticalLayoutItem = JVIOSLayoutItem.ItemNumber;
        uiConfig.sloganTextColor = Colors.black.value;
        uiConfig.sloganTextSize = 15;
        //uiConfig.sloganHidden = 0;

        uiConfig.logBtnWidth = 220;
        uiConfig.logBtnHeight = 50;
        //uiConfig.logBtnOffsetX = isiOS ? 0 : null;//(screenWidth/2 - uiConfig.logBtnWidth/2).toInt();
        uiConfig.logBtnOffsetY = isiOS ? 20 : 230;
        uiConfig.logBtnVerticalLayoutItem = JVIOSLayoutItem.ItemSlogan;
        uiConfig.logBtnText = "登录按钮";
        uiConfig.logBtnTextColor = Colors.brown.value;
        uiConfig.logBtnTextSize = 16;
        uiConfig.loginBtnNormalImage = "login_btn_normal";//图片必须存在
        uiConfig.loginBtnPressedImage = "login_btn_press";//图片必须存在
        uiConfig.loginBtnUnableImage = "login_btn_unable";//图片必须存在


        uiConfig.privacyState = true;//设置默认勾选
        uiConfig.privacyCheckboxSize = 20;
        uiConfig.checkedImgPath = "check_image";//图片必须存在
        uiConfig.uncheckedImgPath = "uncheck_image";//图片必须存在
        uiConfig.privacyCheckboxInCenter = true;
        //uiConfig.privacyCheckboxHidden = false;

        //uiConfig.privacyOffsetX = isiOS ? (20 + uiConfig.privacyCheckboxSize) : null;
        uiConfig.privacyOffsetY = 15;// 距离底部距离
        uiConfig.privacyVerticalLayoutItem = JVIOSLayoutItem.ItemSuper;
        uiConfig.clauseName = "协议1";
        uiConfig.clauseUrl = "http://www.baidu.com";
        uiConfig.clauseBaseColor = Colors.black.value;
        uiConfig.clauseNameTwo = "协议二";
        uiConfig.clauseUrlTwo = "http://www.hao123.com";
        uiConfig.clauseColor = Colors.red.value;
        uiConfig.privacyText = ["1极","2光","3认","4证"];
        uiConfig.privacyTextSize = 13;
        //uiConfig.privacyWithBookTitleMark = true;
        //uiConfig.privacyTextCenterGravity = false;


        uiConfig.privacyNavColor =  Colors.red.value;;
        uiConfig.privacyNavTitleTextColor = Colors.blue.value;
        uiConfig.privacyNavTitleTextSize = 16;
        uiConfig.privacyNavTitleTitle1 = "协议1 web页标题";
        uiConfig.privacyNavTitleTitle2 = "协议2 web页标题";
        uiConfig.privacyNavReturnBtnImage = "return_bg";//图片必须存在;

        /// 添加自定义的 控件 到授权界面
        List<JVCustomWidget>widgetList = [];

        /*
        final String text_widgetId = "jv_add_custom_text";// 标识控件 id
        JVCustomWidget textWidget = JVCustomWidget(text_widgetId, JVCustomWidgetType.textView);
        textWidget.title = "新加 text view 控件";
        textWidget.left = 20;
        textWidget.top = 360 ;
        textWidget.width = 200;
        textWidget.height  = 40;
        textWidget.backgroundColor = Colors.yellow.value;
        textWidget.isShowUnderline = true;
        textWidget.textAlignment = JVTextAlignmentType.center;
        textWidget.isClickEnable = true;

        // 添加点击事件监听
        jverify.addClikWidgetEventListener(text_widgetId, (eventId) {
          print("receive listener - click widget event :$eventId");
          if (text_widgetId == eventId) {
            print("receive listener - 点击【新加 text】");
          }
        });
        widgetList.add(textWidget);

        final String btn_widgetId = "jv_add_custom_button";// 标识控件 id
        JVCustomWidget buttonWidget = JVCustomWidget(btn_widgetId, JVCustomWidgetType.button);
        buttonWidget.title = "新加 button 控件";
        buttonWidget.left = 100;
        buttonWidget.top = 400;
        buttonWidget.width = 150;
        buttonWidget.height  = 40;
        buttonWidget.isShowUnderline = true;
        buttonWidget.backgroundColor = Colors.brown.value;
        //buttonWidget.btnNormalImageName = "";
        //buttonWidget.btnPressedImageName = "";
        //buttonWidget.textAlignment = JVTextAlignmentType.left;

        // 添加点击事件监听
        jverify.addClikWidgetEventListener(btn_widgetId, (eventId) {
          print("receive listener - click widget event :$eventId");
          if (btn_widgetId == eventId) {
            print("receive listener - 点击【新加 button】");
          }
        });
        widgetList.add(buttonWidget);
        */


        /* 弹框模式
        JVPopViewConfig popViewConfig = JVPopViewConfig();
        popViewConfig.width = (screenWidth - 100.0).toInt();
        popViewConfig.height = (screenHeight - 150.0).toInt();

        uiConfig.popViewConfig = popViewConfig;
        */


        /// 步骤 1:调用接口设置 UI
        jverify.setCustomAuthorizationView(true, uiConfig, landscapeConfig: uiConfig);

        /// 步骤 2:调用一键登录接口

        /// 方式一:使用同步接口 (如果想使用异步接口,则忽略此步骤,看方式二)
        /// 先,添加 loginAuthSyncApi 接口回调的监听
        jverify.addLoginAuthCallBackListener((event){
          setState(() {
            _loading = false;
            _result = "监听获取返回数据:[${event.code}] message = ${event.message}";
          });
          print("通过添加监听,获取到 loginAuthSyncApi 接口返回数据,code=${event.code},message = ${event.message},operator = ${event.operator}");
        });
        /// 再,执行同步的一键登录接口
        jverify.loginAuthSyncApi(autoDismiss: true);

        /*

        /// 方式二:使用异步接口 (如果想使用异步接口,则忽略此步骤,看方式二)

        /// 先,执行异步的一键登录接口
        jverify.loginAuth(true).then((map) {

          /// 再,在回调里获取 loginAuth 接口异步返回数据(如果是通过添加 JVLoginAuthCallBackListener 监听来获取返回数据,则忽略此步骤)
          int code = map[f_code_key];
          String content = map[f_msg_key];
          String operator = map[f_opr_key];
          setState(() {
            _loading = false;
            _result = "接口异步返回数据:[$code] message = $content";
          });
          print("通过接口异步返回,获取到 loginAuth 接口返回数据,code=$code,message = $content,operator = $operator");
        });

        */

      } else {
        setState(() {
          _loading = false;
          _result = "[2016],msg = 当前网络环境不支持认证";
        });
      }
    });
  }

  // Platform messages are asynchronous, so we initialize in an async method.
  Future<void> initPlatformState() async {
    String platformVersion;

    // 初始化 SDK 之前添加监听
    jverify.addSDKSetupCallBackListener((JVSDKSetupEvent event){
      print("receive sdk setup call back event :${event.toMap()}");
    });

    jverify.setDebugMode(true); // 打开调试模式
    jverify.setup(
        appKey: "a0e6ace8d5b3e0247e3f58db",//"你自己应用的 AppKey",
        channel: "devloper-default"); // 初始化sdk,  appKey 和 channel 只对ios设置有效
    // If the widget was removed from the tree while the asynchronous platform
    // message was in flight, we want to discard the reply rather than calling
    // setState to update our non-existent appearance.
    if (!mounted) return;

    setState(() {
      _platformVersion = platformVersion;
    });

    /// 授权页面点击时间监听
    jverify.addAuthPageEventListener((JVAuthPageEvent event) {
      print("receive auth page event :${event.toMap()}");
    });
  }
}

/// 封装 按钮
class CustomButton extends StatelessWidget {

  final VoidCallback onPressed;
  final String title;

  const CustomButton({@required this.onPressed, this.title});

  @override
  Widget build(BuildContext context) {
    // TODO: implement build
    return new FlatButton(
      onPressed: onPressed,
      child: new Text("$title"),
      color: Color(0xff585858),
      highlightColor: Color(0xff888888),
      splashColor: Color(0xff888888),
      textColor: Colors.white,
      padding: EdgeInsets.fromLTRB(10, 5, 10, 5),
    );
  }
}

Use this package as a library

1. Depend on it

Add this to your package's pubspec.yaml file:


dependencies:
  jverify: ^0.6.3

2. Install it

You can install packages from the command line:

with Flutter:


$ flutter pub get

Alternatively, your editor might support flutter pub get. Check the docs for your editor to learn more.

3. Import it

Now in your Dart code, you can use:


import 'package:jverify/jverify.dart';
  
Popularity:
Describes how popular the package is relative to other packages. [more]
64
Health:
Code health derived from static analysis. [more]
97
Maintenance:
Reflects how tidy and up-to-date the package is. [more]
98
Overall:
Weighted score of the above. [more]
81
Learn more about scoring.

We analyzed this package on Mar 27, 2020, and provided a score, details, and suggestions below. Analysis was completed with status completed using:

  • Dart: 2.7.1
  • pana: 0.13.6
  • Flutter: 1.12.13+hotfix.8

Health suggestions

Fix lib/jverify.dart. (-3.45 points)

Analysis of lib/jverify.dart reported 7 hints, including:

line 48 col 16: Name non-constant identifiers using lowerCamelCase.

line 51 col 16: Name non-constant identifiers using lowerCamelCase.

line 54 col 16: Name non-constant identifiers using lowerCamelCase.

line 57 col 13: Name non-constant identifiers using lowerCamelCase.

line 62 col 18: The value of the field '_platform' isn't used.

Maintenance suggestions

The package description is too short. (-2 points)

Add more detail to the description field of pubspec.yaml. Use 60 to 180 characters to describe the package, what it does, and its target use case.

Dependencies

Package Constraint Resolved Available
Direct dependencies
Dart SDK >=2.1.0 <3.0.0
flutter 0.0.0
platform ^2.0.0 2.2.1
Transitive dependencies
collection 1.14.11 1.14.12
meta 1.1.8
sky_engine 0.0.99
typed_data 1.1.6
vector_math 2.0.8
Dev dependencies
flutter_test