Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use ruamel.yaml for YAMLEditable #302

Merged
merged 5 commits into from
Mar 9, 2022
Merged

Use ruamel.yaml for YAMLEditable #302

merged 5 commits into from
Mar 9, 2022

Conversation

skowalak
Copy link
Contributor

replace the YAMLEditable.to_yaml() method with ruamel serialization.
migrate some yaml formatting to the helpers module.

replace the YAMLEditable.to_yaml() method with ruamel serialization.
migrate some yaml formatting to the helpers module.
@skowalak
Copy link
Contributor Author

skowalak commented Feb 27, 2022

This PR references (#276)
The entire YAMLEditable.to_yaml() function is rewritten to use ruamel.yaml. This fixes the problem of having illegal yaml values such as unquoted @ chars at the beginning of the value.

What I have not done (yet):

  • Pretty printing still relies on helpers.convert_to_yaml(). I don't know if that level of indentation/alignment is possible with ruamel
  • Values will be inserted in the standard template. I don't know if this breaks some workflows involving custom new user templates (Make YAML template configurable #146).
  • Helper tests still use helpers.convert_to_yaml(). I will add some tests for the new methods when I have some more time.

Copy link
Owner

@lucc lucc left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I did a quick review of the helper code, just to give you an idea. I will of course do another one at least when you remove the draft state.

khard/helpers/__init__.py Outdated Show resolved Hide resolved
khard/helpers/__init__.py Outdated Show resolved Hide resolved
khard/helpers/__init__.py Outdated Show resolved Hide resolved
khard/helpers/__init__.py Outdated Show resolved Hide resolved
khard/helpers/__init__.py Outdated Show resolved Hide resolved
khard/helpers/__init__.py Outdated Show resolved Hide resolved
khard/helpers/__init__.py Outdated Show resolved Hide resolved
khard/helpers/__init__.py Show resolved Hide resolved
@lucc
Copy link
Owner

lucc commented Feb 27, 2022

I think you need not bother with #146 because that issue is still in the discussion and planing phase. You can also leave the pretty printing alone as we just reuse the yaml conversion functions. We do not officially claim that the output of the pretty printer is valid yaml. We can thing about changing the pretty printer in another PR.

Please try to run the tests and mypy (and maybe even pylint) locally because currently travis integration is broken. (I need help from @scheibler to fix this.)

If you could also write a test for #276 (the string with an @) that would be great!

@skowalak
Copy link
Contributor Author

skowalak commented Feb 28, 2022

I have a little difficulty running the tests. When I run python setup.py test hangs at the line

test_contact_is_found_if_name_matches (test.test_command_line_interface.AddEmail) ... 

I have to interrupt the testing via CTRL-C because the process' memory usage grows beyond what I consider normal (10GiB). Is that correct? Could my changes have caused this behaviour, if incorrect?

Edit:
Here is a more detailed log from unittest discover

  File "/home/skowalak/khard/test/test_command_line_interface.py", line 498, in test_contact_is_found_if_name_matches
    run_main("add-email", "--input-file", tmp.name)
  File "/home/skowalak/khard/test/test_command_line_interface.py", line 33, in run_main
    khard.main(args)
  File "/home/skowalak/khard/khard/khard.py", line 1120, in main
    add_email_subcommand(input_from_stdin_or_file,
  File "/home/skowalak/khard/khard/khard.py", line 682, in add_email_subcommand
    add_email_to_contact(name, address, abooks, skip_already_added)
  File "/home/skowalak/khard/khard/khard.py", line 478, in add_email_to_contact
    .format(selected_vcard))
KeyboardInterrupt

@skowalak skowalak marked this pull request as ready for review February 28, 2022 21:23
@skowalak
Copy link
Contributor Author

skowalak commented Mar 8, 2022

Hi @lucc ,
after some troubleshooting the abovementioned issue, I tried running the tests on the develop branch and had the exact same problem (tests.test_command_line_interface.AddEmail hangs in an infinite loop consuming more and more memory). I even tried it on a different computer running a different OS.

So apparently my changes did not break the tests.

Is there anything more I need to do before this PR can be merged?

Copy link
Owner

@lucc lucc left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You can skip the broken test like this:

diff --git a/test/test_command_line_interface.py b/test/test_command_line_interface.py
index cac683c..97b5ecf 100644
--- a/test/test_command_line_interface.py
+++ b/test/test_command_line_interface.py
@@ -480,6 +480,7 @@ class Merge(unittest.TestCase):
         self.assertEqual('contact2.vcf', second)


+@unittest.skip("reason for skipping")
 class AddEmail(unittest.TestCase):

     @TmpConfig(["contact1.vcf", "contact2.vcf"])

If I do that (temporarily!) the other tests all run fine.

I noticed that the birthday field and phone numbers as well as ZIP codes are now wrapped in quotes. Do you know if there is a way to only quote strings that are problematic (like the @ at the beginning)?

@@ -61,6 +62,121 @@ def get_random_uid() -> str:
return ''.join([random.choice(string.ascii_lowercase + string.digits)
for _ in range(36)])

def yaml_clean(value: Optional[Union[str, List, Dict[str, Any], Sequence]]
) -> Optional[Union[Sequence, List, str, Dict[str, Any],
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why did you add Sequence to the type signature? And if it is really needed you can leave out List I think.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I got a mypy error without the Sequence, meaning one of the properties of YAMLEditable that are used in to_yaml is of a Sequence type. I removed List though, thank you.


def yaml_dicts(
data: Optional[Dict[str, Any]],
defaults: Optional[Union[Dict[str, Any], List[str]]] = None
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For Optional[Union[...]] it is nicer to write Union[..., None].

}
template = helpers.get_new_contact_template()
yaml = YAML()
yaml.top_level_colon_align = True
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I do not like the way this alignment looks so I would leave it out.

"Note", self.notes, 0, 5, True)
elif line.lower().startswith("webpage"):
strings += helpers.convert_to_yaml(
"Webpage", self.webpages, 0, 8, True)
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I like this code reduction :)

@skowalak
Copy link
Contributor Author

skowalak commented Mar 9, 2022

@lucc I implemented the changes you requested.
About the quoting, I am not entirely sure. I believe ZIP codes at least are quoted because they are strings consisting of numbers only and ruamel quotes them so they are not interpreted as tag:yaml.org,2002:int, which would for example remove leading zeroes. That does not apply to birthdays (as they include dashes), still they are quoted, when according to the yaml spec they do not have be quoted. I had a look over at ruamels source code but could not find out why.

So, if that is a big problem we could ofc ask Anthon van der Neut from ruamel if he knows if it is possible not to quote this.

@lucc lucc merged commit ef8868c into lucc:develop Mar 9, 2022
@lucc
Copy link
Owner

lucc commented Mar 9, 2022

thank you @skowalak !

We can leave the quoting for later. That is just aesthetics in my opinion. The important thing is that yaml editing should be more robust now that #276 should be fixed.

@skowalak skowalak deleted the feature/276-yaml-generator branch March 9, 2022 21:48
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants