omelop-iplocation
Version:
ip2location parse ip location info
934 lines (917 loc) • 72.7 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.ExportServerTS = void 0;
const path = require("path");
const fs = require("fs");
const exportBase_1 = require("./exportBase");
const constants_1 = require("./constants");
const TSTypeLink = {};
TSTypeLink[constants_1.FIELD_TYPE.FLOAT] = ': number';
TSTypeLink[constants_1.FIELD_TYPE.FLOAT_OPTION] = '?: number';
TSTypeLink[constants_1.FIELD_TYPE.INT] = ': number';
TSTypeLink[constants_1.FIELD_TYPE.INT_OPTION] = '?: number';
TSTypeLink[constants_1.FIELD_TYPE.STRING] = ': string';
TSTypeLink[constants_1.FIELD_TYPE.STRING_OPTION] = '?: string';
TSTypeLink[constants_1.FIELD_TYPE.TABLE] = ': any';
class ExportServerTS extends exportBase_1.ExportBase {
genDataFileName() {
let str = `/** 数据文件名 */
const config_data_file_name = {\r\n`;
let keys = Object.keys(this.dataFileName);
for (let item of keys) {
str += `\t${item}: \'${this.dataFileName[item]}\',\r\n`;
}
str += `}\r\n`;
str += `\r\n`;
str += `export { config_data_file_name };`;
fs.writeFileSync(`${this.outTsRootDir}/config_data_file_name.ts`, str);
}
genBaseModel() {
let str = `import path = require('path');
import fs = require('fs');
/** 配置模型基础类 */
export abstract class config_model_base {
/** 获取文件链接 */
public static getUrl(filename: string): string {
let configUrl = null;
let dir = this.isPublic() ? 'common' : process.env.PUB_PLATFORM;
if (process.env.CONFIG_DIR) {
configUrl = \`\${path.join(process.env.CONFIG_DIR, dir, filename)}\`;
} else {
configUrl = \`\${path.join(__dirname, dir, filename)}\`;
}
return configUrl;
}
/** 加载文件 */
public static loadJson(configUrl: string): any {
if (!fs.existsSync(configUrl)) {
console.log(\`配置文件\${configUrl}不存在\`);
return;
}
return require(configUrl);
}
/** 公共配置 */
public static isPublic(): boolean {
return false;
}
}
export interface ConfigClass<T extends config_model_base> {
new(): T;
FIELDS?: any;
getUrl(filename: string): string;
loadJson(configUrl: string): any;
getConfigName(filename?: string): string;
getClassName(): string;
/** 公共配置 */
isPublic(): boolean;
}`;
let targetFilename = `${this.outTsRootDir}/config_model.ts`;
const pathInfo = path.parse(targetFilename);
this.mkdirsSync(pathInfo.dir);
fs.writeFileSync(targetFilename, str);
}
getModelGetUrl() { return; }
;
/**
* 生成模型类名映射
*/
genModelMap() {
let str = `
export class lang_model_map {
private static maps = new Map<string, any>();
public static add(model: any) {
this.maps.set(model.getClassName(), model);
}
public static get(filename: string) {
return this.maps.get(filename);
}
}`;
let targetFilename = `${this.outTsRootDir}/lang_model_map.ts`;
const pathInfo = path.parse(targetFilename);
this.mkdirsSync(pathInfo.dir);
fs.writeFileSync(targetFilename, str);
}
genDataModel(filename, content, fields, types, descs, isPublic, isAppendData, parent_class) {
const oriFilename = path.parse(filename).name;
let modelrName = `${oriFilename}_model`;
let str = '';
if (isAppendData) {
str += `import { config_data_file_name } from './config_data_file_name';\r\n`;
}
let parentClassname = 'config_model_base';
if (parent_class) {
str += `import { ${parent_class.classname} } from \'${parent_class.path}\';`;
parentClassname = parent_class.classname;
}
else {
str += `import { config_model_base } from './config_model';`;
}
// 检查当前model是否是其他的父类,是则追加字段到子类
for (let [child, par] of this.modelParent.entries()) {
if (par === modelrName) {
let childModel = this.modelDefines.get(child);
this.modelDefines.set(child, { fields: fields.concat(childModel.fields), types: types.concat(childModel.types), descs: descs.concat(childModel.descs) });
}
}
if (this.modelDefines.has(parentClassname)) {
// 存在父类model,则附加上父类定义
let parent = this.modelDefines.get(parentClassname);
this.modelDefines.set(modelrName, { fields: parent.fields.concat(fields), types: parent.types.concat(types), descs: parent.descs.concat(descs) });
}
else {
this.modelDefines.set(modelrName, { fields, types, descs });
if (parentClassname) {
// 保持我的父类model,等待父类model出现后,进行定义追加
this.modelParent.set(modelrName, parentClassname);
}
}
parentClassname = parentClassname || 'config_model_base';
str += `
/**
* ${content}
*/
export class ${modelrName} extends ${parentClassname} {\r\n`;
if (this.getModelGetUrl() && isAppendData) {
str += this.getModelGetUrl();
str += `\r\n`;
}
// 字段定义
str += this._genFieldDefine(fields, types, descs);
str += `\r\n`;
str += `\tpublic static readonly FIELDS = {\r\n`;
if (parent_class) {
str += `\t\t...${parentClassname}.FIELDS,\r\n`;
}
str += this._genFIELDS(types, fields);
str += `\t}\r\n`;
str += `\r\n`;
str += `\tpublic static getClassName(): string {
return \'${modelrName}\'
}
`;
if (isAppendData) {
str += `
public static getConfigName(filename?: string): string {
return filename || config_data_file_name.${oriFilename};
}
`;
}
else {
str += `
public static getConfigName(filename?: string): string {
return filename;
}
`;
}
if (isPublic) {
str += `
public static isPublic(): boolean {
return true;
}
`;
}
str += `
}`;
fs.writeFileSync(`${path.parse(filename).dir}/${modelrName}.ts`, str);
}
/**
* 生成常量DATA配置字段定义
* @param oriFilename 文件名
* @param datas 行数据
*/
_genConstDataFieldDefine(oriFilename, types, datas, TYPE) {
// 查找常量定义key,desc
let keyCol = null;
let keyDescCol = null;
for (let i = 0; i < types.length; i++) {
let typeRules = types[i].split(',');
if (typeRules.indexOf(constants_1.FIELD_RULE.KEY) !== -1) {
keyCol = i;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.KEY_DESC) !== -1) {
keyDescCol = i;
}
}
if (null == keyCol || null == keyDescCol) {
throw `${oriFilename} 常量Data配置异常,未配置字段约束${constants_1.FIELD_RULE.KEY}或者${constants_1.FIELD_RULE.KEY_DESC}`;
}
let str = '';
for (let i = 0; i < datas.length; i++) {
let rowArray = datas[i];
const keyCst = rowArray[keyCol].toString().trim();
str += `\t/** ${rowArray[keyDescCol]} */\r\n`;
str += `\t${keyCst}: ${TYPE};\r\n`;
}
return str;
}
/**
* 生成常量DATA配置字段定义
* @param oriFilename 文件名
* @param datas 行数据
*/
_genConstFIELDS(oriFilename, types, datas) {
// 查找常量定义key,desc
let keyCol = null;
let keyDescCol = null;
for (let i = 0; i < types.length; i++) {
let typeRules = types[i].split(',');
if (typeRules.indexOf(constants_1.FIELD_RULE.KEY) !== -1) {
keyCol = i;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.KEY_DESC) !== -1) {
keyDescCol = i;
}
}
if (null == keyCol || null == keyDescCol) {
throw `${oriFilename} 常量Data配置异常,未配置字段约束${constants_1.FIELD_RULE.KEY}或者${constants_1.FIELD_RULE.KEY_DESC}`;
}
let str = '';
for (let i = 0; i < datas.length; i++) {
let rowArray = datas[i];
const keyCst = rowArray[keyCol].toString().trim();
str += `\t\t/** ${rowArray[keyDescCol]} */\r\n`;
str += `\t\t${keyCst.toUpperCase()}: \'${keyCst}\',\r\n`;
}
return str;
}
genDataConstModel(filename, content, fields, types, descs, isPublic, datas) {
const oriFilename = path.parse(filename).name;
let modelrName = `${oriFilename}_model`;
let str = '';
str += `import { config_data_file_name } from './config_data_file_name';\r\n`;
str += `import { config_model_base } from './config_model';`;
// 加入data item定义
str += `
export type ${modelrName}_data_item = {
${this._genFieldDefine(fields, types, descs)}
}`;
str += `
/**
* ${content}
*/
export class ${modelrName} extends config_model_base {\r\n`;
if (this.getModelGetUrl()) {
str += this.getModelGetUrl();
str += `\r\n`;
}
str += `\r\n`;
str += `\tpublic static readonly FIELDS = {\r\n`;
str += this._genFIELDS(types, fields);
str += `\t}\r\n`;
str += `\r\n`;
str += `\tpublic static readonly CONST_FIELDS = {\r\n`;
str += this._genConstFIELDS(filename, types, datas);
str += `\t}\r\n`;
str += `\r\n`;
// 字段定义
str += this._genConstDataFieldDefine(filename, types, datas, `${modelrName}_data_item`);
str += `\r\n`;
str += `\tpublic static getClassName(): string {
return \'${modelrName}\'
}
`;
str += `
public static getConfigName(filename?: string): string {
return filename || config_data_file_name.${oriFilename};
}
`;
if (isPublic) {
str += `
public static isPublic(): boolean {
return true;
}
`;
}
str += `
}`;
fs.writeFileSync(`${path.parse(filename).dir}/${modelrName}.ts`, str);
}
genConstModel(filename, content, datas) {
const oriFilename = path.parse(filename).name;
let modelrName = `${oriFilename}_model`;
let defaultDataName = `${oriFilename}`;
let str = `import { config_data_file_name } from './config_data_file_name';
import { config_model_base } from './config_model';
/**
* ${content}
*/
export class ${modelrName} extends config_model_base {\r\n`;
if (this.getModelGetUrl()) {
str += this.getModelGetUrl();
str += `\r\n`;
}
// 字段定义
str += this._genConstFieldDefine(oriFilename, datas);
str += `\r\n`;
str += `\r\n`;
str += `\tpublic static getClassName(): string {
return \'${modelrName}\'
}
public static getConfigName(filename?: string): string {
return filename || config_data_file_name.${defaultDataName};
}
}`;
fs.writeFileSync(`${path.parse(filename).dir}/${modelrName}.ts`, str);
}
genLangModel(filename, content, fields, fieldsDef, datas) {
const oriFilename = path.parse(filename).name;
let modelrName = `${oriFilename}_model`;
let str = `import path = require('path');
import { config_model_base } from './config_model';
import { lang_model_map } from './lang_model_map';
/**
* ${content}
*/
export class ${modelrName} extends config_model_base {\r\n`;
if (fieldsDef) {
// 字段定义
str += this._genLangFieldDefine(datas);
str += `\r\n`;
}
if (fields === 1) {
str += `\tpublic static readonly FIELDS = {\r\n`;
str += this._genLangFields(datas);
str += `\t}\r\n`;
}
str += `\r\n`;
str += `\tpublic static getClassName(): string {
return \'${modelrName}\'
}
public static getConfigName(filename?: string): string {
return \`${oriFilename}-\${filename}.json\`;
}
public static getUrl(filename: string): string {
let configUrl = null;
if (process.env.CONFIG_DIR) {
configUrl = \`\${path.join(process.env.CONFIG_DIR, 'i18n', filename)}\`;
} else {
configUrl = \`\${path.join(__dirname, 'i18n', filename)}\`;
}
return configUrl;
}
}
lang_model_map.add(${modelrName});`;
fs.writeFileSync(`${path.parse(filename).dir}/${modelrName}.ts`, str);
}
genErrorModel(filename, content, datas, baseCodeConfig) {
const oriFilename = path.parse(filename).name;
let modelrName = `${oriFilename}_model`;
let str = 'import path = require(\'path\');\r\n';
if (baseCodeConfig) {
str += `import { ${baseCodeConfig.baseCode}, ${baseCodeConfig.baseObj}} from '${baseCodeConfig.path}';\r\n`;
}
str += `import { config_model_base } from './config_model';
/**
* ${content}
*/
export class ${modelrName} extends config_model_base {\r\n`;
str += `\r\n`;
str += `\tpublic static getClassName(): string {
return \'${modelrName}\'
}
public static getConfigName(filename?: string): string {
return \`${oriFilename}-\${filename}.json\`;
}
public static getUrl(filename: string): string {
let configUrl = null;
if (process.env.CONFIG_DIR) {
configUrl = \`\${path.join(process.env.CONFIG_DIR, 'i18n', filename)}\`;
} else {
configUrl = \`\${path.join(__dirname, 'i18n', filename)}\`;
}
return configUrl;
}
}`;
str += `\r\n`;
str += `export const ${oriFilename} = {\r\n`;
if (baseCodeConfig) {
str += `\t...${baseCodeConfig.baseCode},\r\n`;
}
// 字段定义
str += this._genErrorFieldDefine(datas);
str += `}\r\n`;
str += `export const ${oriFilename}_key:any = {};\r\n`;
str += `for (let [k, v] of Object.entries(${oriFilename})) {\r\n`;
str += `\t${oriFilename}_key[v] = k;\r\n`;
str += `}\r\n`;
str += `\r\n`;
str += `export const ${oriFilename}_obj = {\r\n`;
if (baseCodeConfig) {
str += `\t...${baseCodeConfig.baseObj},\r\n`;
}
// 字段定义
str += this._genErrorFieldObj(datas);
str += `}`;
fs.writeFileSync(`${path.parse(filename).dir}/${modelrName}.ts`, str);
}
/**
* 生成JOSN数据配置
* @param filename 文件名称
* @param fmtType 配置文件类型
* @param fields 字段
* @param types 字段类型
* @param datas 数据
* @param descs 描述
*/
genDataBuffer(filename, fmtType, fields, types, datas, descs, categoryModel) {
let oriFilename = path.parse(filename).name;
let str = null;
switch (fmtType) {
case constants_1.CONFIG_TYPE.DATA:
case constants_1.CONFIG_TYPE.MODEL:
str = this.genDataConfigBuffer(oriFilename, fields, types, datas, categoryModel);
break;
case constants_1.CONFIG_TYPE.DATA_CONST:
str = this.genDataConstConfigBuffer(oriFilename, fields, types, datas);
break;
case constants_1.CONFIG_TYPE.CONST:
str = this.genConstConfigBuffer(oriFilename, fields, types, datas, descs);
break;
case constants_1.CONFIG_TYPE.LANG:
this.genLangConfigBuffer(oriFilename, fields, types, datas, descs);
break;
case constants_1.CONFIG_TYPE.ERROR:
this.genErrorConfigBuffer(oriFilename, fields, types, datas, descs);
break;
default:
console.log(`${filename} 不支持的配置结构`);
break;
}
if (str) {
this.dataFileName[oriFilename] = `${oriFilename}.json`;
fs.writeFileSync(`${filename}.json`, str);
}
}
/**
* 生成TS类成员字段定义
* @param fields 字段
* @param types 字段类型
* @param descs 字段描述
*/
_genFieldDefine(fields, types, descs) {
let str = '';
if (!fields) {
return str;
}
for (let i = 0; i < fields.length; i++) {
let typeRules = types[i].split(',');
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_SERVER) !== -1 && this.publishType == 2) {
continue;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_CLIENT) !== -1 && this.publishType == 1) {
continue;
}
let fieldType = typeRules[0];
if (fieldType === constants_1.FIELD_TYPE.UNEXPORT) {
continue;
}
str += `\t/** ${descs[i]} */\r\n`;
str += `\t${fields[i]}${TSTypeLink[fieldType]};\r\n`;
}
return str;
}
/**
* 生成常量配置字段定义
* @param oriFilename 文件名
* @param datas 行数据
*/
_genConstFieldDefine(oriFilename, datas) {
let str = '';
for (let i = 0; i < datas.length; i++) {
let rowArray = datas[i];
if (rowArray.length < 4) {
console.log(`配置文件${oriFilename}第${i + 1 + constants_1.CONFIG_SKIP_ROW}行数据异常, 列数不足4`, JSON.stringify(rowArray));
return;
}
const keyCst = rowArray[0].toString().trim();
let fieldType = rowArray[2];
str += `\t/** ${rowArray[3]} */\r\n`;
str += `\t${keyCst}${TSTypeLink[fieldType]};\r\n`;
}
return str;
}
/**
* 生成语言字段定义
* @param datas 数据
*/
_genLangFieldDefine(datas) {
let str = '';
for (let i = 0; i < datas.length; i++) {
let rowArray = datas[i];
if (rowArray.length < 1) {
return;
}
const keyCst = rowArray[0].toString().trim();
str += `\t/** ${rowArray[1]} */\r\n`;
str += `\t${keyCst}: string;\r\n`;
}
return str;
}
/**
* 生成语言字段名常量集合
* @param datas 数据
*/
_genLangFields(datas) {
let str = '';
for (let i = 0; i < datas.length; i++) {
let rowArray = datas[i];
if (rowArray.length < 1) {
return;
}
const keyCst = rowArray[0].toString().trim();
str += `\t\t/** ${rowArray[1]} */\r\n`;
str += `\t\t${keyCst.toUpperCase()}: \'${keyCst}\',\r\n`;
}
return str;
}
/**
* 生成错误码字段定义
* @param datas 数据
*/
_genErrorFieldDefine(datas) {
let str = '';
for (let i = 0; i < datas.length; i++) {
let rowArray = datas[i];
if (rowArray.length < 1) {
return;
}
const keyCst = rowArray[0].toString().trim();
str += `\t/** ${rowArray[2]} */\r\n`;
str += `\t${keyCst} : ${rowArray[1]},\r\n`;
}
return str;
}
/**
* 生成错误码字段定义
* @param datas 数据
*/
_genErrorFieldObj(datas) {
let str = '';
for (let i = 0; i < datas.length; i++) {
let rowArray = datas[i];
if (rowArray.length < 1) {
return;
}
const keyCst = rowArray[0].toString().trim();
str += `\t/** ${rowArray[2]} */\r\n`;
str += `\t${keyCst}: {\r\n`;
str += `\t\tcode: ${rowArray[1]},\r\n`;
str += `\t\tmsg: \'${rowArray[2]}\'\r\n`;
str += `\t},\r\n`;
}
return str;
}
/**
* 生成字段常量
* @param types 类型
* @param fields 字段
*/
_genFIELDS(types, fields) {
let str = '';
if (!fields) {
return str;
}
for (let i = 0; i < fields.length; i++) {
let typeRules = types[i].split(',');
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_SERVER) !== -1 && this.publishType == 2) {
continue;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_CLIENT) !== -1 && this.publishType == 1) {
continue;
}
let fieldType = typeRules[0];
if (fieldType === constants_1.FIELD_TYPE.UNEXPORT) {
continue;
}
str += `\t\t\'${fields[i].toUpperCase()}\': \'${fields[i]}\',\r\n`;
}
return str;
}
/**
* 生成数据JSON配置
* @param oriFilename 文件名称
* @param fields 字段
* @param types 字段类型
* @param datas 数据
*/
genDataConfigBuffer(oriFilename, fields, types, datas, categoryModel) {
if (!datas || datas.length === 0) {
console.log(`配置文件${oriFilename}数据为空,请检查配置`);
return;
}
let dataModel = {
fields: [],
types: []
};
// 验证model和数据定义是否完全匹配
for (let j = 0; j < fields.length; j++) {
let typeRules = types[j].split(',');
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_SERVER) !== -1 && this.publishType == 2) {
continue;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_CLIENT) !== -1 && this.publishType == 1) {
continue;
}
dataModel.fields.push(fields[j]);
dataModel.types.push(types[j]);
}
let configModels = this.modelDefines.get(categoryModel) || this.modelDefines.get(this.modelParent.get(categoryModel));
if (!configModels || configModels.fields.length === 0) {
console.log(`配置文件${oriFilename}指定的category文件模型未定义模型,请检查配置`);
return;
}
for (let i = 0; i < configModels.fields.length; i++) {
let fid = fields.indexOf(configModels.fields[i]);
if (configModels.fields[i] !== fields[i]) {
console.log(`配置文件${oriFilename}第${i}列数据字段${fields[i]}和模型第${i}列数据字段${configModels.fields[i]}不匹配,请检查配置`);
return;
}
if (types[fid] !== configModels.types[i]) {
console.log(`配置文件${oriFilename}第${i}列数据字段${fields[i]}类型${types[fid]}和模型第${i}列数据字段类型${configModels.types[i]}不匹配,请检查配置`);
return;
}
}
let str = `{\r\n`;
str += `\t\"fieldData\" : [`;
for (let i = 0; i < datas.length; i++) {
let rowDatas = datas[i];
let parseDatas = [];
for (let j = 0; j < fields.length; j++) {
let typeRules = types[j].split(',');
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_SERVER) !== -1 && this.publishType == 2) {
continue;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_CLIENT) !== -1 && this.publishType == 1) {
continue;
}
let rcType = typeRules[0];
if (rcType === constants_1.FIELD_TYPE.UNEXPORT) {
continue;
}
// 字段值合法性校验
let value = this.paresFieldValue(rowDatas[j], rcType);
if (null == value && !rcType.endsWith('?')) {
console.log(`配置文件${oriFilename}第${i + 1 + constants_1.CONFIG_SKIP_ROW}行字段${fields[j]}值类型${rcType}, 异常配置为`, JSON.stringify(rowDatas[j]));
return;
}
parseDatas.push(value);
}
str += `${JSON.stringify(parseDatas).trim()}${datas.length - 1 === i ? '' : ','}`;
}
str += `],\r\n`;
str += `\t\"fieldMap\" : {`;
const repeateCheckObj = {};
for (let i = 0; i < datas.length; i++) {
let noKey = true;
let dotstr = ',';
if (i === datas.length - 1) {
dotstr = '';
}
for (let j = 0; j < fields.length; j++) {
let typeRules = types[j].split(',');
let rcType = typeRules[0];
if (rcType === constants_1.FIELD_TYPE.UNEXPORT) {
// 不倒出字段
continue;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_SERVER) !== -1 && this.publishType == 2) {
// 服务器专用字段
continue;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_CLIENT) !== -1 && this.publishType == 1) {
// 客户端专用字段
continue;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.INDEX) !== -1) {
let key = `${fields[j].trim()}_${datas[i][j].toString().trim()}`;
str += `\"${key}\":${i}${dotstr}`;
if (repeateCheckObj[key]) {
console.error(`配置文件index索引字段字段key=${key}重复, row=${i} col=${j}, 请检查配置`);
return;
}
repeateCheckObj[key] = true;
noKey = false;
}
else if (typeRules.indexOf(constants_1.FIELD_RULE.INDEXS) !== -1) {
let unionString = typeRules[typeRules.indexOf(constants_1.FIELD_RULE.INDEXS) + 1];
if (!unionString) {
console.error(`配置文件联合索引未配置索引字段, 请检查配置`);
return;
}
let unionKey = '';
let unions = unionString.split('|');
unions.push(fields[j].trim());
unions = [...new Set(unions)];
unions.forEach((uField, idx) => {
let uIndex = fields.indexOf(uField);
if (uIndex < 0) {
console.error(`配置文件联合索引字段${uField}不存在, 请检查配置`);
return;
}
let dot = idx === unions.length - 1 ? '' : '_';
unionKey += `${datas[i][uIndex]}${dot}`;
});
unionKey = `${fields[j].trim()}_${unionKey}`;
if (repeateCheckObj[unionKey]) {
console.error(`配置文件联合索引字段字段key=${unionKey}重复, row=${i} col=${j}, 请检查配置`);
return;
}
repeateCheckObj[unionKey] = true;
str += `\"${unionKey}\":${i}${dotstr}`;
noKey = false;
}
else if (typeRules.indexOf(constants_1.FIELD_RULE.UNIQUE) !== -1) {
let key = `${fields[j].trim()}_${datas[i][j].toString().trim()}`;
if (repeateCheckObj[key]) {
console.error(`配置文件unique字段key=${key}重复, row=${i} col=${j}, 请检查配置`);
return;
}
repeateCheckObj[key] = true;
noKey = false;
}
}
if (noKey) {
str += `IDX${i}:${i}${dotstr}`;
}
}
str += `}\r\n`;
str += `}\r\n`;
return str;
}
/**
* 生成数据JSON配置
* @param oriFilename 文件名称
* @param fields 字段
* @param types 字段类型
* @param datas 数据
*/
genDataConstConfigBuffer(oriFilename, fields, types, datas) {
if (!datas || datas.length === 0) {
console.log(`配置文件${oriFilename}数据为空,请检查配置`);
return;
}
let str = `{\r\n`;
str += `\t\"fieldData\" : [`;
for (let i = 0; i < datas.length; i++) {
let rowDatas = datas[i];
let parseDatas = [];
for (let j = 0; j < fields.length; j++) {
let typeRules = types[j].split(',');
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_SERVER) !== -1 && this.publishType == 2) {
continue;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_CLIENT) !== -1 && this.publishType == 1) {
continue;
}
let rcType = typeRules[0];
if (rcType === constants_1.FIELD_TYPE.UNEXPORT) {
continue;
}
// 字段值合法性校验
let value = this.paresFieldValue(rowDatas[j], rcType);
if (null == value && !rcType.endsWith('?')) {
console.log(`配置文件${oriFilename}第${i + 1 + constants_1.CONFIG_SKIP_ROW}行字段${fields[j]}值类型${rcType}, 异常配置为`, JSON.stringify(rowDatas[j]));
return;
}
parseDatas.push(value);
}
str += `${JSON.stringify(parseDatas).trim()}${datas.length - 1 === i ? '' : ','}`;
}
str += `],\r\n`;
str += `\t\"fieldMap\" : {`;
const repeateCheckObj = {};
for (let i = 0; i < datas.length; i++) {
let dotstr = ',';
if (i === datas.length - 1) {
dotstr = '';
}
for (let j = 0; j < fields.length; j++) {
let typeRules = types[j].split(',');
let rcType = typeRules[0];
if (rcType === constants_1.FIELD_TYPE.UNEXPORT) {
// 不倒出字段
continue;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_SERVER) !== -1 && this.publishType == 2) {
// 服务器专用字段
continue;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.ONLY_CLIENT) !== -1 && this.publishType == 1) {
// 客户端专用字段
continue;
}
if (typeRules.indexOf(constants_1.FIELD_RULE.KEY) !== -1) {
let key = `${datas[i][j].toString().trim()}`;
str += `\"${key}\":${i}${dotstr}`;
if (repeateCheckObj[key]) {
console.error(`配置文件${oriFilename}key索引字段字段${fields[j]} value=${key}重复, row=${i} col=${j}, 请检查配置`);
return;
}
repeateCheckObj[key] = true;
}
}
}
str += `}\r\n`;
str += `}\r\n`;
return str;
}
/**
* 生成常量JSON配置
* @param oriFilename 文件名称
* @param fields 字段
* @param types 字段类型
* @param datas 数据
*/
genConstConfigBuffer(oriFilename, fields, types, datas, descs) {
let str = `{\r\n`;
for (let i = 0; i < datas.length; i++) {
let rowArray = datas[i];
if (rowArray.length < 4) {
console.log(`配置文件${oriFilename}第${i + 1 + constants_1.CONFIG_SKIP_ROW}行数据异常, 列数不足4`, JSON.stringify(rowArray));
return;
}
const keyCst = rowArray[0].toString().trim();
let value = this.paresFieldValue(rowArray[1], rowArray[2]);
if (null == value && !rowArray[2].endsWith('?')) {
console.log(`配置文件${oriFilename}第${i + 1 + constants_1.CONFIG_SKIP_ROW}行字段${keyCst}值类型${rowArray[2]}, 异常配置为`, JSON.stringify(rowArray[1]));
return;
}
if (typeof value === 'object') {
value = JSON.stringify(value);
}
if (rowArray[2] == constants_1.FIELD_TYPE.STRING) {
str += `\t\"${keyCst}\":\"${value}\"${datas.length - 1 === i ? '' : ','}\r\n`;
}
else {
str += `\t\"${keyCst}\":${value}${datas.length - 1 === i ? '' : ','}\r\n`;
}
}
str += `}\r\n`;
return str;
}
/**
* 生成语言JSON配置
* @param oriFilename 文件名称
* @param fields 字段
* @param types 字段类型
* @param datas 数据
*/
genLangConfigBuffer(oriFilename, fields, types, datas, descs) {
for (let i = 1; i < fields.length; i++) {
let lang = fields[i];
let str = `{\r\n`;
for (let j = 0; j < datas.length; j++) {
let rowArray = datas[j];
if (rowArray.length < 2) {
console.log(`配置文件${oriFilename}第${i + 1 + constants_1.CONFIG_SKIP_ROW}行数据异常, 列数不足4`, JSON.stringify(rowArray));
return;
}
const keyCst = rowArray[0].toString().trim();
rowArray[i] = rowArray[i] || '';
if (j === datas.length - 1) {
str += `\t\"${keyCst}\":\"${rowArray[i].toString().trim()}\"\r\n`;
}
else {
str += `\t\"${keyCst}\":\"${rowArray[i].toString().trim()}\",\r\n`;
}
}
str += `}\r\n`;
if (str) {
let filename1 = `${this.getLanOutDir(lang)}/${oriFilename}-${lang}.json`;
const pathInfo = path.parse(filename1);
this.mkdirsSync(pathInfo.dir);
fs.writeFileSync(filename1, str);
}
}
}
genErrorConfigBuffer(oriFilename, fields, types, datas, descs) {
for (let i = 2; i < fields.length; i++) {
let lang = fields[i];
let str = `{\r\n`;
for (let j = 0; j < datas.length; j++) {
let rowArray = datas[j];
if (rowArray.length < 2) {
console.log(`配置文件${oriFilename}第${i + 1 + constants_1.CONFIG_SKIP_ROW}行数据异常, 列数不足4`, JSON.stringify(rowArray));
return;
}
const keyCst = rowArray[0].toString().trim();
rowArray[i] = rowArray[i] || '';
if (j === datas.length - 1) {
str += `\t\"${keyCst}\":\"${rowArray[i].toString().trim()}\"\r\n`;
}
else {
str += `\t\"${keyCst}\":\"${rowArray[i].toString().trim()}\",\r\n`;
}
}
str += `}\r\n`;
if (str) {
let filename1 = `${this.getLanOutDir(lang)}/${oriFilename}-${lang}.json`;
const pathInfo = path.parse(filename1);
this.mkdirsSync(pathInfo.dir);
fs.writeFileSync(filename1, str);
}
}
}
}
exports.ExportServerTS = ExportServerTS;
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZXhwb3J0U2VydmVyVFMuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi9saWIvZXhwb3J0U2VydmVyVFMudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7O0FBQUEsNkJBQTZCO0FBQzdCLHlCQUF5QjtBQUN6Qiw2Q0FBMEM7QUFDMUMsMkNBQW1GO0FBRW5GLE1BQU0sVUFBVSxHQUFRLEVBQUUsQ0FBQztBQUMzQixVQUFVLENBQUMsc0JBQVUsQ0FBQyxLQUFLLENBQUMsR0FBRyxVQUFVLENBQUM7QUFDMUMsVUFBVSxDQUFDLHNCQUFVLENBQUMsWUFBWSxDQUFDLEdBQUcsV0FBVyxDQUFDO0FBQ2xELFVBQVUsQ0FBQyxzQkFBVSxDQUFDLEdBQUcsQ0FBQyxHQUFHLFVBQVUsQ0FBQztBQUN4QyxVQUFVLENBQUMsc0JBQVUsQ0FBQyxVQUFVLENBQUMsR0FBRyxXQUFXLENBQUM7QUFDaEQsVUFBVSxDQUFDLHNCQUFVLENBQUMsTUFBTSxDQUFDLEdBQUcsVUFBVSxDQUFDO0FBQzNDLFVBQVUsQ0FBQyxzQkFBVSxDQUFDLGFBQWEsQ0FBQyxHQUFHLFdBQVcsQ0FBQztBQUNuRCxVQUFVLENBQUMsc0JBQVUsQ0FBQyxLQUFLLENBQUMsR0FBRyxPQUFPLENBQUM7QUFFdkMsTUFBYSxjQUFlLFNBQVEsdUJBQVU7SUFDaEMsZUFBZTtRQUNyQixJQUFJLEdBQUcsR0FBRztvQ0FDa0IsQ0FBQTtRQUM1QixJQUFJLElBQUksR0FBRyxNQUFNLENBQUMsSUFBSSxDQUFDLElBQUksQ0FBQyxZQUFZLENBQUMsQ0FBQztRQUMxQyxLQUFLLElBQUksSUFBSSxJQUFJLElBQUksRUFBRTtZQUNuQixHQUFHLElBQUksS0FBSyxJQUFJLE9BQU8sSUFBSSxDQUFDLFlBQVksQ0FBQyxJQUFJLENBQUMsU0FBUyxDQUFBO1NBQzFEO1FBQ0QsR0FBRyxJQUFJLE9BQU8sQ0FBQTtRQUNkLEdBQUcsSUFBSSxNQUFNLENBQUE7UUFDYixHQUFHLElBQUksbUNBQW1DLENBQUE7UUFF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