add protobuf socket
This commit is contained in:
parent
427a6255f5
commit
6d66dc938d
12 changed files with 888 additions and 0 deletions
5
assets/bin/generate_proto.bat
Normal file
5
assets/bin/generate_proto.bat
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
::Protocol Buffer version 3.11.4
|
||||
set CURRENT_PATH=%cd%
|
||||
set UNITY_PACKET_PATH=%CURRENT_PATH%\..\csharp
|
||||
protoc -I=%CURRENT_PATH%\..\protobuf --dart_out=%CURRENT_PATH%\..\..\lib\socket\packets %CURRENT_PATH%\..\protobuf\*.proto --plugin=protoc_plugin.exe
|
||||
protoc -I=%CURRENT_PATH%\..\protobuf --csharp_out=%UNITY_PACKET_PATH% %CURRENT_PATH%\..\protobuf\*.proto
|
||||
BIN
assets/bin/protoc.exe
Normal file
BIN
assets/bin/protoc.exe
Normal file
Binary file not shown.
BIN
assets/bin/protoc_plugin.exe
Normal file
BIN
assets/bin/protoc_plugin.exe
Normal file
Binary file not shown.
385
assets/csharp/MessageCommon.cs
Normal file
385
assets/csharp/MessageCommon.cs
Normal file
|
|
@ -0,0 +1,385 @@
|
|||
// <auto-generated>
|
||||
// Generated by the protocol buffer compiler. DO NOT EDIT!
|
||||
// source: message_common.proto
|
||||
// </auto-generated>
|
||||
#pragma warning disable 1591, 0612, 3021
|
||||
#region Designer generated code
|
||||
|
||||
using pb = global::Google.Protobuf;
|
||||
using pbc = global::Google.Protobuf.Collections;
|
||||
using pbr = global::Google.Protobuf.Reflection;
|
||||
using scg = global::System.Collections.Generic;
|
||||
/// <summary>Holder for reflection information generated from message_common.proto</summary>
|
||||
public static partial class MessageCommonReflection {
|
||||
|
||||
#region Descriptor
|
||||
/// <summary>File descriptor for message_common.proto</summary>
|
||||
public static pbr::FileDescriptor Descriptor {
|
||||
get { return descriptor; }
|
||||
}
|
||||
private static pbr::FileDescriptor descriptor;
|
||||
|
||||
static MessageCommonReflection() {
|
||||
byte[] descriptorData = global::System.Convert.FromBase64String(
|
||||
string.Concat(
|
||||
"ChRtZXNzYWdlX2NvbW1vbi5wcm90byI7CgpQYWNrZXRCYXNlEhAKCHR5cGVO",
|
||||
"YW1lGAEgASgJEg0KBW5vbmNlGAIgASgFEgwKBGRhdGEYAyABKAwiLgoMVGVt",
|
||||
"cGxhdGVEYXRhEg0KBWluZGV4GAEgASgFEg8KB21lc3NhZ2UYAiABKAliBnBy",
|
||||
"b3RvMw=="));
|
||||
descriptor = pbr::FileDescriptor.FromGeneratedCode(descriptorData,
|
||||
new pbr::FileDescriptor[] { },
|
||||
new pbr::GeneratedClrTypeInfo(null, null, new pbr::GeneratedClrTypeInfo[] {
|
||||
new pbr::GeneratedClrTypeInfo(typeof(global::PacketBase), global::PacketBase.Parser, new[]{ "TypeName", "Nonce", "Data" }, null, null, null, null),
|
||||
new pbr::GeneratedClrTypeInfo(typeof(global::TemplateData), global::TemplateData.Parser, new[]{ "Index", "Message" }, null, null, null, null)
|
||||
}));
|
||||
}
|
||||
#endregion
|
||||
|
||||
}
|
||||
#region Messages
|
||||
public sealed partial class PacketBase : pb::IMessage<PacketBase> {
|
||||
private static readonly pb::MessageParser<PacketBase> _parser = new pb::MessageParser<PacketBase>(() => new PacketBase());
|
||||
private pb::UnknownFieldSet _unknownFields;
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public static pb::MessageParser<PacketBase> Parser { get { return _parser; } }
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public static pbr::MessageDescriptor Descriptor {
|
||||
get { return global::MessageCommonReflection.Descriptor.MessageTypes[0]; }
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
pbr::MessageDescriptor pb::IMessage.Descriptor {
|
||||
get { return Descriptor; }
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public PacketBase() {
|
||||
OnConstruction();
|
||||
}
|
||||
|
||||
partial void OnConstruction();
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public PacketBase(PacketBase other) : this() {
|
||||
typeName_ = other.typeName_;
|
||||
nonce_ = other.nonce_;
|
||||
data_ = other.data_;
|
||||
_unknownFields = pb::UnknownFieldSet.Clone(other._unknownFields);
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public PacketBase Clone() {
|
||||
return new PacketBase(this);
|
||||
}
|
||||
|
||||
/// <summary>Field number for the "typeName" field.</summary>
|
||||
public const int TypeNameFieldNumber = 1;
|
||||
private string typeName_ = "";
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public string TypeName {
|
||||
get { return typeName_; }
|
||||
set {
|
||||
typeName_ = pb::ProtoPreconditions.CheckNotNull(value, "value");
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>Field number for the "nonce" field.</summary>
|
||||
public const int NonceFieldNumber = 2;
|
||||
private int nonce_;
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public int Nonce {
|
||||
get { return nonce_; }
|
||||
set {
|
||||
nonce_ = value;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>Field number for the "data" field.</summary>
|
||||
public const int DataFieldNumber = 3;
|
||||
private pb::ByteString data_ = pb::ByteString.Empty;
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public pb::ByteString Data {
|
||||
get { return data_; }
|
||||
set {
|
||||
data_ = pb::ProtoPreconditions.CheckNotNull(value, "value");
|
||||
}
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public override bool Equals(object other) {
|
||||
return Equals(other as PacketBase);
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public bool Equals(PacketBase other) {
|
||||
if (ReferenceEquals(other, null)) {
|
||||
return false;
|
||||
}
|
||||
if (ReferenceEquals(other, this)) {
|
||||
return true;
|
||||
}
|
||||
if (TypeName != other.TypeName) return false;
|
||||
if (Nonce != other.Nonce) return false;
|
||||
if (Data != other.Data) return false;
|
||||
return Equals(_unknownFields, other._unknownFields);
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public override int GetHashCode() {
|
||||
int hash = 1;
|
||||
if (TypeName.Length != 0) hash ^= TypeName.GetHashCode();
|
||||
if (Nonce != 0) hash ^= Nonce.GetHashCode();
|
||||
if (Data.Length != 0) hash ^= Data.GetHashCode();
|
||||
if (_unknownFields != null) {
|
||||
hash ^= _unknownFields.GetHashCode();
|
||||
}
|
||||
return hash;
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public override string ToString() {
|
||||
return pb::JsonFormatter.ToDiagnosticString(this);
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public void WriteTo(pb::CodedOutputStream output) {
|
||||
if (TypeName.Length != 0) {
|
||||
output.WriteRawTag(10);
|
||||
output.WriteString(TypeName);
|
||||
}
|
||||
if (Nonce != 0) {
|
||||
output.WriteRawTag(16);
|
||||
output.WriteInt32(Nonce);
|
||||
}
|
||||
if (Data.Length != 0) {
|
||||
output.WriteRawTag(26);
|
||||
output.WriteBytes(Data);
|
||||
}
|
||||
if (_unknownFields != null) {
|
||||
_unknownFields.WriteTo(output);
|
||||
}
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public int CalculateSize() {
|
||||
int size = 0;
|
||||
if (TypeName.Length != 0) {
|
||||
size += 1 + pb::CodedOutputStream.ComputeStringSize(TypeName);
|
||||
}
|
||||
if (Nonce != 0) {
|
||||
size += 1 + pb::CodedOutputStream.ComputeInt32Size(Nonce);
|
||||
}
|
||||
if (Data.Length != 0) {
|
||||
size += 1 + pb::CodedOutputStream.ComputeBytesSize(Data);
|
||||
}
|
||||
if (_unknownFields != null) {
|
||||
size += _unknownFields.CalculateSize();
|
||||
}
|
||||
return size;
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public void MergeFrom(PacketBase other) {
|
||||
if (other == null) {
|
||||
return;
|
||||
}
|
||||
if (other.TypeName.Length != 0) {
|
||||
TypeName = other.TypeName;
|
||||
}
|
||||
if (other.Nonce != 0) {
|
||||
Nonce = other.Nonce;
|
||||
}
|
||||
if (other.Data.Length != 0) {
|
||||
Data = other.Data;
|
||||
}
|
||||
_unknownFields = pb::UnknownFieldSet.MergeFrom(_unknownFields, other._unknownFields);
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public void MergeFrom(pb::CodedInputStream input) {
|
||||
uint tag;
|
||||
while ((tag = input.ReadTag()) != 0) {
|
||||
switch(tag) {
|
||||
default:
|
||||
_unknownFields = pb::UnknownFieldSet.MergeFieldFrom(_unknownFields, input);
|
||||
break;
|
||||
case 10: {
|
||||
TypeName = input.ReadString();
|
||||
break;
|
||||
}
|
||||
case 16: {
|
||||
Nonce = input.ReadInt32();
|
||||
break;
|
||||
}
|
||||
case 26: {
|
||||
Data = input.ReadBytes();
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public sealed partial class TemplateData : pb::IMessage<TemplateData> {
|
||||
private static readonly pb::MessageParser<TemplateData> _parser = new pb::MessageParser<TemplateData>(() => new TemplateData());
|
||||
private pb::UnknownFieldSet _unknownFields;
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public static pb::MessageParser<TemplateData> Parser { get { return _parser; } }
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public static pbr::MessageDescriptor Descriptor {
|
||||
get { return global::MessageCommonReflection.Descriptor.MessageTypes[1]; }
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
pbr::MessageDescriptor pb::IMessage.Descriptor {
|
||||
get { return Descriptor; }
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public TemplateData() {
|
||||
OnConstruction();
|
||||
}
|
||||
|
||||
partial void OnConstruction();
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public TemplateData(TemplateData other) : this() {
|
||||
index_ = other.index_;
|
||||
message_ = other.message_;
|
||||
_unknownFields = pb::UnknownFieldSet.Clone(other._unknownFields);
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public TemplateData Clone() {
|
||||
return new TemplateData(this);
|
||||
}
|
||||
|
||||
/// <summary>Field number for the "index" field.</summary>
|
||||
public const int IndexFieldNumber = 1;
|
||||
private int index_;
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public int Index {
|
||||
get { return index_; }
|
||||
set {
|
||||
index_ = value;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>Field number for the "message" field.</summary>
|
||||
public const int MessageFieldNumber = 2;
|
||||
private string message_ = "";
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public string Message {
|
||||
get { return message_; }
|
||||
set {
|
||||
message_ = pb::ProtoPreconditions.CheckNotNull(value, "value");
|
||||
}
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public override bool Equals(object other) {
|
||||
return Equals(other as TemplateData);
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public bool Equals(TemplateData other) {
|
||||
if (ReferenceEquals(other, null)) {
|
||||
return false;
|
||||
}
|
||||
if (ReferenceEquals(other, this)) {
|
||||
return true;
|
||||
}
|
||||
if (Index != other.Index) return false;
|
||||
if (Message != other.Message) return false;
|
||||
return Equals(_unknownFields, other._unknownFields);
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public override int GetHashCode() {
|
||||
int hash = 1;
|
||||
if (Index != 0) hash ^= Index.GetHashCode();
|
||||
if (Message.Length != 0) hash ^= Message.GetHashCode();
|
||||
if (_unknownFields != null) {
|
||||
hash ^= _unknownFields.GetHashCode();
|
||||
}
|
||||
return hash;
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public override string ToString() {
|
||||
return pb::JsonFormatter.ToDiagnosticString(this);
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public void WriteTo(pb::CodedOutputStream output) {
|
||||
if (Index != 0) {
|
||||
output.WriteRawTag(8);
|
||||
output.WriteInt32(Index);
|
||||
}
|
||||
if (Message.Length != 0) {
|
||||
output.WriteRawTag(18);
|
||||
output.WriteString(Message);
|
||||
}
|
||||
if (_unknownFields != null) {
|
||||
_unknownFields.WriteTo(output);
|
||||
}
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public int CalculateSize() {
|
||||
int size = 0;
|
||||
if (Index != 0) {
|
||||
size += 1 + pb::CodedOutputStream.ComputeInt32Size(Index);
|
||||
}
|
||||
if (Message.Length != 0) {
|
||||
size += 1 + pb::CodedOutputStream.ComputeStringSize(Message);
|
||||
}
|
||||
if (_unknownFields != null) {
|
||||
size += _unknownFields.CalculateSize();
|
||||
}
|
||||
return size;
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public void MergeFrom(TemplateData other) {
|
||||
if (other == null) {
|
||||
return;
|
||||
}
|
||||
if (other.Index != 0) {
|
||||
Index = other.Index;
|
||||
}
|
||||
if (other.Message.Length != 0) {
|
||||
Message = other.Message;
|
||||
}
|
||||
_unknownFields = pb::UnknownFieldSet.MergeFrom(_unknownFields, other._unknownFields);
|
||||
}
|
||||
|
||||
[global::System.Diagnostics.DebuggerNonUserCodeAttribute]
|
||||
public void MergeFrom(pb::CodedInputStream input) {
|
||||
uint tag;
|
||||
while ((tag = input.ReadTag()) != 0) {
|
||||
switch(tag) {
|
||||
default:
|
||||
_unknownFields = pb::UnknownFieldSet.MergeFieldFrom(_unknownFields, input);
|
||||
break;
|
||||
case 8: {
|
||||
Index = input.ReadInt32();
|
||||
break;
|
||||
}
|
||||
case 18: {
|
||||
Message = input.ReadString();
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
|
||||
#endregion Designer generated code
|
||||
12
assets/protobuf/message_common.proto
Normal file
12
assets/protobuf/message_common.proto
Normal file
|
|
@ -0,0 +1,12 @@
|
|||
syntax = "proto3";
|
||||
|
||||
message PacketBase {
|
||||
string typeName = 1;
|
||||
int32 nonce = 2;
|
||||
bytes data = 3;
|
||||
}
|
||||
|
||||
message TemplateData {
|
||||
int32 index = 1;
|
||||
string message = 2;
|
||||
}
|
||||
89
lib/communicator.dart
Normal file
89
lib/communicator.dart
Normal file
|
|
@ -0,0 +1,89 @@
|
|||
|
||||
// ignore_for_file: prefer_final_fields
|
||||
|
||||
import 'package:protobuf/protobuf.dart';
|
||||
|
||||
abstract class Communicator
|
||||
{
|
||||
Map<String, IDataHandler> _handlerDic = {};
|
||||
late Map<String, GeneratedMessage Function(List<int>)> _instanceGenerator;
|
||||
|
||||
Communicator();
|
||||
|
||||
void initialize(Map<String, GeneratedMessage Function(List<int>)> instanceGenerator)
|
||||
{
|
||||
_instanceGenerator = instanceGenerator;
|
||||
}
|
||||
|
||||
T Function(List<int>) getGenerator<T extends GeneratedMessage>(String type)
|
||||
{
|
||||
if(!_instanceGenerator.containsKey(type))
|
||||
{
|
||||
throw Exception('Must set protobuf packet creator before use it.');
|
||||
}
|
||||
return _instanceGenerator[type] as T Function(List<int>);
|
||||
}
|
||||
|
||||
Future send<T extends GeneratedMessage>(T data);
|
||||
|
||||
void onReceivedData(String typeName, List<int> data)
|
||||
{
|
||||
if( _handlerDic.containsKey(typeName) ) {
|
||||
_handlerDic[typeName]?.onMessage(data);
|
||||
}
|
||||
}
|
||||
|
||||
void addListener<T extends GeneratedMessage>(void Function(T) listener)
|
||||
{
|
||||
var type = T.toString();
|
||||
if(!_handlerDic.containsKey(type))
|
||||
{
|
||||
_handlerDic[type] = DataHandler<T>(getGenerator(type));
|
||||
}
|
||||
var handler = _handlerDic[type] as DataHandler<T>;
|
||||
handler.addListener(listener);
|
||||
}
|
||||
|
||||
void removeListener<T extends GeneratedMessage>(void Function(T) listener)
|
||||
{
|
||||
var type = T.toString();
|
||||
if(_handlerDic.containsKey(type))
|
||||
{
|
||||
var handler = _handlerDic[type] as DataHandler<T>;
|
||||
handler.removeListener(listener);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
abstract class IDataHandler
|
||||
{
|
||||
void onMessage(List<int> data);
|
||||
}
|
||||
|
||||
class DataHandler<T extends GeneratedMessage> implements IDataHandler
|
||||
{
|
||||
T Function(List<int>) _generator;
|
||||
List<void Function(T)> _listeners = [];
|
||||
|
||||
DataHandler(this._generator);
|
||||
|
||||
@override
|
||||
void onMessage(List<int> data)
|
||||
{
|
||||
for(var listener in _listeners)
|
||||
{
|
||||
listener.call(_generator(data));
|
||||
}
|
||||
}
|
||||
|
||||
void addListener(void Function(T) handler)
|
||||
{
|
||||
removeListener(handler); //중복 리스너 불허
|
||||
_listeners.add(handler);
|
||||
}
|
||||
|
||||
void removeListener(void Function(T) handler)
|
||||
{
|
||||
_listeners.remove(handler);
|
||||
}
|
||||
}
|
||||
160
lib/socket/packets/message_common.pb.dart
Normal file
160
lib/socket/packets/message_common.pb.dart
Normal file
|
|
@ -0,0 +1,160 @@
|
|||
//
|
||||
// Generated code. Do not modify.
|
||||
// source: message_common.proto
|
||||
//
|
||||
// @dart = 2.12
|
||||
|
||||
// ignore_for_file: annotate_overrides, camel_case_types, comment_references
|
||||
// ignore_for_file: constant_identifier_names, library_prefixes
|
||||
// ignore_for_file: non_constant_identifier_names, prefer_final_fields
|
||||
// ignore_for_file: unnecessary_import, unnecessary_this, unused_import
|
||||
|
||||
import 'dart:core' as $core;
|
||||
|
||||
import 'package:protobuf/protobuf.dart' as $pb;
|
||||
|
||||
class PacketBase extends $pb.GeneratedMessage {
|
||||
factory PacketBase({
|
||||
$core.String? typeName,
|
||||
$core.int? nonce,
|
||||
$core.List<$core.int>? data,
|
||||
}) {
|
||||
final $result = create();
|
||||
if (typeName != null) {
|
||||
$result.typeName = typeName;
|
||||
}
|
||||
if (nonce != null) {
|
||||
$result.nonce = nonce;
|
||||
}
|
||||
if (data != null) {
|
||||
$result.data = data;
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
PacketBase._() : super();
|
||||
factory PacketBase.fromBuffer($core.List<$core.int> i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromBuffer(i, r);
|
||||
factory PacketBase.fromJson($core.String i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromJson(i, r);
|
||||
|
||||
static final $pb.BuilderInfo _i = $pb.BuilderInfo(_omitMessageNames ? '' : 'PacketBase', createEmptyInstance: create)
|
||||
..aOS(1, _omitFieldNames ? '' : 'typeName', protoName: 'typeName')
|
||||
..a<$core.int>(2, _omitFieldNames ? '' : 'nonce', $pb.PbFieldType.O3)
|
||||
..a<$core.List<$core.int>>(3, _omitFieldNames ? '' : 'data', $pb.PbFieldType.OY)
|
||||
..hasRequiredFields = false
|
||||
;
|
||||
|
||||
@$core.Deprecated(
|
||||
'Using this can add significant overhead to your binary. '
|
||||
'Use [GeneratedMessageGenericExtensions.deepCopy] instead. '
|
||||
'Will be removed in next major version')
|
||||
PacketBase clone() => PacketBase()..mergeFromMessage(this);
|
||||
@$core.Deprecated(
|
||||
'Using this can add significant overhead to your binary. '
|
||||
'Use [GeneratedMessageGenericExtensions.rebuild] instead. '
|
||||
'Will be removed in next major version')
|
||||
PacketBase copyWith(void Function(PacketBase) updates) => super.copyWith((message) => updates(message as PacketBase)) as PacketBase;
|
||||
|
||||
$pb.BuilderInfo get info_ => _i;
|
||||
|
||||
@$core.pragma('dart2js:noInline')
|
||||
static PacketBase create() => PacketBase._();
|
||||
PacketBase createEmptyInstance() => create();
|
||||
static $pb.PbList<PacketBase> createRepeated() => $pb.PbList<PacketBase>();
|
||||
@$core.pragma('dart2js:noInline')
|
||||
static PacketBase getDefault() => _defaultInstance ??= $pb.GeneratedMessage.$_defaultFor<PacketBase>(create);
|
||||
static PacketBase? _defaultInstance;
|
||||
|
||||
@$pb.TagNumber(1)
|
||||
$core.String get typeName => $_getSZ(0);
|
||||
@$pb.TagNumber(1)
|
||||
set typeName($core.String v) { $_setString(0, v); }
|
||||
@$pb.TagNumber(1)
|
||||
$core.bool hasTypeName() => $_has(0);
|
||||
@$pb.TagNumber(1)
|
||||
void clearTypeName() => clearField(1);
|
||||
|
||||
@$pb.TagNumber(2)
|
||||
$core.int get nonce => $_getIZ(1);
|
||||
@$pb.TagNumber(2)
|
||||
set nonce($core.int v) { $_setSignedInt32(1, v); }
|
||||
@$pb.TagNumber(2)
|
||||
$core.bool hasNonce() => $_has(1);
|
||||
@$pb.TagNumber(2)
|
||||
void clearNonce() => clearField(2);
|
||||
|
||||
@$pb.TagNumber(3)
|
||||
$core.List<$core.int> get data => $_getN(2);
|
||||
@$pb.TagNumber(3)
|
||||
set data($core.List<$core.int> v) { $_setBytes(2, v); }
|
||||
@$pb.TagNumber(3)
|
||||
$core.bool hasData() => $_has(2);
|
||||
@$pb.TagNumber(3)
|
||||
void clearData() => clearField(3);
|
||||
}
|
||||
|
||||
class TemplateData extends $pb.GeneratedMessage {
|
||||
factory TemplateData({
|
||||
$core.int? index,
|
||||
$core.String? message,
|
||||
}) {
|
||||
final $result = create();
|
||||
if (index != null) {
|
||||
$result.index = index;
|
||||
}
|
||||
if (message != null) {
|
||||
$result.message = message;
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
TemplateData._() : super();
|
||||
factory TemplateData.fromBuffer($core.List<$core.int> i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromBuffer(i, r);
|
||||
factory TemplateData.fromJson($core.String i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromJson(i, r);
|
||||
|
||||
static final $pb.BuilderInfo _i = $pb.BuilderInfo(_omitMessageNames ? '' : 'TemplateData', createEmptyInstance: create)
|
||||
..a<$core.int>(1, _omitFieldNames ? '' : 'index', $pb.PbFieldType.O3)
|
||||
..aOS(2, _omitFieldNames ? '' : 'message')
|
||||
..hasRequiredFields = false
|
||||
;
|
||||
|
||||
@$core.Deprecated(
|
||||
'Using this can add significant overhead to your binary. '
|
||||
'Use [GeneratedMessageGenericExtensions.deepCopy] instead. '
|
||||
'Will be removed in next major version')
|
||||
TemplateData clone() => TemplateData()..mergeFromMessage(this);
|
||||
@$core.Deprecated(
|
||||
'Using this can add significant overhead to your binary. '
|
||||
'Use [GeneratedMessageGenericExtensions.rebuild] instead. '
|
||||
'Will be removed in next major version')
|
||||
TemplateData copyWith(void Function(TemplateData) updates) => super.copyWith((message) => updates(message as TemplateData)) as TemplateData;
|
||||
|
||||
$pb.BuilderInfo get info_ => _i;
|
||||
|
||||
@$core.pragma('dart2js:noInline')
|
||||
static TemplateData create() => TemplateData._();
|
||||
TemplateData createEmptyInstance() => create();
|
||||
static $pb.PbList<TemplateData> createRepeated() => $pb.PbList<TemplateData>();
|
||||
@$core.pragma('dart2js:noInline')
|
||||
static TemplateData getDefault() => _defaultInstance ??= $pb.GeneratedMessage.$_defaultFor<TemplateData>(create);
|
||||
static TemplateData? _defaultInstance;
|
||||
|
||||
@$pb.TagNumber(1)
|
||||
$core.int get index => $_getIZ(0);
|
||||
@$pb.TagNumber(1)
|
||||
set index($core.int v) { $_setSignedInt32(0, v); }
|
||||
@$pb.TagNumber(1)
|
||||
$core.bool hasIndex() => $_has(0);
|
||||
@$pb.TagNumber(1)
|
||||
void clearIndex() => clearField(1);
|
||||
|
||||
@$pb.TagNumber(2)
|
||||
$core.String get message => $_getSZ(1);
|
||||
@$pb.TagNumber(2)
|
||||
set message($core.String v) { $_setString(1, v); }
|
||||
@$pb.TagNumber(2)
|
||||
$core.bool hasMessage() => $_has(1);
|
||||
@$pb.TagNumber(2)
|
||||
void clearMessage() => clearField(2);
|
||||
}
|
||||
|
||||
|
||||
const _omitFieldNames = $core.bool.fromEnvironment('protobuf.omit_field_names');
|
||||
const _omitMessageNames = $core.bool.fromEnvironment('protobuf.omit_message_names');
|
||||
11
lib/socket/packets/message_common.pbenum.dart
Normal file
11
lib/socket/packets/message_common.pbenum.dart
Normal file
|
|
@ -0,0 +1,11 @@
|
|||
//
|
||||
// Generated code. Do not modify.
|
||||
// source: message_common.proto
|
||||
//
|
||||
// @dart = 2.12
|
||||
|
||||
// ignore_for_file: annotate_overrides, camel_case_types, comment_references
|
||||
// ignore_for_file: constant_identifier_names, library_prefixes
|
||||
// ignore_for_file: non_constant_identifier_names, prefer_final_fields
|
||||
// ignore_for_file: unnecessary_import, unnecessary_this, unused_import
|
||||
|
||||
44
lib/socket/packets/message_common.pbjson.dart
Normal file
44
lib/socket/packets/message_common.pbjson.dart
Normal file
|
|
@ -0,0 +1,44 @@
|
|||
//
|
||||
// Generated code. Do not modify.
|
||||
// source: message_common.proto
|
||||
//
|
||||
// @dart = 2.12
|
||||
|
||||
// ignore_for_file: annotate_overrides, camel_case_types, comment_references
|
||||
// ignore_for_file: constant_identifier_names, library_prefixes
|
||||
// ignore_for_file: non_constant_identifier_names, prefer_final_fields
|
||||
// ignore_for_file: unnecessary_import, unnecessary_this, unused_import
|
||||
|
||||
import 'dart:convert' as $convert;
|
||||
import 'dart:core' as $core;
|
||||
import 'dart:typed_data' as $typed_data;
|
||||
|
||||
@$core.Deprecated('Use packetBaseDescriptor instead')
|
||||
const PacketBase$json = {
|
||||
'1': 'PacketBase',
|
||||
'2': [
|
||||
{'1': 'typeName', '3': 1, '4': 1, '5': 9, '10': 'typeName'},
|
||||
{'1': 'nonce', '3': 2, '4': 1, '5': 5, '10': 'nonce'},
|
||||
{'1': 'data', '3': 3, '4': 1, '5': 12, '10': 'data'},
|
||||
],
|
||||
};
|
||||
|
||||
/// Descriptor for `PacketBase`. Decode as a `google.protobuf.DescriptorProto`.
|
||||
final $typed_data.Uint8List packetBaseDescriptor = $convert.base64Decode(
|
||||
'CgpQYWNrZXRCYXNlEhoKCHR5cGVOYW1lGAEgASgJUgh0eXBlTmFtZRIUCgVub25jZRgCIAEoBV'
|
||||
'IFbm9uY2USEgoEZGF0YRgDIAEoDFIEZGF0YQ==');
|
||||
|
||||
@$core.Deprecated('Use templateDataDescriptor instead')
|
||||
const TemplateData$json = {
|
||||
'1': 'TemplateData',
|
||||
'2': [
|
||||
{'1': 'index', '3': 1, '4': 1, '5': 5, '10': 'index'},
|
||||
{'1': 'message', '3': 2, '4': 1, '5': 9, '10': 'message'},
|
||||
],
|
||||
};
|
||||
|
||||
/// Descriptor for `TemplateData`. Decode as a `google.protobuf.DescriptorProto`.
|
||||
final $typed_data.Uint8List templateDataDescriptor = $convert.base64Decode(
|
||||
'CgxUZW1wbGF0ZURhdGESFAoFaW5kZXgYASABKAVSBWluZGV4EhgKB21lc3NhZ2UYAiABKAlSB2'
|
||||
'1lc3NhZ2U=');
|
||||
|
||||
14
lib/socket/packets/message_common.pbserver.dart
Normal file
14
lib/socket/packets/message_common.pbserver.dart
Normal file
|
|
@ -0,0 +1,14 @@
|
|||
//
|
||||
// Generated code. Do not modify.
|
||||
// source: message_common.proto
|
||||
//
|
||||
// @dart = 2.12
|
||||
|
||||
// ignore_for_file: annotate_overrides, camel_case_types, comment_references
|
||||
// ignore_for_file: constant_identifier_names
|
||||
// ignore_for_file: deprecated_member_use_from_same_package, library_prefixes
|
||||
// ignore_for_file: non_constant_identifier_names, prefer_final_fields
|
||||
// ignore_for_file: unnecessary_import, unnecessary_this, unused_import
|
||||
|
||||
export 'message_common.pb.dart';
|
||||
|
||||
126
lib/socket/protobuf_client.dart
Normal file
126
lib/socket/protobuf_client.dart
Normal file
|
|
@ -0,0 +1,126 @@
|
|||
|
||||
// ignore_for_file: avoid_init_to_null, prefer_final_fields, avoid_print
|
||||
|
||||
import 'dart:io';
|
||||
import 'dart:typed_data';
|
||||
|
||||
import 'package:dart_framework/utils/system_util.dart';
|
||||
import 'package:protobuf/protobuf.dart';
|
||||
import 'package:dart_framework/communicator.dart';
|
||||
import 'package:dart_framework/socket/packets/message_common.pb.dart';
|
||||
|
||||
class ProtobufClient extends Communicator
|
||||
{
|
||||
final int _headerSize = 4;
|
||||
final Socket _socket;
|
||||
int? _length = null;
|
||||
late List<int> _arrivedData = [];
|
||||
List<void Function(ProtobufClient)> _onDisconnectListenerList = [];
|
||||
|
||||
|
||||
ProtobufClient(this._socket)
|
||||
{
|
||||
print('Connected New Client');
|
||||
super.initialize({
|
||||
(TemplateData).toString() : TemplateData.fromBuffer
|
||||
});
|
||||
_socket.listen(onData, onError: onError)
|
||||
.asFuture().then(onDisconnected);
|
||||
}
|
||||
|
||||
void addDisconnectListener(void Function(ProtobufClient) handler)
|
||||
{
|
||||
if(!_onDisconnectListenerList.contains(handler))
|
||||
{
|
||||
_onDisconnectListenerList.add(handler);
|
||||
}
|
||||
}
|
||||
|
||||
void removeDisconnectListener(void Function(ProtobufClient) handler)
|
||||
{
|
||||
if(_onDisconnectListenerList.contains(handler))
|
||||
{
|
||||
_onDisconnectListenerList.remove(handler);
|
||||
}
|
||||
}
|
||||
|
||||
void onDisconnected(dynamic data)
|
||||
{
|
||||
//client disconnected
|
||||
for (var item in _onDisconnectListenerList) {
|
||||
item.call(this);
|
||||
}
|
||||
}
|
||||
|
||||
void onError(dynamic e)
|
||||
{
|
||||
print('=========> onError: $e');
|
||||
}
|
||||
|
||||
void onData(Uint8List data) async
|
||||
{
|
||||
try
|
||||
{
|
||||
// printPacket('## Received', data);
|
||||
if(_length == null)
|
||||
{
|
||||
var header = data.sublist(0, _headerSize);
|
||||
_length = header.buffer.asByteData().getInt32(0);
|
||||
_arrivedData.addAll(data.sublist(_headerSize));
|
||||
}
|
||||
else
|
||||
{
|
||||
_arrivedData.addAll(data);
|
||||
}
|
||||
|
||||
if(_arrivedData.length == _length)
|
||||
{
|
||||
var common = PacketBase.fromBuffer(_arrivedData);
|
||||
var nonce = common.nonce;
|
||||
onReceivedData(common.typeName, common.data);
|
||||
_length = null;
|
||||
_arrivedData.clear();
|
||||
}
|
||||
} on Exception catch(e) {
|
||||
print(e);
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
Future send<T extends GeneratedMessage>(T data) async {
|
||||
List<int> packet = [];
|
||||
var base = PacketBase();
|
||||
base.typeName = data.info_.qualifiedMessageName;
|
||||
base.nonce = 0;
|
||||
base.data = data.writeToBuffer();
|
||||
var baseBytes = base.writeToBuffer();
|
||||
int length = baseBytes.length + _headerSize;
|
||||
var header = Uint8List(_headerSize)
|
||||
..buffer.asByteData().setInt32(0, length);
|
||||
packet.addAll(header);
|
||||
packet.addAll(baseBytes);
|
||||
|
||||
// printPacket('Send', packet);
|
||||
|
||||
_socket.add(packet);
|
||||
await _socket.flush();
|
||||
return simpleFuture;
|
||||
}
|
||||
|
||||
void printPacket(String prefix, List<int> packet)
|
||||
{
|
||||
var s = StringBuffer();
|
||||
for(var item in packet)
|
||||
{
|
||||
s.write('$item, ');
|
||||
}
|
||||
print('$prefix: ${s.toString()}');
|
||||
}
|
||||
|
||||
void dispose()
|
||||
{
|
||||
_onDisconnectListenerList.clear();
|
||||
_arrivedData.clear();
|
||||
_socket.close();
|
||||
}
|
||||
}
|
||||
42
lib/socket/protobuf_server.dart
Normal file
42
lib/socket/protobuf_server.dart
Normal file
|
|
@ -0,0 +1,42 @@
|
|||
// ignore_for_file: avoid_print, prefer_final_fields
|
||||
|
||||
import 'dart:io';
|
||||
import 'package:dart_framework/socket/packets/message_common.pb.dart';
|
||||
import 'package:dart_framework/socket/protobuf_client.dart';
|
||||
|
||||
class ProtobufServer
|
||||
{
|
||||
late ServerSocket _server;
|
||||
List<ProtobufClient> _clientList = [];
|
||||
String _host;
|
||||
int _port;
|
||||
|
||||
ProtobufServer(this._host, this._port);
|
||||
|
||||
Future start() async
|
||||
{
|
||||
_server = await ServerSocket.bind(_host, _port);
|
||||
_server.listen((Socket socket) {
|
||||
var client = ProtobufClient(socket);
|
||||
client.addDisconnectListener(onDisconnectedClient);
|
||||
client.addListener(onTestSocket);
|
||||
_clientList.add(client);
|
||||
});
|
||||
}
|
||||
|
||||
void onDisconnectedClient(ProtobufClient client)
|
||||
{
|
||||
_clientList.remove(client);
|
||||
client.dispose();
|
||||
print('Client disconnected');
|
||||
}
|
||||
|
||||
void onTestSocket(TemplateData data)
|
||||
{
|
||||
print(data.message);
|
||||
var test = TemplateData();
|
||||
test.index = 3125;
|
||||
test.message = 'This message from flutter';
|
||||
_clientList[0].send(test);
|
||||
}
|
||||
}
|
||||
Loading…
Reference in a new issue