mirror of
https://github.com/tiennm99/zfoo.git
synced 2026-09-02 14:21:25 +00:00
Merge branch 'main' of github.com:zfoo-project/zfoo into main
This commit is contained in:
@@ -59,7 +59,6 @@ public abstract class JsonUtils {
|
||||
DefaultPrettyPrinter prettyPrinter = (DefaultPrettyPrinter) MAPPER.getSerializationConfig().getDefaultPrettyPrinter();
|
||||
DefaultPrettyPrinter.Indenter indenter = new DefaultIndenter(StringUtils.TAB_ASCII, FileUtils.LS);
|
||||
prettyPrinter.indentObjectsWith(indenter);
|
||||
prettyPrinter.indentArraysWith(indenter);
|
||||
|
||||
MAPPER_TURBO.setSerializationInclusion(JsonInclude.Include.NON_NULL);
|
||||
MAPPER_TURBO.configure(SerializationFeature.FAIL_ON_EMPTY_BEANS, false);
|
||||
|
||||
+6
-4
@@ -5,6 +5,8 @@
|
||||
|
||||
- 利用Java动态语言的反射特性,用最少的代码去解析Excel
|
||||
|
||||
- 支持Excel导出Json文件
|
||||
|
||||
### Ⅱ. 自动映射
|
||||
|
||||
- Excel的第一行对应Java类属性,第二行和第三行不会起到注释的作用,其中第一列必须是Id属性
|
||||
@@ -16,7 +18,7 @@
|
||||

|
||||
|
||||
- 解析过后有两种使用方式
|
||||
1. 通过注解
|
||||
1. 通过注解
|
||||
```
|
||||
@Component
|
||||
public class StudentManager {
|
||||
@@ -26,7 +28,7 @@
|
||||
|
||||
}
|
||||
```
|
||||
2. 通过类动态获取
|
||||
2. 通过类动态获取
|
||||
```
|
||||
Storage<Integer, StudentResource> studentResources = (Storage<Integer, StudentResource>) StorageContext.getStorageManager().getStorage(StudentResource.class);
|
||||
```
|
||||
@@ -45,10 +47,10 @@ var students = studentResources.getIndex("name", "james0");
|
||||
|
||||
- 唯一索引通过Storage.getUniqueIndex()获取,需要把索引注解标注为@Index(unique = true)
|
||||
|
||||
### Ⅲ. 热更新Excel
|
||||
### Ⅲ. 热更新Excel/Json
|
||||
|
||||
- [tank](https://github.com/zfoo-project/tank-game-server/blob/main/common/src/main/java/com/zfoo/tank/common/util/HotUtils.java)
|
||||
分布式热更新Excel配置文件实现
|
||||
分布式热更新Excel/Json配置文件实现
|
||||
|
||||
### Ⅳ. 用途
|
||||
|
||||
|
||||
@@ -76,11 +76,11 @@ public class ResourceReader implements IResourceReader {
|
||||
var iterator = resource.getRows().iterator();
|
||||
// 从ROW_SERVER这行开始读取数据
|
||||
while (iterator.hasNext()) {
|
||||
var row = iterator.next();
|
||||
var columns = iterator.next().getColumns();
|
||||
var instance = ReflectionUtils.newInstance(clazz);
|
||||
|
||||
for (var fieldInfo : fieldInfos) {
|
||||
var content = row.get(fieldInfo.index);
|
||||
var content = columns.get(fieldInfo.index);
|
||||
if (StringUtils.isNotEmpty(content) || fieldInfo.field.getType() == String.class) {
|
||||
inject(instance, fieldInfo.field, content);
|
||||
}
|
||||
|
||||
@@ -27,7 +27,15 @@ public class ResourceData {
|
||||
// 配置表字段名
|
||||
private List<ResourceHeader> headers = new ArrayList<>();
|
||||
// 配置表数据
|
||||
private List<List<String>> rows = new ArrayList<>();
|
||||
private List<ResourceRow> rows = new ArrayList<>();
|
||||
|
||||
public static ResourceData valueOf(String name, List<ResourceHeader> headers, List<ResourceRow> rows) {
|
||||
var resourceData = new ResourceData();
|
||||
resourceData.name = name;
|
||||
resourceData.headers = headers;
|
||||
resourceData.rows = rows;
|
||||
return resourceData;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
@@ -45,11 +53,11 @@ public class ResourceData {
|
||||
this.headers = headers;
|
||||
}
|
||||
|
||||
public List<List<String>> getRows() {
|
||||
public List<ResourceRow> getRows() {
|
||||
return rows;
|
||||
}
|
||||
|
||||
public void setRows(List<List<String>> rows) {
|
||||
public void setRows(List<ResourceRow> rows) {
|
||||
this.rows = rows;
|
||||
}
|
||||
|
||||
|
||||
@@ -13,6 +13,7 @@
|
||||
package com.zfoo.storage.model.resource;
|
||||
|
||||
import com.zfoo.protocol.util.AssertionUtils;
|
||||
import com.zfoo.protocol.util.StringUtils;
|
||||
import org.springframework.lang.Nullable;
|
||||
|
||||
import java.util.HashMap;
|
||||
@@ -58,6 +59,15 @@ public enum ResourceEnum {
|
||||
return typeMap.containsKey(type);
|
||||
}
|
||||
|
||||
public static boolean isExcel(String type) {
|
||||
var resourceEnum = getResourceEnumByType(type);
|
||||
return resourceEnum == ResourceEnum.EXCEL_XLS || resourceEnum == ResourceEnum.EXCEL_XLSX;
|
||||
}
|
||||
|
||||
public static String typesToString() {
|
||||
return StringUtils.joinWith(StringUtils.SPACE, typeMap.values().toArray());
|
||||
}
|
||||
|
||||
public String getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
@@ -25,13 +25,12 @@ public class ResourceHeader {
|
||||
//列
|
||||
private int index;
|
||||
|
||||
public ResourceHeader() {
|
||||
}
|
||||
|
||||
public ResourceHeader(String name, String type, int index) {
|
||||
this.name = name;
|
||||
this.type = type;
|
||||
this.index = index;
|
||||
public static ResourceHeader valueOf(String name, String type, int index) {
|
||||
var resourceHeader = new ResourceHeader();
|
||||
resourceHeader.name = name;
|
||||
resourceHeader.type = type;
|
||||
resourceHeader.index = index;
|
||||
return resourceHeader;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
|
||||
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* Copyright (C) 2020 The zfoo Authors
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
|
||||
* in compliance with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software distributed under the License is distributed
|
||||
* on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and limitations under the License.
|
||||
*/
|
||||
package com.zfoo.storage.model.resource;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* @author godotg
|
||||
* @version 4.0
|
||||
*/
|
||||
public class ResourceRow {
|
||||
|
||||
private int row;
|
||||
|
||||
private List<String> columns = new ArrayList<>();
|
||||
|
||||
public static ResourceRow valueOf(int row, List<String> columns) {
|
||||
var resourceRow = new ResourceRow();
|
||||
resourceRow.row = row;
|
||||
resourceRow.columns = columns;
|
||||
return resourceRow;
|
||||
}
|
||||
|
||||
public int getRow() {
|
||||
return row;
|
||||
}
|
||||
|
||||
public void setRow(int row) {
|
||||
this.row = row;
|
||||
}
|
||||
|
||||
public List<String> getColumns() {
|
||||
return columns;
|
||||
}
|
||||
|
||||
public void setColumns(List<String> columns) {
|
||||
this.columns = columns;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -20,6 +20,7 @@ import com.zfoo.protocol.util.StringUtils;
|
||||
import com.zfoo.storage.model.resource.ResourceData;
|
||||
import com.zfoo.storage.model.resource.ResourceEnum;
|
||||
import com.zfoo.storage.model.resource.ResourceHeader;
|
||||
import com.zfoo.storage.model.resource.ResourceRow;
|
||||
import org.apache.poi.ss.usermodel.Sheet;
|
||||
import org.apache.poi.ss.usermodel.Workbook;
|
||||
import org.apache.poi.ss.usermodel.WorkbookFactory;
|
||||
@@ -42,27 +43,28 @@ public class ExcelToJsonUtils {
|
||||
public static void excelConvertJson(String inputDir, String outputDir) throws IOException {
|
||||
var listFiles = FileUtils.getAllReadableFiles(new File(inputDir))
|
||||
.stream()
|
||||
.filter(it -> ResourceEnum.containsResourceEnum(FileUtils.fileExtName(it.getName())))
|
||||
.filter(it -> ResourceEnum.isExcel(FileUtils.fileExtName(it.getName())))
|
||||
.collect(Collectors.toList());
|
||||
|
||||
for (var file : listFiles) {
|
||||
var fileName = StringUtils.format("{}.json", FileUtils.fileSimpleName(file.getName()));
|
||||
var fileSimpleName = FileUtils.fileSimpleName(file.getName());
|
||||
var jsonFileName = StringUtils.format("{}.json", fileSimpleName);
|
||||
var inputStream = FileUtils.openInputStream(file);
|
||||
var resourceData = readResourceDataFromExcel(inputStream, fileName);
|
||||
FileUtils.writeStringToFile(new File(FileUtils.joinPath(outputDir, fileName)), JsonUtils.object2StringPrettyPrinter(resourceData));
|
||||
var resourceData = readResourceDataFromExcel(inputStream, file.getName());
|
||||
|
||||
var outputFilePath = FileUtils.joinPath(outputDir, jsonFileName);
|
||||
FileUtils.deleteFile(new File(outputFilePath));
|
||||
FileUtils.writeStringToFile(new File(outputFilePath), JsonUtils.object2StringPrettyPrinter(resourceData));
|
||||
}
|
||||
}
|
||||
|
||||
public static ResourceData readResourceDataFromExcel(InputStream inputStream, String fileName) {
|
||||
// 只读取代码里写的字段
|
||||
var wb = createWorkbook(inputStream, fileName);
|
||||
var resource = new ResourceData();
|
||||
resource.setName(fileName);
|
||||
// 默认取到第一个sheet页
|
||||
var sheet = wb.getSheetAt(0);
|
||||
//设置所有列
|
||||
var headers = getHeaders(sheet, fileName);
|
||||
resource.setHeaders(headers);
|
||||
|
||||
// 行数定位到有效数据行,默认是第四行为有效数据行
|
||||
var iterator = sheet.iterator();
|
||||
@@ -70,19 +72,18 @@ public class ExcelToJsonUtils {
|
||||
iterator.next();
|
||||
iterator.next();
|
||||
// 从ROW_SERVER这行开始读取数据
|
||||
List<List<String>> data = new ArrayList<>();
|
||||
List<ResourceRow> rows = new ArrayList<>();
|
||||
while (iterator.hasNext()) {
|
||||
var row = iterator.next();
|
||||
List<String> rowData = new ArrayList<>();
|
||||
var columns = new ArrayList<String>();
|
||||
for (var header : headers) {
|
||||
var cell = row.getCell(header.getIndex());
|
||||
var content = CellUtils.getCellStringValue(cell);
|
||||
rowData.add(content);
|
||||
columns.add(content);
|
||||
}
|
||||
data.add(rowData);
|
||||
rows.add(ResourceRow.valueOf(row.getRowNum() + 1, columns));
|
||||
}
|
||||
resource.setRows(data);
|
||||
return resource;
|
||||
return ResourceData.valueOf(fileName, headers, rows);
|
||||
}
|
||||
|
||||
// 只读取代码里写的字段
|
||||
@@ -122,7 +123,7 @@ public class ExcelToJsonUtils {
|
||||
if (Objects.nonNull(previousValue)) {
|
||||
throw new RunException("资源[class:{}]的Excel文件出现重复的属性控制列[field:{}]", fileName, fieldName);
|
||||
}
|
||||
headerList.add(new ResourceHeader(fieldName, typeName, i));
|
||||
headerList.add(ResourceHeader.valueOf(fieldName, typeName, i));
|
||||
}
|
||||
return headerList;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user