6a-spec-install 1.0.1-dev.2 → 1.0.1-dev.20
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.6aspec/rules/6A/6A_code_implementation_sop.md +65 -0
- package/.6aspec/rules/6A/6A_import_model_table_sop.md +96 -0
- package/.6aspec/rules/6A/6A_init_event_list_sop.md +62 -0
- package/.6aspec/rules/6A/6A_init_map_sop.md +79 -0
- package/.6aspec/rules/6A/6A_model_sop.md +139 -0
- package/.6aspec/rules/6A/6A_new_feature_sop.md +174 -0
- package/.6aspec/rules/6A/6A_task_sop.md +137 -0
- package/{.cursor → .6aspec}/rules/6A/6A_visual_logic_sop.md +2 -2
- package/.6aspec/rules/biz/c_user_system_rule.md +240 -0
- package/.6aspec/script/create_entities_from_markdown.py +688 -0
- package/.claude/commands/6A/6A-execute-task.md +20 -0
- package/.claude/commands/6A/6A-import-model-table.md +8 -0
- package/.claude/commands/6A/6A-init.md +14 -0
- package/.claude/commands/6A/6A-model.md +11 -0
- package/.claude/commands/6A/6A-new.md +7 -0
- package/.claude/commands/6A/6A-task.md +7 -0
- package/.claude/commands/6A/6A-visual-logic.md +9 -0
- package/.cursor/commands/6A-execute-task.md +21 -0
- package/.cursor/commands/6A-import-model-table.md +9 -0
- package/.cursor/commands/6A-init.md +15 -0
- package/.cursor/commands/6A-model.md +7 -3
- package/.cursor/commands/6A-new.md +1 -1
- package/.cursor/commands/6A-task.md +1 -1
- package/.cursor/commands/6A-visual-logic.md +1 -1
- package/lib/installer.js +96 -56
- package/package.json +3 -1
- package/.cursor/commands/6A-excel-table-gen.md +0 -9
- package/.cursor/commands/execute-task.md +0 -9
- package/.cursor/rules/6A/6A_export_table_to_excel_sop.md +0 -133
- package/.cursor/rules/6A/6A_model_sop.md +0 -91
- package/.cursor/rules/6A/6A_new_feature.md +0 -255
- package/.cursor/rules/6A/6A_new_feature_sop.md +0 -168
- package/.cursor/rules/6A/6A_task_sop.md +0 -106
- package/.cursor/rules/biz/event-list.md +0 -9742
- package/.cursor/rules/biz/functional-capability-Map.md +0 -12
- package/.cursor/script/md_to_excel.py +0 -376
- /package/{.cursor → .6aspec}/rules/biz/api_rule.md +0 -0
- /package/{.cursor → .6aspec}/rules/biz/background_job_rule.md +0 -0
- /package/{.cursor → .6aspec}/rules/biz/code.md +0 -0
- /package/{.cursor → .6aspec}/rules/biz/event_subscriber_rule.md +0 -0
- /package/{.cursor → .6aspec}/rules/biz/project-structure.md +0 -0
- /package/{.cursor → .6aspec}/rules/biz/scheduled_job_rule.md +0 -0
|
@@ -1,376 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env python
|
|
2
|
-
# -*- coding: utf-8 -*-
|
|
3
|
-
"""
|
|
4
|
-
Markdown文档转Excel工具
|
|
5
|
-
从Markdown文档中提取表结构并生成Excel文件
|
|
6
|
-
"""
|
|
7
|
-
|
|
8
|
-
import re
|
|
9
|
-
import json
|
|
10
|
-
import openpyxl
|
|
11
|
-
from openpyxl.styles import Font, PatternFill, Alignment, Border, Side
|
|
12
|
-
import sys
|
|
13
|
-
import os
|
|
14
|
-
from typing import List, Dict
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
def extract_table_schemas(markdown_content: str) -> List[Dict]:
|
|
18
|
-
"""
|
|
19
|
-
从Markdown文档中提取表结构设计部分的所有表格
|
|
20
|
-
|
|
21
|
-
Args:
|
|
22
|
-
markdown_content: Markdown文档内容
|
|
23
|
-
|
|
24
|
-
Returns:
|
|
25
|
-
List[Dict]: 表结构列表
|
|
26
|
-
"""
|
|
27
|
-
result = []
|
|
28
|
-
|
|
29
|
-
# 查找所有以 "##### 数字. 表名" 开头的表定义
|
|
30
|
-
lines = markdown_content.split('\n')
|
|
31
|
-
|
|
32
|
-
i = 0
|
|
33
|
-
while i < len(lines):
|
|
34
|
-
line = lines[i].strip()
|
|
35
|
-
|
|
36
|
-
# 查找表标题行,例如: ##### 1. 服务评价单表 (rental_ServiceEvaluation)
|
|
37
|
-
if re.match(r'^#{5}\s+\d+\.\s+', line):
|
|
38
|
-
# 提取表名
|
|
39
|
-
match = re.search(r'#{5}\s+\d+\.\s+(.+?)\s+\((.+?)\)', line)
|
|
40
|
-
if match:
|
|
41
|
-
table_name_cn = match.group(1).strip()
|
|
42
|
-
table_name_en = match.group(2).strip()
|
|
43
|
-
|
|
44
|
-
table_info = {
|
|
45
|
-
'table_name_cn': table_name_cn,
|
|
46
|
-
'table_name_en': table_name_en,
|
|
47
|
-
'description': '',
|
|
48
|
-
'fields': []
|
|
49
|
-
}
|
|
50
|
-
|
|
51
|
-
# 继续查找后续内容
|
|
52
|
-
i += 1
|
|
53
|
-
|
|
54
|
-
# 查找表信息(第一个表格:表中文名称 | 表英文名称)
|
|
55
|
-
while i < len(lines):
|
|
56
|
-
current_line = lines[i].strip()
|
|
57
|
-
|
|
58
|
-
# 找到表信息表格
|
|
59
|
-
if '| 表中文名称 | 表英文名称 |' in current_line or '| 表英文名称 | rental_' in current_line:
|
|
60
|
-
# 跳过表头和分隔线
|
|
61
|
-
i += 1
|
|
62
|
-
if i < len(lines) and '|' in lines[i] and '-' in lines[i]:
|
|
63
|
-
i += 1
|
|
64
|
-
|
|
65
|
-
# 读取表英文名称行
|
|
66
|
-
if i < len(lines) and '|' in lines[i]:
|
|
67
|
-
i += 1
|
|
68
|
-
|
|
69
|
-
# 读取说明行
|
|
70
|
-
if i < len(lines) and '|' in lines[i]:
|
|
71
|
-
parts = [p.strip() for p in lines[i].split('|')]
|
|
72
|
-
if len(parts) >= 3:
|
|
73
|
-
table_info['description'] = parts[2]
|
|
74
|
-
i += 1
|
|
75
|
-
break
|
|
76
|
-
|
|
77
|
-
i += 1
|
|
78
|
-
if i >= len(lines) or lines[i].startswith('#'):
|
|
79
|
-
break
|
|
80
|
-
|
|
81
|
-
# 查找字段信息表格
|
|
82
|
-
while i < len(lines):
|
|
83
|
-
current_line = lines[i].strip()
|
|
84
|
-
|
|
85
|
-
# 找到字段表格的表头
|
|
86
|
-
if '| 字段中文名称 | 字段英文名称 | 字段类型 | 长度 | 是否必填 | 字段说明 |' in current_line:
|
|
87
|
-
# 跳过表头
|
|
88
|
-
i += 1
|
|
89
|
-
# 跳过分隔线
|
|
90
|
-
if i < len(lines) and '|' in lines[i] and '-' in lines[i]:
|
|
91
|
-
i += 1
|
|
92
|
-
|
|
93
|
-
# 读取所有字段行
|
|
94
|
-
while i < len(lines):
|
|
95
|
-
field_line = lines[i].strip()
|
|
96
|
-
|
|
97
|
-
# 如果遇到空行或新的标题,停止读取字段
|
|
98
|
-
if not field_line or field_line.startswith('#'):
|
|
99
|
-
break
|
|
100
|
-
|
|
101
|
-
# 解析字段行
|
|
102
|
-
if field_line.startswith('|') and field_line.endswith('|'):
|
|
103
|
-
parts = [p.strip() for p in field_line.split('|')[1:-1]]
|
|
104
|
-
|
|
105
|
-
if len(parts) == 6:
|
|
106
|
-
field_info = {
|
|
107
|
-
'field_name_cn': parts[0],
|
|
108
|
-
'field_name_en': parts[1],
|
|
109
|
-
'field_type': parts[2],
|
|
110
|
-
'length': parts[3],
|
|
111
|
-
'is_required': parts[4],
|
|
112
|
-
'description': parts[5]
|
|
113
|
-
}
|
|
114
|
-
table_info['fields'].append(field_info)
|
|
115
|
-
|
|
116
|
-
i += 1
|
|
117
|
-
|
|
118
|
-
break
|
|
119
|
-
|
|
120
|
-
i += 1
|
|
121
|
-
# 如果遇到下一个表定义,停止查找
|
|
122
|
-
if i >= len(lines) or re.match(r'^#{5}\s+\d+\.\s+', lines[i]):
|
|
123
|
-
break
|
|
124
|
-
|
|
125
|
-
result.append(table_info)
|
|
126
|
-
|
|
127
|
-
i += 1
|
|
128
|
-
|
|
129
|
-
return result
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
def convert_table_schema_format(table_data: Dict) -> Dict:
|
|
133
|
-
"""
|
|
134
|
-
将表结构格式转换为Excel生成函数期望的格式
|
|
135
|
-
|
|
136
|
-
Args:
|
|
137
|
-
table_data: 单个表的字典数据
|
|
138
|
-
|
|
139
|
-
Returns:
|
|
140
|
-
dict: 转换后的字典格式
|
|
141
|
-
"""
|
|
142
|
-
converted = {
|
|
143
|
-
'表中文名': table_data.get('table_name_cn', ''),
|
|
144
|
-
'表英文名': table_data.get('table_name_en', ''),
|
|
145
|
-
'说明': table_data.get('description', ''),
|
|
146
|
-
'字段列表': []
|
|
147
|
-
}
|
|
148
|
-
|
|
149
|
-
# 转换字段格式
|
|
150
|
-
for field in table_data.get('fields', []):
|
|
151
|
-
converted_field = {
|
|
152
|
-
'字段中文名': field.get('field_name_cn', ''),
|
|
153
|
-
'字段英文名': field.get('field_name_en', ''),
|
|
154
|
-
'字段类型': field.get('field_type', ''),
|
|
155
|
-
'长度': field.get('length', ''),
|
|
156
|
-
'是否必填': field.get('is_required', ''),
|
|
157
|
-
'字段说明': field.get('description', '')
|
|
158
|
-
}
|
|
159
|
-
converted['字段列表'].append(converted_field)
|
|
160
|
-
|
|
161
|
-
return converted
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
def create_excel_from_json(json_data: Dict, output_file: str) -> str:
|
|
165
|
-
"""
|
|
166
|
-
根据JSON数据生成Excel文件
|
|
167
|
-
|
|
168
|
-
Args:
|
|
169
|
-
json_data: 字典,包含表结构信息
|
|
170
|
-
output_file: 输出的Excel文件名
|
|
171
|
-
|
|
172
|
-
Returns:
|
|
173
|
-
str: 生成的Excel文件路径
|
|
174
|
-
"""
|
|
175
|
-
data = json_data
|
|
176
|
-
|
|
177
|
-
# 创建工作簿
|
|
178
|
-
wb = openpyxl.Workbook()
|
|
179
|
-
ws = wb.active
|
|
180
|
-
ws.title = "表结构设计"
|
|
181
|
-
|
|
182
|
-
# 定义样式
|
|
183
|
-
header_fill = PatternFill(start_color="D3D3D3", end_color="D3D3D3", fill_type="solid")
|
|
184
|
-
header_font = Font(bold=True, size=11)
|
|
185
|
-
border = Border(
|
|
186
|
-
left=Side(style='thin'),
|
|
187
|
-
right=Side(style='thin'),
|
|
188
|
-
top=Side(style='thin'),
|
|
189
|
-
bottom=Side(style='thin')
|
|
190
|
-
)
|
|
191
|
-
center_alignment = Alignment(horizontal='center', vertical='center')
|
|
192
|
-
left_alignment = Alignment(horizontal='left', vertical='center', wrap_text=True)
|
|
193
|
-
|
|
194
|
-
# 第一部分:表基本信息(前3行)
|
|
195
|
-
# 第1行
|
|
196
|
-
ws['A1'] = '表中文名'
|
|
197
|
-
ws['A1'].fill = header_fill
|
|
198
|
-
ws['A1'].font = header_font
|
|
199
|
-
ws['A1'].border = border
|
|
200
|
-
ws['A1'].alignment = center_alignment
|
|
201
|
-
|
|
202
|
-
ws.merge_cells('B1:F1')
|
|
203
|
-
ws['B1'] = data.get('表中文名', '')
|
|
204
|
-
ws['B1'].border = border
|
|
205
|
-
ws['B1'].alignment = left_alignment
|
|
206
|
-
|
|
207
|
-
# 第2行
|
|
208
|
-
ws['A2'] = '表英文名'
|
|
209
|
-
ws['A2'].fill = header_fill
|
|
210
|
-
ws['A2'].font = header_font
|
|
211
|
-
ws['A2'].border = border
|
|
212
|
-
ws['A2'].alignment = center_alignment
|
|
213
|
-
|
|
214
|
-
ws.merge_cells('B2:F2')
|
|
215
|
-
ws['B2'] = data.get('表英文名', '')
|
|
216
|
-
ws['B2'].border = border
|
|
217
|
-
ws['B2'].alignment = left_alignment
|
|
218
|
-
|
|
219
|
-
# 第3行
|
|
220
|
-
ws['A3'] = '说明'
|
|
221
|
-
ws['A3'].fill = header_fill
|
|
222
|
-
ws['A3'].font = header_font
|
|
223
|
-
ws['A3'].border = border
|
|
224
|
-
ws['A3'].alignment = center_alignment
|
|
225
|
-
|
|
226
|
-
ws.merge_cells('B3:F3')
|
|
227
|
-
ws['B3'] = data.get('说明', '')
|
|
228
|
-
ws['B3'].border = border
|
|
229
|
-
ws['B3'].alignment = left_alignment
|
|
230
|
-
|
|
231
|
-
# 第二部分:字段详情(从第4行开始)
|
|
232
|
-
# 第4行:字段表头
|
|
233
|
-
headers = ['字段中文名', '字段英文名', '字段类型', '长度', '是否必填', '字段说明']
|
|
234
|
-
for col_idx, header in enumerate(headers, start=1):
|
|
235
|
-
cell = ws.cell(row=4, column=col_idx)
|
|
236
|
-
cell.value = header
|
|
237
|
-
cell.fill = header_fill
|
|
238
|
-
cell.font = header_font
|
|
239
|
-
cell.border = border
|
|
240
|
-
cell.alignment = center_alignment
|
|
241
|
-
|
|
242
|
-
# 第5行开始:字段数据
|
|
243
|
-
fields = data.get('字段列表', [])
|
|
244
|
-
for row_idx, field in enumerate(fields, start=5):
|
|
245
|
-
# 字段中文名
|
|
246
|
-
cell = ws.cell(row=row_idx, column=1)
|
|
247
|
-
cell.value = field.get('字段中文名', '')
|
|
248
|
-
cell.border = border
|
|
249
|
-
cell.alignment = left_alignment
|
|
250
|
-
|
|
251
|
-
# 字段英文名
|
|
252
|
-
cell = ws.cell(row=row_idx, column=2)
|
|
253
|
-
cell.value = field.get('字段英文名', '')
|
|
254
|
-
cell.border = border
|
|
255
|
-
cell.alignment = left_alignment
|
|
256
|
-
|
|
257
|
-
# 字段类型
|
|
258
|
-
cell = ws.cell(row=row_idx, column=3)
|
|
259
|
-
cell.value = field.get('字段类型', '')
|
|
260
|
-
cell.border = border
|
|
261
|
-
cell.alignment = center_alignment
|
|
262
|
-
|
|
263
|
-
# 长度
|
|
264
|
-
cell = ws.cell(row=row_idx, column=4)
|
|
265
|
-
cell.value = field.get('长度', '')
|
|
266
|
-
cell.border = border
|
|
267
|
-
cell.alignment = center_alignment
|
|
268
|
-
|
|
269
|
-
# 是否必填
|
|
270
|
-
cell = ws.cell(row=row_idx, column=5)
|
|
271
|
-
cell.value = field.get('是否必填', '')
|
|
272
|
-
cell.border = border
|
|
273
|
-
cell.alignment = center_alignment
|
|
274
|
-
|
|
275
|
-
# 字段说明
|
|
276
|
-
cell = ws.cell(row=row_idx, column=6)
|
|
277
|
-
cell.value = field.get('字段说明', '')
|
|
278
|
-
cell.border = border
|
|
279
|
-
cell.alignment = left_alignment
|
|
280
|
-
|
|
281
|
-
# 调整列宽
|
|
282
|
-
ws.column_dimensions['A'].width = 25
|
|
283
|
-
ws.column_dimensions['B'].width = 30
|
|
284
|
-
ws.column_dimensions['C'].width = 15
|
|
285
|
-
ws.column_dimensions['D'].width = 12
|
|
286
|
-
ws.column_dimensions['E'].width = 12
|
|
287
|
-
ws.column_dimensions['F'].width = 60
|
|
288
|
-
|
|
289
|
-
# 调整行高
|
|
290
|
-
for row in range(1, ws.max_row + 1):
|
|
291
|
-
ws.row_dimensions[row].height = 25
|
|
292
|
-
|
|
293
|
-
# 保存文件
|
|
294
|
-
wb.save(output_file)
|
|
295
|
-
print(f"✅ Excel文件已生成: {output_file}")
|
|
296
|
-
return output_file
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
def markdown_to_excel(markdown_file_path: str, output_dir: str = ".") -> List[str]:
|
|
300
|
-
"""
|
|
301
|
-
从Markdown文件生成Excel文件
|
|
302
|
-
|
|
303
|
-
Args:
|
|
304
|
-
markdown_file_path: Markdown文件路径
|
|
305
|
-
output_dir: 输出目录,默认为当前目录
|
|
306
|
-
|
|
307
|
-
Returns:
|
|
308
|
-
List[str]: 生成的Excel文件路径列表
|
|
309
|
-
"""
|
|
310
|
-
# 检查Markdown文件是否存在
|
|
311
|
-
if not os.path.exists(markdown_file_path):
|
|
312
|
-
raise FileNotFoundError(f"Markdown文件不存在: {markdown_file_path}")
|
|
313
|
-
|
|
314
|
-
# 读取Markdown文件
|
|
315
|
-
print(f"📖 读取Markdown文件: {markdown_file_path}")
|
|
316
|
-
with open(markdown_file_path, 'r', encoding='utf-8') as f:
|
|
317
|
-
markdown_content = f.read()
|
|
318
|
-
|
|
319
|
-
# 提取表结构
|
|
320
|
-
print("🔍 正在提取表结构...")
|
|
321
|
-
schemas = extract_table_schemas(markdown_content)
|
|
322
|
-
|
|
323
|
-
if not schemas:
|
|
324
|
-
raise ValueError("未提取到任何表结构,请检查Markdown格式")
|
|
325
|
-
|
|
326
|
-
print(f"✅ 共提取到 {len(schemas)} 个表结构")
|
|
327
|
-
|
|
328
|
-
# 创建输出目录(如果不存在)
|
|
329
|
-
if output_dir != "." and not os.path.exists(output_dir):
|
|
330
|
-
os.makedirs(output_dir)
|
|
331
|
-
print(f"📁 创建输出目录: {output_dir}")
|
|
332
|
-
|
|
333
|
-
# 为每个表生成Excel文件
|
|
334
|
-
generated_files = []
|
|
335
|
-
print(f"\n📊 开始生成Excel文件...")
|
|
336
|
-
|
|
337
|
-
for table in schemas:
|
|
338
|
-
# 转换格式
|
|
339
|
-
converted_data = convert_table_schema_format(table)
|
|
340
|
-
|
|
341
|
-
# 生成输出文件名
|
|
342
|
-
table_name_en = table.get('table_name_en', 'table')
|
|
343
|
-
output_file = os.path.join(output_dir, f"{table_name_en}.xlsx")
|
|
344
|
-
|
|
345
|
-
# 生成Excel
|
|
346
|
-
create_excel_from_json(converted_data, output_file)
|
|
347
|
-
generated_files.append(output_file)
|
|
348
|
-
|
|
349
|
-
return generated_files
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
if __name__ == "__main__":
|
|
353
|
-
if len(sys.argv) < 2:
|
|
354
|
-
print("使用方法: python md_to_excel.py <markdown_file_path> [output_dir]")
|
|
355
|
-
print("\n参数说明:")
|
|
356
|
-
print(" markdown_file_path: Markdown文档文件路径(必需)")
|
|
357
|
-
print(" output_dir: Excel文件输出目录(可选,默认为当前目录)")
|
|
358
|
-
print("\n示例:")
|
|
359
|
-
print(" python md_to_excel.py MODEL_服务评价.md .")
|
|
360
|
-
print(" python md_to_excel.py MODEL_服务评价.md ./excel_output")
|
|
361
|
-
sys.exit(1)
|
|
362
|
-
|
|
363
|
-
markdown_file_path = sys.argv[1]
|
|
364
|
-
output_dir = sys.argv[2] if len(sys.argv) > 2 else "."
|
|
365
|
-
|
|
366
|
-
try:
|
|
367
|
-
generated_files = markdown_to_excel(markdown_file_path, output_dir)
|
|
368
|
-
print(f"\n🎉 成功生成 {len(generated_files)} 个Excel文件:")
|
|
369
|
-
for file_path in generated_files:
|
|
370
|
-
print(f" - {file_path}")
|
|
371
|
-
except Exception as e:
|
|
372
|
-
print(f"❌ 错误: {e}")
|
|
373
|
-
import traceback
|
|
374
|
-
traceback.print_exc()
|
|
375
|
-
sys.exit(1)
|
|
376
|
-
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|