Skip to content

Commit

Permalink
Refactor page specific template variables.
Browse files Browse the repository at this point in the history
A deprecation warning is issued for all old variables and all new
page specific variables are attributes of the 'page' object.

Global variables are uneffected, except page_description.

See the changes described in the release notes for details.

Fixes mkdocs#874.
  • Loading branch information
waylan committed May 1, 2016
1 parent 5713289 commit 5bcd79f
Show file tree
Hide file tree
Showing 13 changed files with 159 additions and 78 deletions.
40 changes: 40 additions & 0 deletions docs/about/release-notes.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,46 @@ You can determine your currently installed version using `mkdocs --version`:

## Version 0.16 (2016-02-??)

### Major Additions to Version 0.16.0

#### Template variables refactored. (#874)

Page specific variable names in the template context have been refactored as
defined in [Custom Themes](../../user-guide/custom-themes/#page). The
old variable names will issue a warning but continue to work for version 0.16,
but may be removed in a future version.

No global variables were altered except `page_description`. Previously
its value was altered programicaly based on whether the current
page was the homepage. Now it simply maps to `config['site_description']`.
Use `page.is_homepage` in the template to conditionally change the
description.

Any of the following old variables should be updated to the new ones in user
created and third-party templates:

| Old Variable Name | New Variable Name |
| ----------------- | ------------------- |
| current_page | [page] |
| page_title | [page.title] |
| content | [page.content] |
| toc | [page.toc] |
| meta | [page.meta] |
| canonical_url | [page.canonical_url]|
| previous_page | [page.previous_page]|
| next_page | [page.next_page] |

[page]: ../../user-guide/custom-themes/#page
[page.title]: ../../user-guide/custom-themes/#pagetitle
[page.content]: ../../user-guide/custom-themes/#pagecontent
[page.toc]: ../../user-guide/custom-themes/#pagetoc
[page.meta]: ../../user-guide/custom-themes/#pagemeta
[page.canonical_url]: ../../user-guide/custom-themes/#pagecanonical_url
[page.previous_page]: ../../user-guide/custom-themes/#pageprevious_page
[page.next_page]: ../../user-guide/custom-themes/#pagenext_page

### Other Changes and Additions to Version 0.16.0

* Bugfix: Support `gh-deploy` command on Windows with Python 3 (#722)
* Bugfix: Include .woff2 font files in Pyhton package build (#894)
* Various updates and improvements to Documentation Home Page/Tutorial (#870)
Expand Down
51 changes: 26 additions & 25 deletions docs/user-guide/custom-themes.md
Original file line number Diff line number Diff line change
Expand Up @@ -170,32 +170,28 @@ A Python datetime object that represents the date and time the documentation
was built in UTC. This is useful for showing how recently the documentation
was updated.

### Page Context
#### page

The page context includes all of the above Global context and the following
additional variables.
In templates which are not rendered from a Markdown source file, the `page`
variable is `None`. In templates which are rendered from a Markdown source file,
the `page` variable contains a page object with the following attributes:

#### page_title
##### page.title

Contains the Title for the current page.

#### page_description

Contains the description for the current page on the homepage, it is blank on
other pages.

#### content
##### page.content

The rendered Markdown as HTML, this is the contents of the documentation.

#### toc
##### page.toc

An object representing the Table of contents for a page. Displaying the table
of contents as a simple list can be achieved like this.

```django
<ul>
{% for toc_item in toc %}
{% for toc_item in page.toc %}
<li><a href="{{ toc_item.url }}">{{ toc_item.title }}</a></li>
{% for toc_item in toc_item.children %}
<li><a href="{{ toc_item.url }}">{{ toc_item.title }}</a></li>
Expand All @@ -204,7 +200,7 @@ of contents as a simple list can be achieved like this.
</ul>
```

#### meta
##### page.meta

A mapping of the metadata included at the top of the markdown page. In this
example we define a `source` property above the page title.
Expand All @@ -223,36 +219,41 @@ variable. This could then be used to link to source files related to the
documentation page.

```django
{% for filename in meta.source %}
{% for filename in page.meta.source %}
<a class="github" href="https://github.com/.../{{ filename }}">
<span class="label label-info">{{ filename }}</span>
</a>
{% endfor %}
```

#### canonical_url
##### page.canonical_url

The full, canonical URL to the current page. This includes the site_url from
The full, canonical URL to the current page. This includes the `site_url` from
the configuration.

#### current_page
##### page.url

The URL to the current page not including the `site_url` from the configuration.

##### page.is_homepage

The page object for the current page. The page path and url properties can be
displayed like this.
Evaluates to `True` for the homepage of the site and `False` for all other
pages. This can be used in conjuction with other attributes of the `page`
object to alter the behavior. For example, to display a differant title
on the homepage:

```django
<h1>{{ current_page.title }}</h1>
<p> This page is at {{ current_page.url }}</p>
{% if not page.is_homepage %}{{ page.title }} - {% endif %}{{ site_name }}
```

#### previous_page
##### page.previous_page

The page object for the previous page. The usage is the same as for
`current_page`.
`page`.

#### next_page
##### page.next_page

The page object for the next page.The usage is the same as for `current_page`.
The page object for the next page.The usage is the same as for `page`.

### Extra Context

Expand Down
62 changes: 45 additions & 17 deletions mkdocs/commands/build.py
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,14 @@ def get_page_context(page, content, toc, meta, config):
Generate the page context by extending the global context and adding page
specific variables.
"""
if config['site_url']:
page.set_canonical_url(config['site_url'])

page.content = content
page.toc = toc
page.meta = meta

# TODO: remove the rest in version 1.0 as they are deprecated

if page.is_homepage or page.title is None:
page_title = None
Expand All @@ -106,25 +114,17 @@ def get_page_context(page, content, toc, meta, config):
else:
page_description = None

if config['site_url']:
base = config['site_url']
if not base.endswith('/'):
base += '/'
canonical_url = utils.urljoin(
base, page.abs_url.lstrip('/'))
else:
canonical_url = None

return {
'page': page,
# TODO: remove the rest in version 1.0 as they are deprecated
'page_title': page_title,
'page_description': page_description,

'content': content,
'toc': toc,
'meta': meta,


'canonical_url': canonical_url,
'canonical_url': page.canonical_url,

'current_page': page,
'previous_page': page.previous_page,
Expand All @@ -141,10 +141,9 @@ def build_template(template_name, env, config, site_navigation=None):
except TemplateNotFound:
return False

context = {'page': None}
if site_navigation is not None:
context = get_global_context(site_navigation, config)
else:
context = {}
context.update(get_global_context(site_navigation, config))

output_content = template.render(context)
output_path = os.path.join(config['site_dir'], template_name)
Expand Down Expand Up @@ -212,10 +211,9 @@ def build_extra_templates(extra_templates, config, site_navigation=None):
with io.open(input_path, 'r', encoding='utf-8') as template_file:
template = jinja2.Template(template_file.read())

context = {'page': None}
if site_navigation is not None:
context = get_global_context(site_navigation, config)
else:
context = {}
context.update(get_global_context(site_navigation, config))

output_content = template.render(context)
output_path = os.path.join(config['site_dir'], extra_template)
Expand All @@ -229,6 +227,36 @@ def build_pages(config, dump_json=False):
site_navigation = nav.SiteNavigation(config['pages'], config['use_directory_urls'])
loader = jinja2.FileSystemLoader(config['theme_dir'] + [config['mkdocs_templates'], ])
env = jinja2.Environment(loader=loader)

# TODO: remove DeprecationContext in v1.0 when all deprecated vars have been removed
from jinja2.runtime import Context
deprecated_vars = [
'page_title',
'content',
'toc',
'meta',
'current_page',
'canonical_url',
'previous_page',
'next_page'
]


class DeprecationContext(Context):
def resolve(self, key):
""" Log a warning when acessing any deprecated variable name. """
if key in deprecated_vars:
replacement = "page" if key == 'current_page' else "page.{0}".format(key)
log.warn(
"Template variable warning: '{0}' is being deprecated and will not be "
"available in a future version. Use '{1}' instead.".format(key, replacement)
)
return super(DeprecationContext, self).resolve(key)


env.context_class = DeprecationContext
# TODO: end remove DeprecationContext

env.filters['tojson'] = filters.tojson
search_index = search.SearchIndex()

Expand Down
12 changes: 12 additions & 0 deletions mkdocs/nav.py
Original file line number Diff line number Diff line change
Expand Up @@ -148,6 +148,13 @@ def __init__(self, title, url, path, url_context):
self.next_page = None
self.ancestors = []

# Placeholders to be filled in later in the build
# process when we have access to the config.
self.canonical_url = None
self.content = None
self.meta = None
self.toc = None

@property
def url(self):
return self.url_context.make_relative(self.abs_url)
Expand All @@ -174,6 +181,11 @@ def set_active(self, active=True):
for ancestor in self.ancestors:
ancestor.set_active(active)

def set_canonical_url(self, base):
if not base.endswith('/'):
base += '/'
self.canonical_url = utils.urljoin(base, self.abs_url.lstrip('/'))


class Header(object):
def __init__(self, title, children):
Expand Down
10 changes: 5 additions & 5 deletions mkdocs/themes/mkdocs/base.html
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,13 @@
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
{% if page_description %}<meta name="description" content="{{ page_description }}">{% endif %}
{% if page and page.is_homepage %}<meta name="description" content="{{ config['site_description'] }}">{% endif %}
{% if site_author %}<meta name="author" content="{{ site_author }}">{% endif %}
{% if canonical_url %}<link rel="canonical" href="{{ canonical_url }}">{% endif %}
{% if page and page.canonical_url %}<link rel="canonical" href="{{ page.canonical_url }}">{% endif %}
{% if favicon %}<link rel="shortcut icon" href="{{ base_url }}/{{ favicon }}">
{% else %}<link rel="shortcut icon" href="{{ base_url }}/img/favicon.ico">{% endif %}

<title>{% if page_title %}{{ page_title }} - {% endif %}{{ site_name }}</title>
<title>{% if page and page.title and not page.is_homepage %}{{ page.title }} - {% endif %}{{ site_name }}</title>

<link href="{{ base_url }}/css/bootstrap-custom.min.css" rel="stylesheet">
<link href="{{ base_url }}/css/font-awesome-4.5.0.css" rel="stylesheet">
Expand Down Expand Up @@ -39,7 +39,7 @@
{% endif %}
</head>

<body{% if current_page and current_page.is_homepage %} class="homepage"{% endif %}>
<body{% if page and page.is_homepage %} class="homepage"{% endif %}>

{% include "nav.html" %}

Expand Down Expand Up @@ -95,7 +95,7 @@ <h4 class="modal-title" id="exampleModalLabel">Search</h4>

</body>
</html>
{% if current_page and current_page.is_homepage %}
{% if page and page.is_homepage %}
<!--
MkDocs version : {{ mkdocs_version }}
Build Date UTC : {{ build_date_utc }}
Expand Down
6 changes: 3 additions & 3 deletions mkdocs/themes/mkdocs/content.html
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
{% if meta.source %}
{% if page.meta.source %}
<div class="source-links">
{% for filename in meta.source %}
{% for filename in page.meta.source %}
<span class="label label-primary">{{ filename }}</span>
{% endfor %}
</div>
{% endif %}

{{ content }}
{{ page.content }}
10 changes: 5 additions & 5 deletions mkdocs/themes/mkdocs/nav.html
Original file line number Diff line number Diff line change
Expand Up @@ -47,14 +47,14 @@
<i class="fa fa-search"></i> Search
</a>
</li>
{% if include_next_prev %}
<li {% if not previous_page %}class="disabled"{% endif %}>
<a rel="next" {% if previous_page %}href="{{ previous_page.url }}"{% endif %}>
{% if include_next_prev and page %}
<li {% if not page.previous_page %}class="disabled"{% endif %}>
<a rel="next" {% if page.previous_page %}href="{{ page.previous_page.url }}"{% endif %}>
<i class="fa fa-arrow-left"></i> Previous
</a>
</li>
<li {% if not next_page %}class="disabled"{% endif %}>
<a rel="prev" {% if next_page %}href="{{ next_page.url }}"{% endif %}>
<li {% if not page.next_page %}class="disabled"{% endif %}>
<a rel="prev" {% if page.next_page %}href="{{ page.next_page.url }}"{% endif %}>
Next <i class="fa fa-arrow-right"></i>
</a>
</li>
Expand Down
2 changes: 1 addition & 1 deletion mkdocs/themes/mkdocs/toc.html
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
<div class="bs-sidebar hidden-print affix well" role="complementary">
<ul class="nav bs-sidenav">
{% for toc_item in toc %}
{% for toc_item in page.toc %}
<li class="main {% if toc_item.active %}active{% endif %}"><a href="{{ toc_item.url }}">{{ toc_item.title }}</a></li>
{% for toc_item in toc_item.children %}
<li><a href="{{ toc_item.url }}">{{ toc_item.title }}</a></li>
Expand Down
Loading

0 comments on commit 5bcd79f

Please sign in to comment.