sphinx-codeautolink 0.18.0__tar.gz → 0.19.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (192) hide show
  1. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/PKG-INFO +1 -1
  2. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/docs/src/reference.rst +9 -0
  3. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/docs/src/release_notes.rst +17 -0
  4. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/pyproject.toml +2 -0
  5. sphinx_codeautolink-0.19.0/requirements/tests +5 -0
  6. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/__init__.py +4 -1
  7. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/extension/__init__.py +3 -0
  8. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/extension/block.py +17 -5
  9. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/extension/resolve.py +50 -8
  10. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/parse.py +10 -8
  11. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink.egg-info/PKG-INFO +1 -1
  12. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink.egg-info/SOURCES.txt +6 -0
  13. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/__init__.py +57 -0
  14. sphinx_codeautolink-0.19.0/tests/extension/ref/ref_attribute_assignment.txt +17 -0
  15. sphinx_codeautolink-0.19.0/tests/extension/ref/ref_type_checking_aliased.txt +15 -0
  16. sphinx_codeautolink-0.19.0/tests/extension/ref/self_type.txt +17 -0
  17. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/src/future_project.py +1 -1
  18. sphinx_codeautolink-0.19.0/tests/extension/src/self_type.py +23 -0
  19. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/src/test_project/__init__.py +1 -1
  20. sphinx_codeautolink-0.19.0/tests/extension/src/type_checking_aliased/__init__.py +14 -0
  21. sphinx_codeautolink-0.19.0/tests/extension/src/type_checking_aliased/foo.py +4 -0
  22. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/parse/assign.py +42 -0
  23. sphinx_codeautolink-0.18.0/requirements/tests +0 -4
  24. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/LICENSE +0 -0
  25. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/MANIFEST.in +0 -0
  26. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/contributing.rst +0 -0
  27. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/docs/requirements.txt +0 -0
  28. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/docs/src/404.rst +0 -0
  29. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/docs/src/about.rst +0 -0
  30. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/docs/src/conf.py +0 -0
  31. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/docs/src/example_library.rst +0 -0
  32. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/docs/src/examples.rst +0 -0
  33. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/docs/src/index.rst +0 -0
  34. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/docs/src/lib.py +0 -0
  35. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/docs/src/static/custom.css +0 -0
  36. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/readme_pypi.rst +0 -0
  37. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/requirements/build +0 -0
  38. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/requirements/dev +0 -0
  39. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/requirements/docs +0 -0
  40. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/requirements/extras +0 -0
  41. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/setup.cfg +0 -0
  42. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/extension/backref.py +0 -0
  43. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/extension/cache.py +0 -0
  44. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/extension/directive.py +0 -0
  45. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/extension/translation.py +0 -0
  46. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/de/LC_MESSAGES/sphinx-codeautolink.mo +0 -0
  47. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/de/LC_MESSAGES/sphinx-codeautolink.po +0 -0
  48. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/es/LC_MESSAGES/sphinx-codeautolink.mo +0 -0
  49. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/es/LC_MESSAGES/sphinx-codeautolink.po +0 -0
  50. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/fi/LC_MESSAGES/sphinx-codeautolink.mo +0 -0
  51. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/fi/LC_MESSAGES/sphinx-codeautolink.po +0 -0
  52. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/fr/LC_MESSAGES/sphinx-codeautolink.mo +0 -0
  53. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/fr/LC_MESSAGES/sphinx-codeautolink.po +0 -0
  54. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/it/LC_MESSAGES/sphinx-codeautolink.mo +0 -0
  55. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/it/LC_MESSAGES/sphinx-codeautolink.po +0 -0
  56. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/nl/LC_MESSAGES/sphinx-codeautolink.mo +0 -0
  57. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/nl/LC_MESSAGES/sphinx-codeautolink.po +0 -0
  58. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/ru/LC_MESSAGES/sphinx-codeautolink.po +0 -0
  59. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/sphinx-codeautolink.pot +0 -0
  60. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/locale/uk/LC_MESSAGES/sphinx-codeautolink.po +0 -0
  61. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/static/sphinx-codeautolink.css +0 -0
  62. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink/warn.py +0 -0
  63. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink.egg-info/dependency_links.txt +0 -0
  64. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink.egg-info/requires.txt +0 -0
  65. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/src/sphinx_codeautolink.egg-info/top_level.txt +0 -0
  66. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/__init__.py +0 -0
  67. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/_check.py +0 -0
  68. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/concat_invalid.txt +0 -0
  69. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/custom_block_import_invalid.txt +0 -0
  70. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/custom_block_syntax_error.txt +0 -0
  71. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/failed_resolve_invalid_location.txt +0 -0
  72. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/failed_resolve_no_module.txt +0 -0
  73. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/failed_resolve_return_type.txt +0 -0
  74. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/match_block_warning.txt +0 -0
  75. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/missing_inventory.txt +0 -0
  76. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/no_backreference.txt +0 -0
  77. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/no_module_docs.txt +0 -0
  78. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/preface_invalid_arg.txt +0 -0
  79. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/ref_import_star_invalid.txt +0 -0
  80. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/ref_invalid_block_type.txt +0 -0
  81. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/ref_invalid_syntax.txt +0 -0
  82. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/ref_invalid_syntax_complex.txt +0 -0
  83. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/ref_ipython_non-python.txt +0 -0
  84. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/fail/skip_invalid.txt +0 -0
  85. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/class_mro_fix.txt +0 -0
  86. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/concat_default.txt +0 -0
  87. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/concat_off.txt +0 -0
  88. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/concat_on_across_sections.txt +0 -0
  89. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/concat_on_breaks.txt +0 -0
  90. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/concat_section_breaks.txt +0 -0
  91. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/concat_section_returns_to_global.txt +0 -0
  92. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/custom_block.txt +0 -0
  93. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/custom_block_imported.txt +0 -0
  94. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/empty_project.txt +0 -0
  95. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/inventory_map_is_needed.txt +0 -0
  96. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/inventory_map_not_needed.txt +0 -0
  97. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_Python.txt +0 -0
  98. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_bazel.txt +0 -0
  99. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_default.txt +0 -0
  100. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_default_fail.txt +0 -0
  101. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_doctest.txt +0 -0
  102. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_doctest_empty_input.txt +0 -0
  103. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_extdoctest_doctest.txt +0 -0
  104. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_extdoctest_setup.txt +0 -0
  105. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_extdoctest_setup_wrong.txt +0 -0
  106. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_extdoctest_testcode.txt +0 -0
  107. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_highlight_language.txt +0 -0
  108. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_highlight_none.txt +0 -0
  109. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_ipython.txt +0 -0
  110. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_ipython3.txt +0 -0
  111. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_ipython_directive.txt +0 -0
  112. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_ipython_directive_comment.txt +0 -0
  113. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_ipython_syntax.txt +0 -0
  114. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_literal.txt +0 -0
  115. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_non_python_block.txt +0 -0
  116. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_py.txt +0 -0
  117. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_py3.txt +0 -0
  118. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_pycon.txt +0 -0
  119. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_pycon_implicit.txt +0 -0
  120. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_pyi.txt +0 -0
  121. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_python3.txt +0 -0
  122. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_sage.txt +0 -0
  123. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/lexer_starlark.txt +0 -0
  124. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/line_numbers.txt +0 -0
  125. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/preface_concatenated.txt +0 -0
  126. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/preface_consumed_non_python.txt +0 -0
  127. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/preface_document.txt +0 -0
  128. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/preface_global.txt +0 -0
  129. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/preface_global_multiline.txt +0 -0
  130. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/preface_global_overwritten.txt +0 -0
  131. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/preface_multiline.txt +0 -0
  132. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/preface_multiline_and_arg.txt +0 -0
  133. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/preface_multiple.txt +0 -0
  134. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/preface_single.txt +0 -0
  135. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_assign_targets.txt +0 -0
  136. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_builtins.txt +0 -0
  137. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_chain.txt +0 -0
  138. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_chain_call.txt +0 -0
  139. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_class_attr.txt +0 -0
  140. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_class_meth_returns_self.txt +0 -0
  141. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_class_type_attr.txt +0 -0
  142. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_decorator.txt +0 -0
  143. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_fluent_attrs.txt +0 -0
  144. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_fluent_call.txt +0 -0
  145. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_for_loop.txt +0 -0
  146. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_func_args.txt +0 -0
  147. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_func_no_module.txt +0 -0
  148. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_import_as.txt +0 -0
  149. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_import_from.txt +0 -0
  150. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_import_from_complex.txt +0 -0
  151. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_import_multiple.txt +0 -0
  152. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_import_multiple_libs.txt +0 -0
  153. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_import_star.txt +0 -0
  154. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_import_submodule.txt +0 -0
  155. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_imported_func.txt +0 -0
  156. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_imported_func_relocated.txt +0 -0
  157. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_inherited.txt +0 -0
  158. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_intersphinx_only.txt +0 -0
  159. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_invalid_func.txt +0 -0
  160. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_invalid_typehint.txt +0 -0
  161. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_module_attribute.txt +0 -0
  162. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_module_attribute_builtin.txt +0 -0
  163. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_module_attribute_class.txt +0 -0
  164. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_optional.txt +0 -0
  165. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_optional_future.txt +0 -0
  166. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_shadow_builtin.txt +0 -0
  167. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_simple.txt +0 -0
  168. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/ref_type_checking_gated.txt +0 -0
  169. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/search_css_duplicates_removed.txt +0 -0
  170. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/skip_file.txt +0 -0
  171. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/skip_next.txt +0 -0
  172. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/skip_next_consumed_non_python.txt +0 -0
  173. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/skip_off.txt +0 -0
  174. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/ref/skip_section.txt +0 -0
  175. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/src/class_mro_fix.py +0 -0
  176. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/src/parser_func.py +0 -0
  177. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/src/test_project/sub.py +0 -0
  178. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/src/type_checking/__init__.py +0 -0
  179. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/src/type_checking/foo.py +0 -0
  180. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/table/tab_autodoc_empty.txt +0 -0
  181. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/table/tab_autodoc_links.txt +0 -0
  182. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/table/tab_manual_collapse.txt +0 -0
  183. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/table/tab_manual_empty.txt +0 -0
  184. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/table/tab_manual_links.txt +0 -0
  185. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/table/tab_manual_links_subsection.txt +0 -0
  186. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/extension/table/tab_no_table.txt +0 -0
  187. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/parse/__init__.py +0 -0
  188. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/parse/_util.py +0 -0
  189. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/parse/chain.py +0 -0
  190. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/parse/match.py +0 -0
  191. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tests/parse/scope.py +0 -0
  192. {sphinx_codeautolink-0.18.0 → sphinx_codeautolink-0.19.0}/tox.ini +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: sphinx-codeautolink
3
- Version: 0.18.0
3
+ Version: 0.19.0
4
4
  Summary: Automatic links from code examples to reference documentation.
5
5
  Author-email: Felix Hildén <felix.hilden@gmail.com>
6
6
  Maintainer-email: Felix Hildén <felix.hilden@gmail.com>
@@ -55,6 +55,15 @@ Configuration
55
55
  Useful when objects are imported and documented somewhere else than their
56
56
  original location as advertised by ``__module__``.
57
57
 
58
+ .. confval:: codeautolink_disable_link_titles
59
+
60
+ Type: ``bool``. Don't add a ``title`` attribute, shown as a tooltip on
61
+ hover, to code links. By default the title contains the resolved location
62
+ of the linked object, but only when it differs from the code that is being
63
+ linked: hovering over ``instance.method()`` shows ``module.Class.method``,
64
+ while hovering over ``module.Class`` adds no tooltip.
65
+ Defaults to :code:`False`.
66
+
58
67
  .. confval:: codeautolink_warn_on_missing_inventory
59
68
 
60
69
  Type: ``bool``. Warn when an object cannot be found in
@@ -8,6 +8,23 @@ These release notes are based on
8
8
  sphinx-codeautolink adheres to
9
9
  `Semantic Versioning <https://semver.org>`_.
10
10
 
11
+ 0.19.0 (2026-07-29)
12
+ -------------------
13
+ - Only add a hover title to links when the resolved location of the object
14
+ differs from the linked code, and add
15
+ :confval:`codeautolink_disable_link_titles`
16
+ to disable the titles altogether (:issue:`200`)
17
+ - Fix "Could not match transformation" warnings for assignments to
18
+ attributes such as ``thing.attr = 1`` (:issue:`201`)
19
+ - Resolve ``typing.Self`` return annotations, respecting inheritance so a
20
+ ``Self``-returning method accessed through a subclass or mixin resolves to
21
+ the accessing class rather than the class it's defined on (:issue:`147`)
22
+
23
+ 0.18.1 (2026-04-30)
24
+ -------------------
25
+ - Recognize aliased ``TYPE_CHECKING`` imports such as
26
+ ``from typing import TYPE_CHECKING as _TYPE_CHECKING`` (:issue:`199`)
27
+
11
28
  0.18.0 (2026-04-25)
12
29
  -------------------
13
30
  - Support module attributes and class aliases (:issue:`65`)
@@ -72,6 +72,7 @@ ignore = [
72
72
  extend-ignore = [
73
73
  "ARG001", # unused args needed in interfaces
74
74
  "ARG002", # unused args needed in interfaces
75
+ "CPY001", # no copyright notices needed
75
76
  "D107", # docstring missing is fine
76
77
  "D203", # recommended by ruff format
77
78
  "D212", # docstring format clash
@@ -80,6 +81,7 @@ extend-ignore = [
80
81
  "ISC001", # recommended by ruff format
81
82
  "PLR0913", # many arguments is fine
82
83
  "PLR0915", # many statements is fine
84
+ "PLR0917", # many arguments is fine
83
85
  ]
84
86
  extend-unsafe-fixes = ["F401"]
85
87
  isort.split-on-trailing-comma = false
@@ -0,0 +1,5 @@
1
+ -r extras
2
+
3
+ pytest>=6
4
+ coverage[toml]>=5
5
+ typing-extensions>=4; python_version < "3.11"
@@ -8,7 +8,7 @@ from .extension import SphinxCodeAutoLink, backref, directive
8
8
  from .extension.block import clean_ipython, clean_pycon
9
9
  from .extension.translation import MESSAGE_CATALOG_NAME
10
10
 
11
- __version__ = "0.18.0"
11
+ __version__ = "0.19.0"
12
12
 
13
13
 
14
14
  def setup(app: Sphinx):
@@ -34,6 +34,9 @@ def setup(app: Sphinx):
34
34
  app.add_config_value(
35
35
  "codeautolink_inventory_map", default={}, rebuild="html", types=[dict]
36
36
  )
37
+ app.add_config_value(
38
+ "codeautolink_disable_link_titles", default=False, rebuild="html", types=[bool]
39
+ )
37
40
  app.add_config_value(
38
41
  "codeautolink_warn_on_missing_inventory",
39
42
  default=False,
@@ -78,6 +78,7 @@ class SphinxCodeAutoLink:
78
78
  self.warn_no_backreference = None
79
79
  self.warn_default_parse_fail = None
80
80
  self.highlight_lang = None
81
+ self.disable_link_titles = None
81
82
 
82
83
  # Populated once
83
84
  self.outdated_docs: set[str] = set()
@@ -112,6 +113,7 @@ class SphinxCodeAutoLink:
112
113
  app.config.codeautolink_warn_on_default_parse_fail
113
114
  )
114
115
  self.highlight_lang = app.config.highlight_language
116
+ self.disable_link_titles = app.config.codeautolink_disable_link_titles
115
117
 
116
118
  # Append static resources path so references in setup() are valid
117
119
  app.config.html_static_path.append(
@@ -295,6 +297,7 @@ class SphinxCodeAutoLink:
295
297
  self.custom_blocks,
296
298
  self.search_css_classes,
297
299
  builder_name=app.builder.name,
300
+ disable_link_titles=self.disable_link_titles,
298
301
  )
299
302
 
300
303
  self.cache.write()
@@ -369,6 +369,14 @@ class CodeBlockAnalyser(nodes.SparseNodeVisitor):
369
369
  )
370
370
 
371
371
 
372
+ def format_title(location: str, text: str) -> str:
373
+ """Format the title attribute of a link, empty if it wouldn't add information."""
374
+ code = re.sub(r"\s+", "", BeautifulSoup(text, "html.parser").get_text())
375
+ if code == location:
376
+ return ""
377
+ return f' title="{location}"'
378
+
379
+
372
380
  def link_html(
373
381
  document: str,
374
382
  out_dir: str,
@@ -377,6 +385,8 @@ def link_html(
377
385
  custom_blocks: dict,
378
386
  search_css_classes: list,
379
387
  builder_name: str = "html",
388
+ *,
389
+ disable_link_titles: bool,
380
390
  ) -> None:
381
391
  """Inject links to code blocks on disk."""
382
392
  if builder_name == "dirhtml" and Path(document).name != "index":
@@ -400,9 +410,7 @@ def link_html(
400
410
 
401
411
  up_lvls = len(html_file.relative_to(out_dir).parents) - 1
402
412
  local_prefix = "../" * up_lvls
403
- link_pattern = (
404
- '<a href="{link}" title="{title}" class="sphinx-codeautolink-a">{text}</a>'
405
- )
413
+ link_pattern = '<a href="{link}"{title} class="sphinx-codeautolink-a">{text}</a>'
406
414
 
407
415
  for trans in transforms:
408
416
  for ix in range(len(inners)):
@@ -447,9 +455,13 @@ def link_html(
447
455
  location = inventory[name.resolved_location]
448
456
  if not any(location.startswith(s) for s in ("http://", "https://")):
449
457
  location = local_prefix + location
450
- link = link_pattern.format(
451
- link=location, title=name.resolved_location, text=selection[start:end]
458
+ text = selection[start:end]
459
+ title = (
460
+ ""
461
+ if disable_link_titles
462
+ else format_title(name.resolved_location, text)
452
463
  )
464
+ link = link_pattern.format(link=location, title=title, text=text)
453
465
  transformed = selection[:start] + link + selection[end:]
454
466
  lines[begin_line : end_line + 1] = transformed.split("\n")
455
467
 
@@ -16,6 +16,14 @@ from typing import Any, Union, get_type_hints
16
16
 
17
17
  from sphinx_codeautolink.parse import Name, NameBreak
18
18
 
19
+ try:
20
+ from typing import Self # Python >= 3.11
21
+ except ImportError: # pragma: no cover
22
+ try:
23
+ from typing_extensions import Self
24
+ except ImportError:
25
+ Self = None # type: ignore[assignment,misc]
26
+
19
27
  # Containers whose first generic argument is the element type produced
20
28
  # by iteration. ``tuple`` only fits ``tuple[T, ...]``; for mixed tuples
21
29
  # like ``tuple[int, str]`` we pick the first arg, which may be wrong.
@@ -87,6 +95,13 @@ class Cursor:
87
95
  value: Any
88
96
  instance: bool
89
97
  annotation: Any = None
98
+ # The live object/class this cursor's value was accessed on, e.g. the
99
+ # receiver of a bound method. Used to resolve `Self` return annotations
100
+ # to the accessing class rather than the (possibly different, e.g. a
101
+ # mixin) class the method happens to be defined on. Unlike `location`,
102
+ # this is never rewritten by the MRO fallback below, so it reflects the
103
+ # true runtime receiver even when the naive `location` doesn't resolve.
104
+ receiver: Any = None
90
105
 
91
106
 
92
107
  def make_cursor(components: list[str]) -> tuple[list[str], Cursor]:
@@ -121,6 +136,7 @@ def locate_type(cursor: Cursor, components: tuple[str, ...], inventory) -> Curso
121
136
  getattr(previous.value, component, None),
122
137
  previous.instance,
123
138
  annotation=annotation,
139
+ receiver=previous.value,
124
140
  )
125
141
 
126
142
  if cursor.value is None:
@@ -163,6 +179,21 @@ def call_value(cursor: Cursor) -> None:
163
179
  raise CouldNotResolve # not a function either
164
180
 
165
181
  annotation = get_return_annotation(cursor.value)
182
+ if Self is not None and annotation is Self and cursor.receiver is not None:
183
+ # `Self` refers to whichever class/instance the method was accessed
184
+ # on, which is not necessarily the class it's defined on (e.g. a
185
+ # mixin). Use the receiver rather than re-deriving the owner from
186
+ # `cursor.location`, since that string may have been rewritten to
187
+ # the *defining* class by the MRO fallback above.
188
+ owner_value = cursor.receiver
189
+ if not isclass(owner_value):
190
+ owner_value = type(owner_value)
191
+ cursor.value = owner_value
192
+ cursor.location = fully_qualified_name(owner_value)
193
+ cursor.instance = True
194
+ cursor.annotation = annotation
195
+ return
196
+
166
197
  type_ = origin_type(annotation)
167
198
  if not isinstance(type_, type):
168
199
  msg = f"Unable to follow return annotation of {annotation!r}."
@@ -282,10 +313,13 @@ def populate_type_checking(mod: ModuleType) -> None:
282
313
  return
283
314
 
284
315
  tree = ast.parse(source)
316
+ aliases = collect_type_checking_aliases(tree)
285
317
 
286
318
  filename = getattr(mod, "__file__", None) or "<type_checking>"
287
319
  for node in tree.body:
288
- if not isinstance(node, ast.If) or not is_type_checking_test(node.test):
320
+ if not isinstance(node, ast.If):
321
+ continue
322
+ if not is_type_checking_test(node.test, aliases):
289
323
  continue
290
324
  body = ast.Module(body=node.body, type_ignores=[])
291
325
  # Catch e.g. optional deps and cyclic imports
@@ -293,15 +327,23 @@ def populate_type_checking(mod: ModuleType) -> None:
293
327
  exec(compile(body, filename, "exec"), mod.__dict__) # noqa: S102
294
328
 
295
329
 
296
- def is_type_checking_test(expr: ast.expr) -> bool:
297
- """
298
- Determine if expr is a test for type checking.
330
+ def collect_type_checking_aliases(tree: ast.Module) -> set[str]:
331
+ """Walk top-level imports, return names bound to ``typing.TYPE_CHECKING``."""
332
+ aliases: set[str] = set()
333
+ for node in tree.body:
334
+ if isinstance(node, ast.ImportFrom) and node.module == "typing":
335
+ for alias in node.names:
336
+ if alias.name in ("TYPE_CHECKING", "MYPY"):
337
+ aliases.add(alias.asname or alias.name)
338
+ return aliases
299
339
 
300
- Mirror mypy's ``infer_condition_value``: match a bare name or any
301
- attribute access regardless of qualifier.
302
- """
340
+
341
+ def is_type_checking_test(
342
+ expr: ast.expr, aliases: frozenset[str] | set[str] = frozenset()
343
+ ) -> bool:
344
+ """Determine if expr is a test for type checking."""
303
345
  if isinstance(expr, ast.Name):
304
- return expr.id in ("TYPE_CHECKING", "MYPY")
346
+ return expr.id in ("TYPE_CHECKING", "MYPY") or expr.id in aliases
305
347
  if isinstance(expr, ast.Attribute):
306
348
  return expr.attr in ("TYPE_CHECKING", "MYPY")
307
349
  return False
@@ -286,15 +286,17 @@ class ImportTrackerVisitor(ast.NodeVisitor):
286
286
  if target is None:
287
287
  return
288
288
 
289
- if len(target.components) == 1:
290
- comp = target.components[0]
291
- if value is None:
292
- self.overwrite_name(comp.name)
293
- else:
294
- self.assign_name(comp.name, value.components)
295
- self._create_access(target.components)
289
+ if len(target.components) != 1:
290
+ # Dotted targets don't assign to the current scope, and their access
291
+ # was already resolved when the access chain was visited.
292
+ return
293
+
294
+ comp = target.components[0]
295
+ if value is None:
296
+ self.overwrite_name(comp.name)
296
297
  else:
297
- self.resolve_pending_access(target)
298
+ self.assign_name(comp.name, value.components)
299
+ self._create_access(target.components)
298
300
 
299
301
  def create_simple_access(self, name: str, lineno: int) -> None:
300
302
  """Create single-component access to scope."""
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: sphinx-codeautolink
3
- Version: 0.18.0
3
+ Version: 0.19.0
4
4
  Summary: Automatic links from code examples to reference documentation.
5
5
  Author-email: Felix Hildén <felix.hilden@gmail.com>
6
6
  Maintainer-email: Felix Hildén <felix.hilden@gmail.com>
@@ -122,6 +122,7 @@ tests/extension/ref/preface_multiline_and_arg.txt
122
122
  tests/extension/ref/preface_multiple.txt
123
123
  tests/extension/ref/preface_single.txt
124
124
  tests/extension/ref/ref_assign_targets.txt
125
+ tests/extension/ref/ref_attribute_assignment.txt
125
126
  tests/extension/ref/ref_builtins.txt
126
127
  tests/extension/ref/ref_chain.txt
127
128
  tests/extension/ref/ref_chain_call.txt
@@ -154,8 +155,10 @@ tests/extension/ref/ref_optional.txt
154
155
  tests/extension/ref/ref_optional_future.txt
155
156
  tests/extension/ref/ref_shadow_builtin.txt
156
157
  tests/extension/ref/ref_simple.txt
158
+ tests/extension/ref/ref_type_checking_aliased.txt
157
159
  tests/extension/ref/ref_type_checking_gated.txt
158
160
  tests/extension/ref/search_css_duplicates_removed.txt
161
+ tests/extension/ref/self_type.txt
159
162
  tests/extension/ref/skip_file.txt
160
163
  tests/extension/ref/skip_next.txt
161
164
  tests/extension/ref/skip_next_consumed_non_python.txt
@@ -164,10 +167,13 @@ tests/extension/ref/skip_section.txt
164
167
  tests/extension/src/class_mro_fix.py
165
168
  tests/extension/src/future_project.py
166
169
  tests/extension/src/parser_func.py
170
+ tests/extension/src/self_type.py
167
171
  tests/extension/src/test_project/__init__.py
168
172
  tests/extension/src/test_project/sub.py
169
173
  tests/extension/src/type_checking/__init__.py
170
174
  tests/extension/src/type_checking/foo.py
175
+ tests/extension/src/type_checking_aliased/__init__.py
176
+ tests/extension/src/type_checking_aliased/foo.py
171
177
  tests/extension/table/tab_autodoc_empty.txt
172
178
  tests/extension/table/tab_autodoc_links.txt
173
179
  tests/extension/table/tab_manual_collapse.txt
@@ -282,6 +282,63 @@ Test project
282
282
  assert check_link_targets(result_dir) == n_subfiles * len(links)
283
283
 
284
284
 
285
+ title_index = """
286
+ Test project
287
+ ============
288
+
289
+ .. code:: python
290
+
291
+ import test_project
292
+
293
+ test_project.bar().attr
294
+
295
+ .. code:: python
296
+
297
+ import test_project
298
+
299
+ (test_project
300
+ .bar())
301
+
302
+ .. automodule:: test_project
303
+ """
304
+
305
+
306
+ def link_titles(file: Path) -> list[tuple[str, str | None]]:
307
+ """Return the text and title of all code links in a file."""
308
+ soup = BeautifulSoup(file.read_text("utf-8"), "html.parser")
309
+ links = soup.find_all("a", attrs={"class": "sphinx-codeautolink-a"})
310
+ return [(any_whitespace.sub("", "".join(a.strings)), a.get("title")) for a in links]
311
+
312
+
313
+ def test_link_titles_show_resolved_location(tmp_path: Path):
314
+ """Titles are added only when they differ from the code being linked."""
315
+ files = {"conf.py": default_conf, "index.rst": title_index}
316
+ result_dir = _sphinx_build(tmp_path, "html", files)
317
+
318
+ assert link_titles(result_dir / "index.html") == [
319
+ ("test_project", None),
320
+ ("test_project.bar", None),
321
+ ("attr", "test_project.Foo.attr"),
322
+ ("test_project", None),
323
+ ("test_project.bar", None),
324
+ ]
325
+
326
+
327
+ def test_link_titles_disabled(tmp_path: Path):
328
+ """No titles are added when they are turned off."""
329
+ conf = default_conf + "\ncodeautolink_disable_link_titles = True"
330
+ files = {"conf.py": conf, "index.rst": title_index}
331
+ result_dir = _sphinx_build(tmp_path, "html", files)
332
+
333
+ assert link_titles(result_dir / "index.html") == [
334
+ ("test_project", None),
335
+ ("test_project.bar", None),
336
+ ("attr", None),
337
+ ("test_project", None),
338
+ ("test_project.bar", None),
339
+ ]
340
+
341
+
285
342
  def test_skip_identical_code(tmp_path: Path):
286
343
  """Code skipped and then linked in an identical block after."""
287
344
  index = """
@@ -0,0 +1,17 @@
1
+ test_project
2
+ thing
3
+ test_project.Foo
4
+ thing.attr
5
+ # split
6
+ # split
7
+ Test project
8
+ ============
9
+
10
+ .. code:: python
11
+
12
+ import test_project
13
+
14
+ thing = test_project.Foo()
15
+ thing.attr = "value"
16
+
17
+ .. automodule:: test_project
@@ -0,0 +1,15 @@
1
+ type_checking_aliased
2
+ type_checking_aliased.pick
3
+ attr
4
+ # split
5
+ # split
6
+ Test project
7
+ ============
8
+
9
+ .. code:: python
10
+
11
+ import type_checking_aliased
12
+ type_checking_aliased.pick(["a"]).attr
13
+
14
+ .. automodule:: type_checking_aliased
15
+ .. automodule:: type_checking_aliased.foo
@@ -0,0 +1,17 @@
1
+ self_type
2
+ self_type.Derived
3
+ make
4
+ own
5
+ # split
6
+ # split
7
+ Test project
8
+ ============
9
+
10
+ .. code:: python
11
+
12
+ import self_type
13
+
14
+ self_type.Derived().make().own()
15
+
16
+ .. automodule:: self_type
17
+ :no-inherited-members:
@@ -14,7 +14,7 @@ def optional() -> Optional[Foo]: # noqa: UP045
14
14
  """Return optional type."""
15
15
 
16
16
 
17
- def optional_manual() -> None | Foo:
17
+ def optional_manual() -> None | Foo: # noqa: RUF036
18
18
  """Return manually constructed optional type."""
19
19
 
20
20
 
@@ -0,0 +1,23 @@
1
+ # noqa: INP001
2
+ # Test resolving `typing.Self` return annotations, see #147 for details.
3
+
4
+ try:
5
+ from typing import Self # Python >= 3.11
6
+ except ImportError:
7
+ from typing_extensions import Self
8
+
9
+
10
+ class Base:
11
+ """Base class defining a method that returns `Self`."""
12
+
13
+ def make(self) -> Self:
14
+ """Return an instance of whatever class this was accessed through."""
15
+ return self
16
+
17
+
18
+ class Derived(Base):
19
+ """Combines a `Self`-returning base with its own method, like a mixin."""
20
+
21
+ def own(self) -> Self:
22
+ """Test method defined directly on the subclass."""
23
+ return self
@@ -56,7 +56,7 @@ def optional() -> Foo | None:
56
56
  """Return optional type."""
57
57
 
58
58
 
59
- def optional_manual() -> None | Foo:
59
+ def optional_manual() -> None | Foo: # noqa: RUF036
60
60
  """Return manually constructed optional type."""
61
61
 
62
62
 
@@ -0,0 +1,14 @@
1
+ from __future__ import annotations
2
+
3
+ from typing import TYPE_CHECKING as _TYPE_CHECKING
4
+
5
+ if _TYPE_CHECKING:
6
+ from collections.abc import Collection
7
+
8
+ from .foo import Foo
9
+
10
+
11
+ def pick(items: Collection[str]) -> Foo:
12
+ """Return value whose annotation references a name guarded by an
13
+ aliased ``if TYPE_CHECKING: ...``
14
+ """
@@ -0,0 +1,4 @@
1
+ class Foo:
2
+ """Foo test class."""
3
+
4
+ attr: str = "test"
@@ -88,6 +88,48 @@ class TestAssign:
88
88
  refs = [("a", "a"), ("a", "a")]
89
89
  return s, refs
90
90
 
91
+ @refs_equal
92
+ def test_assign_to_attribute_uses_once(self):
93
+ s = "import a\na.b = 1"
94
+ refs = [("a", "a"), ("a.b", "a.b")]
95
+ return s, refs
96
+
97
+ @refs_equal
98
+ def test_assign_to_nested_attribute_uses_once(self):
99
+ s = "import a\na.b.c = 1"
100
+ refs = [("a", "a"), ("a.b.c", "a.b.c")]
101
+ return s, refs
102
+
103
+ @refs_equal
104
+ def test_assign_to_attribute_of_followed_name_uses_once(self):
105
+ s = "import a\nb = a()\nb.c = 1"
106
+ refs = [("a", "a"), ("a", "a"), ("a.()", "b"), ("a.().c", "b.c")]
107
+ return s, refs
108
+
109
+ @refs_equal
110
+ def test_multitarget_assign_to_attributes_uses_once_each(self):
111
+ s = "import a\na.b = a.c = 1"
112
+ refs = [("a", "a"), ("a.c", "a.c"), ("a.b", "a.b")]
113
+ return s, refs
114
+
115
+ @refs_equal
116
+ def test_unpack_assign_to_attribute_uses_once(self):
117
+ s = "import a\na.b, c = 1, 2"
118
+ refs = [("a", "a"), ("a.b", "a.b")]
119
+ return s, refs
120
+
121
+ @refs_equal
122
+ def test_annassign_to_attribute_uses_once(self):
123
+ s = "import a\na.b: int = 1"
124
+ refs = [("a", "a"), ("int", "int"), ("a.b", "a.b")]
125
+ return s, refs
126
+
127
+ @refs_equal
128
+ def test_augassign_to_attribute_uses_once(self):
129
+ s = "import a\na.b += 1"
130
+ refs = [("a", "a"), ("a.b", "a.b")]
131
+ return s, refs
132
+
91
133
  @refs_equal
92
134
  def test_assign_subscript_uses(self):
93
135
  s = "import a\na.b[0] = 1"
@@ -1,4 +0,0 @@
1
- -r extras
2
-
3
- pytest>=6
4
- coverage[toml]>=5