Skip to content

Failed pyproject.toml read with unicode char present #1421

@nathanjmcdougall

Description

@nathanjmcdougall

The character ā in a comment meant that usethis failed to read pyproject.toml when running the command usethis tool import-linter

Details
uvx usethis tool import-linter
Installed 26 packages in 889ms
╭──────────────────────────────────────────────────────── Traceback (most recent call last) ────────────────────────────────────────────────────────╮
│ C:\Users\namc\AppData\Local\uv\cache\archive-v0\-9VPuSvSg0z_h-I2P96_m\Lib\site-packages\usethis\_ui\interface\tool.py:136 in import_linter        │
│                                                                                                                                                   │
│   133 │   │   ),                                                                                                                                  │
│   134 │   │   files_manager(),                                                                                                                    │
│   135 │   ):                                                                                                                                      │
│ ❱ 136 │   │   _run_tool(use_import_linter, remove=remove, how=how)                                                                                │
│   137                                                                                                                                             │
│   138                                                                                                                                             │
│   139 @app.command(                                                                                                                               │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Local\uv\cache\archive-v0\-9VPuSvSg0z_h-I2P96_m\Lib\site-packages\usethis\_ui\interface\tool.py:339 in _run_tool            │
│                                                                                                                                                   │
│   336 │   from usethis.errors import UsethisError                                                                                                 │
│   337 │                                                                                                                                           │
│   338 │   try:                                                                                                                                    │
│ ❱ 339 │   │   caller(remove=remove, how=how, **kwargs)                                                                                            │
│   340 │   except UsethisError as err:                                                                                                             │
│   341 │   │   err_print(err)                                                                                                                      │
│   342 │   │   raise typer.Exit(code=1) from None                                                                                                  │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Local\uv\cache\archive-v0\-9VPuSvSg0z_h-I2P96_m\Lib\site-packages\usethis\_core\tool.py:140 in use_import_linter            │
│                                                                                                                                                   │
│   137 │   rule_config = tool.get_rule_config()                                                                                                    │
│   138 │                                                                                                                                           │
│   139 │   if not remove:                                                                                                                          │
│ ❱ 140 │   │   ensure_dep_declaration_file()                                                                                                       │
│   141 │   │                                                                                                                                       │
│   142 │   │   tool.add_dev_deps()                                                                                                                 │
│   143 │   │   tool.add_configs()                                                                                                                  │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Local\uv\cache\archive-v0\-9VPuSvSg0z_h-I2P96_m\Lib\site-packages\usethis\_init.py:89 in ensure_dep_declaration_file        │
│                                                                                                                                                   │
│    86                                                                                                                                             │
│    87 def ensure_dep_declaration_file() -> None:                                                                                                  │
│    88 │   """Ensure that the file where dependencies are declared exists, if necessary."""                                                        │
│ ❱  89 │   backend = get_backend()                                                                                                                 │
│    90 │   if backend is BackendEnum.uv:                                                                                                           │
│    91 │   │   ensure_pyproject_toml()                                                                                                             │
│    92 │   elif backend is BackendEnum.none:                                                                                                       │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Local\uv\cache\archive-v0\-9VPuSvSg0z_h-I2P96_m\Lib\site-packages\usethis\_integrations\backend\dispatch.py:20 in           │
│ get_backend                                                                                                                                       │
│                                                                                                                                                   │
│   17 │                                                                                                                                            │
│   18 │   if usethis_config.backend is not BackendEnum.auto:                                                                                       │
│   19 │   │   usethis_config.inferred_backend = usethis_config.backend                                                                             │
│ ❱ 20 │   elif is_poetry_used():                                                                                                                   │
│   21 │   │   warn_print(                                                                                                                          │
│   22 │   │   │   "This project is using Poetry, which is not fully supported by usethis."                                                         │
│   23 │   │   )                                                                                                                                    │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Local\uv\cache\archive-v0\-9VPuSvSg0z_h-I2P96_m\Lib\site-packages\usethis\_integrations\backend\poetry\used.py:13 in        │
│ is_poetry_used                                                                                                                                    │
│                                                                                                                                                   │
│   10 │   │   or (usethis_config.cpd() / "poetry.toml").exists()                                                                                   │
│   11 │   │   or (                                                                                                                                 │
│   12 │   │   │   pyproject_toml_manager.path.exists()                                                                                             │
│ ❱ 13 │   │   │   and ["tool", "poetry"] in pyproject_toml_manager                                                                                 │
│   14 │   │   )                                                                                                                                    │
│   15 │   )                                                                                                                                        │
│   16                                                                                                                                              │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Local\uv\cache\archive-v0\-9VPuSvSg0z_h-I2P96_m\Lib\site-packages\usethis\_integrations\file\toml\io_.py:105 in             │
│ __contains__                                                                                                                                      │
│                                                                                                                                                   │
│   102 │   │   keys = _validate_keys(keys)                                                                                                         │
│   103 │   │   try:                                                                                                                                │
│   104 │   │   │   try:                                                                                                                            │
│ ❱ 105 │   │   │   │   container = self.get()                                                                                                      │
│   106 │   │   │   except FileNotFoundError:                                                                                                       │
│   107 │   │   │   │   return False                                                                                                                │
│   108 │   │   │   for key in keys:                                                                                                                │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Local\uv\cache\archive-v0\-9VPuSvSg0z_h-I2P96_m\Lib\site-packages\usethis\_integrations\file\toml\io_.py:78 in get          │
│                                                                                                                                                   │
│    75 │   │   return tomlkit.api.parse(content)                                                                                                   │
│    76 │                                                                                                                                           │
│    77 │   def get(self) -> TOMLDocument:                                                                                                          │
│ ❱  78 │   │   return super().get()                                                                                                                │
│    79 │                                                                                                                                           │
│    80 │   def commit(self, document: TOMLDocument) -> None:                                                                                       │
│    81 │   │   return super().commit(document)                                                                                                     │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Local\uv\cache\archive-v0\-9VPuSvSg0z_h-I2P96_m\Lib\site-packages\usethis\_io.py:98 in get                                  │
│                                                                                                                                                   │
│    95 │   │   self._validate_lock()                                                                                                               │
│    96 │   │                                                                                                                                       │
│    97 │   │   if self._content is None:                                                                                                           │
│ ❱  98 │   │   │   return self.read_file()                                                                                                         │
│    99 │   │   else:                                                                                                                               │
│   100 │   │   │   return self._content                                                                                                            │
│   101                                                                                                                                             │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Local\uv\cache\archive-v0\-9VPuSvSg0z_h-I2P96_m\Lib\site-packages\usethis\_integrations\file\pyproject_toml\io_.py:49 in    │
│ read_file                                                                                                                                         │
│                                                                                                                                                   │
│   46 │                                                                                                                                            │
│   47 │   def read_file(self) -> TOMLDocument:                                                                                                     │
│   48 │   │   try:                                                                                                                                 │
│ ❱ 49 │   │   │   return super().read_file()                                                                                                       │
│   50 │   │   except TOMLNotFoundError as err:                                                                                                     │
│   51 │   │   │   raise PyprojectTOMLNotFoundError(err) from None                                                                                  │
│   52 │   │   except UnexpectedTOMLIOError as err:                                                                                                 │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Local\uv\cache\archive-v0\-9VPuSvSg0z_h-I2P96_m\Lib\site-packages\usethis\_integrations\file\toml\io_.py:58 in read_file    │
│                                                                                                                                                   │
│    55 │                                                                                                                                           │
│    56 │   def read_file(self) -> TOMLDocument:                                                                                                    │
│    57 │   │   try:                                                                                                                                │
│ ❱  58 │   │   │   return super().read_file()                                                                                                      │
│    59 │   │   except FileNotFoundError as err:                                                                                                    │
│    60 │   │   │   raise TOMLNotFoundError(err) from None                                                                                          │
│    61 │   │   except UnexpectedFileIOError as err:                                                                                                │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Local\uv\cache\archive-v0\-9VPuSvSg0z_h-I2P96_m\Lib\site-packages\usethis\_io.py:135 in read_file                           │
│                                                                                                                                                   │
│   132 │   │   │   )                                                                                                                               │
│   133 │   │   │   raise UnexpectedFileIOError(msg)                                                                                                │
│   134 │   │   try:                                                                                                                                │
│ ❱ 135 │   │   │   document = self._parse_content(self.path.read_text())                                                                           │
│   136 │   │   except FileNotFoundError:                                                                                                           │
│   137 │   │   │   msg = f"'{self.name}' not found in the current directory at '{self.path}'."                                                     │
│   138 │   │   │   raise FileNotFoundError(msg) from None                                                                                          │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Roaming\uv\data\python\cpython-3.14.0-windows-x86_64-none\Lib\pathlib\__init__.py:793 in read_text                          │
│                                                                                                                                                   │
│    790 │   │   # appropriate stack level.                                                                                                         │
│    791 │   │   encoding = io.text_encoding(encoding)                                                                                              │
│    792 │   │   with self.open(mode='r', encoding=encoding, errors=errors, newline=newline) as f                                                   │
│ ❱  793 │   │   │   return f.read()                                                                                                                │
│    794 │                                                                                                                                          │
│    795 │   def write_bytes(self, data):                                                                                                           │
│    796 │   │   """                                                                                                                                │
│                                                                                                                                                   │
│ C:\Users\namc\AppData\Roaming\uv\data\python\cpython-3.14.0-windows-x86_64-none\Lib\encodings\cp1252.py:23 in decode                              │
│                                                                                                                                                   │
│    20                                                                                                                                             │
│    21 class IncrementalDecoder(codecs.IncrementalDecoder):                                                                                        │
│    22 │   def decode(self, input, final=False):                                                                                                   │
│ ❱  23 │   │   return codecs.charmap_decode(input,self.errors,decoding_table)[0]                                                                   │
│    24                                                                                                                                             │
│    25 class StreamWriter(Codec,codecs.StreamWriter):                                                                                              │
│    26 │   pass                                                                                                                                    │
╰───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯
UnicodeDecodeError: 'charmap' codec can't decode byte 0x81 in position 8672: character maps to <undefined>

Metadata

Metadata

Labels

bugSomething isn't working

Type

No type
No fields configured for issues without a type.

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions