This commit is contained in:
v7lin
2021-07-31 16:18:26 +08:00
parent e903ecf4dd
commit 1fd77f8d59
8 changed files with 129 additions and 127 deletions

88
lib/src/model/resp.dart Normal file
View File

@ -0,0 +1,88 @@
import 'dart:convert';
import 'package:json_annotation/json_annotation.dart';
part 'resp.g.dart';
abstract class BaseResp {
const BaseResp({
required this.ret,
this.msg,
});
/// 网络请求成功发送至服务器,并且服务器返回数据格式正确
/// 这里包括所请求业务操作失败的情况,例如没有授权等原因导致
static const int RET_SUCCESS = 0;
/// 网络异常,或服务器返回的数据格式不正确导致无法解析
static const int RET_FAILED = 1;
static const int RET_COMMON = -1;
static const int RET_USERCANCEL = -2;
@JsonKey(
defaultValue: RET_SUCCESS,
)
final int ret;
final String? msg;
bool get isSuccessful => ret == RET_SUCCESS;
bool get isCancelled => ret == RET_USERCANCEL;
Map<String, dynamic> toJson();
@override
String toString() => const JsonEncoder.withIndent(' ').convert(toJson());
}
@JsonSerializable(
explicitToJson: true,
fieldRename: FieldRename.snake,
)
class LoginResp extends BaseResp {
const LoginResp({
required int ret,
String? msg,
this.openid,
this.accessToken,
this.expiresIn,
this.createAt,
}) : super(ret: ret, msg: msg);
factory LoginResp.fromJson(Map<String, dynamic> json) =>
_$LoginRespFromJson(json);
final String? openid;
final String? accessToken;
final int? expiresIn;
final int? createAt;
bool? get isExpired => isSuccessful
? DateTime.now().millisecondsSinceEpoch - createAt! >= expiresIn! * 1000
: null;
@override
Map<String, dynamic> toJson() => _$LoginRespToJson(this);
}
@JsonSerializable(
explicitToJson: true,
fieldRename: FieldRename.snake,
)
class ShareMsgResp extends BaseResp {
const ShareMsgResp({
required int ret,
String? msg,
}) : super(
ret: ret,
msg: msg,
);
factory ShareMsgResp.fromJson(Map<String, dynamic> json) =>
_$ShareMsgRespFromJson(json);
@override
Map<String, dynamic> toJson() => _$ShareMsgRespToJson(this);
}

View File

@ -1,13 +1,13 @@
// GENERATED CODE - DO NOT MODIFY BY HAND
part of 'tencent_login_resp.dart';
part of 'resp.dart';
// **************************************************************************
// JsonSerializableGenerator
// **************************************************************************
TencentLoginResp _$TencentLoginRespFromJson(Map<String, dynamic> json) {
return TencentLoginResp(
LoginResp _$LoginRespFromJson(Map<String, dynamic> json) {
return LoginResp(
ret: json['ret'] as int? ?? 0,
msg: json['msg'] as String?,
openid: json['openid'] as String?,
@ -17,8 +17,7 @@ TencentLoginResp _$TencentLoginRespFromJson(Map<String, dynamic> json) {
);
}
Map<String, dynamic> _$TencentLoginRespToJson(TencentLoginResp instance) =>
<String, dynamic>{
Map<String, dynamic> _$LoginRespToJson(LoginResp instance) => <String, dynamic>{
'ret': instance.ret,
'msg': instance.msg,
'openid': instance.openid,
@ -26,3 +25,16 @@ Map<String, dynamic> _$TencentLoginRespToJson(TencentLoginResp instance) =>
'expires_in': instance.expiresIn,
'create_at': instance.createAt,
};
ShareMsgResp _$ShareMsgRespFromJson(Map<String, dynamic> json) {
return ShareMsgResp(
ret: json['ret'] as int? ?? 0,
msg: json['msg'] as String?,
);
}
Map<String, dynamic> _$ShareMsgRespToJson(ShareMsgResp instance) =>
<String, dynamic>{
'ret': instance.ret,
'msg': instance.msg,
};

View File

@ -1,34 +0,0 @@
import 'package:json_annotation/json_annotation.dart';
import 'package:tencent_kit/src/model/tencent_sdk_resp.dart';
part 'tencent_login_resp.g.dart';
@JsonSerializable(
explicitToJson: true,
fieldRename: FieldRename.snake,
)
class TencentLoginResp extends TencentSdkResp {
const TencentLoginResp({
required int ret,
String? msg,
this.openid,
this.accessToken,
this.expiresIn,
this.createAt,
}) : super(ret: ret, msg: msg);
factory TencentLoginResp.fromJson(Map<String, dynamic> json) =>
_$TencentLoginRespFromJson(json);
final String? openid;
final String? accessToken;
final int? expiresIn;
final int? createAt;
bool? get isExpired => isSuccessful
? DateTime.now().millisecondsSinceEpoch - createAt! >= expiresIn! * 1000
: null;
@override
Map<String, dynamic> toJson() => _$TencentLoginRespToJson(this);
}

View File

@ -1,40 +0,0 @@
import 'package:json_annotation/json_annotation.dart';
part 'tencent_sdk_resp.g.dart';
@JsonSerializable(
explicitToJson: true,
fieldRename: FieldRename.snake,
)
class TencentSdkResp {
const TencentSdkResp({
required this.ret,
this.msg,
});
factory TencentSdkResp.fromJson(Map<String, dynamic> json) =>
_$TencentSdkRespFromJson(json);
/// 网络请求成功发送至服务器,并且服务器返回数据格式正确
/// 这里包括所请求业务操作失败的情况,例如没有授权等原因导致
static const int RET_SUCCESS = 0;
/// 网络异常,或服务器返回的数据格式不正确导致无法解析
static const int RET_FAILED = 1;
static const int RET_COMMON = -1;
static const int RET_USERCANCEL = -2;
@JsonKey(
defaultValue: RET_SUCCESS,
)
final int ret;
final String? msg;
bool get isSuccessful => ret == RET_SUCCESS;
bool get isCancelled => ret == RET_USERCANCEL;
Map<String, dynamic> toJson() => _$TencentSdkRespToJson(this);
}

View File

@ -1,20 +0,0 @@
// GENERATED CODE - DO NOT MODIFY BY HAND
part of 'tencent_sdk_resp.dart';
// **************************************************************************
// JsonSerializableGenerator
// **************************************************************************
TencentSdkResp _$TencentSdkRespFromJson(Map<String, dynamic> json) {
return TencentSdkResp(
ret: json['ret'] as int? ?? 0,
msg: json['msg'] as String?,
);
}
Map<String, dynamic> _$TencentSdkRespToJson(TencentSdkResp instance) =>
<String, dynamic>{
'ret': instance.ret,
'msg': instance.msg,
};

View File

@ -1,8 +1,7 @@
import 'dart:async';
import 'package:flutter/services.dart';
import 'package:tencent_kit/src/model/tencent_login_resp.dart';
import 'package:tencent_kit/src/model/tencent_sdk_resp.dart';
import 'package:tencent_kit/src/model/resp.dart';
import 'package:tencent_kit/src/tencent_constant.dart';
///
@ -48,20 +47,17 @@ class Tencent {
const MethodChannel('v7lin.github.io/tencent_kit')
..setMethodCallHandler(_handleMethod);
final StreamController<TencentLoginResp> _loginRespStreamController =
StreamController<TencentLoginResp>.broadcast();
final StreamController<TencentSdkResp> _shareRespStreamController =
StreamController<TencentSdkResp>.broadcast();
final StreamController<BaseResp> _respStreamController =
StreamController<BaseResp>.broadcast();
Future<dynamic> _handleMethod(MethodCall call) async {
switch (call.method) {
case _METHOD_ONLOGINRESP:
_loginRespStreamController.add(TencentLoginResp.fromJson(
_respStreamController.add(LoginResp.fromJson(
(call.arguments as Map<dynamic, dynamic>).cast<String, dynamic>()));
break;
case _METHOD_ONSHARERESP:
_shareRespStreamController.add(TencentSdkResp.fromJson(
_respStreamController.add(ShareMsgResp.fromJson(
(call.arguments as Map<dynamic, dynamic>).cast<String, dynamic>()));
break;
}
@ -82,14 +78,9 @@ class Tencent {
);
}
/// 登录
Stream<TencentLoginResp> loginResp() {
return _loginRespStreamController.stream;
}
/// 分享
Stream<TencentSdkResp> shareResp() {
return _shareRespStreamController.stream;
///
Stream<BaseResp> respStream() {
return _respStreamController.stream;
}
/// 检查QQ是否已安装

View File

@ -1,6 +1,5 @@
library tencent_kit;
export 'src/model/tencent_login_resp.dart';
export 'src/model/tencent_sdk_resp.dart';
export 'src/model/resp.dart';
export 'src/tencent.dart';
export 'src/tencent_constant.dart';

View File

@ -64,25 +64,31 @@ void main() {
});
test('login', () async {
final StreamSubscription<TencentLoginResp> sub =
Tencent.instance.loginResp().listen((TencentLoginResp resp) {
expect(resp.ret, TencentSdkResp.RET_USERCANCEL);
final StreamSubscription<BaseResp> subs =
Tencent.instance.respStream().listen((BaseResp resp) {
expect(resp.runtimeType, LoginResp);
expect(resp.ret, BaseResp.RET_USERCANCEL);
});
await Tencent.instance.login(
scope: <String>[TencentScope.GET_SIMPLE_USERINFO],
scope: <String>[
TencentScope.GET_SIMPLE_USERINFO,
],
);
await sub.cancel();
await Future<void>.delayed(const Duration(seconds: 1));
await subs.cancel();
});
test('share', () async {
final StreamSubscription<TencentSdkResp> sub =
Tencent.instance.shareResp().listen((TencentSdkResp resp) {
expect(resp.ret, TencentSdkResp.RET_SUCCESS);
final StreamSubscription<BaseResp> subs =
Tencent.instance.respStream().listen((BaseResp resp) {
expect(resp.runtimeType, ShareMsgResp);
expect(resp.ret, BaseResp.RET_SUCCESS);
});
await Tencent.instance.shareMood(
scene: TencentScene.SCENE_QZONE,
summary: 'share text',
);
await sub.cancel();
await Future<void>.delayed(const Duration(seconds: 1));
await subs.cancel();
});
}