提交 b7ce0d39 编写于 作者: L luxin

add keywords_must and keywords_forbid

上级 15539b61
......@@ -9,5 +9,7 @@
"export": [
"HelloWorld.json"
],
"title": "Hello World"
"title": "Hello World",
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -7,5 +7,7 @@
],
"export": [
"Intro.json"
]
],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -7,5 +7,7 @@
"children": [],
"export": [
"Standard.json"
]
],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -8,5 +8,7 @@
"children": [],
"export": [
"Lib.json"
]
],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -6,5 +6,7 @@
"children": [],
"export": [
"StandardQuery.json"
]
],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-e2aeed39b8d5434581176882e1838aa5",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -6,5 +6,7 @@
"children": [],
"export": [
"HelloWorld2.json"
]
],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -10,5 +10,7 @@
"export": [
"String.json",
"Variable.json"
]
],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -7,5 +7,7 @@
"export": [
"Format.json",
"StringFormatting.json"
]
],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -7,5 +7,7 @@
"children": [],
"export": [
"Calc.json"
]
],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -6,5 +6,7 @@
"children": [],
"export": [
"Guess.json"
]
],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -7,5 +7,7 @@
"export": [
"Guard.json",
"Switch.json"
]
],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -8,5 +8,7 @@
"children": [],
"export": [
"Loop.json"
]
],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -7,5 +7,7 @@
"children": [],
"export": [
"Comments.json"
]
],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-29be47be65ab45a1afa37ac2f2fdccc9",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -9,5 +9,7 @@
"扩展方法"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -7,5 +7,7 @@
"动态查找"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -8,5 +8,7 @@
"绑定运算符,:=:"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -14,5 +14,7 @@
"表达式方法体"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -20,5 +20,7 @@
"只读引用"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -9,5 +9,7 @@
"接口成员的默认实现"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -13,5 +13,7 @@
"非破坏性变化"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -17,5 +17,7 @@
"文件范围的 namespace"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-a0968f78949448b7948a6a207b1d3262",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-ce2781d4e5344ae7b5b82f34c5fcaed2",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -4,5 +4,7 @@
"Razor"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -4,5 +4,7 @@
".NET MVC"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -4,5 +4,7 @@
".NET Blazor"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -4,5 +4,7 @@
".NET Web API"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -4,5 +4,7 @@
".NET Minimal API"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-f788d93e151e4f0ca4f1f2f809da584a",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -4,5 +4,7 @@
"WinFrom开发"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -4,5 +4,7 @@
"WPF开发"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -4,5 +4,7 @@
"UWP开发"
],
"children": [],
"export": []
"export": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-7f969ccd70e048c99f8699b52cb1b744",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-119e018d28074c5f99ff3288a70f5e95",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-d779ab6fdf9d44f6ae18e0126665b9c0",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-f00a308a6b5e4dfdbda247f8ab924bde",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-4e9dd748b8b24a9180948c53d649cb86",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-e931f114f5f44d53878989744c1f5e99",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-96369fdba7914281b33829b2ad1272da",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-f977fca66f044f05964ae467369a9e2a",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"node_id": "csharp-abf1bc85e96749d5a8c6a6a32f95d804",
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
{
"tree_name": "csharp",
"keywords": [],
"node_id": "csharp-f436d19758c84b0bb741e51f1f839c24"
"node_id": "csharp-f436d19758c84b0bb741e51f1f839c24",
"keywords_must": [],
"keywords_forbid": []
}
\ No newline at end of file
......@@ -21,7 +21,9 @@
"dotnet new",
"程序入口"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -32,7 +34,9 @@
".NET",
"跨平台"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -42,7 +46,9 @@
".NET Standard",
".NET 实现"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -53,7 +59,9 @@
".NET 类库",
".NET 标准库"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -62,10 +70,14 @@
"keywords": [
".NET Standard 版本"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
}
]
],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -79,7 +91,9 @@
"keywords": [
"C# HelloWorld"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -91,7 +105,9 @@
"C# 整型",
"C# 基本类型"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -100,7 +116,9 @@
"keywords": [
"C# 字符串格式化"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -110,7 +128,9 @@
"C# 数字运算符",
"C# 四则运算"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -119,7 +139,9 @@
"keywords": [
".NET 基础类库"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -128,7 +150,9 @@
"keywords": [
"C# 分支判断"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -139,7 +163,9 @@
"foreach",
"斐波那契数列"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -149,10 +175,14 @@
"C# 编码规范",
"C# 注释"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
}
]
],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -171,7 +201,9 @@
"对象与集合初始化器",
"扩展方法"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -183,7 +215,9 @@
"命名参数和可选参数",
"动态查找"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -196,7 +230,9 @@
"支持null类型运算",
"绑定运算符,:=:"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -215,7 +251,9 @@
"在集合初始化器中使用扩展的Add方法",
"表达式方法体"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -240,7 +278,9 @@
"占位符",
"只读引用"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -254,7 +294,9 @@
"Switch 表达式",
"接口成员的默认实现"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -272,7 +314,9 @@
"不可变性",
"非破坏性变化"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -294,13 +338,19 @@
"CallerArgumentExpression",
"文件范围的 namespace"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
}
]
],
"keywords_must": [],
"keywords_forbid": []
}
}
]
],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -319,7 +369,9 @@
"keywords": [
"Razor"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -328,7 +380,9 @@
"keywords": [
".NET MVC"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -337,7 +391,9 @@
"keywords": [
".NET Blazor"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -346,7 +402,9 @@
"keywords": [
".NET Web API"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -355,10 +413,14 @@
"keywords": [
".NET Minimal API"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
}
]
],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -372,7 +434,9 @@
"keywords": [
"WinFrom开发"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -381,7 +445,9 @@
"keywords": [
"WPF开发"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -390,41 +456,55 @@
"keywords": [
"UWP开发"
],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
}
]
],
"keywords_must": [],
"keywords_forbid": []
}
},
{
"MAUI跨平台移动应用": {
"node_id": "csharp-119e018d28074c5f99ff3288a70f5e95",
"keywords": [],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
"机器学习应用": {
"node_id": "csharp-d779ab6fdf9d44f6ae18e0126665b9c0",
"keywords": [],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
"游戏应用": {
"node_id": "csharp-f00a308a6b5e4dfdbda247f8ab924bde",
"keywords": [],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
"云原生应用": {
"node_id": "csharp-4e9dd748b8b24a9180948c53d649cb86",
"keywords": [],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
}
]
],
"keywords_must": [],
"keywords_forbid": []
}
},
{
......@@ -436,19 +516,27 @@
" Dapr应用": {
"node_id": "csharp-96369fdba7914281b33829b2ad1272da",
"keywords": [],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
},
{
"Web进阶应用": {
"node_id": "csharp-f977fca66f044f05964ae467369a9e2a",
"keywords": [],
"children": []
"children": [],
"keywords_must": [],
"keywords_forbid": []
}
}
]
],
"keywords_must": [],
"keywords_forbid": []
}
}
]
],
"keywords_must": [],
"keywords_forbid": []
}
}
\ No newline at end of file
......@@ -2,10 +2,10 @@ import json
import logging
import os
import re
import subprocess
import sys
import uuid
import re
import git
id_set = set()
logger = logging.getLogger(__name__)
......@@ -14,15 +14,31 @@ handler = logging.StreamHandler(sys.stdout)
formatter = logging.Formatter('%(asctime)s - %(levelname)s - %(message)s')
handler.setFormatter(formatter)
logger.addHandler(handler)
repo = git.Repo(".")
def user_name():
return repo.config_reader().get_value("user", "name")
def search_author(author_dict, username):
for key in author_dict:
names = author_dict[key]
if username in names:
return key
return username
def user_name(md_file, author_dict):
ret = subprocess.Popen([
"git", "log", md_file
], stdout=subprocess.PIPE)
lines = list(map(lambda l: l.decode(), ret.stdout.readlines()))
author_lines = []
for line in lines:
if line.startswith('Author'):
author_lines.append(line.split(' ')[1])
author_nick_name = author_lines[-1]
return search_author(author_dict, author_nick_name)
def load_json(p):
with open(p, 'r') as f:
with open(p, 'r', encoding="utf-8") as f:
return json.loads(f.read())
......@@ -77,7 +93,18 @@ def check_export(base, cfg):
class TreeWalker:
def __init__(self, root, tree_name, title=None, log=None):
def __init__(
self, root,
tree_name,
title=None,
log=None,
authors=None,
enable_notebook=None,
ignore_keywords=False
):
self.ignore_keywords = ignore_keywords
self.authors = authors if authors else {}
self.enable_notebook = enable_notebook
self.name = tree_name
self.root = root
self.title = tree_name if title is None else title
......@@ -89,7 +116,9 @@ class TreeWalker:
root_node = {
"node_id": root["node_id"],
"keywords": root["keywords"],
"children": []
"children": [],
"keywords_must": root["keywords_must"],
"keywords_forbid": root["keywords_forbid"]
}
self.tree[root["tree_name"]] = root_node
self.load_levels(root_node)
......@@ -144,6 +173,8 @@ class TreeWalker:
"node_id": config["node_id"],
"keywords": config["keywords"],
"children": [],
"keywords_must": config["keywords_must"],
"keywords_forbid": config["keywords_forbid"]
}
}
......@@ -195,6 +226,8 @@ class TreeWalker:
"tree_name": self.name,
"keywords": [],
"node_id": self.gen_node_id(),
"keywords_must": [],
"keywords_forbid": []
}
dump_json(config_path, config, exist_ok=True, override=True)
else:
......@@ -224,7 +257,9 @@ class TreeWalker:
if not os.path.exists(config_path):
config = {
"node_id": self.gen_node_id(),
"keywords": []
"keywords": [],
"keywords_must": [],
"keywords_forbid": []
}
dump_json(config_path, config, exist_ok=True, override=True)
else:
......@@ -290,6 +325,8 @@ class TreeWalker:
"node_id": config["node_id"],
"keywords": config["keywords"],
"children": [],
"keywords_must": config["keywords_must"],
"keywords_forbid": config["keywords_forbid"]
}
}
return num, result
......@@ -301,7 +338,9 @@ class TreeWalker:
name: {
"node_id": config["node_id"],
"keywords": config["keywords"],
"children": config.get("children", [])
"children": config.get("children", []),
"keywords_must": config["keywords_must"],
"keywords_forbid": config["keywords_forbid"]
}
}
# if "children" in config:
......@@ -318,7 +357,8 @@ class TreeWalker:
continue
mfile = base + ".json"
meta_path = os.path.join(section_path, mfile)
self.ensure_exercises_meta(meta_path, source)
md_file = os.path.join(section_path, e)
self.ensure_exercises_meta(meta_path, source, md_file)
export = config.get("export", [])
if mfile not in export and self.name != "algorithm":
export.append(mfile)
......@@ -339,7 +379,7 @@ class TreeWalker:
else:
id_set.add(exercise["exercise_id"])
def ensure_exercises_meta(self, meta_path, source):
def ensure_exercises_meta(self, meta_path, source, md_file):
_, mfile = os.path.split(meta_path)
meta = None
if os.path.exists(meta_path):
......@@ -354,13 +394,14 @@ class TreeWalker:
if "source" not in meta:
meta["source"] = source
if "author" not in meta:
meta["author"] = user_name()
meta["author"] = user_name(md_file, self.authors)
if "type" not in meta:
meta["type"] = "code_options"
if meta is None:
meta = {
"type": "code_options",
"author": user_name(),
"author": user_name(md_file, self.authors),
"source": source,
"notebook_enable": self.default_notebook(),
"exercise_id": uuid.uuid4().hex
......@@ -368,12 +409,16 @@ class TreeWalker:
dump_json(meta_path, meta, True, True)
def default_notebook(self):
if self.enable_notebook is not None:
return self.enable_notebook
if self.name in ["python", "java", "c"]:
return True
else:
return False
def check_section_keywords(self, full_path):
if self.ignore_keywords:
return
config = self.ensure_section_config(full_path)
if not config.get("keywords", []):
self.logger.error(f"节点 [{full_path}] 的关键字为空,请修改配置文件写入关键字")
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册