1.. _ctags-lang-python(7): 2 3============================================================== 4ctags-lang-python 5============================================================== 6------------------------------------------------------------------- 7Random notes about tagging python source code with Universal Ctags 8------------------------------------------------------------------- 9:Version: @VERSION@ 10:Manual group: Universal Ctags 11:Manual section: 7 12 13SYNOPSIS 14-------- 15| **@CTAGS_NAME_EXECUTABLE@** ... --languages=+Python ... 16| **@CTAGS_NAME_EXECUTABLE@** ... --language-force=Python ... 17| **@CTAGS_NAME_EXECUTABLE@** ... --map-Python=+.py ... 18 19DESCRIPTION 20----------- 21This man page gathers random notes about tagging python source code. 22 23TAGGING ``import`` STATEMENTS 24----------------------------- 25 26Summary 27~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 28 29`import X` 30 31 ==== ========== ================== =================== 32 name kind role other noticeable fields 33 ==== ========== ================== =================== 34 X module imported N/A 35 ==== ========== ================== =================== 36 37`import X as Y` 38 39 ==== ========== ================== =================== 40 name kind role other noticeable fields 41 ==== ========== ================== =================== 42 X module indirectlyImported N/A 43 Y namespace definition nameref:module:X 44 ==== ========== ================== =================== 45 46`from X import *` 47 48 ==== ========== ================== =================== 49 name kind role other noticeable fields 50 ==== ========== ================== =================== 51 `X` module namespace N/A 52 ==== ========== ================== =================== 53 54`from X import Y` 55 56 ==== ========== ================== =================== 57 name kind role other noticeable fields 58 ==== ========== ================== =================== 59 `X` module namespace N/A 60 `Y` unknown imported scope:module:`X` 61 ==== ========== ================== =================== 62 63`from X import Y as Z` 64 65 ==== ========== ================== =================== 66 name kind role other noticeable fields 67 ==== ========== ================== =================== 68 `X` module namespace N/A 69 `Y` unknown indirectlyImported scope:module:`X` 70 `Z` unknown definition nameref:unknown:`Y` 71 ==== ========== ================== =================== 72 73.. 74 ===================== ==== ========== ================== =================== 75 input code name kind role other noticeable fields 76 ===================== ==== ========== ================== =================== 77 import X X module imported 78 import X as Y X module indirectlyImported 79 import X as Y Y namespace definition nameref:module:X 80 from X import * X module namespace 81 from X import Y X module namespace 82 from X import Y Y unknown imported scope:module:X 83 from X import Y as Z X module namespace 84 from X import Y as Z Y unknown indirectlyImported scope:module:X 85 from X import Y as Z Z unknown definition nameref:unknown:Y 86 ===================== ==== ========== ================== =================== 87 88.. a table having merged cells cannot be converted to man page 89.. 90 +--------------------+------------------------------------------------------+ 91 |input code |output tags | 92 | +----+----------+------------------+-------------------+ 93 | |name| kind |role |other noticeable fields | 94 +====================+====+==========+==================+===================+ 95 |import X |X | module |imported | | 96 +--------------------+----+----------+------------------+-------------------+ 97 |import X as Y |X | module |indirectlyImported| | 98 | +----+----------+------------------+-------------------+ 99 | |Y | namespace|definition |nameref:module:X | 100 +--------------------+----+----------+------------------+-------------------+ 101 |from X import * |X | module |namespace | | 102 +--------------------+----+----------+------------------+-------------------+ 103 |from X import Y |X | module |namespace | | 104 | +----+----------+------------------+-------------------+ 105 | |Y | unknown |imported |scope:module:X | 106 +--------------------+----+----------+------------------+-------------------+ 107 |from X import Y as Z|X | module |namespace | | 108 | +----+----------+------------------+-------------------+ 109 | |Y | unknown |indirectlyImported|scope:module:X | 110 | +----+----------+------------------+-------------------+ 111 | |Z | unknown |definition |nameref:unknown:Y | 112 +--------------------+----+----------+------------------+-------------------+ 113 114Examples 115~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 116"input.py" 117 118.. code-block:: Python 119 120 import X0 121 122"output.tags" 123with "--options=NONE -o - --extras=+r --fields=+rzK input.py" 124 125.. code-block:: tags 126 127 X0 input.py /^import X0$/;" kind:module roles:imported 128 129A tag for an imported module has ``module`` kind with ``imported`` role. The 130module is not defined here; it is defined in another file. So the tag for the 131imported module is a reference tag; specify ``--extras=+r`` (or 132``--extras=+{reference}``) option for tagging it. "roles:" field enabled with 133``--fields=+r`` is for recording the module is "imported" to the tag file. 134 135"input.py" 136 137.. code-block:: Python 138 139 import X1 as Y1 140 141"output.tags" 142with "--options=NONE -o - --extras=+r --fields=+rzK --fields-Python=+{nameref} input.py" 143 144.. code-block:: tags 145 146 X1 input.py /^import X1 as Y1$/;" kind:module roles:indirectlyImported 147 Y1 input.py /^import X1 as Y1$/;" kind:namespace roles:def nameref:module:X1 148 149"Y1" introduces a new name and is defined here. So "Y1" is tagged as a 150definition tag. "X1" is imported in a way that its name cannot be used 151in this source file. For letting client tools know that the name cannot be used, 152``indirectlyImported`` role is assigned for "X1". "Y1" is the name for 153accessing objects defined in the module imported via "X1". For recording this 154relationship, ``nameref:`` field is attached to the tag of "Y1". Instead of 155``module`` kind, ``namespace`` kind is assigned to "Y1" because "Y1" itself 156isn't a module. 157 158"input.py" 159 160.. code-block:: Python 161 162 from X2 import * 163 164"output.tags" 165with "--options=NONE -o - --extras=+r --fields=+rzK input.py" 166 167.. code-block:: tags 168 169 X2 input.py /^from X2 import *$/;" kind:module roles:namespace 170 171The module is not defined here; it is defined in another file. So the tag for 172the imported module is a reference tag. Unlike "X0" in "import X0", "X2" may not 173be used because the names defined in "X2" can be used in this source file. To represent 174the difference ``namespace`` role is attached to "X2" instead of ``imported``. 175 176"input.py" 177 178.. code-block:: Python 179 180 from X3 import Y3 181 182"output.tags" 183with "--options=NONE -o - --extras=+r --fields=+rzKZ input.py" 184 185.. code-block:: tags 186 187 X3 input.py /^from X3 import Y3$/;" kind:module roles:namespace 188 Y3 input.py /^from X3 import Y3$/;" kind:unknown scope:module:X3 roles:imported 189 190"Y3" is a name for a language object defined in "X3" module. "scope:module:X3" 191attached to "Y3" represents this relation between "Y3" and "X3". ctags 192assigns ``unknown`` kind to "Y3" because ctags cannot know whether "Y3" is a 193class, a variable, or a function from the input file. 194 195"input.py" 196 197.. code-block:: Python 198 199 from X4 import Y4 as Z4 200 201"output.tags" 202with "--options=NONE -o - --extras=+r --fields=+rzKZ input.py" 203 204.. code-block:: tags 205 206 X4 input.py /^from X4 import Y4 as Z4$/;" kind:module roles:namespace 207 Y4 input.py /^from X4 import Y4 as Z4$/;" kind:unknown scope:module:X4 roles:indirectlyImported 208 Z4 input.py /^from X4 import Y4 as Z4$/;" kind:unknown roles:def nameref:unknown:Y4 209 210"Y4" is similar to "Y3" of "from X3 import Y3" but the name cannot be used here. 211``indirectlyImported`` role assigned to "Y4" representing this. "Z4" is the name for 212accessing the language object named in "Y4" in "X4" module. "nameref:unknown:Y4" 213attached to "Z4" and "scope:module:X4" attached to "Y4" represent the relations. 214 215LAMBDA EXPRESSION AND TYPE HINT 216------------------------------- 217 218Summary 219~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 220 221`id = lambda var0: var0` 222 223 =========== ========== ================== =================== 224 name kind role other noticeable fields 225 =========== ========== ================== =================== 226 `id` function definition signature:(`var0`) 227 =========== ========== ================== =================== 228 229`id_t: Callable[[int], int] = lambda var1: var1` 230 231 =========== ========== ================== =================== 232 name kind role other noticeable fields 233 =========== ========== ================== =================== 234 `id_t` variable definition typeref:typename:`Callable[[int], int]` nameref:function:anonFuncN 235 anonFuncN function definition signature:(`var1`) 236 =========== ========== ================== =================== 237 238Examples 239~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 240"input.py" 241 242.. code-block:: Python 243 244 from typing import Callable 245 id = lambda var0: var0 246 id_t: Callable[[int], int] = lambda var1: var1 247 248"output.tags" 249with "--options=NONE -o - --sort=no --fields=+KS --fields-Python=+{nameref} --extras=+{anonymous} input.py" 250 251.. code-block:: tags 252 253 id input.py /^id = lambda var0: var0$/;" function signature:(var0) 254 id_t input.py /^id_t: Callable[[int], int] = lambda var1: var1$/;"\ 255 variable typeref:typename:Callable[[int], int] nameref:function:anonFunc84011d2c0101 256 anonFunc84011d2c0101 input.py /^id_t: Callable[[int], int] = lambda var1: var1$/;"\ 257 function signature:(var1) 258 259If a variable ("id") with no type hint is initialized with a lambda expression, 260ctags assigns ``function`` kind for the tag of "id". 261 262If a variable ("id_t") with a type hint is initialized with a lambda expression, 263ctags assigns ``variable`` kind for the tag of "id_t" with ``typeref:`` and 264``nameref:`` fields. ctags fills ``typeref:`` field with the value of the type 265hint. The way of filling ``nameref:`` is a bit complicated. 266 267For the lambda expression used in initializing the type-hint'ed variable, ctags 268creates ``anonymous`` extra tag ("anonFunc84011d2c0101"). ctags fills the 269``nameref:`` field of "id_t" with the name of ``anonymous`` extra tag: 270"nameref:function:anonFunc84011d2c0101". 271 272You may think why ctags does so complicated, and why ctags doesn't emit 273following tags output for the input:: 274 275 id input.py /^id = \\$/;" function signature:(var0) 276 id_t input.py /^id_t: \\$/;" function typeref:typename:Callable[[int], int] signature:(var1) 277 278There is a reason. The other languages of ctags obey the following rule: ctags fills 279``typeref:`` field for a tag of a callable object (like function) with the type 280of its return value. If we consider "id_t" is a function, its ``typeref:`` field 281should have "typename:int". However, for filling ``typeref:`` with "typename:int", 282ctags has to analyze "Callable[[int], int]" deeper. We don't want to do so. 283 284SEE ALSO 285-------- 286ctags(1), ctags-client-tools(7), ctags-lang-iPythonCell(7) 287