sphinx autodoc can't find module

  • Last Update :
  • Techknowledgy :

By the way: you can use the Makefile created by Sphinx to create your documentation. Just call

make

If something went wrong before try:

make clean

It sounds like os.path.append() is working OK for folks, but if you follow the conf.py template, you would insert the module path to the front of sys.path using os.path.insert(0, ...), and just add an extra .

import os
import sys
sys.path.insert(0, os.path.abspath('..'))

If you have setup your sphinx project to use separate build and source directories, that call should instead be:

sys.path.insert(0, os.path.abspath('../..'))

I use linux, so directories are specified with a forward slash, but a cross-platform method for specifying parent directories can be acheived with pathlib.

from pathlib
import Path

parent = Path(__file__).parent
parents_parent = Path(__file__).parents[1]

just add the path to your project folder.

sys.path.append('/home/workspace/myproj/myproj')

For the following example folder structure

project_dir
   |
   -setup.py |
   -src |
   | -__init__.py |
   | -source1.py |
   | -sub_project |
   | -__init__.py |
   | -source2.py |
   -docs |
   -conf.py |
   -source |
   | -index.rst |
   -_build

I included

for x in os.walk('../../src'):
   sys.path.insert(0, x[0])

My .. automethod:: mymodule.func directive should actually have been:

..automethod::mymodule::func

I think I did this the first time I tried to add a file to the toctree. I think it was because I left out the blank line between the :maxdepth line and the file name.

..Animatrix Concepts documentation master file, created by
sphinx - quickstart on Thu Mar 22 18: 06: 15 2012.
You can adapt this file completely to your liking, but it should at least
contain the root `toctree`
directive.

Welcome to Animatrix Concepts documentation!
   ===
   === === === === === === === === === === === === === ==

   Contents:

   ..toctree::
   : maxdepth: 2

stuff

Indices and tables
   ===
   === === === === ===

   *
   : ref: `genindex` *
   : ref: `modindex` *
   : ref: `search`

Suggestion : 2

Add the module you are documenting to sys.path in the sphinx conf.py file for your project. Autodoc actually has to import your python code, so it needs to be able to find it.,So my project has the documentation root directory in a subdirectory called docs/ I tried adding sys.path.append(os.path.abspath('..')) to docs/conf.py but that didn't quit get it. Going up two levels did the trick.,Final solution, add the following to conf.py (exact path will vary based on your configuration):,This worked fine, until I renamed my module and my tests in the tests/ subdirectory started throwing import errors. I really hate how painful python makes organizing your code. Before fixing my $PYTHONPATH so my unit tests work again, I tried adding two sys.path.append() calls to fix it and it worked. So in the end my conf.py looks like:

sphinx-autodoc ImportError: No module named foo

> make html
sphinx - build - b html - d _build / doctrees._build / html
Running Sphinx v1 .5 .5
loading pickled environment...done
building[mo]: targets
for 0 po files that are out of date
building[html]: targets
for 0 source files that are out of date
updating environment: 0 added, 2 changed, 0 removed
reading sources...[100 % ] accounting.tests /
   home / macgregor / Repos / personal / accounting / docs / accounting.rst: 17: WARNING: autodoc: failed to
import module u 'accounting.accounting';
the following exception was raised:
   Traceback(most recent call last):
   File "/usr/lib64/python2.7/site-packages/sphinx/ext/autodoc.py", line 551, in import_object
__import__(self.modname)
ImportError: No module named accounting

Add the module you are documenting to sys.path in the sphinx conf.py file for your project. Autodoc actually has to import your python code, so it needs to be able to find it.

> tree - L 2
   . / ├──accounting.py├── docs / │├──accounting.rst│├── accounting.tests.rst│├── _build / │├──conf.py│├── index.rst│├── Makefile│├── modules.rst│├── _static / │└──_templates / ├──__init__.py├── mapping.py├── models.py├── README.md└── tests /

Final solution, add the following to conf.py (exact path will vary based on your configuration):

import os
import sys
sys.path.append(os.path.abspath('../..'))

Suggestion : 3

You have to include the path to your modules in in the sys.path in your conf.py. Look at the top of your conf.py (just after the import of sys), there is a sys.path.insert() statement, which you can adapt.,It sounds like os.path.append() is working OK for folks, but if you follow the conf.py template, you would insert the module path to the front of sys.path using os.path.insert(0, ...), and just add an extra .,To run python code, the python interpreter needs to know where it is. With the sphinx config being a python script, it's location needs to be made known, which is done by adding it the the sys.path variable using the insert method (see the docs on module search path).,It may be because the dependencies of those modules are not satisfied under your python environment. You will want to check if all the import statements are working within the modules.

By the way: you can use the Makefile created by Sphinx to create your documentation. Just call

make

If something went wrong before try:

make clean

It sounds like os.path.append() is working OK for folks, but if you follow the conf.py template, you would insert the module path to the front of sys.path using os.path.insert(0, ...), and just add an extra .

import os
import sys sys.path.insert(0, os.path.abspath('..'))

If you have setup your sphinx project to use separate build and source directories, that call should instead be:

sys.path.insert(0, os.path.abspath('../..'))

I use linux, so directories are specified with a forward slash, but a cross-platform method for specifying parent directories can be acheived with pathlib.

from pathlib
import Path parent = Path(__file__).parent parents_parent = Path(__file__).parents[1]

just add the path to your project folder.

sys.path.append('/home/workspace/myproj/myproj')

For the following example folder structure

project_dir | -setup.py | -src | | -__init__.py | | -source1.py | | -sub_project | | -__init__.py | | -source2.py | -docs | -conf.py | -source | | -index.rst | -_build

I included

for x in os.walk('../../src'): sys.path.insert(0, x[0])

Suggestion : 4

This extension can import the modules you are documenting, and pull in documentation from docstrings in a semi-automatic way.,Only the class’ docstring is inserted. This is the default. You can still document __init__ as a separate method using automethod or the members option to autoclass.,The “auto” directives can also contain content of their own, it will be inserted into the resulting non-auto directive source after the docstring (but before any automatic member documentation).,sphinx.ext.autodoc – Include documentation from docstrings Directives Configuration Docstring preprocessing Skipping members

..autoclass::Noodle
..class::Noodle

Noodle 's docstring.
..autoclass::Noodle: members: eat, slurp

   ..method::boil(time = 10)

Boil the noodle * time * minutes.
..automodule::noodle: members:
..autoclass::Noodle: members:
..autoclass::Noodle: members: eat, slurp

Suggestion : 5

I need nextgen/docs/Makefile to generate the HTML for ys_utils and all other modules I"m going to have.,If you are not yet on Python 3.5 or need to write backward-compatible code, and you want this in a single expression, the most performant while the correct approach is to put it in a function:,Again, it doesn"t work for 3 when keys are not strings. The implicit calling contract is that namespaces take ordinary dictionaries, while users must only pass keyword arguments that are strings. All other callables enforced it. dict broke this consistency in Python 2:,Dictionaries are intended to take hashable keys (e.g. frozensets or tuples), but this method fails in Python 3 when keys are not strings.

If you want just files, you could either filter this down using os.path:

from os
import listdir
from os.path
import isfile, join
onlyfiles = [f
   for f in listdir(mypath) if isfile(join(mypath, f))
]

or you could use os.walk() which will yield two lists for each directory it visits - splitting into files and dirs for you. If you only want the top directory you can break the first time it yields

from os
import walk

f = []
for (dirpath, dirnames, filenames) in walk(mypath):
   f.extend(filenames)
break

or, shorter:

from os
import walk

filenames = next(walk(mypath), (None, None, []))[2] #[]
if no file

I prefer using the glob module, as it does pattern matching and expansion.

import glob
print(glob.glob("/home/adam/*"))

It does pattern matching intuitively

import glob
# All files ending with.txt
print(glob.glob("/home/adam/*.txt"))
# All files ending with.txt with depth of 2 folder
print(glob.glob("/home/adam/*/*.txt"))

It will return a list with the queried files:

["/home/adam/file1.txt", "/home/adam/file2.txt", ....]

With listdir in os module you get the files and the folders in the current dir

 import os
 arr = os.listdir()
 print(arr)

    >>>
    ["$RECYCLE.BIN", "work.txt", "3ebooks.txt", "documents"]

Looking in a directory

arr = os.listdir("c:\files")

with glob you can specify a type of file to list like this

import glob

txtfiles = []
for file in glob.glob("*.txt"):
   txtfiles.append(file)

get the full path of only files in the current directory

import os
from os
import listdir
from os.path
import isfile, join

cwd = os.getcwd()
onlyfiles = [os.path.join(cwd, f) for f in os.listdir(cwd) if
   os.path.isfile(os.path.join(cwd, f))
]
print(onlyfiles)

["G:\getfilesname\getfilesname.py", "G:\getfilesname\example.txt"]

You get the full path in return

 import os
 files_path = [os.path.abspath(x) for x in os.listdir()]
 print(files_path)

 ["F:\documentiapplications.txt", "F:\documenticollections.txt"]

I have two Python dictionaries, and I want to write a single expression that returns these two dictionaries, merged (i.e. taking the union). The update() method would be what I need, if it returned its result instead of modifying a dictionary in-place.

>>> x = {
      "a": 1,
      "b": 2
   } >>>
   y = {
      "b": 10,
      "c": 11
   } >>>
   z = x.update(y) >>>
   print(z)
None
   >>>
   x {
      "a": 1,
      "b": 10,
      "c": 11
   }

In Python 3.9.0 or greater (released 17 October 2020): PEP-584, discussed here, was implemented and provides the simplest method:

z = x | y # NOTE: 3.9 + ONLY

In Python 3.5 or greater:

z = {
   ** x,
   ** y
}