mirror of
https://github.com/tiennm99/zfoo.git
synced 2026-10-08 10:13:45 +00:00
perf[protocol]: 使用模板生成协议
This commit is contained in:
1 parent
5eb2530eae
commit
d4ded2dd19
15 files changed
+99
-144
No files matched your search
@@ -128,7 +128,9 @@ public abstract class GenerateProtocolFile {
|
||||
if (generateLanguages.contains(CodeLanguage.Lua)) {
|
||||
GenerateLuaUtils.init(generateOperation);
|
||||
GenerateLuaUtils.createProtocolManager(allSortedGenerateProtocols);
|
||||
allSortedGenerateProtocols.forEach(it -> GenerateLuaUtils.createLuaProtocolFile((ProtocolRegistration) it));
|
||||
for (var protocolRegistration : allSortedGenerateProtocols) {
|
||||
GenerateLuaUtils.createLuaProtocolFile((ProtocolRegistration) protocolRegistration);
|
||||
}
|
||||
}
|
||||
|
||||
// 生成GdScript协议
|
||||
|
||||
@@ -17,9 +17,9 @@ import com.zfoo.protocol.generate.GenerateOperation;
|
||||
import com.zfoo.protocol.generate.GenerateProtocolDocument;
|
||||
import com.zfoo.protocol.generate.GenerateProtocolFile;
|
||||
import com.zfoo.protocol.generate.GenerateProtocolPath;
|
||||
import com.zfoo.protocol.model.Pair;
|
||||
import com.zfoo.protocol.registration.IProtocolRegistration;
|
||||
import com.zfoo.protocol.registration.ProtocolRegistration;
|
||||
import com.zfoo.protocol.registration.field.IFieldRegistration;
|
||||
import com.zfoo.protocol.serializer.reflect.*;
|
||||
import com.zfoo.protocol.util.ClassUtils;
|
||||
import com.zfoo.protocol.util.FileUtils;
|
||||
@@ -28,8 +28,10 @@ import com.zfoo.protocol.util.StringUtils;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.lang.reflect.Field;
|
||||
import java.util.*;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import static com.zfoo.protocol.util.FileUtils.LS;
|
||||
@@ -79,7 +81,6 @@ public abstract class GenerateLuaUtils {
|
||||
|
||||
public static void createProtocolManager(List<IProtocolRegistration> protocolList) throws IOException {
|
||||
var list = List.of("lua/Buffer/ByteBuffer.lua", "lua/Buffer/Long.lua");
|
||||
|
||||
for (var fileName : list) {
|
||||
var fileInputStream = ClassUtils.getFileFromClassPath(fileName);
|
||||
var createFile = new File(StringUtils.format("{}/{}", protocolOutputRootPath, StringUtils.substringAfterFirst(fileName, "lua/")));
|
||||
@@ -87,110 +88,71 @@ public abstract class GenerateLuaUtils {
|
||||
}
|
||||
|
||||
// 生成Protocol.lua文件
|
||||
var luaBuilder = new StringBuilder();
|
||||
var protocolManagerTemplate = StringUtils.bytesToString(IOUtils.toByteArray(ClassUtils.getFileFromClassPath("lua/ProtocolManagerTemplate.lua")));
|
||||
var fieldBuilder = new StringBuilder();
|
||||
var protocolBuilder = new StringBuilder();
|
||||
for (var protocol : protocolList) {
|
||||
var protocolId = protocol.protocolId();
|
||||
var name = protocol.protocolConstructor().getDeclaringClass().getSimpleName();
|
||||
var path = GenerateProtocolPath.getCapitalizeProtocolPath(protocolId);
|
||||
if (StringUtils.isBlank(path)) {
|
||||
fieldBuilder.append(TAB).append(StringUtils.format("local {} = require(\"LuaProtocol.{}\")", name, name)).append(LS);
|
||||
} else {
|
||||
fieldBuilder.append(TAB).append(StringUtils.format("local {} = require(\"LuaProtocol.{}.{}\")"
|
||||
, name, path.replaceAll(StringUtils.SLASH, StringUtils.PERIOD), name)).append(LS);
|
||||
}
|
||||
|
||||
var protocolManagerStr = StringUtils.bytesToString(IOUtils.toByteArray(ClassUtils.getFileFromClassPath("lua/ProtocolManager.lua")));
|
||||
luaBuilder.append(protocolManagerStr);
|
||||
|
||||
luaBuilder.append("function initProtocol()").append(LS);
|
||||
protocolList.stream()
|
||||
.filter(it -> Objects.nonNull(it))
|
||||
.forEach(it -> {
|
||||
var name = it.protocolConstructor().getDeclaringClass().getSimpleName();
|
||||
var path = GenerateProtocolPath.getCapitalizeProtocolPath(it.protocolId());
|
||||
|
||||
if (StringUtils.isBlank(path)) {
|
||||
luaBuilder.append(TAB).append(StringUtils.format("local {} = require(\"LuaProtocol.{}\")", name, name)).append(LS);
|
||||
} else {
|
||||
luaBuilder.append(TAB).append(StringUtils.format("local {} = require(\"LuaProtocol.{}.{}\")"
|
||||
, name, path.replaceAll(StringUtils.SLASH, StringUtils.PERIOD), name)).append(LS);
|
||||
}
|
||||
});
|
||||
|
||||
protocolList.stream().filter(it -> Objects.nonNull(it))
|
||||
.forEach(it -> luaBuilder.append(TAB).append(StringUtils.format("protocols[{}] = {}", it.protocolId(), it.protocolConstructor().getDeclaringClass().getSimpleName())).append(LS));
|
||||
|
||||
luaBuilder.append("end").append(LS + LS);
|
||||
luaBuilder.append("ProtocolManager.initProtocol = initProtocol").append(LS);
|
||||
luaBuilder.append("return ProtocolManager").append(LS);
|
||||
|
||||
FileUtils.writeStringToFile(new File(StringUtils.format("{}/{}", protocolOutputRootPath, "ProtocolManager.lua")), luaBuilder.toString());
|
||||
protocolBuilder.append(TAB).append(StringUtils.format("protocols[{}] = {}", protocolId, name)).append(LS);
|
||||
}
|
||||
protocolManagerTemplate = StringUtils.format(protocolManagerTemplate, "{}", "{}", fieldBuilder.toString().trim(), protocolBuilder.toString().trim());
|
||||
FileUtils.writeStringToFile(new File(StringUtils.format("{}/{}", protocolOutputRootPath, "ProtocolManager.lua")), protocolManagerTemplate);
|
||||
}
|
||||
|
||||
public static void createLuaProtocolFile(ProtocolRegistration registration) {
|
||||
public static void createLuaProtocolFile(ProtocolRegistration registration) throws IOException {
|
||||
// 初始化index
|
||||
GenerateProtocolFile.index.set(0);
|
||||
|
||||
var protocolId = registration.protocolId();
|
||||
var registrationConstructor = registration.getConstructor();
|
||||
var fieldRegistrations = registration.getFieldRegistrations();
|
||||
|
||||
var protocolClazzName = registrationConstructor.getDeclaringClass().getSimpleName();
|
||||
var protocolTemplate = StringUtils.bytesToString(IOUtils.toByteArray(ClassUtils.getFileFromClassPath("lua/ProtocolTemplate.lua")));
|
||||
|
||||
var luaBuilder = new StringBuilder();
|
||||
|
||||
// document
|
||||
luaBuilder.append(documentTitle(registration));
|
||||
|
||||
// new object
|
||||
luaBuilder.append(newFunction(registration));
|
||||
|
||||
// protocolId method
|
||||
luaBuilder.append(protocolIdFunction(registration));
|
||||
|
||||
// writeObject method
|
||||
luaBuilder.append(writePacket(registration));
|
||||
|
||||
// readObject method
|
||||
luaBuilder.append(readPacket(registration)).append(LS);
|
||||
|
||||
|
||||
luaBuilder.append(StringUtils.format("return {}", protocolClazzName)).append(LS);
|
||||
var docTitle = docTitle(registration);
|
||||
var valueOfMethod = valueOfMethod(registration);
|
||||
var writePacket = writePacket(registration);
|
||||
var readPacket = readPacket(registration);
|
||||
|
||||
protocolTemplate = StringUtils.format(protocolTemplate, docTitle, protocolClazzName, "{}", protocolClazzName
|
||||
, valueOfMethod.getKey().trim(), valueOfMethod.getValue().trim(), protocolClazzName, protocolId
|
||||
, protocolClazzName, writePacket.trim(), protocolClazzName, protocolClazzName, readPacket.trim(), protocolClazzName);
|
||||
|
||||
var protocolOutputPath = StringUtils.format("{}/{}/{}.lua"
|
||||
, protocolOutputRootPath
|
||||
, GenerateProtocolPath.getCapitalizeProtocolPath(protocolId)
|
||||
, protocolClazzName);
|
||||
FileUtils.writeStringToFile(new File(protocolOutputPath), luaBuilder.toString());
|
||||
, protocolOutputRootPath, GenerateProtocolPath.getCapitalizeProtocolPath(protocolId), protocolClazzName);
|
||||
FileUtils.writeStringToFile(new File(protocolOutputPath), protocolTemplate);
|
||||
}
|
||||
|
||||
private static String documentTitle(ProtocolRegistration registration) {
|
||||
private static String docTitle(ProtocolRegistration registration) {
|
||||
var protocolId = registration.protocolId();
|
||||
var registrationConstructor = registration.getConstructor();
|
||||
var fieldRegistrations = registration.getFieldRegistrations();
|
||||
var luaBuilder = new StringBuilder();
|
||||
|
||||
var protocolDocument = GenerateProtocolDocument.getProtocolDocument(protocolId);
|
||||
var docTitle = protocolDocument.getKey();
|
||||
|
||||
if (StringUtils.isNotBlank(docTitle)) {
|
||||
Arrays.stream(docTitle.split(LS)).forEach(it -> luaBuilder.append(docToLuaDoc(it)).append(LS));
|
||||
luaBuilder.append(LS);
|
||||
}
|
||||
|
||||
return luaBuilder.toString();
|
||||
}
|
||||
|
||||
private static String newFunction(ProtocolRegistration registration) {
|
||||
short protocolId = registration.getId();
|
||||
private static Pair<String, String> valueOfMethod(ProtocolRegistration registration) {
|
||||
var protocolId = registration.getId();
|
||||
var fields = registration.getFields();
|
||||
var protocolClazzName = registration.getConstructor().getDeclaringClass().getSimpleName();
|
||||
|
||||
var protocolDocument = GenerateProtocolDocument.getProtocolDocument(protocolId);
|
||||
var docFieldMap = protocolDocument.getValue();
|
||||
|
||||
var valueOfParams = StringUtils.joinWith(", ", Arrays.stream(fields).map(it -> it.getName()).collect(Collectors.toList()).toArray());
|
||||
var luaBuilder = new StringBuilder();
|
||||
|
||||
luaBuilder.append(StringUtils.format("local {} = {}", protocolClazzName)).append(LS + LS);
|
||||
|
||||
luaBuilder.append(StringUtils.format("function {}:new(", protocolClazzName));
|
||||
luaBuilder.append(StringUtils.joinWith(", ", Arrays.stream(fields).map(it -> it.getName()).collect(Collectors.toList()).toArray()))
|
||||
.append(")")
|
||||
.append(LS);
|
||||
luaBuilder.append(TAB).append("local obj = {").append(LS);
|
||||
|
||||
for (int i = 0; i < fields.length; i++) {
|
||||
for (var i = 0; i < fields.length; i++) {
|
||||
var field = fields[i];
|
||||
var propertyName = field.getName();
|
||||
|
||||
@@ -201,92 +163,42 @@ public abstract class GenerateLuaUtils {
|
||||
}
|
||||
|
||||
if (i == fields.length - 1) {
|
||||
luaBuilder.append(TAB + TAB)
|
||||
.append(StringUtils.format("{} = {}", propertyName, propertyName));
|
||||
luaBuilder.append(TAB + TAB).append(StringUtils.format("{} = {}", propertyName, propertyName));
|
||||
} else {
|
||||
luaBuilder.append(TAB + TAB)
|
||||
.append(StringUtils.format("{} = {},", propertyName, propertyName));
|
||||
luaBuilder.append(TAB + TAB).append(StringUtils.format("{} = {},", propertyName, propertyName));
|
||||
}
|
||||
|
||||
// 生成类型的注释
|
||||
luaBuilder.append(" -- ").append(field.getGenericType().getTypeName()).append(LS);
|
||||
}
|
||||
luaBuilder.append(TAB).append("}").append(LS);
|
||||
luaBuilder.append(TAB).append("setmetatable(obj, self)").append(LS);
|
||||
luaBuilder.append(TAB).append("self.__index = self").append(LS);
|
||||
luaBuilder.append(TAB).append("return obj").append(LS);
|
||||
luaBuilder.append("end").append(LS).append(LS);
|
||||
return luaBuilder.toString();
|
||||
return new Pair<>(valueOfParams, luaBuilder.toString());
|
||||
}
|
||||
|
||||
private static String protocolIdFunction(ProtocolRegistration registration) {
|
||||
short protocolId = registration.getId();
|
||||
var protocolClazzName = registration.getConstructor().getDeclaringClass().getSimpleName();
|
||||
|
||||
var luaBuilder = new StringBuilder();
|
||||
luaBuilder.append(StringUtils.format("function {}:protocolId()", protocolClazzName)).append(LS);
|
||||
luaBuilder.append(TAB).append(StringUtils.format("return {}", protocolId)).append(LS);
|
||||
luaBuilder.append("end").append(LS).append(LS);
|
||||
|
||||
return luaBuilder.toString();
|
||||
}
|
||||
|
||||
|
||||
private static String writePacket(ProtocolRegistration registration) {
|
||||
var fields = registration.getFields();
|
||||
var fieldRegistrations = registration.getFieldRegistrations();
|
||||
var protocolClazzName = registration.getConstructor().getDeclaringClass().getSimpleName();
|
||||
|
||||
var luaBuilder = new StringBuilder();
|
||||
luaBuilder.append(StringUtils.format("function {}:write(buffer, packet)", protocolClazzName)).append(LS);
|
||||
|
||||
luaBuilder.append(TAB).append("if buffer:writePacketFlag(packet) then").append(LS);
|
||||
luaBuilder.append(TAB + TAB).append("return").append(LS);
|
||||
luaBuilder.append(TAB).append("end").append(LS);
|
||||
|
||||
for (var i = 0; i < fields.length; i++) {
|
||||
var field = fields[i];
|
||||
var fieldRegistration = fieldRegistrations[i];
|
||||
|
||||
luaSerializer(fieldRegistration.serializer()).writeObject(luaBuilder, "packet." + field.getName(), 1, field, fieldRegistration);
|
||||
}
|
||||
|
||||
luaBuilder.append("end").append(LS).append(LS);
|
||||
return luaBuilder.toString();
|
||||
}
|
||||
|
||||
|
||||
private static String readPacket(ProtocolRegistration registration) {
|
||||
Field[] fields = registration.getFields();
|
||||
IFieldRegistration[] fieldRegistrations = registration.getFieldRegistrations();
|
||||
var protocolClazzName = registration.getConstructor().getDeclaringClass().getSimpleName();
|
||||
|
||||
var jsBuilder = new StringBuilder();
|
||||
jsBuilder.append(StringUtils.format("function {}:read(buffer)", protocolClazzName)).append(LS);
|
||||
jsBuilder.append(TAB).append("if not(buffer:readBoolean()) then").append(LS);
|
||||
jsBuilder.append(TAB + TAB).append("return nil").append(LS);
|
||||
jsBuilder.append(TAB).append("end").append(LS);
|
||||
|
||||
|
||||
jsBuilder.append(TAB).append(StringUtils.format("local packet = {}:new()", protocolClazzName)).append(LS);
|
||||
|
||||
|
||||
var fields = registration.getFields();
|
||||
var fieldRegistrations = registration.getFieldRegistrations();
|
||||
var luaBuilder = new StringBuilder();
|
||||
for (int i = 0; i < fields.length; i++) {
|
||||
Field field = fields[i];
|
||||
IFieldRegistration fieldRegistration = fieldRegistrations[i];
|
||||
|
||||
String readObject = luaSerializer(fieldRegistration.serializer()).readObject(jsBuilder, 1, field, fieldRegistration);
|
||||
jsBuilder.append(TAB).append(StringUtils.format("packet.{} = {}", field.getName(), readObject)).append(LS);
|
||||
var field = fields[i];
|
||||
var fieldRegistration = fieldRegistrations[i];
|
||||
var readObject = luaSerializer(fieldRegistration.serializer()).readObject(luaBuilder, 1, field, fieldRegistration);
|
||||
luaBuilder.append(TAB).append(StringUtils.format("packet.{} = {}", field.getName(), readObject)).append(LS);
|
||||
}
|
||||
|
||||
jsBuilder.append(TAB).append("return packet").append(LS);
|
||||
|
||||
jsBuilder.append("end").append(LS);
|
||||
|
||||
return jsBuilder.toString();
|
||||
return luaBuilder.toString();
|
||||
}
|
||||
|
||||
|
||||
private static String docToLuaDoc(String doc) {
|
||||
return doc.replaceFirst("//", "--");
|
||||
}
|
||||
|
||||
+7
@@ -32,3 +32,10 @@ function ProtocolManager.read(buffer)
|
||||
return ProtocolManager.getProtocol(protocolId):read(buffer)
|
||||
end
|
||||
|
||||
function initProtocol()
|
||||
{}
|
||||
{}
|
||||
end
|
||||
|
||||
ProtocolManager.initProtocol = initProtocol
|
||||
return ProtocolManager
|
||||
@@ -0,0 +1,33 @@
|
||||
{}
|
||||
local {} = {}
|
||||
|
||||
function {}:new({})
|
||||
local obj = {
|
||||
{}
|
||||
}
|
||||
setmetatable(obj, self)
|
||||
self.__index = self
|
||||
return obj
|
||||
end
|
||||
|
||||
function {}:protocolId()
|
||||
return {}
|
||||
end
|
||||
|
||||
function {}:write(buffer, packet)
|
||||
if buffer:writePacketFlag(packet) then
|
||||
return
|
||||
end
|
||||
{}
|
||||
end
|
||||
|
||||
function {}:read(buffer)
|
||||
if not(buffer:readBoolean()) then
|
||||
return nil
|
||||
end
|
||||
local packet = {}:new()
|
||||
{}
|
||||
return packet
|
||||
end
|
||||
|
||||
return {}
|
||||
@@ -13,7 +13,7 @@ namespace csharp
|
||||
|
||||
ProtocolManager.InitProtocol();
|
||||
// 获取复杂对象的字节流
|
||||
var complexObjectBytes = File.ReadAllBytes("C:\\zfoo\\protocol\\src\\test\\resources\\ComplexObject.bytes");
|
||||
var complexObjectBytes = File.ReadAllBytes("../resources/ComplexObject.bytes");
|
||||
var buffer = ByteBuffer.ValueOf();
|
||||
buffer.WriteBytes(complexObjectBytes);
|
||||
var packet = ProtocolManager.Read(buffer);
|
||||
@@ -187,4 +187,4 @@ namespace csharp
|
||||
throw new Exception("a is not equals b");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
+5
-4
@@ -1,6 +1,7 @@
|
||||
using System.IO;
|
||||
using System.Text;
|
||||
using NUnit.Framework;
|
||||
using Spring.Util;
|
||||
using XLua;
|
||||
|
||||
namespace Test.Editor.LuaTest
|
||||
@@ -18,7 +19,7 @@ namespace Test.Editor.LuaTest
|
||||
var luaEnv = new LuaEnv();
|
||||
var luaDebugBuilder = new StringBuilder();
|
||||
// Rider的断点调试
|
||||
// luaDebugBuilder.Append("package.cpath = package.cpath .. ';C:/Users/jm/AppData/Roaming/JetBrains/Rider2020.1/plugins/intellij-emmylua/classes/debugger/emmy/windows/x64/?.dll'").Append(FileUtils.LS);
|
||||
// luaDebugBuilder.Append("package.cpath = package.cpath .. ';C:/Users/jaysunxiao/AppData/Roaming/JetBrains/Rider2021.1/plugins/EmmyLua/classes/debugger/emmy/windows/x64/?.dll'").Append(FileUtils.LS);
|
||||
// luaDebugBuilder.Append("local dbg = require('emmy_core')").Append(FileUtils.LS);
|
||||
// luaDebugBuilder.Append("dbg.tcpListen('localhost', 9966)").Append(FileUtils.LS);
|
||||
// luaDebugBuilder.Append("dbg.waitIDE()").Append(FileUtils.LS);
|
||||
@@ -27,8 +28,8 @@ namespace Test.Editor.LuaTest
|
||||
|
||||
luaEnv.AddLoader(CustomLoader);
|
||||
|
||||
var luaProtocolTestStr = File.ReadAllText(TEST_PATH + "LuaProtocolTest.lua");
|
||||
luaEnv.DoString(luaProtocolTestStr, "LuaProtocolTest");
|
||||
var luaProtocolTestStr = File.ReadAllText(TEST_PATH + "main.lua");
|
||||
luaEnv.DoString(luaProtocolTestStr, "main");
|
||||
|
||||
LuaFunction byteBufferTestFunction = luaEnv.Global.Get<LuaFunction>("byteBufferTest");
|
||||
byteBufferTestFunction.Call();
|
||||
@@ -44,4 +45,4 @@ namespace Test.Editor.LuaTest
|
||||
return File.ReadAllBytes(TEST_PATH + filepath);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
File renamed without changes.
Reference in new issue
Block a user