Commits

Chance Jiang committed 34a51b9 Merge

Merge with default 67701bff2aee, to get Chinese docs in doc_zh

Comments (0)

Files changed (291)

 ^env/
 \.DS_Store$
 ~$
+^utils/.*3\.py$
+^distribute-
+^tests/root/_build/*
+^tests/root/generated/*
 * Martin Hans -- autodoc improvements
 * Dave Kuhlman -- original LaTeX writer
 * Thomas Lamb -- linkcheck builder
+* Robert Lehmann -- gettext builder (GSOC project)
 * Dan MacKinlay -- metadata fixes
 * Martin Mahner -- nature theme
 * Will Maier -- directory HTML builder
+* Jacob Mason -- websupport library (GSOC project)
 * Roland Meister -- epub builder
 * Ezio Melotti -- collapsible sidebar JavaScript
-* Daniel Neuhäuser -- JavaScript domain
+* Daniel Neuhäuser -- JavaScript domain, Python 3 support (GSOC)
 * Christopher Perkins -- autosummary integration
 * Benjamin Peterson -- unittests
 * T. Powers -- HTML output improvements
 * Antonio Valentino -- qthelp builder
 * Pauli Virtanen -- autodoc improvements, autosummary extension
 * Stefan van der Walt -- autosummary extension
+* John Waltman -- Texinfo builder
 * Barry Warsaw -- setup command improvements
 * Sebastian Wiesner -- image handling, distutils support
 

CHANGES

File contents unchanged.

EXAMPLES

File contents unchanged.
 
 include babel.cfg
 include Makefile
-include ez_setup.py
+include distribute_setup.py
 include sphinx-autogen.py
 include sphinx-build.py
 include sphinx-quickstart.py
 PYTHON ?= python
 
-export PYTHONPATH = $(shell echo "$$PYTHONPATH"):./sphinx
+.PHONY: all check clean clean-pyc clean-patchfiles clean-backupfiles \
+        clean-generated pylint reindent test covertest build convert-utils
 
-.PHONY: all check clean clean-pyc clean-patchfiles pylint reindent test
+DONT_CHECK = -i build -i dist -i sphinx/style/jquery.js \
+             -i sphinx/pycode/pgen2 -i sphinx/util/smartypants.py \
+             -i .ropeproject -i doc/_build -i tests/path.py \
+             -i tests/coverage.py -i env -i utils/convert.py \
+             -i utils/reindent3.py -i utils/check_sources3.py -i .tox
 
-all: clean-pyc check test
+all: clean-pyc clean-backupfiles check test
 
+ifeq ($(PYTHON), python3)
+check: convert-utils
+	@$(PYTHON) utils/check_sources3.py $(DONT_CHECK) .
+else
 check:
-	@$(PYTHON) utils/check_sources.py -i build -i dist -i sphinx/style/jquery.js \
-		-i sphinx/pycode/pgen2 -i sphinx/util/smartypants.py -i .ropeproject \
-		-i doc/_build -i ez_setup.py -i tests/path.py -i tests/coverage.py \
-		-i env -i .tox .
+	@$(PYTHON) utils/check_sources.py $(DONT_CHECK) .
+endif
 
-clean: clean-pyc clean-patchfiles
+clean: clean-pyc clean-patchfiles clean-backupfiles clean-generated
 
 clean-pyc:
 	find . -name '*.pyc' -exec rm -f {} +
 	find . -name '*.pyo' -exec rm -f {} +
-	find . -name '*~' -exec rm -f {} +
 
 clean-patchfiles:
 	find . -name '*.orig' -exec rm -f {} +
 	find . -name '*.rej' -exec rm -f {} +
 
+clean-backupfiles:
+	find . -name '*~' -exec rm -f {} +
+	find . -name '*.bak' -exec rm -f {} +
+
+clean-generated:
+	rm -f utils/*3.py*
+
 pylint:
 	@pylint --rcfile utils/pylintrc sphinx
 
+ifeq ($(PYTHON), python3)
+reindent: convert-utils
+	@$(PYTHON) utils/reindent3.py -r -n .
+else
 reindent:
-	@$(PYTHON) utils/reindent.py -r -B .
+	@$(PYTHON) utils/reindent.py -r -n .
+endif
 
-test:
+test: build
 	@cd tests; $(PYTHON) run.py -d -m '^[tT]est' $(TEST)
 
-covertest:
-	@cd tests; $(PYTHON) run.py -d -m '^[tT]est' --with-coverage --cover-package=sphinx $(TEST)
+covertest: build
+	@cd tests; $(PYTHON) run.py -d -m '^[tT]est' --with-coverage \
+		--cover-package=sphinx $(TEST)
+
+build:
+	@$(PYTHON) setup.py build
+
+ifeq ($(PYTHON), python3)
+convert-utils:
+	@python3 utils/convert.py -i utils/convert.py utils/
+endif
 Or read them online at <http://sphinx.pocoo.org/>.
 
 
+Testing
+=======
+
+To run the tests with the interpreter available as ``python``, use::
+
+    make test
+
+If you want to use a different interpreter, e.g. ``python3``, use::
+
+    PYTHON=python3 make test
+
+
 Contributing
 ============
 

custom_fixers/__init__.py

Empty file added.

custom_fixers/fix_alt_unicode.py

+from lib2to3.fixer_base import BaseFix
+from lib2to3.fixer_util import Name
+
+class FixAltUnicode(BaseFix):
+    PATTERN = """
+    func=funcdef< 'def' name='__unicode__'
+                  parameters< '(' NAME ')' > any+ >
+    """
+
+    def transform(self, node, results):
+        name = results['name']
+        name.replace(Name('__str__', prefix=name.prefix))

distribute_setup.py

+#!python
+"""Bootstrap distribute installation
+
+If you want to use setuptools in your package's setup.py, just include this
+file in the same directory with it, and add this to the top of your setup.py::
+
+    from distribute_setup import use_setuptools
+    use_setuptools()
+
+If you want to require a specific version of setuptools, set a download
+mirror, or use an alternate download directory, you can do so by supplying
+the appropriate options to ``use_setuptools()``.
+
+This file can also be run as a script to install or upgrade setuptools.
+"""
+import os
+import sys
+import time
+import fnmatch
+import tempfile
+import tarfile
+from distutils import log
+
+try:
+    from site import USER_SITE
+except ImportError:
+    USER_SITE = None
+
+try:
+    import subprocess
+
+    def _python_cmd(*args):
+        args = (sys.executable,) + args
+        return subprocess.call(args) == 0
+
+except ImportError:
+    # will be used for python 2.3
+    def _python_cmd(*args):
+        args = (sys.executable,) + args
+        # quoting arguments if windows
+        if sys.platform == 'win32':
+            def quote(arg):
+                if ' ' in arg:
+                    return '"%s"' % arg
+                return arg
+            args = [quote(arg) for arg in args]
+        return os.spawnl(os.P_WAIT, sys.executable, *args) == 0
+
+DEFAULT_VERSION = "0.6.13"
+DEFAULT_URL = "http://pypi.python.org/packages/source/d/distribute/"
+SETUPTOOLS_FAKED_VERSION = "0.6c11"
+
+SETUPTOOLS_PKG_INFO = """\
+Metadata-Version: 1.0
+Name: setuptools
+Version: %s
+Summary: xxxx
+Home-page: xxx
+Author: xxx
+Author-email: xxx
+License: xxx
+Description: xxx
+""" % SETUPTOOLS_FAKED_VERSION
+
+
+def _install(tarball):
+    # extracting the tarball
+    tmpdir = tempfile.mkdtemp()
+    log.warn('Extracting in %s', tmpdir)
+    old_wd = os.getcwd()
+    try:
+        os.chdir(tmpdir)
+        tar = tarfile.open(tarball)
+        _extractall(tar)
+        tar.close()
+
+        # going in the directory
+        subdir = os.path.join(tmpdir, os.listdir(tmpdir)[0])
+        os.chdir(subdir)
+        log.warn('Now working in %s', subdir)
+
+        # installing
+        log.warn('Installing Distribute')
+        if not _python_cmd('setup.py', 'install'):
+            log.warn('Something went wrong during the installation.')
+            log.warn('See the error message above.')
+    finally:
+        os.chdir(old_wd)
+
+
+def _build_egg(egg, tarball, to_dir):
+    # extracting the tarball
+    tmpdir = tempfile.mkdtemp()
+    log.warn('Extracting in %s', tmpdir)
+    old_wd = os.getcwd()
+    try:
+        os.chdir(tmpdir)
+        tar = tarfile.open(tarball)
+        _extractall(tar)
+        tar.close()
+
+        # going in the directory
+        subdir = os.path.join(tmpdir, os.listdir(tmpdir)[0])
+        os.chdir(subdir)
+        log.warn('Now working in %s', subdir)
+
+        # building an egg
+        log.warn('Building a Distribute egg in %s', to_dir)
+        _python_cmd('setup.py', '-q', 'bdist_egg', '--dist-dir', to_dir)
+
+    finally:
+        os.chdir(old_wd)
+    # returning the result
+    log.warn(egg)
+    if not os.path.exists(egg):
+        raise IOError('Could not build the egg.')
+
+
+def _do_download(version, download_base, to_dir, download_delay):
+    egg = os.path.join(to_dir, 'distribute-%s-py%d.%d.egg'
+                       % (version, sys.version_info[0], sys.version_info[1]))
+    if not os.path.exists(egg):
+        tarball = download_setuptools(version, download_base,
+                                      to_dir, download_delay)
+        _build_egg(egg, tarball, to_dir)
+    sys.path.insert(0, egg)
+    import setuptools
+    setuptools.bootstrap_install_from = egg
+
+
+def use_setuptools(version=DEFAULT_VERSION, download_base=DEFAULT_URL,
+                   to_dir=os.curdir, download_delay=15, no_fake=True):
+    # making sure we use the absolute path
+    to_dir = os.path.abspath(to_dir)
+    was_imported = 'pkg_resources' in sys.modules or \
+        'setuptools' in sys.modules
+    try:
+        try:
+            import pkg_resources
+            if not hasattr(pkg_resources, '_distribute'):
+                if not no_fake:
+                    _fake_setuptools()
+                raise ImportError
+        except ImportError:
+            return _do_download(version, download_base, to_dir, download_delay)
+        try:
+            pkg_resources.require("distribute>="+version)
+            return
+        except pkg_resources.VersionConflict:
+            e = sys.exc_info()[1]
+            if was_imported:
+                sys.stderr.write(
+                "The required version of distribute (>=%s) is not available,\n"
+                "and can't be installed while this script is running. Please\n"
+                "install a more recent version first, using\n"
+                "'easy_install -U distribute'."
+                "\n\n(Currently using %r)\n" % (version, e.args[0]))
+                sys.exit(2)
+            else:
+                del pkg_resources, sys.modules['pkg_resources']    # reload ok
+                return _do_download(version, download_base, to_dir,
+                                    download_delay)
+        except pkg_resources.DistributionNotFound:
+            return _do_download(version, download_base, to_dir,
+                                download_delay)
+    finally:
+        if not no_fake:
+            _create_fake_setuptools_pkg_info(to_dir)
+
+def download_setuptools(version=DEFAULT_VERSION, download_base=DEFAULT_URL,
+                        to_dir=os.curdir, delay=15):
+    """Download distribute from a specified location and return its filename
+
+    `version` should be a valid distribute version number that is available
+    as an egg for download under the `download_base` URL (which should end
+    with a '/'). `to_dir` is the directory where the egg will be downloaded.
+    `delay` is the number of seconds to pause before an actual download
+    attempt.
+    """
+    # making sure we use the absolute path
+    to_dir = os.path.abspath(to_dir)
+    try:
+        from urllib.request import urlopen
+    except ImportError:
+        from urllib2 import urlopen
+    tgz_name = "distribute-%s.tar.gz" % version
+    url = download_base + tgz_name
+    saveto = os.path.join(to_dir, tgz_name)
+    src = dst = None
+    if not os.path.exists(saveto):  # Avoid repeated downloads
+        try:
+            log.warn("Downloading %s", url)
+            src = urlopen(url)
+            # Read/write all in one block, so we don't create a corrupt file
+            # if the download is interrupted.
+            data = src.read()
+            dst = open(saveto, "wb")
+            dst.write(data)
+        finally:
+            if src:
+                src.close()
+            if dst:
+                dst.close()
+    return os.path.realpath(saveto)
+
+def _no_sandbox(function):
+    def __no_sandbox(*args, **kw):
+        try:
+            from setuptools.sandbox import DirectorySandbox
+            if not hasattr(DirectorySandbox, '_old'):
+                def violation(*args):
+                    pass
+                DirectorySandbox._old = DirectorySandbox._violation
+                DirectorySandbox._violation = violation
+                patched = True
+            else:
+                patched = False
+        except ImportError:
+            patched = False
+
+        try:
+            return function(*args, **kw)
+        finally:
+            if patched:
+                DirectorySandbox._violation = DirectorySandbox._old
+                del DirectorySandbox._old
+
+    return __no_sandbox
+
+def _patch_file(path, content):
+    """Will backup the file then patch it"""
+    existing_content = open(path).read()
+    if existing_content == content:
+        # already patched
+        log.warn('Already patched.')
+        return False
+    log.warn('Patching...')
+    _rename_path(path)
+    f = open(path, 'w')
+    try:
+        f.write(content)
+    finally:
+        f.close()
+    return True
+
+_patch_file = _no_sandbox(_patch_file)
+
+def _same_content(path, content):
+    return open(path).read() == content
+
+def _rename_path(path):
+    new_name = path + '.OLD.%s' % time.time()
+    log.warn('Renaming %s into %s', path, new_name)
+    os.rename(path, new_name)
+    return new_name
+
+def _remove_flat_installation(placeholder):
+    if not os.path.isdir(placeholder):
+        log.warn('Unkown installation at %s', placeholder)
+        return False
+    found = False
+    for file in os.listdir(placeholder):
+        if fnmatch.fnmatch(file, 'setuptools*.egg-info'):
+            found = True
+            break
+    if not found:
+        log.warn('Could not locate setuptools*.egg-info')
+        return
+
+    log.warn('Removing elements out of the way...')
+    pkg_info = os.path.join(placeholder, file)
+    if os.path.isdir(pkg_info):
+        patched = _patch_egg_dir(pkg_info)
+    else:
+        patched = _patch_file(pkg_info, SETUPTOOLS_PKG_INFO)
+
+    if not patched:
+        log.warn('%s already patched.', pkg_info)
+        return False
+    # now let's move the files out of the way
+    for element in ('setuptools', 'pkg_resources.py', 'site.py'):
+        element = os.path.join(placeholder, element)
+        if os.path.exists(element):
+            _rename_path(element)
+        else:
+            log.warn('Could not find the %s element of the '
+                     'Setuptools distribution', element)
+    return True
+
+_remove_flat_installation = _no_sandbox(_remove_flat_installation)
+
+def _after_install(dist):
+    log.warn('After install bootstrap.')
+    placeholder = dist.get_command_obj('install').install_purelib
+    _create_fake_setuptools_pkg_info(placeholder)
+
+def _create_fake_setuptools_pkg_info(placeholder):
+    if not placeholder or not os.path.exists(placeholder):
+        log.warn('Could not find the install location')
+        return
+    pyver = '%s.%s' % (sys.version_info[0], sys.version_info[1])
+    setuptools_file = 'setuptools-%s-py%s.egg-info' % \
+            (SETUPTOOLS_FAKED_VERSION, pyver)
+    pkg_info = os.path.join(placeholder, setuptools_file)
+    if os.path.exists(pkg_info):
+        log.warn('%s already exists', pkg_info)
+        return
+
+    log.warn('Creating %s', pkg_info)
+    f = open(pkg_info, 'w')
+    try:
+        f.write(SETUPTOOLS_PKG_INFO)
+    finally:
+        f.close()
+
+    pth_file = os.path.join(placeholder, 'setuptools.pth')
+    log.warn('Creating %s', pth_file)
+    f = open(pth_file, 'w')
+    try:
+        f.write(os.path.join(os.curdir, setuptools_file))
+    finally:
+        f.close()
+
+_create_fake_setuptools_pkg_info = _no_sandbox(_create_fake_setuptools_pkg_info)
+
+def _patch_egg_dir(path):
+    # let's check if it's already patched
+    pkg_info = os.path.join(path, 'EGG-INFO', 'PKG-INFO')
+    if os.path.exists(pkg_info):
+        if _same_content(pkg_info, SETUPTOOLS_PKG_INFO):
+            log.warn('%s already patched.', pkg_info)
+            return False
+    _rename_path(path)
+    os.mkdir(path)
+    os.mkdir(os.path.join(path, 'EGG-INFO'))
+    pkg_info = os.path.join(path, 'EGG-INFO', 'PKG-INFO')
+    f = open(pkg_info, 'w')
+    try:
+        f.write(SETUPTOOLS_PKG_INFO)
+    finally:
+        f.close()
+    return True
+
+_patch_egg_dir = _no_sandbox(_patch_egg_dir)
+
+def _before_install():
+    log.warn('Before install bootstrap.')
+    _fake_setuptools()
+
+
+def _under_prefix(location):
+    if 'install' not in sys.argv:
+        return True
+    args = sys.argv[sys.argv.index('install')+1:]
+    for index, arg in enumerate(args):
+        for option in ('--root', '--prefix'):
+            if arg.startswith('%s=' % option):
+                top_dir = arg.split('root=')[-1]
+                return location.startswith(top_dir)
+            elif arg == option:
+                if len(args) > index:
+                    top_dir = args[index+1]
+                    return location.startswith(top_dir)
+        if arg == '--user' and USER_SITE is not None:
+            return location.startswith(USER_SITE)
+    return True
+
+
+def _fake_setuptools():
+    log.warn('Scanning installed packages')
+    try:
+        import pkg_resources
+    except ImportError:
+        # we're cool
+        log.warn('Setuptools or Distribute does not seem to be installed.')
+        return
+    ws = pkg_resources.working_set
+    try:
+        setuptools_dist = ws.find(pkg_resources.Requirement.parse('setuptools',
+                                  replacement=False))
+    except TypeError:
+        # old distribute API
+        setuptools_dist = ws.find(pkg_resources.Requirement.parse('setuptools'))
+
+    if setuptools_dist is None:
+        log.warn('No setuptools distribution found')
+        return
+    # detecting if it was already faked
+    setuptools_location = setuptools_dist.location
+    log.warn('Setuptools installation detected at %s', setuptools_location)
+
+    # if --root or --preix was provided, and if
+    # setuptools is not located in them, we don't patch it
+    if not _under_prefix(setuptools_location):
+        log.warn('Not patching, --root or --prefix is installing Distribute'
+                 ' in another location')
+        return
+
+    # let's see if its an egg
+    if not setuptools_location.endswith('.egg'):
+        log.warn('Non-egg installation')
+        res = _remove_flat_installation(setuptools_location)
+        if not res:
+            return
+    else:
+        log.warn('Egg installation')
+        pkg_info = os.path.join(setuptools_location, 'EGG-INFO', 'PKG-INFO')
+        if (os.path.exists(pkg_info) and
+            _same_content(pkg_info, SETUPTOOLS_PKG_INFO)):
+            log.warn('Already patched.')
+            return
+        log.warn('Patching...')
+        # let's create a fake egg replacing setuptools one
+        res = _patch_egg_dir(setuptools_location)
+        if not res:
+            return
+    log.warn('Patched done.')
+    _relaunch()
+
+
+def _relaunch():
+    log.warn('Relaunching...')
+    # we have to relaunch the process
+    # pip marker to avoid a relaunch bug
+    if sys.argv[:3] == ['-c', 'install', '--single-version-externally-managed']:
+        sys.argv[0] = 'setup.py'
+    args = [sys.executable] + sys.argv
+    sys.exit(subprocess.call(args))
+
+
+def _extractall(self, path=".", members=None):
+    """Extract all members from the archive to the current working
+       directory and set owner, modification time and permissions on
+       directories afterwards. `path' specifies a different directory
+       to extract to. `members' is optional and must be a subset of the
+       list returned by getmembers().
+    """
+    import copy
+    import operator
+    from tarfile import ExtractError
+    directories = []
+
+    if members is None:
+        members = self
+
+    for tarinfo in members:
+        if tarinfo.isdir():
+            # Extract directories with a safe mode.
+            directories.append(tarinfo)
+            tarinfo = copy.copy(tarinfo)
+            tarinfo.mode = 448 # decimal for oct 0700
+        self.extract(tarinfo, path)
+
+    # Reverse sort directories.
+    if sys.version_info < (2, 4):
+        def sorter(dir1, dir2):
+            return cmp(dir1.name, dir2.name)
+        directories.sort(sorter)
+        directories.reverse()
+    else:
+        directories.sort(key=operator.attrgetter('name'), reverse=True)
+
+    # Set correct owner, mtime and filemode on directories.
+    for tarinfo in directories:
+        dirpath = os.path.join(path, tarinfo.name)
+        try:
+            self.chown(tarinfo, dirpath)
+            self.utime(tarinfo, dirpath)
+            self.chmod(tarinfo, dirpath)
+        except ExtractError:
+            e = sys.exc_info()[1]
+            if self.errorlevel > 1:
+                raise
+            else:
+                self._dbg(1, "tarfile: %s" % e)
+
+
+def main(argv, version=DEFAULT_VERSION):
+    """Install or upgrade setuptools and EasyInstall"""
+    tarball = download_setuptools()
+    _install(tarball)
+
+
+if __name__ == '__main__':
+    main(sys.argv[1:])
 	@echo "  epub       to make an epub file"
 	@echo "  latex      to make LaTeX files, you can set PAPER=a4 or PAPER=letter"
 	@echo "  latexpdf   to make LaTeX files and run pdflatex"
+	@echo "  texinfo    to make Texinfo files"
+	@echo "  info       to make Texinfo files and run them through makeinfo"
+	@echo "  gettext    to make PO message catalogs"
 	@echo "  changes    to make an overview over all changed/added/deprecated items"
 	@echo "  linkcheck  to check all external links for integrity"
 
 	make -C _build/latex all-pdf
 	@echo "pdflatex finished; the PDF files are in _build/latex."
 
+gettext:
+	$(SPHINXBUILD) -b gettext $(ALLSPHINXOPTS) _build/locale
+	@echo
+	@echo "Build finished. The message catalogs are in _build/locale."
+
 changes:
 	$(SPHINXBUILD) -b changes $(ALLSPHINXOPTS) _build/changes
 	@echo
 
 doctest:
 	$(SPHINXBUILD) -b doctest $(ALLSPHINXOPTS) _build/doctest
+
+texinfo:
+	$(SPHINXBUILD) -b texinfo $(ALLSPHINXOPTS) _build/texinfo
+	@echo
+	@echo "Build finished. The Texinfo files are in _build/texinfo."
+	@echo "Run \`make' in that directory to run these through makeinfo" \
+	      "(use \`make info' here to do that automatically)."
+
+info:
+	$(SPHINXBUILD) -b texinfo $(ALLSPHINXOPTS) _build/texinfo
+	@echo "Running Texinfo files through makeinfo..."
+	make -C _build/texinfo info
+	@echo "makeinfo finished; the Info files are in _build/texinfo."
 
    .. versionadded:: 1.0
 
+
+.. module:: sphinx.builders.texinfo
+.. class:: TexinfoBuilder
+
+   This builder produces Texinfo files that can be processed into Info files by
+   the :program:`makeinfo` program.  You have to specify which documents are to
+   be included in which Texinfo files via the :confval:`texinfo_documents`
+   configuration value.
+
+   The Info format is the basis of the on-line help system used by GNU Emacs and
+   the terminal-based program :program:`info`.  See :ref:`texinfo-faq` for more
+   details.  The Texinfo format is the official documentation system used by the
+   GNU project.  More information on Texinfo can be found at
+   `<http://www.gnu.org/software/texinfo/>`_.
+
+   Its name is ``texinfo``.
+
+   .. versionadded:: 1.1
+
+
 .. currentmodule:: sphinx.builders.html
 .. class:: SerializingHTMLBuilder
 
 
    .. versionadded:: 0.5
 
+.. module:: sphinx.builders.intl
+.. class:: MessageCatalogBuilder
+
+   This builder produces gettext-style message catalos.  Each top-level file or
+   subdirectory grows a single ``.pot`` catalog template.
+
+   See the documentation on :ref:`intl` for further reference.
+
+   Its name is ``gettext``.
+
+   .. versionadded:: 1.1
+
 .. module:: sphinx.builders.changes
 .. class:: ChangesBuilder
 

doc/conf.py

File contents unchanged.

doc/config.rst

File contents unchanged.
    domains
    builders
    config
+   intl
    theming
    templating
    extensions
+   websupport
 
    faq
    glossary

doc/ext/appapi.rst

File contents unchanged.

doc/ext/autodoc.rst

File contents unchanged.

doc/ext/doctest.rst

    but executed before the doctests of the group(s) it belongs to.
 
 
+.. rst:directive:: .. testcleanup:: [group]
+
+   A cleanup code block.  This code is not shown in the output for other
+   builders, but executed after the doctests of the group(s) it belongs to.
+
+   .. versionadded:: 1.1
+
+
 .. rst:directive:: .. doctest:: [group]
 
    A doctest-style code block.  You can use standard :mod:`doctest` flags for
 
    .. versionadded:: 0.6
 
+.. confval:: doctest_global_cleanup
+
+   Python code that is treated like it were put in a ``testcleanup`` directive
+   for *every* file that is tested, and for every group.  You can use this to
+   e.g. remove any temporary files that the tests leave behind.
+
+   .. versionadded:: 1.1
+
 .. confval:: doctest_test_doctest_blocks
 
    If this is a nonempty string (the default is ``'default'``), standard reST

doc/ext/graphviz.rst

    :confval:`graphviz_output_format`).  In LaTeX output, the code will be
    rendered to an embeddable PDF file.
 
+   You can also embed external dot files, by giving the file name as an
+   argument to :rst:dir:`graphviz` and no additional content::
+
+      .. graphviz:: external.dot
+
+   As for all file references in Sphinx, if the filename is absolute, it is
+   taken as relative to the source directory.
+
+   .. versionchanged:: 1.1
+      Added support for external files.
+
 
 .. rst:directive:: graph
 
    alternate text for HTML output.  If not given, the alternate text defaults to
    the graphviz code.
 
+.. versionadded:: 1.1
+   All three directives support an ``inline`` flag that controls
+   paragraph breaks in the output.  When set, the graph is inserted
+   into the current paragraph.  If the flag is not given, paragraph
+   breaks are introduced before and after the image (the default).
 
 There are also these new config values:
 

doc/faq.rst

File contents unchanged.
+.. _intl:
+
+Internationalization
+====================
+
+.. versionadded:: 1.1
+
+Complementary to translations provided for Sphinx-generated messages such as
+navigation bars, Sphinx provides mechanisms facilitating *document* translations
+in itself.  See the :ref:`intl-options` for details on configuration.
+
+.. figure:: translation.png
+   :width: 100%
+
+   Workflow visualization of translations in Sphinx. [1]_
+
+**gettext** [2]_ is an established standard for internationalization and
+localization.  It naïvely maps messages in a program to a translated string.
+Sphinx uses these facilities to translate whole documents.
+
+Initially project maintainers have to collect all translatable strings (also
+referred to as *messages*) to make them known to translators.  Sphinx extracts
+these through invocation of ``sphinx-build -b gettext``.
+
+Every single element in the doctree will end up in a single message which
+results in lists being equally split into different chunks while large
+paragraphs will remain as coarsely-grained as they were in the original
+document.  This grants seamless document updates while still providing a little
+bit of context for translators in free-text passages.  It is the maintainer's
+task to split up paragraphs which are too large as there is no sane automated
+way to do that.
+
+After Sphinx successfully ran the
+:class:`~sphinx.builders.intl.MessageCatalogBuilder` you will find a collection
+of ``.pot`` files in your output directory.  These are **catalog templates**
+and contain messages in your original language *only*.
+
+They can be delivered to translators which will transform them to ``.po`` files
+--- so called **message catalogs** --- containing a mapping from the original
+messages to foreign-language strings.
+
+Gettext compiles them into a binary format known as **binary catalogs** through
+:program:`msgfmt` for efficiency reasons.  If you make these files discoverable
+with :confval:`locale_dirs` for your :confval:`language`, Sphinx will pick them
+up automatically.
+
+An example: you have a document ``usage.rst`` in your Sphinx project.  The
+gettext builder will put its messages into ``usage.pot``.  Image you have
+Spanish translations [3]_ on your hands in ``usage.po`` --- for your builds to
+be translated you need to follow these instructions:
+
+* Compile your message catalog to a locale directory, say ``translated``, so it
+  ends up in ``./translated/es/LC_MESSAGES/usage.mo`` in your source directory
+  (where ``es`` is the language code for Spanish.) ::
+
+        msgfmt "usage.po" -o "translated/es/LC_MESSAGES/usage.mo"
+
+* Set :confval:`locale_dirs` to ``["translated/"]``.
+* Set :confval:`language` to ``es`` (also possible via :option:`-D`).
+* Run your desired build.
+
+
+.. rubric:: Footnotes
+
+.. [1] The stick-figure is taken from an `XKCD comic <http://xkcd.com/779/>`_.
+.. [2] See the `GNU gettext utilites
+       <http://www.gnu.org/software/gettext/manual/gettext.html#Introduction>`_
+       for details on that software suite.
+.. [3] Because nobody expects the Spanish Inquisition!
 Prerequisites
 -------------
 
-Sphinx needs at least **Python 2.4** to run, as well as the docutils_ and
-Jinja2_ libraries.  Sphinx should work with docutils version 0.5 or some
-(not broken) SVN trunk snapshot.  If you like to have source code highlighting
-support, you must also install the Pygments_ library.
+Sphinx needs at least **Python 2.4** or **Python 3.1** to run, as well as the
+docutils_ and Jinja2_ libraries.  Sphinx should work with docutils version 0.5
+or some (not broken) SVN trunk snapshot.  If you like to have source code
+highlighting support, you must also install the Pygments_ library.
+
+If you use **Python 2.4** you also need uuid_.
 
 .. _reStructuredText: http://docutils.sf.net/rst.html
 .. _docutils: http://docutils.sf.net/
 .. _Jinja2: http://jinja.pocoo.org/2/
 .. _Pygments: http://pygments.org/
+.. The given homepage is only a directory listing so I'm using the pypi site.
+.. _uuid: http://pypi.python.org/pypi/uuid/
 
 
 Usage

doc/invocation.rst

    **man**
       Build manual pages in groff format for UNIX systems.
 
+   **texinfo**
+      Build Texinfo files that can be processed into Info files using
+      :program:`makeinfo`.
+
    **text**
       Build plain text files.
 
+   **gettext**
+      Build gettext-style message catalogs (``.pot`` files).
+
    **doctest**
       Run all doctests in the documentation, if the :mod:`~sphinx.ext.doctest`
       extension is enabled.

doc/markup/inline.rst

File contents unchanged.

doc/markup/misc.rst

File contents unchanged.

doc/markup/para.rst

    Similar to :rst:dir:`versionadded`, but describes when and what changed in
    the named feature in some way (new parameters, changed side effects, etc.).
 
-.. rst:directive:: .. deprecated:: vesion
+.. rst:directive:: .. deprecated:: version
 
    Similar to :rst:dir:`versionchanged`, but describes when the feature was
    deprecated.  An explanation can also be given, for example to inform the
 
       .. centered:: LICENSE AGREEMENT
 
+   .. deprecated:: 1.1
+      This presentation-only directive is a legacy from older versions.  Use a
+      :rst:dir:`rst-class` directive instead and add an appropriate style.
+
 
 .. rst:directive:: hlist
 
 <contents>`.
 
 
-Index-generating markup
------------------------
-
-Sphinx automatically creates index entries from all object descriptions (like
-functions, classes or attributes) like discussed in :ref:`domains`.
-
-However, there is also an explicit directive available, to make the index more
-comprehensive and enable index entries in documents where information is not
-mainly contained in information units, such as the language reference.
-
-.. rst:directive:: .. index:: <entries>
-
-   This directive contains one or more index entries.  Each entry consists of a
-   type and a value, separated by a colon.
-
-   For example::
-
-      .. index::
-         single: execution; context
-         module: __main__
-         module: sys
-         triple: module; search; path
-
-      The execution context
-      ---------------------
-
-      ...
-
-   This directive contains five entries, which will be converted to entries in
-   the generated index which link to the exact location of the index statement
-   (or, in case of offline media, the corresponding page number).
-
-   Since index directives generate cross-reference targets at their location in
-   the source, it makes sense to put them *before* the thing they refer to --
-   e.g. a heading, as in the example above.
-
-   The possible entry types are:
-
-   single
-      Creates a single index entry.  Can be made a subentry by separating the
-      subentry text with a semicolon (this notation is also used below to
-      describe what entries are created).
-   pair
-      ``pair: loop; statement`` is a shortcut that creates two index entries,
-      namely ``loop; statement`` and ``statement; loop``.
-   triple
-      Likewise, ``triple: module; search; path`` is a shortcut that creates
-      three index entries, which are ``module; search path``, ``search; path,
-      module`` and ``path; module search``.
-   module, keyword, operator, object, exception, statement, builtin
-      These all create two index entries.  For example, ``module: hashlib``
-      creates the entries ``module; hashlib`` and ``hashlib; module``.  (These
-      are Python-specific and therefore deprecated.)
-
-   For index directives containing only "single" entries, there is a shorthand
-   notation::
-
-      .. index:: BNF, grammar, syntax, notation
-
-   This creates four index entries.
-
-
 Glossary
 --------
 

doc/markup/toctree.rst

      document, the library index.  From this information it generates "next
      chapter", "previous chapter" and "parent chapter" links.
 
+   **Entries**
+
    Document titles in the :rst:dir:`toctree` will be automatically read from the
    title of the referenced document. If that isn't what you want, you can
    specify an explicit title and target using a similar syntax to reST
    You can also add external links, by giving an HTTP URL instead of a document
    name.
 
+   **Section numbering**
+
    If you want to have section numbers even in HTML output, give the toctree a
-   ``numbered`` flag option.  For example::
+   ``numbered`` option.  For example::
 
       .. toctree::
          :numbered:
    Numbering then starts at the heading of ``foo``.  Sub-toctrees are
    automatically numbered (don't give the ``numbered`` flag to those).
 
+   Numbering up to a specific depth is also possible, by giving the depth as a
+   numeric argument to ``numbered``.
+
+   **Additional options**
+
    If you want only the titles of documents in the tree to show up, not other
    headings of the same level, you can use the ``titlesonly`` option::
 
    .. versionchanged:: 1.0
       Added "titlesonly" option.
 
+   .. versionchanged:: 1.1
+      Added numeric argument to "numbered".
+
 
 Special names
 -------------
 * A :file:`theme.conf` file, see below.
 * HTML templates, if needed.
 * A ``static/`` directory containing any static files that will be copied to the
-  output statid directory on build.  These can be images, styles, script files.
+  output static directory on build.  These can be images, styles, script files.
 
 The :file:`theme.conf` file is in INI format [1]_ (readable by the standard
 Python :mod:`ConfigParser` module) and has the following structure:

doc/translation.png

Added
New image
+.. _websupportapi:
+
+.. currentmodule:: sphinx.websupport
+
+The WebSupport Class
+====================
+
+.. class:: WebSupport
+
+   The main API class for the web support package.  All interactions with the
+   web support package should occur through this class.
+
+   The class takes the following keyword arguments:
+
+   srcdir
+      The directory containing reStructuredText source files.
+
+   builddir
+      The directory that build data and static files should be placed in.  This
+      should be used when creating a :class:`WebSupport` object that will be
+      used to build data.
+
+   datadir
+      The directory that the web support data is in.  This should be used when
+      creating a :class:`WebSupport` object that will be used to retrieve data.
+
+   search
+       This may contain either a string (e.g. 'xapian') referencing a built-in
+       search adapter to use, or an instance of a subclass of
+       :class:`~.search.BaseSearch`.
+
+   storage
+       This may contain either a string representing a database uri, or an
+       instance of a subclass of :class:`~.storage.StorageBackend`.  If this is
+       not provided, a new sqlite database will be created.
+
+   moderation_callback
+       A callable to be called when a new comment is added that is not
+       displayed.  It must accept one argument: a dictionary representing the
+       comment that was added.
+
+   staticdir
+       If static files are served from a location besides ``'/static'``, this
+       should be a string with the name of that location
+       (e.g. ``'/static_files'``).
+
+   docroot
+       If the documentation is not served from the base path of a URL, this
+       should be a string specifying that path (e.g. ``'docs'``).
+
+
+Methods
+~~~~~~~
+
+.. automethod:: sphinx.websupport.WebSupport.build
+
+.. automethod:: sphinx.websupport.WebSupport.get_document
+
+.. automethod:: sphinx.websupport.WebSupport.get_data
+
+.. automethod:: sphinx.websupport.WebSupport.add_comment
+
+.. automethod:: sphinx.websupport.WebSupport.process_vote
+
+.. automethod:: sphinx.websupport.WebSupport.get_search_results

doc/web/quickstart.rst

+.. _websupportquickstart:
+
+Web Support Quick Start
+=======================
+
+Building Documentation Data
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+To make use of the web support package in your application you'll need to build
+the data it uses.  This data includes pickle files representing documents,
+search indices, and node data that is used to track where comments and other
+things are in a document.  To do this you will need to create an instance of the
+:class:`~.WebSupport` class and call its :meth:`~.WebSupport.build` method::
+
+   from sphinx.websupport import WebSupport
+
+   support = WebSupport(srcdir='/path/to/rst/sources/',
+                        builddir='/path/to/build/outdir',
+                        search='xapian')
+
+   support.build()
+
+This will read reStructuredText sources from `srcdir` and place the necessary
+data in `builddir`.  The `builddir` will contain two sub-directories: one named
+"data" that contains all the data needed to display documents, search through
+documents, and add comments to documents.  The other directory will be called
+"static" and contains static files that should be served from "/static".
+
+.. note::
+
+   If you wish to serve static files from a path other than "/static", you can
+   do so by providing the *staticdir* keyword argument when creating the
+   :class:`~.WebSupport` object.
+
+
+Integrating Sphinx Documents Into Your Webapp
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Now that the data is built, it's time to do something useful with it.  Start off
+by creating a :class:`~.WebSupport` object for your application::
+
+   from sphinx.websupport import WebSupport
+
+   support = WebSupport(datadir='/path/to/the/data',
+                        search='xapian')
+
+You'll only need one of these for each set of documentation you will be working
+with.  You can then call it's :meth:`~.WebSupport.get_document` method to access
+individual documents::
+
+   contents = support.get_document('contents')
+
+This will return a dictionary containing the following items:
+
+* **body**: The main body of the document as HTML
+* **sidebar**: The sidebar of the document as HTML
+* **relbar**: A div containing links to related documents
+* **title**: The title of the document
+* **css**: Links to css files used by Sphinx
+* **js**: Javascript containing comment options
+
+This dict can then be used as context for templates.  The goal is to be easy to
+integrate with your existing templating system.  An example using `Jinja2
+<http://jinja.pocoo.org/2/>`_ is:
+
+.. sourcecode:: html+jinja
+
+   {%- extends "layout.html" %}
+
+   {%- block title %}
+       {{ document.title }}
+   {%- endblock %}
+
+   {% block css %}
+       {{ super() }}
+       {{ document.css|safe }}
+       <link rel="stylesheet" href="/static/websupport-custom.css" type="text/css">
+   {% endblock %}
+
+   {%- block js %}
+       {{ super() }}
+       {{ document.js|safe }}
+   {%- endblock %}
+
+   {%- block relbar %}
+       {{ document.relbar|safe }}
+   {%- endblock %}
+
+   {%- block body %}
+       {{ document.body|safe }}
+   {%- endblock %}
+
+   {%- block sidebar %}
+       {{ document.sidebar|safe }}
+   {%- endblock %}
+
+
+Authentication
+--------------
+
+To use certain features such as voting, it must be possible to authenticate
+users.  The details of the authentication are left to your application.  Once a
+user has been authenticated you can pass the user's details to certain
+:class:`~.WebSupport` methods using the *username* and *moderator* keyword
+arguments.  The web support package will store the username with comments and
+votes.  The only caveat is that if you allow users to change their username you
+must update the websupport package's data::
+
+   support.update_username(old_username, new_username)
+
+*username* should be a unique string which identifies a user, and *moderator*
+should be a boolean representing whether the user has moderation privilieges.
+The default value for *moderator* is *False*.
+
+An example `Flask <http://flask.pocoo.org/>`_ function that checks whether a
+user is logged in and then retrieves a document is::
+
+   from sphinx.websupport.errors import *
+
+   @app.route('/<path:docname>')
+   def doc(docname):
+       username = g.user.name if g.user else ''
+       moderator = g.user.moderator if g.user else False
+       try:
+           document = support.get_document(docname, username, moderator)
+       except DocumentNotFoundError:
+           abort(404)
+       return render_template('doc.html', document=document)
+
+The first thing to notice is that the *docname* is just the request path.  This
+makes accessing the correct document easy from a single view.  If the user is
+authenticated, then the username and moderation status are passed along with the
+docname to :meth:`~.WebSupport.get_document`.  The web support package will then
+add this data to the ``COMMENT_OPTIONS`` that are used in the template.
+
+.. note::
+
+   This only works works if your documentation is served from your
+   document root. If it is served from another directory, you will
+   need to prefix the url route with that directory, and give the `docroot`
+   keyword argument when creating the web support object::
+
+      support = WebSupport(..., docroot='docs')
+
+      @app.route('/docs/<path:docname>')
+
+
+Performing Searches
+~~~~~~~~~~~~~~~~~~~
+
+To use the search form built-in to the Sphinx sidebar, create a function to
+handle requests to the url 'search' relative to the documentation root.  The
+user's search query will be in the GET parameters, with the key `q`.  Then use
+the :meth:`~sphinx.websupport.WebSupport.get_search_results` method to retrieve
+search results. In `Flask <http://flask.pocoo.org/>`_ that would be like this::
+
+   @app.route('/search')
+   def search():
+       q = request.args.get('q')
+       document = support.get_search_results(q)
+       return render_template('doc.html', document=document)
+
+Note that we used the same template to render our search results as we did to
+render our documents.  That's because :meth:`~.WebSupport.get_search_results`
+returns a context dict in the same format that :meth:`~.WebSupport.get_document`
+does.
+
+
+Comments & Proposals
+~~~~~~~~~~~~~~~~~~~~
+
+Now that this is done it's time to define the functions that handle the AJAX
+calls from the script.  You will need three functions.  The first function is
+used to add a new comment, and will call the web support method
+:meth:`~.WebSupport.add_comment`::
+
+   @app.route('/docs/add_comment', methods=['POST'])
+   def add_comment():
+       parent_id = request.form.get('parent', '')
+       node_id = request.form.get('node', '')
+       text = request.form.get('text', '')
+       proposal = request.form.get('proposal', '')
+       username = g.user.name if g.user is not None else 'Anonymous'
+       comment = support.add_comment(text, node_id='node_id',
+                                     parent_id='parent_id',
+                                     username=username, proposal=proposal)
+       return jsonify(comment=comment)
+
+You'll notice that both a `parent_id` and `node_id` are sent with the
+request. If the comment is being attached directly to a node, `parent_id`
+will be empty. If the comment is a child of another comment, then `node_id`
+will be empty. Then next function handles the retrieval of comments for a
+specific node, and is aptly named
+:meth:`~sphinx.websupport.WebSupport.get_data`::
+
+    @app.route('/docs/get_comments')
+    def get_comments():
+        username = g.user.name if g.user else None
+        moderator = g.user.moderator if g.user else False
+        node_id = request.args.get('node', '')
+        data = support.get_data(parent_id, user_id)
+        return jsonify(**data)
+
+The final function that is needed will call :meth:`~.WebSupport.process_vote`,
+and will handle user votes on comments::
+
+   @app.route('/docs/process_vote', methods=['POST'])
+   def process_vote():
+       if g.user is None:
+           abort(401)
+       comment_id = request.form.get('comment_id')
+       value = request.form.get('value')
+       if value is None or comment_id is None:
+           abort(400)
+       support.process_vote(comment_id, g.user.id, value)
+       return "success"
+
+
+Comment Moderation
+~~~~~~~~~~~~~~~~~~
+
+By default, all comments added through :meth:`~.WebSupport.add_comment` are
+automatically displayed.  If you wish to have some form of moderation, you can
+pass the `displayed` keyword argument::
+
+   comment = support.add_comment(text, node_id='node_id',
+                                 parent_id='parent_id',
+                                 username=username, proposal=proposal,
+                                 displayed=False)
+
+You can then create a new view to handle the moderation of comments.  It
+will be called when a moderator decides a comment should be accepted and
+displayed::
+
+   @app.route('/docs/accept_comment', methods=['POST'])
+   def accept_comment():
+       moderator = g.user.moderator if g.user else False
+       comment_id = request.form.get('id')
+       support.accept_comment(comment_id, moderator=moderator)
+       return 'OK'
+
+Rejecting comments happens via comment deletion.
+
+To perform a custom action (such as emailing a moderator) when a new comment is
+added but not displayed, you can pass callable to the :class:`~.WebSupport`
+class when instantiating your support object::
+
+   def moderation_callback(comment):
+       """Do something..."""
+
+   support = WebSupport(..., moderation_callback=moderation_callback)
+
+The moderation callback must take one argument, which will be the same comment
+dict that is returned by :meth:`add_comment`.

doc/web/searchadapters.rst

+.. _searchadapters:
+
+.. currentmodule:: sphinx.websupport.search
+
+Search Adapters
+===============
+
+To create a custom search adapter you will need to subclass the
+:class:`BaseSearch` class.  Then create an instance of the new class and pass
+that as the `search` keyword argument when you create the :class:`~.WebSupport`
+object::
+
+   support = WebSupport(srcdir=srcdir,
+                        builddir=builddir,
+                        search=MySearch())
+
+For more information about creating a custom search adapter, please see the
+documentation of the :class:`BaseSearch` class below.
+
+.. class:: BaseSearch
+
+   Defines an interface for search adapters.
+
+
+BaseSearch Methods
+~~~~~~~~~~~~~~~~~~
+
+   The following methods are defined in the BaseSearch class. Some methods do
+   not need to be overridden, but some (:meth:`~BaseSearch.add_document` and
+   :meth:`~BaseSearch.handle_query`) must be overridden in your subclass. For a
+   working example, look at the built-in adapter for whoosh.
+
+.. automethod:: BaseSearch.init_indexing
+
+.. automethod:: BaseSearch.finish_indexing
+
+.. automethod:: BaseSearch.feed
+
+.. automethod:: BaseSearch.add_document
+
+.. automethod:: BaseSearch.query
+
+.. automethod:: BaseSearch.handle_query
+
+.. automethod:: BaseSearch.extract_context

doc/web/storagebackends.rst

+.. _storagebackends:
+
+.. currentmodule:: sphinx.websupport.storage
+
+Storage Backends
+================
+
+To create a custom storage backend you will need to subclass the
+:class:`StorageBackend` class.  Then create an instance of the new class and
+pass that as the `storage` keyword argument when you create the
+:class:`~.WebSupport` object::
+
+   support = WebSupport(srcdir=srcdir,
+                        builddir=builddir,
+                        storage=MyStorage())
+
+For more information about creating a custom storage backend, please see the
+documentation of the :class:`StorageBackend` class below.
+
+.. class:: StorageBackend
+
+   Defines an interface for storage backends.
+
+
+StorageBackend Methods
+~~~~~~~~~~~~~~~~~~~~~~
+
+.. automethod:: StorageBackend.pre_build
+
+.. automethod:: StorageBackend.add_node
+
+.. automethod:: StorageBackend.post_build
+
+.. automethod:: StorageBackend.add_comment
+
+.. automethod:: StorageBackend.delete_comment
+
+.. automethod:: StorageBackend.get_data
+
+.. automethod:: StorageBackend.process_vote
+
+.. automethod:: StorageBackend.update_username
+
+.. automethod:: StorageBackend.accept_comment

doc/websupport.rst

+.. _websupport:
+
+Sphinx Web Support
+==================
+
+.. versionadded:: 1.1
+
+Sphinx provides a Python API to easily integrate Sphinx documentation into your
+web application.  To learn more read the :ref:`websupportquickstart`.
+
+.. toctree::
+
+   web/quickstart
+   web/api
+   web/searchadapters
+   web/storagebackends
+# Makefile for Sphinx documentation
+#
+
+# You can set these variables from the command line.
+SPHINXOPTS   =
+SPHINXBUILD  = python ../sphinx-build.py
+PAPER        =
+
+PAPEROPT_a4      = -D latex_paper_size=a4
+PAPEROPT_letter  = -D latex_paper_size=letter
+ALLSPHINXOPTS = -d _build/doctrees $(PAPEROPT_$(PAPER)) \
+                $(SPHINXOPTS) $(O) .
+
+.PHONY: help clean html dirhtml singlehtml text man pickle json htmlhelp \
+	qthelp devhelp epub latex latexpdf changes linkcheck doctest
+
+help:
+	@echo "Please use \`make <target>' where <target> is one of"
+	@echo "  html       to make standalone HTML files"
+	@echo "  dirhtml    to make HTML files called index.html in directories"
+	@echo "  singlehtml to make one big HTML file"
+	@echo "  text       to make text files"
+	@echo "  man        to make manual pages"
+	@echo "  pickle     to make pickle files"
+	@echo "  json       to make json files"
+	@echo "  htmlhelp   to make HTML files and a HTML help project"
+	@echo "  qthelp     to make Qt help files and project"
+	@echo "  devhelp    to make Devhelp files and project"
+	@echo "  epub       to make an epub file"
+	@echo "  latex      to make LaTeX files, you can set PAPER=a4 or PAPER=letter"
+	@echo "  latexpdf   to make LaTeX files and run pdflatex"
+	@echo "  gettext    to make PO message catalogs"
+	@echo "  changes    to make an overview over all changed/added/deprecated items"
+	@echo "  linkcheck  to check all external links for integrity"
+
+clean:
+	-rm -rf _build/*
+
+html:
+	$(SPHINXBUILD) -b html $(ALLSPHINXOPTS) _build/html
+	@echo
+	@echo "Build finished. The HTML pages are in _build/html."
+
+dirhtml:
+	$(SPHINXBUILD) -b dirhtml $(ALLSPHINXOPTS) _build/dirhtml
+	@echo
+	@echo "Build finished. The HTML pages are in _build/dirhtml."
+
+singlehtml:
+	$(SPHINXBUILD) -b singlehtml $(ALLSPHINXOPTS) _build/singlehtml
+	@echo
+	@echo "Build finished. The HTML page is in _build/singlehtml."
+
+text:
+	$(SPHINXBUILD) -b text $(ALLSPHINXOPTS) _build/text
+	@echo
+	@echo "Build finished."
+
+man:
+	$(SPHINXBUILD) -b man $(ALLSPHINXOPTS) _build/man
+	@echo
+	@echo "Build finished."
+
+pickle:
+	$(SPHINXBUILD) -b pickle $(ALLSPHINXOPTS) _build/pickle
+	@echo
+	@echo "Build finished."
+
+json:
+	$(SPHINXBUILD) -b json $(ALLSPHINXOPTS) _build/json
+	@echo
+	@echo "Build finished."
+
+htmlhelp:
+	$(SPHINXBUILD) -b htmlhelp $(ALLSPHINXOPTS) _build/htmlhelp
+	@echo
+	@echo "Build finished; now you can run HTML Help Workshop with the" \
+	      ".hhp project file in _build/htmlhelp."
+
+qthelp:
+	$(SPHINXBUILD) -b qthelp $(ALLSPHINXOPTS) _build/qthelp
+	@echo
+	@echo "Build finished; now you can run qcollectiongenerator with the" \
+	      ".qhcp project file in build/qthelp."
+	@echo "# qcollectiongenerator _build/qthelp/Sphinx.qhcp"
+	@echo "To view the help collection:"
+	@echo "# assistant -collectionFile _build/qthelp/Sphinx.qhc"
+
+devhelp:
+	$(SPHINXBUILD) -b devhelp $(ALLSPHINXOPTS) _build/devhelp
+	@echo
+	@echo "Build finished."
+	@echo "To view the help file:"
+	@echo "# mkdir -p $$HOME/.local/share/devhelp/sphinx"
+	@echo "# ln -s _build/devhelp $$HOME/.local/share/devhelp/sphinx"
+	@echo "# devhelp"
+
+epub:
+	$(SPHINXBUILD) -b epub $(ALLSPHINXOPTS) _build/epub
+	@echo
+	@echo "Build finished. The epub file is in _build/epub."
+
+latex:
+	$(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) _build/latex
+	@echo
+	@echo "Build finished; the LaTeX files are in _build/latex."
+	@echo "Run \`make all-pdf' or \`make all-ps' in that directory to" \
+	      "run these through (pdf)latex."
+
+latexpdf:
+	$(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) _build/latex
+	@echo "Running LaTeX files through pdflatex..."
+	make -C _build/latex all-pdf
+	@echo "pdflatex finished; the PDF files are in _build/latex."
+
+gettext:
+	$(SPHINXBUILD) -b gettext $(ALLSPHINXOPTS) _build/locale
+	@echo
+	@echo "Build finished. The message catalogs are in _build/locale."
+
+changes:
+	$(SPHINXBUILD) -b changes $(ALLSPHINXOPTS) _build/changes
+	@echo
+	@echo "The overview file is in _build/changes."
+
+linkcheck:
+	$(SPHINXBUILD) -b linkcheck $(ALLSPHINXOPTS) _build/linkcheck
+	@echo
+	@echo "Link check complete; look for any errors in the above output " \
+	      "or in _build/linkcheck/output.txt."
+
+doctest:
+	$(SPHINXBUILD) -b doctest $(ALLSPHINXOPTS) _build/doctest

doc_zh/_static/sphinx.png

Added
New image

doc_zh/_templates/index.html

+{% extends "layout.html" %}
+{% set title = 'Overview' %}
+{% block body %}
+  <h1>嗨!</h1>
+
+  <div class="quotebar">
+    <p><em>用户有曰:</em></p>
+    <p>&ldquo;为这一伟大工具欢呼吧!总算出现一个令程序员<b>愿意</b>写文档的玩意儿了!&rdquo;</p>
+  </div>
+
+  <p>
+    Sphinx 是种令人可以轻松撰写出明智/优美的文档工具,
+    由 Georg Brandl 在BSD 许可证下创造.</p>
+    
+  <p>Sphinx 已在支持是 <a href="http://docs.python.org/dev/">the
+    新版Python 文档</a>的生成,
+    也成为Python项目首选的文档工具,同时也对 C/C++ 工程有很好的支持;
+    进一步的,也将对其它开发语言进行特殊支持.
+    当然,本站就是使用 Sphnix 
+    从<a href="http://docutils.sourceforge.net/rst.html">新结构化文本</a>中架构而成!
+  </p>
+  <p>
+    Sphnix还在继续开发. 下列特性工作良好,并在Python官方文档中有&#8220;体现&#8221;:
+  </p>
+  <ul>
+    <li><b>丰富的输出格式:</b> HTML (包括M$帮助), LaTeX (为PDF输出), manual pages(man), 纯文本</li>
+    <li><b>完备的交叉引用:</b> 语义化的标签,并对 函式,类,引文,术语以及类似片段消息可以自动化链接</li>
+    
+    <li><b>明晰的分层结构:</b> 轻松定义文档树,并自动化链接同级/父级/下级文章</li>
+    
+    <li><b>美观的自动索引:</b> 可自动生成美观的模块索引 </li>
+    <li><b>精确的语法高亮:</b> 基于 <a
+      href="http://pygments.org">Pygments</a> 自动生成语法高亮</li>
+    <li><b>开放的扩展:</b> 支持代码块的自动测试,自动包含Python 的模块自述文档,等等</li>
+  </ul>
+  <p>
+    Sphinx 使用<a href="http://docutils.sf.net/rst.html">新结构化文本</a>
+    作为标记语言,因而直接享受了来自<a href="http://docutils.sf.net/">Docutils</a>
+    为 reStructuredText 提供的多种工具和能力!
+  </p>
+
+  <h2>Documentation</h2>
+
+  <table class="contentstable" align="center" style="margin-left: 30px"><tr>
+    <td width="50%">
+      <p class="biglink"><a class="biglink" href="{{ pathto("tutorial") }}">
+      初尝</a><br/>
+         <span class="linkdescr">基本作業概览</span></p>
+      <p class="biglink"><a class="biglink" href="{{ pathto("contents") }}">内容</a><br/>
+         <span class="linkdescr">完整索引</span></p>
+    </td><td width="50%">
+      <p class="biglink"><a class="biglink" href="{{ pathto("search") }}">搜索</a><br/>
+         <span class="linkdescr">搜索文档</span></p>
+      <p class="biglink"><a class="biglink" href="{{ pathto("genindex") }}">索引</a><br/>
+         <span class="linkdescr">所有函式/类/条目</span></p>
+    </td></tr>
+  </table>
+
+  <p>
+    有Sphnix 文档的PDF版本下载:
+    基于 LaTeX Sphinx 的<a href="http://sphinx.pocoo.org/sphinx.pdf">版本</a> , 
+    以及 使用rst2pdf 生成的<a href="http://sphinx.pocoo.org/sphinx-rst2pdf.pdf">版本</a> .
+  </p>
+
+  <h2>实例</h2>
+  <p>收集了那些
+    <a href="{{ pathto("examples") }}">使用Sphnix 的项目</a> 文档入口链接.
+  </p>
+  <p>
+    想查阅 Sphnix 源文档,点击任何一页的 &#8220;显示源文&#8221; 链接.
+  </p>
+
+  <p>请跟随由matplotlib开发人员组织的,非常简洁的<a href="http://matplotlib.sourceforge.net/sampledoc/">教程</a>,
+  来体验如何运用 Sphnix 创建文档!
+  </p>
+
+  <p>这儿是当前文档的<a href="http://sphinx-users.jp/doc10/">日文翻译</a>,
+    感谢Yoshiki Shibukawa.</p>
+  <p>本文是 <a href="http://zoomquiet.org/sphinx_zh/">中文译本</a>
+    由 Zoom.Quiet 私人创建.</p>
+
+  <h2>获取 Sphinx</h2>
+  <p>
+    Sphinx 释放有 <a
+    href="http://peak.telecommunity.com/DevCenter/EasyInstall">easy-install</a>支持的模块,
+    可在 <a href="http://pypi.python.org/pypi/Sphinx">Python 模块索引</a>中查阅到.
+  </p>
+  <p>所有代码可在水银仓库中克隆到:
+    <tt>http://bitbucket.org/birkenfeld/sphinx/</tt>.</p>
+
+{% endblock %}