mirror of
https://github.com/tiennm99/serena.git
synced 2026-10-13 06:15:43 +00:00
Transfer comments from template when re-saving project.yml files
This commit is contained in:
1 parent
57423142fe
commit
a58a1c2f16
2 files changed
+52
-6
No files matched your search
@@ -29,7 +29,7 @@ from serena.constants import (
|
||||
SERENA_MANAGED_DIR_NAME,
|
||||
)
|
||||
from serena.util.inspection import determine_programming_language_composition
|
||||
from serena.util.yaml import load_yaml, save_yaml
|
||||
from serena.util.yaml import YamlCommentNormalisation, load_yaml, save_yaml, transfer_missing_yaml_comments
|
||||
from solidlsp.ls_config import Language
|
||||
|
||||
from ..analytics import RegisteredTokenCountEstimator
|
||||
@@ -174,6 +174,11 @@ class ProjectConfig(ToolInclusionDefinition, ModeSelectionDefinition, ToStringMi
|
||||
|
||||
SERENA_DEFAULT_PROJECT_FILE = "project.yml"
|
||||
FIELDS_WITHOUT_DEFAULTS = {"project_name", "languages"}
|
||||
YAML_COMMENT_NORMALISATION = YamlCommentNormalisation.LEADING
|
||||
"""
|
||||
the comment normalisation strategy to use when loading/saving project configuration files.
|
||||
The template file must match this configuration (i.e. it must use leading comments if this is set to LEADING).
|
||||
"""
|
||||
|
||||
def _tostring_includes(self) -> list[str]:
|
||||
return ["project_name"]
|
||||
@@ -265,7 +270,9 @@ class ProjectConfig(ToolInclusionDefinition, ModeSelectionDefinition, ToStringMi
|
||||
return os.path.join(SERENA_MANAGED_DIR_NAME, cls.SERENA_DEFAULT_PROJECT_FILE)
|
||||
|
||||
@classmethod
|
||||
def _load_yaml(cls, yml_path: str) -> tuple[CommentedMap, bool]:
|
||||
def _load_yaml(
|
||||
cls, yml_path: str, comment_normalisation: YamlCommentNormalisation = YamlCommentNormalisation.NONE
|
||||
) -> tuple[CommentedMap, bool]:
|
||||
"""
|
||||
Load the project configuration as a CommentedMap, preserving comments and ensuring
|
||||
completeness of the configuration by applying default values for missing fields
|
||||
@@ -276,7 +283,7 @@ class ProjectConfig(ToolInclusionDefinition, ModeSelectionDefinition, ToStringMi
|
||||
full project configuration and `was_complete` indicates whether the loaded configuration
|
||||
was complete (i.e., did not require any default values to be applied)
|
||||
"""
|
||||
data = load_yaml(yml_path)
|
||||
data = load_yaml(yml_path, comment_normalisation=comment_normalisation)
|
||||
|
||||
# apply defaults
|
||||
was_complete = True
|
||||
@@ -379,9 +386,13 @@ class ProjectConfig(ToolInclusionDefinition, ModeSelectionDefinition, ToStringMi
|
||||
log.info("Saving updated project configuration to %s", config_path)
|
||||
|
||||
# load original commented map and update it with current values
|
||||
config_with_comments, _ = self._load_yaml(config_path)
|
||||
config_with_comments, _ = self._load_yaml(config_path, self.YAML_COMMENT_NORMALISATION)
|
||||
config_with_comments.update(self._to_yaml_dict())
|
||||
|
||||
# transfer missing comments from the template file
|
||||
template_config, _ = self._load_yaml(PROJECT_TEMPLATE_FILE, self.YAML_COMMENT_NORMALISATION)
|
||||
transfer_missing_yaml_comments(template_config, config_with_comments, self.YAML_COMMENT_NORMALISATION)
|
||||
|
||||
save_yaml(config_path, config_with_comments)
|
||||
|
||||
|
||||
|
||||
+37
-2
@@ -31,8 +31,8 @@ DOC_COMMENT_INDEX_POST = 0
|
||||
DOC_COMMENT_INDEX_PRE = 1
|
||||
|
||||
# item comment indices: (post key, pre key, post value, pre value)
|
||||
ITEM_COMMENT_INDEX_BEFORE = 1 # Must be a list at this index
|
||||
ITEM_COMMENT_INDEX_AFTER = 2 # Not a list at this index
|
||||
ITEM_COMMENT_INDEX_BEFORE = 1 # (pre-key; must be a list at this index)
|
||||
ITEM_COMMENT_INDEX_AFTER = 2 # (post-value; typically no list at this index)
|
||||
|
||||
|
||||
def load_yaml(path: str, comment_normalisation: YamlCommentNormalisation = YamlCommentNormalisation.NONE) -> CommentedMap:
|
||||
@@ -81,3 +81,38 @@ def save_yaml(path: str, data: dict | CommentedMap, preserve_comments: bool = Tr
|
||||
os.makedirs(os.path.dirname(path), exist_ok=True)
|
||||
with open(path, "w", encoding=SERENA_FILE_ENCODING) as f:
|
||||
yaml.dump(data, f)
|
||||
|
||||
|
||||
def transfer_missing_yaml_comments_by_index(source: CommentedMap, target: CommentedMap, indices: list[int]) -> None:
|
||||
"""
|
||||
:param source: the source, from which to transfer missing comments
|
||||
:param target: the target map, whose comments will be updated
|
||||
:param indices: list of comment indices to transfer
|
||||
"""
|
||||
for key in target.keys():
|
||||
if key in source:
|
||||
source_comment = source.ca.items.get(key)
|
||||
if source_comment is None:
|
||||
continue
|
||||
target_comment = target.ca.items.get(key, [None, None, None, None])
|
||||
target.ca.items[key] = target_comment
|
||||
for index in indices:
|
||||
if target_comment[index] is None:
|
||||
target_comment[index] = source_comment[index]
|
||||
|
||||
|
||||
def transfer_missing_yaml_comments(source: CommentedMap, target: CommentedMap, comment_normalisation: YamlCommentNormalisation) -> None:
|
||||
"""
|
||||
Transfers missing comments from source to target YAML.
|
||||
|
||||
:param source: the source, from which to transfer missing comments
|
||||
:param target: the target map, whose comments will be updated.
|
||||
:param comment_normalisation: the comment normalisation to assume; if NONE, no comments are transferred
|
||||
"""
|
||||
match comment_normalisation:
|
||||
case YamlCommentNormalisation.NONE:
|
||||
pass
|
||||
case YamlCommentNormalisation.LEADING:
|
||||
transfer_missing_yaml_comments_by_index(source, target, [ITEM_COMMENT_INDEX_BEFORE])
|
||||
case _:
|
||||
raise ValueError(f"Unhandled comment normalisation: {comment_normalisation}")
|
||||
Reference in new issue
Block a user