def path_to_url(url, nav): scheme, netloc, path, query, query, fragment = urlparse(url) if scheme or netloc or not path: # Ignore URLs unless they are a relative link to a markdown file. return url if nav and not utils.is_markdown_file(path): path = utils.create_media_urls(nav, [path])[0] elif nav: # If the site navigation has been provided, then validate # the internal hyperlink, making sure the target actually exists. target_file = nav.file_context.make_absolute(path) if target_file not in nav.source_files: source_file = nav.file_context.current_file msg = ('The page "%s" contained a hyperlink to "%s" which ' 'is not listed in the "pages" configuration.') assert False, msg % (source_file, target_file) path = utils.get_url_path(target_file, nav.use_directory_urls) path = nav.url_context.make_relative(path) else: path = utils.get_url_path(path).lstrip('/') # Convert the .md hyperlink to a relative hyperlink to the HTML page. url = urlunparse((scheme, netloc, path, query, query, fragment)) return url
def path_to_url(url, nav): scheme, netloc, path, query, query, fragment = urlparse(url) if scheme or netloc or not path: # Ignore URLs unless they are a relative link to a markdown file. return url if nav and not utils.is_markdown_file(path): path = utils.create_media_urls(nav, [path])[0] elif nav: # If the site navigation has been provided, then validate # the internal hyperlink, making sure the target actually exists. target_file = nav.file_context.make_absolute(path) if target_file not in nav.source_files: source_file = nav.file_context.current_file msg = ( 'The page "%s" contained a hyperlink to "%s" which ' 'is not listed in the "pages" configuration.' ) assert False, msg % (source_file, target_file) path = utils.get_url_path(target_file, nav.use_directory_urls) path = nav.url_context.make_relative(path) else: path = utils.get_url_path(path).lstrip('/') # Convert the .md hyperlink to a relative hyperlink to the HTML page. url = urlunparse((scheme, netloc, path, query, query, fragment)) return url
def __call__(self, match): url = match.groups()[0] scheme, netloc, path, query, query, fragment = urlparse(url) if (scheme or netloc or not utils.is_markdown_file(path)): # Ignore URLs unless they are a relative link to a markdown file. return 'a href="%s"' % url if self.nav: # If the site navigation has been provided, then validate # the internal hyperlink, making sure the target actually exists. target_file = self.nav.file_context.make_absolute(path) if target_file not in self.nav.source_files: source_file = self.nav.file_context.current_file msg = ( 'The page "%s" contained a hyperlink to "%s" which ' 'is not listed in the "pages" configuration.' ) assert False, msg % (source_file, target_file) path = utils.get_url_path(target_file) path = self.nav.url_context.make_relative(path) else: path = utils.get_url_path(path).lstrip('/') # Convert the .md hyperlink to a relative hyperlink to the HTML page. url = urlunparse((scheme, netloc, path, query, query, fragment)) return 'a href="%s"' % url
def __call__(self, match): url = match.groups()[0] scheme, netloc, path, query, query, fragment = urlparse.urlparse(url) if (scheme or netloc or not utils.is_markdown_file(path)): # Ignore URLs unless they are a relative link to a markdown file. return 'a href="%s"' % url if self.nav: # If the site navigation has been provided, then validate # the internal hyperlink, making sure the target actually exists. target_file = self.nav.file_context.make_absolute(path) if target_file not in self.nav.source_files: source_file = self.nav.file_context.current_file msg = ( 'The page "%s" contained a hyperlink to "%s" which ' 'is not listed in the "pages" configuration.' ) assert False, msg % (source_file, target_file) path = utils.get_url_path(target_file, self.url_format) path = self.nav.url_context.make_relative(path) else: path = utils.get_url_path(path, self.url_format).lstrip('/') # Convert the .md hyperlink to a relative hyperlink to the HTML page. url = urlparse.urlunparse((scheme, netloc, path, query, query, fragment)) return 'a href="%s"' % url
def path_to_url(url, nav, strict): scheme, netloc, path, query, query, fragment = urlparse(url) if scheme or netloc or not path: # Ignore URLs unless they are a relative link to a markdown file. return url if nav and not utils.is_markdown_file(path): path = utils.create_relative_media_url(nav, path) elif nav: # If the site navigation has been provided, then validate # the internal hyperlink, making sure the target actually exists. target_file = nav.file_context.make_absolute(path) if target_file not in nav.source_files: source_file = nav.file_context.current_file msg = ( 'The page "%s" contained a hyperlink to "%s" which ' 'is not listed in the "pages" configuration.' ) % (source_file, target_file) # In strict mode raise an error at this point. if strict: raise MarkdownNotFound(msg) # Otherwise, when strict mode isn't enabled, print out a warning # to the user and leave the URL as it is. #print(msg) #return url path = utils.get_url_path(target_file, nav.use_directory_urls) path = nav.url_context.make_relative(path) else: path = utils.get_url_path(path).lstrip('/') # Convert the .md hyperlink to a relative hyperlink to the HTML page. url = urlunparse((scheme, netloc, path, query, query, fragment)) return url
def test_url_path(self): expected_results = { 'index.md': '/', 'api-guide.md': '/api-guide/', 'api-guide/index.md': '/api-guide/', 'api-guide/testing.md': '/api-guide/testing/', } for file_path, expected_url_path in expected_results.items(): url_path = utils.get_url_path(file_path, 'directory') self.assertEqual(url_path, expected_url_path) expected_results = { 'index.md': '/index.html', 'api-guide.md': '/api-guide/index.html', 'api-guide/index.md': '/api-guide/index.html', 'api-guide/testing.md': '/api-guide/testing/index.html', } for file_path, expected_url_path in expected_results.items(): url_path = utils.get_url_path(file_path, 'index') self.assertEqual(url_path, expected_url_path) expected_results = { 'index.md': '/index.html', 'api-guide.md': '/api-guide.html', 'api-guide/index.md': '/api-guide/index.html', 'api-guide/testing.md': '/api-guide/testing.html', } for file_path, expected_url_path in expected_results.items(): url_path = utils.get_url_path(file_path, 'file') self.assertEqual(url_path, expected_url_path)
def _generate_site_navigation(pages_config, url_context, use_directory_urls=True): """ Returns a list of Page and Header instances that represent the top level site navigation. """ nav_items = [] pages = [] previous = None for config_line in pages_config: if isinstance(config_line, str): path = config_line title, child_title = None, None elif len(config_line) in (1, 2, 3): # Pad any items that don't exist with 'None' padded_config = (list(config_line) + [None, None])[:3] path, title, child_title = padded_config else: msg = ( "Line in 'page' config contained %d items. " "Expected 1, 2 or 3 strings." % len(config_line) ) assert False, msg if title is None: filename = path.split('/')[0] title = filename_to_title(filename) if child_title is None and '/' in path: filename = path.split('/')[1] child_title = filename_to_title(filename) url = utils.get_url_path(path, use_directory_urls) if not child_title: # New top level page. page = Page(title=title, url=url, path=path, url_context=url_context) if not utils.is_homepage(path): nav_items.append(page) elif not nav_items or (nav_items[-1].title != title): # New second level page. page = Page(title=child_title, url=url, path=path, url_context=url_context) header = Header(title=title, children=[page]) nav_items.append(header) page.ancestors = [header] else: # Additional second level page. page = Page(title=child_title, url=url, path=path, url_context=url_context) header = nav_items[-1] header.children.append(page) page.ancestors = [header] # Add in previous and next information. if previous: page.previous_page = previous previous.next_page = page previous = page pages.append(page) return (nav_items, pages)
def __init__(self, title, path, url_context, config): self._title = title self.classTitle = utils.get_html_title_class(title, path) self.htmlTitle = "Bmob后端云" if path.find("data/") != -1: self.htmlTitle = "数据存储 · " + self.classTitle + " – Bmob后端云" elif path.find("cloud_function/") != -1: self.htmlTitle = "云函数 · " + self.classTitle + " – Bmob后端云" elif path.find("sms/") != -1: self.htmlTitle = "短信服务 · " + self.classTitle + " – Bmob后端云" elif path.find("game/") != -1: self.htmlTitle = "游戏实时后端 · " + self.classTitle + " – Bmob后端云" elif path.find("im/") != -1: self.htmlTitle = "即时通讯 · " + self.classTitle + " – Bmob后端云" elif path.find("push/") != -1: self.htmlTitle = "推送服务 · " + self.classTitle + " – Bmob后端云" elif path.find("other/") != -1: self.htmlTitle = self.classTitle + " – Bmob后端云" self.abs_url = utils.get_url_path(path, config['use_directory_urls']) self.active = False self.url_context = url_context # Support SOURCE_DATE_EPOCH environment variable for "reproducible" builds. # See https://reproducible-builds.org/specs/source-date-epoch/ if 'SOURCE_DATE_EPOCH' in os.environ: self.update_date = datetime.datetime.utcfromtimestamp( int(os.environ['SOURCE_DATE_EPOCH'])).strftime("%Y-%m-%d") else: self.update_date = datetime.datetime.now().strftime("%Y-%m-%d") # Relative and absolute paths to the input markdown file and output html file. self.input_path = path self.output_path = utils.get_html_path(path) self.abs_input_path = os.path.join(config['docs_dir'], self.input_path) self.abs_output_path = os.path.join(config['site_dir'], self.output_path) self.canonical_url = None if config['site_url']: self._set_canonical_url(config['site_url']) self.edit_url = None if config['repo_url'] and config['edit_uri']: self._set_edit_url(config['repo_url'], config['edit_uri']) # Placeholders to be filled in later in the build # process when we have access to the config. self.markdown = '' self.meta = {} self.content = None self.toc = None self.previous_page = None self.next_page = None self.ancestors = []
def _generate_site_navigation(pages_config, url_context, use_directory_urls=True): """ Returns a list of Page and Header instances that represent the top level site navigation. """ nav_items = [] pages = [] previous = None for config_line in pages_config: if isinstance(config_line, str): path = config_line title, child_title = None, None elif len(config_line) in (1, 2, 3): # Pad any items that don't exist with 'None' padded_config = (list(config_line) + [None, None])[:3] path, title, child_title = padded_config else: msg = ( "Line in 'page' config contained %d items. " "Expected 1, 2 or 3 strings." % len(config_line) ) assert False, msg url = utils.get_url_path(path, use_directory_urls) if not child_title: # New top level page. page = Page(title=title, url=url, path=path, url_context=url_context) if page.title is not None: # Page config lines that do not include a title, such as: # - ['index.md'] # Will not be added to the nav items heiarchy, although they # are included in the full list of pages, and have the # appropriate 'next'/'prev' links generated. nav_items.append(page) elif not nav_items or (nav_items[-1].title != title): # New second level page. page = Page(title=child_title, url=url, path=path, url_context=url_context) header = Header(title=title, children=[page]) nav_items.append(header) page.ancestors = [header] else: # Additional second level page. page = Page(title=child_title, url=url, path=path, url_context=url_context) header = nav_items[-1] header.children.append(page) page.ancestors = [header] # Add in previous and next information. if previous: page.previous_page = previous previous.next_page = page previous = page pages.append(page) return (nav_items, pages)
def path_to_url(url, nav, strict): scheme, netloc, path, params, query, fragment = (utils.urlparse(url)) if scheme or netloc or not path or AMP_SUBSTITUTE in url: # Ignore URLs unless they are a relative link to a markdown file. # AMP_SUBSTITUTE is used internally by Markdown only for email,which is # not a relative link. As urlparse errors on them, skip explicitly return url if nav and not utils.is_markdown_file(path): path = utils.create_relative_media_url(nav, path) elif nav: # If the site navigation has been provided, then validate # the internal hyperlink, making sure the target actually exists. target_file = nav.file_context.make_absolute(path) if target_file.startswith(os.path.sep): target_file = target_file[1:] if target_file not in nav.source_files: source_file = nav.file_context.current_file msg = ('The page "%s" contained a hyperlink to "%s" which ' 'is not listed in the "pages" configuration.') % ( source_file, target_file) # In strict mode raise an error at this point. if strict: raise MarkdownNotFound(msg) # Otherwise, when strict mode isn't enabled, log a warning # to the user and leave the URL as it is. # suppress the Warning # log.warning(msg) # return url path = utils.get_url_path(target_file, nav.use_directory_urls) path = nav.url_context.make_relative(path) else: path = utils.get_url_path(path).lstrip('/') # Convert the .md hyperlink to a relative hyperlink to the HTML page. fragments = (scheme, netloc, path, params, query, fragment) url = utils.urlunparse(fragments) return url
def path_to_url(url, nav, strict): scheme, netloc, path, params, query, fragment = ( utils.urlparse(url)) if scheme or netloc or not path or AMP_SUBSTITUTE in url: # Ignore URLs unless they are a relative link to a markdown file. # AMP_SUBSTITUTE is used internally by Markdown only for email,which is # not a relative link. As urlparse errors on them, skip explicitly return url if nav and not utils.is_markdown_file(path): path = utils.create_relative_media_url(nav, path) elif nav: # If the site navigation has been provided, then validate # the internal hyperlink, making sure the target actually exists. target_file = nav.file_context.make_absolute(path) if target_file.startswith(os.path.sep): target_file = target_file[1:] if target_file not in nav.source_files: source_file = nav.file_context.current_file msg = ( 'The page "%s" contained a hyperlink to "%s" which ' 'is not listed in the "pages" configuration.' ) % (source_file, target_file) # In strict mode raise an error at this point. if strict: raise MarkdownNotFound(msg) # Otherwise, when strict mode isn't enabled, log a warning # to the user and leave the URL as it is. log.warning(msg) return url path = utils.get_url_path(target_file, nav.use_directory_urls) path = nav.url_context.make_relative(path) else: path = utils.get_url_path(path).lstrip('/') # Convert the .md hyperlink to a relative hyperlink to the HTML page. fragments = (scheme, netloc, path, params, query, fragment) url = utils.urlunparse(fragments) return url
def test_url_path(self): expected_results = { 'index.md': '/', 'api-guide.md': '/api-guide/', 'api-guide/index.md': '/api-guide/', 'api-guide/testing.md': '/api-guide/testing/', } for file_path, expected_html_path in expected_results.items(): html_path = utils.get_url_path(file_path) self.assertEqual(html_path, expected_html_path)
def _generate_site_navigation(pages_config, url_context, use_directory_urls=True): """ Returns a list of Page and Header instances that represent the top level site navigation. """ nav_items = [] pages = [] previous = None for config_line in pages_config: if len(config_line) == 2: path, title = config_line child_title = None elif len(config_line) == 3: path, title, child_title = config_line else: msg = ( "Line in 'page' config contained %d items. " "Expected 2 or 3." % len(config_line) ) assert False, msg url = utils.get_url_path(path, use_directory_urls) if not child_title: # New top level page. page = Page(title=title, url=url, path=path, url_context=url_context) nav_items.append(page) elif not nav_items or (nav_items[-1].title != title): # New second level page. page = Page(title=child_title, url=url, path=path, url_context=url_context) header = Header(title=title, children=[page]) nav_items.append(header) page.ancestors = [header] else: # Additional second level page. page = Page(title=child_title, url=url, path=path, url_context=url_context) header = nav_items[-1] header.children.append(page) page.ancestors = [header] # Add in previous and next information. if previous: page.previous_page = previous previous.next_page = page previous = page pages.append(page) return (nav_items, pages)
def create_tree(event): """ Processes all the auto-generated API pages for the documentation. ### Parameters event | <mkdocs.events.PreBuild> ### Returns <bool> """ # generate a set of autodoc pages match = re.match('^tree:(.*)$', event.path) if match: root = match.group(1) path = os.path.abspath(os.path.join(config.docs_dir, root)) base = path[:-(len(root) + 1)] pages = [] for base_path, folder, files in os.walk(path): files.sort() if 'index.md' in files: files.remove('index.md') files.insert(0, 'index.md') for file in files: filepath = os.path.join(base_path, file) filepath = filepath.replace('\\', '/') if file == 'index.md': title = nav.filename_to_title(os.path.basename(base_path)) else: title = nav.filename_to_title(file) base_file_path = filepath[len(base) + 1:].replace('\\', '/') url = utils.get_url_path(base_file_path, True) page = nav.Page(title=title, url=url, path=base_file_path, url_context=event.url_context) page.base_path = base_path # Add in previous and next information. if pages: pages[-1].next_page = page page.previous_page = pages[-1] pages.append(page) event.pages = pages event.consumed = True
def __init__(self, title, path, url_context, config): self._title = title self.abs_url = utils.get_url_path(path, config['use_directory_urls']) self.active = False self.url_context = url_context # Support SOURCE_DATE_EPOCH environment variable for "reproducible" builds. # See https://reproducible-builds.org/specs/source-date-epoch/ if 'SOURCE_DATE_EPOCH' in os.environ: self.update_date = datetime.datetime.utcfromtimestamp( int(os.environ['SOURCE_DATE_EPOCH'])).strftime("%Y-%m-%d") else: self.update_date = datetime.datetime.now().strftime("%Y-%m-%d") # Relative and absolute paths to the input markdown file and output html file. self.input_path = path self.output_path = utils.get_html_path(path) self.abs_input_path = os.path.join(config['docs_dir'], self.input_path) self.abs_output_path = os.path.join(config['site_dir'], self.output_path) self.canonical_url = None if config['site_url']: self._set_canonical_url(config['site_url']) self.edit_url = None if config['repo_url']: self._set_edit_url(config['repo_url'], config['edit_uri']) # Placeholders to be filled in later in the build # process when we have access to the config. self.markdown = '' self.meta = {} self.content = None self.toc = None self.previous_page = None self.next_page = None self.ancestors = []
def __init__(self, title, path, url_context, config): self._title = title self.abs_url = utils.get_url_path(path, config['use_directory_urls']) self.active = False self.url_context = url_context # Support SOURCE_DATE_EPOCH environment variable for "reproducible" builds. # See https://reproducible-builds.org/specs/source-date-epoch/ if 'SOURCE_DATE_EPOCH' in os.environ: self.update_date = datetime.datetime.utcfromtimestamp( int(os.environ['SOURCE_DATE_EPOCH']) ).strftime("%Y-%m-%d") else: self.update_date = datetime.datetime.now().strftime("%Y-%m-%d") # Relative and absolute paths to the input markdown file and output html file. self.input_path = path self.output_path = utils.get_html_path(path) self.abs_input_path = os.path.join(config['docs_dir'], self.input_path) self.abs_output_path = os.path.join(config['site_dir'], self.output_path) self.canonical_url = None if config['site_url']: self._set_canonical_url(config['site_url']) self.edit_url = None if config['repo_url'] and config['edit_uri']: self._set_edit_url(config['repo_url'], config['edit_uri']) # Placeholders to be filled in later in the build # process when we have access to the config. self.markdown = '' self.meta = {} self.content = None self.toc = None self.previous_page = None self.next_page = None self.ancestors = []
def _follow(config_line, url_context, use_dir_urls, header=None, title=None): if isinstance(config_line, utils.string_types): path = os.path.normpath(config_line) page = _path_to_page(path, title, url_context, use_dir_urls) if header: page.ancestors = header.ancestors + [ header, ] header.children.append(page) yield page raise StopIteration elif not isinstance(config_line, dict): msg = ("Line in 'page' config is of type {0}, dict or string " "expected. Config: {1}").format(type(config_line), config_line) raise exceptions.ConfigurationError(msg) if len(config_line) > 1: raise exceptions.ConfigurationError( "Page configs should be in the format 'name: markdown.md'. The " "config contains an invalid entry: {0}".format(config_line)) elif len(config_line) == 0: log.warning("Ignoring empty line in the pages config.") raise StopIteration next_cat_or_title, subpages_or_path = next(iter(config_line.items())) if isinstance(subpages_or_path, utils.string_types): path = subpages_or_path for sub in _follow(path, url_context, use_dir_urls, header=header, title=next_cat_or_title): yield sub raise StopIteration elif not isinstance(subpages_or_path, list): msg = ("Line in 'page' config is of type {0}, list or string " "expected for sub pages. Config: {1}").format( type(config_line), config_line) raise exceptions.ConfigurationError(msg) subpages = subpages_or_path if len(subpages) and isinstance( subpages[0], utils.string_types) and subpages[0].endswith('index.md'): # The first child is an index page. Use it as the URL of the header. path = os.path.normpath(subpages.pop(0)) url = utils.get_url_path(path, use_dir_urls) next_header = HeaderPage(next_cat_or_title, url, path, url_context, children=[]) else: next_header = Header(title=next_cat_or_title, children=[]) if header: next_header.ancestors = [header] header.children.append(next_header) yield next_header for subpage in subpages: for sub in _follow(subpage, url_context, use_dir_urls, next_header): yield sub
def build_pages(config, dump_json=False): """ Builds all the pages and writes them into the build directory. """ site_navigation = nav.SiteNavigation(config['pages'], config['use_directory_urls']) loader = jinja2.FileSystemLoader(config['theme_dir']) env = jinja2.Environment(loader=loader) search_index = search.SearchIndex() build_template('404.html', env, config, site_navigation) build_template('search.html', env, config, site_navigation) nav_pages = [] for page in site_navigation.walk_pages(): nav_pages.append(page.input_path) # Read the input file input_path = os.path.join(config['docs_dir'], page.input_path) input_content = open(input_path, 'r').read() if PY2: input_content = input_content.decode('utf-8') # Process the markdown text html_content, table_of_contents, meta = convert_markdown( input_content, site_navigation, extensions=config['markdown_extensions'], strict=config['strict']) context = get_global_context(site_navigation, config) context.update( get_page_context(page, html_content, site_navigation, table_of_contents, meta, config)) # Allow 'template:' override in md source files. if 'template' in meta: template = env.get_template(meta['template'][0]) else: template = env.get_template('base.html') if not utils.is_markdown_file(page.input_path): template = env.get_template('base_without_toc.html') # Render the template. output_content = template.render(context) # Write the output file. output_path = os.path.join(config['site_dir'], page.output_path) if dump_json: json_context = { 'content': context['content'], 'title': context['current_page'].title, 'url': context['current_page'].abs_url, 'language': 'en', } utils.write_file( json.dumps(json_context, indent=4).encode('utf-8'), output_path.replace('.html', '.json')) else: utils.write_file(output_content.encode('utf-8'), output_path) search_index.add_entry_from_context(page, html_content, table_of_contents) # generate html for other md files files = ListFilesByTxt(os.path.join(config['docs_dir']), '.md') for mdf in files: title = os.path.basename(mdf) title = os.path.splitext(title)[0] path = os.path.relpath(mdf, config['docs_dir']) url = utils.get_url_path(path, config['use_directory_urls']) output_path = utils.get_html_path(path) if (path in nav_pages): continue input_content = open(mdf, 'r').read() if PY2: input_content = input_content.decode('utf-8') site_navigation.url_context.set_current_url(url) # Process the markdown text html_content, table_of_contents, meta = convert_markdown( input_content, site_navigation, extensions=config['markdown_extensions']) context = get_global_context(site_navigation, config) page = nav.Page(title=title, url=url, path=path, url_context=site_navigation.url_context) context.update( get_page_context(page, html_content, site_navigation, table_of_contents, meta, config)) if 'template' in meta: template = env.get_template(meta['template'][0]) else: template = env.get_template('base.html') if not utils.is_markdown_file(mdf): template = env.get_template('base_without_toc.html') # Render the template. output_content = template.render(context) # Write the output file. output_path = os.path.join(config['site_dir'], output_path) utils.write_file(output_content.encode('utf-8'), output_path) #search_index.add_entry_from_context(page, html_content, table_of_contents) build_template( 'js/tipuesearch/tipuesearch_content.js', env, config, extra_context={'search_index': search_index.generate_search_index()})
def _path_to_page(path, title, url_context, use_directory_urls): if title is None: title = filename_to_title(path.split(os.path.sep)[-1]) url = utils.get_url_path(path, use_directory_urls) return Page(title=title, url=url, path=path, url_context=url_context)
def build_pages(config, dump_json=False): """ Builds all the pages and writes them into the build directory. """ site_navigation = nav.SiteNavigation(config['pages'], config['use_directory_urls']) loader = jinja2.FileSystemLoader(config['theme_dir']) env = jinja2.Environment(loader=loader) search_index = search.SearchIndex() build_template('404.html', env, config, site_navigation) build_template('search.html', env, config, site_navigation) nav_pages = [] for page in site_navigation.walk_pages(): nav_pages.append(page.input_path) # Read the input file input_path = os.path.join(config['docs_dir'], page.input_path) input_content = open(input_path, 'r').read() if PY2: input_content = input_content.decode('utf-8') # Process the markdown text html_content, table_of_contents, meta = convert_markdown( input_content, site_navigation, extensions=config['markdown_extensions'], strict=config['strict'] ) context = get_global_context(site_navigation, config) context.update(get_page_context( page, html_content, site_navigation, table_of_contents, meta, config )) # Allow 'template:' override in md source files. if 'template' in meta: template = env.get_template(meta['template'][0]) else: template = env.get_template('base.html') if not utils.is_markdown_file(page.input_path): template = env.get_template('base_without_toc.html') # Render the template. output_content = template.render(context) # Write the output file. output_path = os.path.join(config['site_dir'], page.output_path) if dump_json: json_context = { 'content': context['content'], 'title': context['current_page'].title, 'url': context['current_page'].abs_url, 'language': 'en', } utils.write_file(json.dumps(json_context, indent=4).encode('utf-8'), output_path.replace('.html', '.json')) else: utils.write_file(output_content.encode('utf-8'), output_path) search_index.add_entry_from_context(page, html_content, table_of_contents) # generate html for other md files files = ListFilesByTxt(os.path.join(config['docs_dir']),'.md') for mdf in files: title = os.path.basename(mdf) title = os.path.splitext(title)[0] path = os.path.relpath(mdf,config['docs_dir']) url = utils.get_url_path(path,config['use_directory_urls']) output_path = utils.get_html_path(path) if(path in nav_pages):continue input_content = open(mdf, 'r').read() if PY2: input_content = input_content.decode('utf-8') site_navigation.url_context.set_current_url(url) # Process the markdown text html_content, table_of_contents, meta = convert_markdown( input_content, site_navigation, extensions=config['markdown_extensions'] ) context = get_global_context(site_navigation, config) page = nav.Page(title=title, url=url,path=path,url_context=site_navigation.url_context) context.update(get_page_context( page, html_content, site_navigation, table_of_contents, meta, config )) if 'template' in meta: template = env.get_template(meta['template'][0]) else: template = env.get_template('base.html') if not utils.is_markdown_file(mdf): template = env.get_template('base_without_toc.html') # Render the template. output_content = template.render(context) # Write the output file. output_path = os.path.join(config['site_dir'], output_path) utils.write_file(output_content.encode('utf-8'), output_path) #search_index.add_entry_from_context(page, html_content, table_of_contents) build_template('js/tipuesearch/tipuesearch_content.js', env, config, extra_context={ 'search_index': search_index.generate_search_index() })
def _generate_site_navigation(pages_config, url_context, use_directory_urls=True): """ Returns a list of Page and Header instances that represent the top level site navigation. """ nav_items = [] pages = [] previous = None for config_line in pages_config: if isinstance(config_line, str): path = os.path.normpath(config_line) title, child_title = None, None elif len(config_line) in (1, 2, 3): # Pad any items that don't exist with 'None' padded_config = (list(config_line) + [None, None])[:3] path, title, child_title = padded_config path = os.path.normpath(path) else: msg = ("Line in 'page' config contained %d items. " "Expected 1, 2 or 3 strings." % len(config_line)) raise exceptions.ConfigurationError(msg) # If both the title and child_title are None, then we # have just been given a path. If that path contains a / # then lets automatically nest it. if title is None and child_title is None and os.path.sep in path: filename = path.split(os.path.sep)[-1] child_title = filename_to_title(filename) if title is None: filename = path.split(os.path.sep)[0] title = filename_to_title(filename) # If we don't have a child title but the other title is the same, we # should be within a section and the child title needs to be inferred # from the filename. if len(nav_items) and title == nav_items[ -1].title == title and child_title is None: filename = path.split(os.path.sep)[-1] child_title = filename_to_title(filename) url = utils.get_url_path(path, use_directory_urls) if not child_title: # New top level page. page = Page(title=title, url=url, path=path, url_context=url_context) nav_items.append(page) elif not nav_items or (nav_items[-1].title != title): # New second level page. page = Page(title=child_title, url=url, path=path, url_context=url_context) header = Header(title=title, children=[page]) nav_items.append(header) page.ancestors = [header] else: # Additional second level page. page = Page(title=child_title, url=url, path=path, url_context=url_context) header = nav_items[-1] header.children.append(page) page.ancestors = [header] # Add in previous and next information. if previous: page.previous_page = previous previous.next_page = page previous = page pages.append(page) return (nav_items, pages)
def _generate_site_navigation(pages_config, url_context, use_directory_urls=True): """ Returns a list of Page and Header instances that represent the top level site navigation. """ nav_items = [] pages = [] previous = None for config_line in pages_config: if isinstance(config_line, str): path = os.path.normpath(config_line) title, child_title = None, None elif len(config_line) in (1, 2, 3): # Pad any items that don't exist with 'None' padded_config = (list(config_line) + [None, None])[:3] path, title, child_title = padded_config path = os.path.normpath(path) else: msg = ( "Line in 'page' config contained %d items. " "Expected 1, 2 or 3 strings." % len(config_line) ) raise exceptions.ConfigurationError(msg) # If both the title and child_title are None, then we # have just been given a path. If that path contains a / # then lets automatically nest it. if title is None and child_title is None and os.path.sep in path: filename = path.split(os.path.sep)[-1] child_title = file_to_tile(filename) if title is None: filename = path.split(os.path.sep)[0] title = file_to_tile(filename) # If we don't have a child title but the other title is the same, we # should be within a section and the child title needs to be inferred # from the filename. if len(nav_items) and title == nav_items[-1].title == title and child_title is None: filename = path.split(os.path.sep)[-1] child_title = file_to_tile(filename) url = utils.get_url_path(path, use_directory_urls) if not child_title: # New top level page. page = Page(title=title, url=url, path=path, url_context=url_context) nav_items.append(page) elif not nav_items or (nav_items[-1].title != title): # New second level page. page = Page(title=child_title, url=url, path=path, url_context=url_context) header = Header(title=title, children=[page]) nav_items.append(header) page.ancestors = [header] else: # Additional second level page. page = Page(title=child_title, url=url, path=path, url_context=url_context) header = nav_items[-1] header.children.append(page) page.ancestors = [header] # Add in previous and next information. if previous: page.previous_page = previous previous.next_page = page previous = page pages.append(page) return (nav_items, pages)
def __call__(self, match): path = match.groups()[0] return 'a href="%s"' % utils.get_url_path(path)
def _generate_site_navigation(pages_config, url_context, use_directory_urls=True): """ Returns a list of Page and Header instances that represent the top level site navigation. """ nav_items = [] pages = [] previous = None for config_line in pages_config: if isinstance(config_line, str): path = config_line title, child_title = None, None elif len(config_line) in (1, 2, 3): # Pad any items that don't exist with 'None' padded_config = (list(config_line) + [None, None])[:3] path, title, child_title = padded_config else: msg = ("Line in 'page' config contained %d items. " "Expected 1, 2 or 3 strings." % len(config_line)) assert False, msg if title is None and os.path.splitext(path)[0] != 'index': title = path.split('/')[0] title = os.path.splitext(title)[0] title = title.replace('-', ' ').replace('_', ' ') title = title.capitalize() if child_title is None and '/' in path: child_title = path.split('/')[1] child_title = os.path.splitext(child_title)[0] child_title = child_title.replace('-', ' ').replace('_', ' ') child_title = child_title.capitalize() url = utils.get_url_path(path, use_directory_urls) if not child_title: # New top level page. page = Page(title=title, url=url, path=path, url_context=url_context) if page.title is not None: # Page config lines that do not include a title, such as: # - ['index.md'] # Will not be added to the nav items heiarchy, although they # are included in the full list of pages, and have the # appropriate 'next'/'prev' links generated. nav_items.append(page) elif not nav_items or (nav_items[-1].title != title): # New second level page. page = Page(title=child_title, url=url, path=path, url_context=url_context) header = Header(title=title, children=[page]) nav_items.append(header) page.ancestors = [header] else: # Additional second level page. page = Page(title=child_title, url=url, path=path, url_context=url_context) header = nav_items[-1] header.children.append(page) page.ancestors = [header] # Add in previous and next information. if previous: page.previous_page = previous previous.next_page = page previous = page pages.append(page) return (nav_items, pages)