소스 정보
- 저장소
- microwind/ai-skills
- 최근 소스 활동
- 2026년 3월 26일 14:58
- 감지된 SKILL.md 언어
- 중국어
- 스타
- 68
- 포크
- 17
설치 방법
기본적으로 소스를 먼저 확인하는 Prompt가 선택됩니다. 직접 명령으로 전환하거나 로컬 사본을 다운로드할 수도 있습니다.
소스 파일 검토
설치 여부를 결정하기 전에 SKILL.md와 SkillsMP에 표시된 보조 파일을 읽어 보세요.
메뉴
기본적으로 소스를 먼저 확인하는 Prompt가 선택됩니다. 직접 명령으로 전환하거나 로컬 사본을 다운로드할 수도 있습니다.
설치 여부를 결정하기 전에 SKILL.md와 SkillsMP에 표시된 보조 파일을 읽어 보세요.
Codex 또는 Claude로 설치 이 Prompt를 복사해 Codex, Claude 또는 다른 어시스턴트에 붙여 넣으면 Skill 페이지를 검토하고 설치를 진행할 수 있습니다.
직접 명령은 검토 Prompt를 거치지 않습니다. 실행하기 전에 소스를 확인하세요.
npx skills add https://github.com/microwind/ai-skills --skill yaml명령은 한 줄로 유지됩니다. 복사하기 전에 가로로 스크롤해 전체 내용을 확인하세요.
로컬 사본을 원하시나요? SkillsMP에서 현재 제공할 수 있는 파일을 다운로드하세요.
SOC 직업 분류 기준
SKILL.md 표시 중
| name | YAML验证器 |
| description | 当验证YAML文件、检查Kubernetes清单、调试Docker Compose或验证配置文件时,在部署前验证YAML。 |
| license | MIT |
YAML是DevOps中的核心技术 - Kubernetes、Docker Compose、GitHub Actions都使用YAML。无效的YAML会以神秘的错误消息静默破坏部署。
核心原则: 无效的YAML = 部署失败。在部署前验证。
始终:
触发短语:
问题:
YAML使用空格缩进,不能使用制表符
错误示例:
services:
web:
image: nginx:latest ← 使用了制表符
database:
image: postgres:13
解决方案:
- 使用2个或4个空格进行缩进
- 统一缩进风格
- 配置编辑器显示空白字符
问题:
特殊字符需要引号包围
错误示例:
password: my#password ← #会被当作注释
url: https://example.com/api/v1/resource?id=123&key=value
解决方案:
password: "my#password"
url: "https://example.com/api/v1/resource?id=123&key=value"
问题:
YAML会自动推断数据类型
错误示例:
port: "8080" ← 字符串而不是数字
enabled: "true" ← 字符串而不是布尔值
timeout: 30s ← 无效的时间格式
解决方案:
port: 8080
enabled: true
timeout: 30
import yaml
import json
import re
from typing import Dict, List, Any, Optional, Union
from dataclasses import dataclass
from enum import Enum
from pathlib import Path
import jsonschema
class ValidationLevel(Enum):
ERROR = "error"
WARNING = "warning"
INFO = "info"
@dataclass
class ValidationResult:
"""验证结果"""
level: ValidationLevel
message: str
line: Optional[int] = None
column: Optional[int] = None
suggestion: Optional[str] = None
@dataclass
class YAMLDocument:
"""YAML文档"""
content: Dict[str, Any]
line_map: Dict[int, str]
metadata: Dict[str, Any]
class YAMLValidator:
"""YAML验证器"""
():
.validation_rules = ._initialize_validation_rules()
.kubernetes_schemas = ._load_kubernetes_schemas()
.docker_compose_schema = ._load_docker_compose_schema()
() -> [ValidationResult]:
:
(file_path, , encoding=) f:
content = f.read()
lines = content.split()
Exception e:
[ValidationResult(
level=ValidationLevel.ERROR,
message=
)]
.validate_yaml_content(content, lines)
() -> [ValidationResult]:
results = []
syntax_results = ._validate_syntax(content, lines)
results.extend(syntax_results)
(r.level == ValidationLevel.ERROR r syntax_results):
results
:
yaml_data = yaml.safe_load(content)
structure_results = ._validate_structure(yaml_data, lines)
results.extend(structure_results)
semantic_results = ._validate_semantics(yaml_data, lines)
results.extend(semantic_results)
framework_results = ._validate_framework_specific(yaml_data, lines)
results.extend(framework_results)
yaml.YAMLError e:
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
line=(e, , ).line + (e, ) ,
column=(e, , ).column + (e, )
))
results
() -> [ValidationResult]:
results = []
lines:
lines = content.split()
line_num, line (lines, ):
line:
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
line=line_num,
column=line.find() + ,
suggestion=
))
line.strip():
leading_spaces = (line) - (line.lstrip())
leading_spaces % != :
results.append(ValidationResult(
level=ValidationLevel.WARNING,
message=,
line=line_num,
column=,
suggestion=
))
line line.strip().startswith():
parts = line.split(, )
(parts) == :
value = parts[].strip()
value (value.startswith() value.startswith()):
re.search(, value):
results.append(ValidationResult(
level=ValidationLevel.WARNING,
message=,
line=line_num,
column=(parts[]) + ,
suggestion=
))
results
() -> [ValidationResult]:
results = []
(yaml_data, ):
required_fields = .validation_rules.get(, [])
field required_fields:
field yaml_data:
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
type_rules = .validation_rules.get(, {})
._check_data_types(yaml_data, type_rules, , results)
structure_rules = .validation_rules.get(, {})
._check_structure(yaml_data, structure_rules, , results)
results
():
(data, ):
key, value data.items():
current_path = path key
key type_rules:
expected_type = type_rules[key]
._is_valid_type(value, expected_type):
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
(value, (, )):
._check_data_types(value, type_rules, current_path, results)
(data, ):
i, item (data):
current_path =
(item, (, )):
._check_data_types(item, type_rules, current_path, results)
() -> :
type_mapping = {
: ,
: ,
: (, ),
: ,
: ,
:
}
expected_python_type = type_mapping.get(expected_type)
expected_python_type:
(value, expected_python_type)
():
(data, ):
key, value data.items():
current_path = path key
key structure_rules:
rule = structure_rules[key]
(rule, ):
rule:
field rule[]:
field value:
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
rule (value, ):
(value) > rule[]:
results.append(ValidationResult(
level=ValidationLevel.WARNING,
message=,
suggestion=
))
(value, (, )):
._check_structure(value, structure_rules, current_path, results)
() -> [ValidationResult]:
results = []
semantic_rules = .validation_rules.get(, {})
._check_port_ranges(yaml_data, results)
._check_resource_limits(yaml_data, results)
._check_environment_variables(yaml_data, results)
._check_secrets(yaml_data, results)
results
():
(data, ):
key, value data.items():
current_path = path key
key.lower() (value, ):
( <= value <= ):
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
._check_port_ranges(value, results, current_path)
(data, ):
i, item (data):
current_path =
._check_port_ranges(item, results, current_path)
():
(data, ):
key, value data.items():
current_path = path key
key [, ] (value, ):
re.(, value):
results.append(ValidationResult(
level=ValidationLevel.WARNING,
message=,
suggestion=
))
key [] (value, ):
re.(, value):
results.append(ValidationResult(
level=ValidationLevel.WARNING,
message=,
suggestion=
))
._check_resource_limits(value, results, current_path)
(data, ):
i, item (data):
current_path =
._check_resource_limits(item, results, current_path)
():
(data, ):
key, value data.items():
current_path = path key
key.lower() [, , ] (value, ):
env_key, env_value value.items():
(env_value, ) env_value.startswith() env_value.endswith():
var_name = env_value[:-]
re.(, var_name):
results.append(ValidationResult(
level=ValidationLevel.WARNING,
message=,
suggestion=
))
._check_environment_variables(value, results, current_path)
(data, ):
i, item (data):
current_path =
._check_environment_variables(item, results, current_path)
():
sensitive_keys = [, , , , , ]
(data, ):
key, value data.items():
current_path = path key
(sensitive key.lower() sensitive sensitive_keys):
(value, ) (value) > :
results.append(ValidationResult(
level=ValidationLevel.WARNING,
message=,
suggestion=
))
._check_secrets(value, results, current_path)
(data, ):
i, item (data):
current_path =
._check_secrets(item, results, current_path)
() -> [ValidationResult]:
results = []
framework_type = ._detect_framework_type(yaml_data)
framework_type == :
results.extend(._validate_kubernetes(yaml_data))
framework_type == :
results.extend(._validate_docker_compose(yaml_data))
framework_type == :
results.extend(._validate_github_actions(yaml_data))
results
() -> :
(yaml_data, ):
keys = yaml_data.keys()
keys keys:
keys keys yaml_data.get(, {}):
keys keys:
() -> [ValidationResult]:
results = []
required_fields = [, , ]
field required_fields:
field yaml_data:
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
yaml_data (yaml_data[], ):
spec = yaml_data[]
spec spec.get(, {}):
spec spec[]:
template_labels = spec[][].get(, {})
selector_labels = spec[][]
key, value selector_labels.items():
template_labels.get(key) != value:
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
results
() -> [ValidationResult]:
results = []
yaml_data:
version = yaml_data[]
(version, ) version.startswith() version.startswith():
results.append(ValidationResult(
level=ValidationLevel.WARNING,
message=,
suggestion=
))
yaml_data (yaml_data[], ):
service_name, service_config yaml_data[].items():
(service_config, ):
service_config:
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
service_config (service_config[], ):
port service_config[]:
(port, ) port:
host_port, container_port = port.split(, )
:
host_port_num = (host_port)
( <= host_port_num <= ):
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
ValueError:
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
results
() -> [ValidationResult]:
results = []
required_fields = [, ]
field required_fields:
field yaml_data:
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
yaml_data (yaml_data[], ):
job_name, job_config yaml_data[].items():
(job_config, ):
job_config:
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
job_config:
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
(job_config[], ):
i, step (job_config[]):
(step, ) step step:
results.append(ValidationResult(
level=ValidationLevel.ERROR,
message=,
suggestion=
))
results
() -> [, ]:
{
: [],
: {},
: {},
: {}
}
() -> [, ]:
{}
() -> [, ]:
{}
() -> :
results:
report = []
by_level = {
ValidationLevel.ERROR: [],
ValidationLevel.WARNING: [],
ValidationLevel.INFO: []
}
result results:
by_level[result.level].append(result)
level [ValidationLevel.ERROR, ValidationLevel.WARNING, ValidationLevel.INFO]:
by_level[level]:
level_name = level.value.upper()
report.append()
result by_level[level]:
location =
result.line:
location =
result.column:
location +=
location +=
report.append()
result.suggestion:
report.append()
report.append()
error_count = (by_level[ValidationLevel.ERROR])
warning_count = (by_level[ValidationLevel.WARNING])
info_count = (by_level[ValidationLevel.INFO])
summary =
error_count > :
summary +=
warning_count > :
summary +=
:
summary +=
report.append(summary)
.join(report)
():
validator = YAMLValidator()
yaml_content =
results = validator.validate_yaml_content(yaml_content)
report = validator.generate_validation_report(results)
(report)
__name__ == :
main()
import yaml
from typing import Dict, Any, Optional
from pathlib import Path
class YAMLFormatter:
"""YAML格式化工具"""
def __init__(self):
self.indent_size = 2
self.sort_keys = False
self.default_flow_style = False
def format_yaml_file(self, file_path: str, output_path: Optional[str] = None) -> bool:
"""格式化YAML文件"""
try:
# 读取文件
with open(file_path, 'r', encoding='utf-8') as f:
content = f.read()
# 解析YAML
data = yaml.safe_load(content)
# 格式化输出
formatted_content = yaml.dump(
data,
indent=self.indent_size,
sort_keys=self.sort_keys,
default_flow_style=self.default_flow_style,
allow_unicode=True,
encoding=None
)
# 写入文件
output_file = output_path or file_path
(output_file, , encoding=) f:
f.write(formatted_content)
Exception e:
()
() -> :
:
(yaml_file, , encoding=) f:
data = yaml.safe_load(f)
(json_file, , encoding=) f:
json.dump(data, f, indent=, ensure_ascii=)
Exception e:
()
() -> :
:
(json_file, , encoding=) f:
data = json.load(f)
(yaml_file, , encoding=) f:
yaml.dump(data, f, indent=.indent_size, allow_unicode=)
Exception e:
()
():
formatter = YAMLFormatter()
success = formatter.format_yaml_file()
success:
()
formatter.yaml_to_json(, )
formatter.json_to_yaml(, )
__name__ == :
main()