Separated some more readers from the main reader.rb file.

- Draft Reader
 - Collection Reader
 - Page Reader
 - Post Reader
 - Static File Reader

Fixed references and ran tests.

Signed-off-by: Martin Jorn Rogalla <martin@martinrogalla.com>
This commit is contained in:
Martin Jorn Rogalla 2015-03-06 17:20:25 +01:00
parent bebd80342e
commit 00cdcbc184
30 changed files with 467 additions and 214 deletions

View File

@ -11,6 +11,7 @@
* Move to Rouge as default highlighter (#3323) * Move to Rouge as default highlighter (#3323)
* Mimic GitHub Pages `.html` extension stripping behavior in WEBrick (#3452) * Mimic GitHub Pages `.html` extension stripping behavior in WEBrick (#3452)
* Always include file extension on output files (#3490) * Always include file extension on output files (#3490)
* Improved permalinks for pages and collections (#3538)
### Minor Enhancements ### Minor Enhancements
@ -46,6 +47,9 @@
* Docs: document 'ordinal' built-in permalink style (#3532) * Docs: document 'ordinal' built-in permalink style (#3532)
* Upgrade liquid-c to 3.x (#3531) * Upgrade liquid-c to 3.x (#3531)
* Use consistent syntax for deprecation warning (#3535) * Use consistent syntax for deprecation warning (#3535)
* Added build --destination and --source flags (#3418)
* Site template: remove unused `page.meta` attribute (#3537)
* Improve the error message when sorting null objects (#3520)
### Bug Fixes ### Bug Fixes
@ -89,6 +93,9 @@
* Remove trailing whitespace (#3497) * Remove trailing whitespace (#3497)
* Use `fixture_site` for Document tests (#3511) * Use `fixture_site` for Document tests (#3511)
* Remove adapters deprecation warning (#3529) * Remove adapters deprecation warning (#3529)
* Minor fixes to `url.rb` to follow GitHub style guide (#3544)
* Minor changes to resolve deprecation warnings (#3547)
* Convert remaining textile test documents to markdown (#3528)
### Site Enhancements ### Site Enhancements
@ -129,6 +136,7 @@
* Add jekyll-auto-image generator to the list of third-party plugins (#3489) * Add jekyll-auto-image generator to the list of third-party plugins (#3489)
* Replace link to the proposed `picture` element spec (#3530) * Replace link to the proposed `picture` element spec (#3530)
* Add frontmatter date formatting information (#3469) * Add frontmatter date formatting information (#3469)
* Improve consistency and clarity of plugins options note (#3546)
## 2.5.3 / 2014-12-22 ## 2.5.3 / 2014-12-22
@ -293,7 +301,6 @@
* Allow Travis to 'parallelize' our tests (#2859) * Allow Travis to 'parallelize' our tests (#2859)
* Fix test for Liquid rendering in Sass (#2856) * Fix test for Liquid rendering in Sass (#2856)
* Fixing "vertycal" typo in site template's `_base.scss` (#2889) * Fixing "vertycal" typo in site template's `_base.scss` (#2889)
* Convert remaining textile test documents to markdown (#3528)
### Site Enhancements ### Site Enhancements

View File

@ -49,9 +49,13 @@ module Jekyll
autoload :Filters, 'jekyll/filters' autoload :Filters, 'jekyll/filters'
autoload :FrontmatterDefaults, 'jekyll/frontmatter_defaults' autoload :FrontmatterDefaults, 'jekyll/frontmatter_defaults'
autoload :Layout, 'jekyll/layout' autoload :Layout, 'jekyll/layout'
autoload :LayoutReader, 'jekyll/readers/layout_reader' autoload :CollectionReader, 'jekyll/readers/dynamic/collection_reader'
autoload :DraftReader, 'jekyll/readers/draft_reader' autoload :DataReader, 'jekyll/readers/dynamic/data_reader'
autoload :PostReader, 'jekyll/readers/post_reader' autoload :LayoutReader, 'jekyll/readers/dynamic/layout_reader'
autoload :DraftReader, 'jekyll/readers/dynamic/draft_reader'
autoload :PostReader, 'jekyll/readers/dynamic/post_reader'
autoload :PageReader, 'jekyll/readers/dynamic/page_reader'
autoload :StaticFileReader, 'jekyll/readers/static/static_file_reader'
autoload :LogAdapter, 'jekyll/log_adapter' autoload :LogAdapter, 'jekyll/log_adapter'
autoload :Page, 'jekyll/page' autoload :Page, 'jekyll/page'
autoload :PluginManager, 'jekyll/plugin_manager' autoload :PluginManager, 'jekyll/plugin_manager'

View File

@ -170,7 +170,9 @@ module Jekyll
# #
# Returns the URL template to render collection's documents at. # Returns the URL template to render collection's documents at.
def url_template def url_template
metadata.fetch('permalink', "/:collection/:path:output_ext") metadata.fetch('permalink') do
Utils.add_permalink_suffix("/:collection/:path", site.permalink_style)
end
end end
# Extract options for this collection from the site configuration. # Extract options for this collection from the site configuration.

View File

@ -49,6 +49,8 @@ module Jekyll
# Returns nothing # Returns nothing
def add_build_options(c) def add_build_options(c)
c.option 'config', '--config CONFIG_FILE[,CONFIG_FILE2,...]', Array, 'Custom configuration file' c.option 'config', '--config CONFIG_FILE[,CONFIG_FILE2,...]', Array, 'Custom configuration file'
c.option 'destination', '-d', '--destination DESTINATION', 'The current folder will be generated into DESTINATION'
c.option 'source', '-s', '--source SOURCE', 'Custom source directory'
c.option 'future', '--future', 'Publishes posts with a future date' c.option 'future', '--future', 'Publishes posts with a future date'
c.option 'limit_posts', '--limit_posts MAX_POSTS', Integer, 'Limits the number of posts to parse and publish' c.option 'limit_posts', '--limit_posts MAX_POSTS', Integer, 'Limits the number of posts to parse and publish'
c.option 'watch', '-w', '--[no-]watch', 'Watch for changes and rebuild' c.option 'watch', '-w', '--[no-]watch', 'Watch for changes and rebuild'

View File

@ -137,7 +137,7 @@ module Jekyll
config_files = override.delete('config') config_files = override.delete('config')
if config_files.to_s.empty? if config_files.to_s.empty?
default = %w[yml yaml].find(Proc.new { 'yml' }) do |ext| default = %w[yml yaml].find(Proc.new { 'yml' }) do |ext|
File.exists? Jekyll.sanitized_path(source(override), "_config.#{ext}") File.exist?(Jekyll.sanitized_path(source(override), "_config.#{ext}"))
end end
config_files = Jekyll.sanitized_path(source(override), "_config.#{default}") config_files = Jekyll.sanitized_path(source(override), "_config.#{default}")
@default_config_file = true @default_config_file = true

View File

@ -222,6 +222,9 @@ module Jekyll
# #
# Returns the filtered array of objects # Returns the filtered array of objects
def sort(input, property = nil, nils = "first") def sort(input, property = nil, nils = "first")
if input.nil?
raise ArgumentError.new("Cannot sort a null object.")
end
if property.nil? if property.nil?
input.sort input.sort
else else

View File

@ -63,16 +63,12 @@ module Jekyll
# #
# Returns the template String. # Returns the template String.
def template def template
if site.permalink_style == :pretty if !html?
if index? && html? "/:path/:basename:output_ext"
elsif index?
"/:path/" "/:path/"
elsif html?
"/:path/:basename/"
else else
"/:path/:basename:output_ext" Utils.add_permalink_suffix("/:path/:basename", site.permalink_style)
end
else
"/:path/:basename:output_ext"
end end
end end

View File

@ -13,10 +13,76 @@ module Jekyll
# #
# Returns nothing. # Returns nothing.
def read def read
site.layouts = LayoutReader.new(site).read @site.layouts = LayoutReader.new(site).read
read_directories read_directories
read_data(site.config['data_source']) @site.data = DataReader.new(site).read(site.config['data_source'])
read_collections CollectionReader.new(site).read
end
# Recursively traverse directories to find posts, pages and static files
# that will become part of the site according to the rules in
# filter_entries.
#
# dir - The String relative path of the directory to read. Default: ''.
#
# Returns nothing.
def read_directories(dir = '')
retrieve_posts(dir)
# Obtain sub-directories in order to recursively read them.
base = site.in_source_dir(dir)
dot = Dir.chdir(base) { filter_entries(Dir.entries('.'), base) }
dot_dirs = dot.select{ |file| File.directory?(@site.in_source_dir(base,file)) }
retrieve_dirs(base, dir, dot_dirs)
dot_files = (dot - dot_dirs)
# Obtain all the pages.
dot_pages = dot_files.select{ |file| Utils.has_yaml_header?(@site.in_source_dir(base,file)) }
retrieve_pages(dir, dot_pages)
# Assume the remaining files to be static files.
dot_static_files = dot_files - dot_pages
retrieve_static_files(dir, dot_static_files)
end
# Retrieves all the posts(posts/drafts) from the given directory
# and add them to the site and sort them.
#
# Returns nothing.
def retrieve_posts(dir)
site.posts += PostReader.new(site).read(dir)
site.posts += DraftReader.new(site).read(dir) if site.show_drafts
site.posts.sort!
end
# Recursively traverse directories with the read_directories function.
#
# Returns nothing.
def retrieve_dirs(base, dir, dot_dirs)
dot_dirs.map { |file|
dir_path = site.in_source_dir(dir,file)
rel_path = File.join(dir, file)
@site.reader.read_directories(rel_path) unless @site.dest.sub(/\/$/, '') == dir_path
}
end
# Retrieve all the pages from the current directory,
# add them to the site and sort them.
#
# Returns nothing.
def retrieve_pages(dir, dot_pages)
site.pages += PageReader.new(site, dir).read(dot_pages)
site.pages.sort_by!(&:name)
end
# Retrieve all the static files from the current directory,
# add them to the site and sort them.
#
# Returns nothing.
def retrieve_static_files(dir, dot_static_files)
site.static_files += StaticFileReader.new(site, dir).read(dot_static_files)
site.static_files.sort_by!(&:relative_path)
end end
# Filter out any files/directories that are hidden or backup files (start # Filter out any files/directories that are hidden or backup files (start
@ -43,144 +109,5 @@ module Jekyll
entries = Dir.chdir(base) { filter_entries(Dir['**/*'], base) } entries = Dir.chdir(base) { filter_entries(Dir['**/*'], base) }
entries.delete_if { |e| File.directory?(site.in_source_dir(base, e)) } entries.delete_if { |e| File.directory?(site.in_source_dir(base, e)) }
end end
# Determines how to read a data file.
#
# Returns the contents of the data file.
def read_data_file(path)
case File.extname(path).downcase
when '.csv'
CSV.read(path, {
:headers => true,
:encoding => site.config['encoding']
}).map(&:to_hash)
else
SafeYAML.load_file(path)
end
end
# Recursively traverse directories to find posts, pages and static files
# that will become part of the site according to the rules in
# filter_entries.
#
# dir - The String relative path of the directory to read. Default: ''.
#
# Returns nothing.
def read_directories(dir = '')
base = site.in_source_dir(dir)
entries = Dir.chdir(base) { filter_entries(Dir.entries('.'), base) }
site.posts += PostReader.new(site).read(dir)
if site.show_drafts
site.posts += DraftReader.new(site).read(dir)
end
site.posts.sort!
limit_posts if site.limit_posts > 0 # limit the posts if :limit_posts option is set
entries.each do |f|
f_abs = site.in_source_dir(base, f)
if File.directory?(f_abs)
f_rel = File.join(dir, f)
read_directories(f_rel) unless site.dest.sub(/\/$/, '') == f_abs
elsif Utils.has_yaml_header?(f_abs)
page = Page.new(site, site.source, dir, f)
site.pages << page if site.publisher.publish?(page)
else
site.static_files << StaticFile.new(site, site.source, dir, f)
end
end
site.pages.sort_by!(&:name)
site.static_files.sort_by!(&:relative_path)
end
# Read all the content files from <source>/<dir>/magic_dir
# and return them with the type klass.
#
# dir - The String relative path of the directory to read.
# magic_dir - The String relative directory to <dir>,
# looks for content here.
# klass - The return type of the content.
#
# Returns klass type of content files
def read_content(dir, magic_dir, klass)
get_entries(dir, magic_dir).map do |entry|
klass.new(site, site.source, dir, entry) if klass.valid?(entry)
end.reject do |entry|
entry.nil?
end
end
# Read and parse all yaml files under <source>/<dir>
#
# Returns nothing
def read_data(dir)
base = site.in_source_dir(dir)
read_data_to(base, site.data)
end
# Read and parse all yaml files under <dir> and add them to the
# <data> variable.
#
# dir - The string absolute path of the directory to read.
# data - The variable to which data will be added.
#
# Returns nothing
def read_data_to(dir, data)
return unless File.directory?(dir) && (!site.safe || !File.symlink?(dir))
entries = Dir.chdir(dir) do
Dir['*.{yaml,yml,json,csv}'] + Dir['*'].select { |fn| File.directory?(fn) }
end
entries.each do |entry|
path = site.in_source_dir(dir, entry)
next if File.symlink?(path) && site.safe
key = sanitize_filename(File.basename(entry, '.*'))
if File.directory?(path)
read_data_to(path, data[key] = {})
else
data[key] = read_data_file(path)
end
end
end
# Read in all collections specified in the configuration
#
# Returns nothing.
def read_collections
site.collections.each do |_, collection|
collection.read unless collection.label.eql?('data')
end
end
def sanitize_filename(name)
name.gsub!(/[^\w\s_-]+/, '')
name.gsub!(/(^|\b\s)\s+($|\s?\b)/, '\\1\\2')
name.gsub(/\s+/, '_')
end
# Aggregate post information
#
# post - The Post object to aggregate information for
#
# Returns nothing
def aggregate_post_info(post)
site.posts << post
end
private
# Limits the current posts; removes the posts which exceed the limit_posts
#
# Returns nothing
def limit_posts
limit = site.posts.length < site.limit_posts ? site.posts.length : site.limit_posts
site.posts = site.posts[-limit, limit]
end
end end
end end

View File

@ -1,20 +0,0 @@
module Jekyll
class DraftReader
attr_reader :site, :unfiltered_content
def initialize(site)
@site = site
@unfiltered_content = Array.new
end
# Read all the files in <source>/<dir>/_drafts and create a new Draft
# object with each one.
#
# dir - The String relative path of the directory to read.
#
# Returns nothing.
def read(dir)
@unfiltered_content = @site.reader.read_content(dir, '_drafts', Draft)
@unfiltered_content.select{ |draft| site.publisher.publish?(draft) }
end
end
end

View File

@ -0,0 +1,19 @@
module Jekyll
class CollectionReader
attr_reader :site, :content
def initialize(site)
@site = site
@content = {}
end
# Read in all collections specified in the configuration
#
# Returns nothing.
def read
site.collections.each do |_, collection|
collection.read unless collection.label.eql?('data')
end
end
end
end

View File

@ -0,0 +1,69 @@
module Jekyll
class DataReader
attr_reader :site, :content
def initialize(site)
@site = site
@content = {}
end
# Read all the files in <source>/<dir>/_drafts and create a new Draft
# object with each one.
#
# dir - The String relative path of the directory to read.
#
# Returns nothing.
def read(dir)
base = site.in_source_dir(dir)
read_data_to(base, @content)
@content
end
# Read and parse all yaml files under <dir> and add them to the
# <data> variable.
#
# dir - The string absolute path of the directory to read.
# data - The variable to which data will be added.
#
# Returns nothing
def read_data_to(dir, data)
return unless File.directory?(dir) && (!site.safe || !File.symlink?(dir))
entries = Dir.chdir(dir) do
Dir['*.{yaml,yml,json,csv}'] + Dir['*'].select { |fn| File.directory?(fn) }
end
entries.each do |entry|
path = @site.in_source_dir(dir, entry)
next if File.symlink?(path) && site.safe
key = sanitize_filename(File.basename(entry, '.*'))
if File.directory?(path)
read_data_to(path, data[key] = {})
else
data[key] = read_data_file(path)
end
end
end
# Determines how to read a data file.
#
# Returns the contents of the data file.
def read_data_file(path)
case File.extname(path).downcase
when '.csv'
CSV.read(path, {
:headers => true,
:encoding => site.config['encoding']
}).map(&:to_hash)
else
SafeYAML.load_file(path)
end
end
def sanitize_filename(name)
name.gsub!(/[^\w\s_-]+/, '')
name.gsub!(/(^|\b\s)\s+($|\s?\b)/, '\\1\\2')
name.gsub(/\s+/, '_')
end
end
end

View File

@ -0,0 +1,37 @@
module Jekyll
class DraftReader
attr_reader :site, :unfiltered_content
def initialize(site)
@site = site
@unfiltered_content = Array.new
end
# Read all the files in <source>/<dir>/_drafts and create a new Draft
# object with each one.
#
# dir - The String relative path of the directory to read.
#
# Returns nothing.
def read(dir)
@unfiltered_content = read_content(dir, '_drafts')
@unfiltered_content.select{ |draft| site.publisher.publish?(draft) }
end
# Read all the content files from <source>/<dir>/magic_dir
# and return them with the type klass.
#
# dir - The String relative path of the directory to read.
# magic_dir - The String relative directory to <dir>,
# looks for content here.
# klass - The return type of the content.
#
# Returns klass type of content files
def read_content(dir, magic_dir)
@site.reader.get_entries(dir, magic_dir).map do |entry|
Draft.new(site, site.source, dir, entry) if Draft.valid?(entry)
end.reject do |entry|
entry.nil?
end
end
end
end

View File

@ -0,0 +1,21 @@
module Jekyll
class PageReader
attr_reader :site, :dir, :unfiltered_content
def initialize(site, dir)
@site = site
@dir = dir
@unfiltered_content = Array.new
end
# Read all the files in <source>/<dir>/ for Yaml header and create a new Page
# object for each file.
#
# dir - The String relative path of the directory to read.
#
# Returns an array of static pages.
def read(files)
files.map{ |page| @unfiltered_content << Page.new(@site, @site.source, @dir, page) }
@unfiltered_content.select{ |page| site.publisher.publish?(page) }
end
end
end

View File

@ -0,0 +1,37 @@
module Jekyll
class PostReader
attr_reader :site, :unfiltered_content
def initialize(site)
@site = site
@unfiltered_content = Array.new
end
# Read all the files in <source>/<dir>/_posts and create a new Post
# object with each one.
#
# dir - The String relative path of the directory to read.
#
# Returns nothing.
def read(dir)
@unfiltered_content = read_content(dir, '_posts')
@unfiltered_content.select{ |post| site.publisher.publish?(post) }
end
# Read all the content files from <source>/<dir>/magic_dir
# and return them with the type klass.
#
# dir - The String relative path of the directory to read.
# magic_dir - The String relative directory to <dir>,
# looks for content here.
# klass - The return type of the content.
#
# Returns klass type of content files
def read_content(dir, magic_dir)
@site.reader.get_entries(dir, magic_dir).map do |entry|
Post.new(site, site.source, dir, entry) if Post.valid?(entry)
end.reject do |entry|
entry.nil?
end
end
end
end

View File

@ -1,20 +0,0 @@
module Jekyll
class PostReader
attr_reader :site, :unfiltered_content
def initialize(site)
@site = site
@unfiltered_content = Array.new
end
# Read all the files in <source>/<dir>/_posts and create a new Post
# object with each one.
#
# dir - The String relative path of the directory to read.
#
# Returns nothing.
def read(dir)
@unfiltered_content = @site.reader.read_content(dir, '_posts', Post)
@unfiltered_content.select{ |post| site.publisher.publish?(post) }
end
end
end

View File

@ -0,0 +1,21 @@
module Jekyll
class StaticFileReader
attr_reader :site, :dir, :unfiltered_content
def initialize(site, dir)
@site = site
@dir = dir
@unfiltered_content = Array.new
end
# Read all the files in <source>/<dir>/ for Yaml header and create a new Page
# object for each file.
#
# dir - The String relative path of the directory to read.
#
# Returns an array of static files.
def read(files)
files.map{ |file| @unfiltered_content << StaticFile.new(@site, @site.source, @dir, file)}
@unfiltered_content
end
end
end

View File

@ -130,6 +130,7 @@ module Jekyll
# Returns nothing. # Returns nothing.
def read def read
reader.read reader.read
limit_posts!
end end
# Run each of the Generators. # Run each of the Generators.
@ -383,5 +384,15 @@ module Jekyll
def site_cleaner def site_cleaner
@site_cleaner ||= Cleaner.new(self) @site_cleaner ||= Cleaner.new(self)
end end
# Limits the current posts; removes the posts which exceed the limit_posts
#
# Returns nothing
def limit_posts!
if limit_posts > 0
limit = posts.length < limit_posts ? posts.length : limit_posts
self.posts = posts[-limit, limit]
end
end
end end
end end

View File

@ -44,12 +44,12 @@ module Jekyll
# #
# Returns the _unsanitized String URL # Returns the _unsanitized String URL
def generated_permalink def generated_permalink
(@generated_permlink ||= generate_url(@permalink)) if @permalink (@generated_permalink ||= generate_url(@permalink)) if @permalink
end end
# Generates a URL from the template # Generates a URL from the template
# #
# Returns the _unsanitized String URL # Returns the unsanitized String URL
def generated_url def generated_url
@generated_url ||= generate_url(@template) @generated_url ||= generate_url(@template)
end end
@ -57,7 +57,7 @@ module Jekyll
# Internal: Generate the URL by replacing all placeholders with their # Internal: Generate the URL by replacing all placeholders with their
# respective values in the given template # respective values in the given template
# #
# Returns the _unsanitizied_ String URL # Returns the unsanitized String URL
def generate_url(template) def generate_url(template)
@placeholders.inject(template) do |result, token| @placeholders.inject(template) do |result, token|
break result if result.index(':').nil? break result if result.index(':').nil?
@ -81,7 +81,7 @@ module Jekyll
.gsub(/\A([^\/])/, '/\1') .gsub(/\A([^\/])/, '/\1')
# Append a trailing slash to the URL if the unsanitized URL had one # Append a trailing slash to the URL if the unsanitized URL had one
url << "/" if in_url[-1].eql?('/') url << "/" if in_url.end_with?("/")
url url
end end
@ -107,7 +107,7 @@ module Jekyll
# pct-encoded = "%" HEXDIG HEXDIG # pct-encoded = "%" HEXDIG HEXDIG
# sub-delims = "!" / "$" / "&" / "'" / "(" / ")" # sub-delims = "!" / "$" / "&" / "'" / "(" / ")"
# / "*" / "+" / "," / ";" / "=" # / "*" / "+" / "," / ";" / "="
URI.escape(path, /[^a-zA-Z\d\-._~!$&\'()*+,;=:@\/]/).encode('utf-8') URI.escape(path, /[^a-zA-Z\d\-._~!$&'()*+,;=:@\/]/).encode('utf-8')
end end
# Unescapes a URL path segment # Unescapes a URL path segment

View File

@ -158,5 +158,45 @@ module Jekyll
downcase downcase
end end
# Add an appropriate suffix to template so that it matches the specified
# permalink style.
#
# template - permalink template without trailing slash or file extension
# permalink_style - permalink style, either built-in or custom
#
# The returned permalink template will use the same ending style as
# specified in permalink_style. For example, if permalink_style contains a
# trailing slash (or is :pretty, which indirectly has a trailing slash),
# then so will the returned template. If permalink_style has a trailing
# ":output_ext" (or is :none, :date, or :ordinal) then so will the returned
# template. Otherwise, template will be returned without modification.
#
# Examples:
# add_permalink_suffix("/:basename", :pretty)
# # => "/:basename/"
#
# add_permalink_suffix("/:basename", :date)
# # => "/:basename:output_ext"
#
# add_permalink_suffix("/:basename", "/:year/:month/:title/")
# # => "/:basename/"
#
# add_permalink_suffix("/:basename", "/:year/:month/:title")
# # => "/:basename"
#
# Returns the updated permalink template
def add_permalink_suffix(template, permalink_style)
case permalink_style
when :pretty
template << "/"
when :date, :ordinal, :none
template << ":output_ext"
else
template << "/" if permalink_style.to_s.end_with?("/")
template << ":output_ext" if permalink_style.to_s.end_with?(":output_ext")
end
template
end
end end
end end

View File

@ -1,3 +1,3 @@
module Jekyll module Jekyll
VERSION = '3.0.0-beta1' VERSION = '3.0.0.beta2'
end end

View File

@ -5,7 +5,7 @@ layout: default
<header class="post-header"> <header class="post-header">
<h1 class="post-title" itemprop="name headline">{{ page.title }}</h1> <h1 class="post-title" itemprop="name headline">{{ page.title }}</h1>
<p class="post-meta"><time datetime="{{ page.date | date_to_xmlschema }}" itemprop="datePublished">{{ page.date | date: "%b %-d, %Y" }}</time>{% if page.author %} • <span itemprop="author" itemscope itemtype="http://schema.org/Person"><span itemprop="name">{{ page.author }}</span></span>{% endif %}{% if page.meta %} • {{ page.meta }}{% endif %}</p> <p class="post-meta"><time datetime="{{ page.date | date_to_xmlschema }}" itemprop="datePublished">{{ page.date | date: "%b %-d, %Y" }}</time>{% if page.author %} • <span itemprop="author" itemscope itemtype="http://schema.org/Person"><span itemprop="name">{{ page.author }}</span></span>{% endif %}</p>
</header> </header>
<div class="post-content" itemprop="articleBody"> <div class="post-content" itemprop="articleBody">

View File

@ -191,6 +191,7 @@ permalink: "/docs/history/"
- Allow Travis to 'parallelize' our tests ([#2859]({{ site.repository }}/issues/2859)) - Allow Travis to 'parallelize' our tests ([#2859]({{ site.repository }}/issues/2859))
- Fix test for Liquid rendering in Sass ([#2856]({{ site.repository }}/issues/2856)) - Fix test for Liquid rendering in Sass ([#2856]({{ site.repository }}/issues/2856))
- Fixing "vertycal" typo in site template's `_base.scss` ([#2889]({{ site.repository }}/issues/2889)) - Fixing "vertycal" typo in site template's `_base.scss` ([#2889]({{ site.repository }}/issues/2889))
- Convert remaining textile test documents to markdown ([#3528]({{ site.repository }}/issues/3528))
### Site Enhancements ### Site Enhancements
{: #site-enhancements-v2-4-0} {: #site-enhancements-v2-4-0}

View File

@ -42,12 +42,12 @@ You have 3 options for installing plugins:
<div class="note info"> <div class="note info">
<h5> <h5>
<code>_plugins</code> and <code>gems</code> <code>_plugins</code>, <code>_config.yml</code> and <code>Gemfile</code>
can be used simultaneously can be used simultaneously
</h5> </h5>
<p> <p>
You may use both of the aforementioned plugin options simultaneously in the You may use any of the aforementioned plugin options simultaneously in the
same site if you so choose. Use of one does not restrict the use of the other same site if you so choose. Use of one does not restrict the use of the others.
</p> </p>
</div> </div>

View File

@ -42,12 +42,12 @@ class TestConfiguration < JekyllUnitTest
assert_equal [source_dir("_config.yml")], @config.config_files(@no_override) assert_equal [source_dir("_config.yml")], @config.config_files(@no_override)
end end
should "return .yaml if it exists but .yml does not" do should "return .yaml if it exists but .yml does not" do
mock(File).exists?(source_dir("_config.yml")) { false } mock(File).exist?(source_dir("_config.yml")) { false }
mock(File).exists?(source_dir("_config.yaml")) { true } mock(File).exist?(source_dir("_config.yaml")) { true }
assert_equal [source_dir("_config.yaml")], @config.config_files(@no_override) assert_equal [source_dir("_config.yaml")], @config.config_files(@no_override)
end end
should "return .yml if both .yml and .yaml exist" do should "return .yml if both .yml and .yaml exist" do
mock(File).exists?(source_dir("_config.yml")) { true } mock(File).exist?(source_dir("_config.yml")) { true }
assert_equal [source_dir("_config.yml")], @config.config_files(@no_override) assert_equal [source_dir("_config.yml")], @config.config_files(@no_override)
end end
should "return the config if given one config file" do should "return the config if given one config file" do

View File

@ -219,7 +219,31 @@ class TestDocument < JekyllUnitTest
assert_equal "/slides/test/example-slide-1", @document.url assert_equal "/slides/test/example-slide-1", @document.url
end end
should "produce the right destination" do should "produce the right destination file" do
assert_equal @dest_file, @document.destination(dest_dir)
end
end
context "a document in a collection with pretty permalink style" do
setup do
@site = fixture_site({
"collections" => {
"slides" => {
"output" => true,
}
},
})
@site.permalink_style = :pretty
@site.process
@document = @site.collections["slides"].docs[0]
@dest_file = dest_dir("slides/example-slide-1/index.html")
end
should "produce the right URL" do
assert_equal "/slides/example-slide-1/", @document.url
end
should "produce the right destination file" do
assert_equal @dest_file, @document.destination(dest_dir) assert_equal @dest_file, @document.destination(dest_dir)
end end
end end

View File

@ -280,6 +280,12 @@ class TestFilters < JekyllUnitTest
end end
context "sort filter" do context "sort filter" do
should "raise Exception when input is nil" do
err = assert_raises ArgumentError do
@filter.sort(nil)
end
assert_equal "Cannot sort a null object.", err.message
end
should "return sorted numbers" do should "return sorted numbers" do
assert_equal [1, 2, 2.2, 3], @filter.sort([3, 2.2, 2, 1]) assert_equal [1, 2, 2.2, 3], @filter.sort([3, 2.2, 2, 1])
end end

View File

@ -46,7 +46,7 @@ class TestPage < JekyllUnitTest
should "create index url based on filename" do should "create index url based on filename" do
@page = setup_page('/contacts', 'index.html') @page = setup_page('/contacts', 'index.html')
assert_equal "/contacts/index.html", @page.url assert_equal "/contacts/", @page.url
end end
end end
@ -129,6 +129,58 @@ class TestPage < JekyllUnitTest
end end
end end
context "with date permalink style" do
setup do
@site.permalink_style = :date
end
should "return url and destination correctly" do
@page = setup_page('contacts.html')
@dest_file = dest_dir("contacts.html")
assert_equal '/contacts.html', @page.url
assert_equal @dest_file, @page.destination(dest_dir)
end
end
context "with custom permalink style with trailing slash" do
setup do
@site.permalink_style = "/:title/"
end
should "return url and destination correctly" do
@page = setup_page('contacts.html')
@dest_file = dest_dir("contacts/index.html")
assert_equal '/contacts/', @page.url
assert_equal @dest_file, @page.destination(dest_dir)
end
end
context "with custom permalink style with file extension" do
setup do
@site.permalink_style = "/:title:output_ext"
end
should "return url and destination correctly" do
@page = setup_page('contacts.html')
@dest_file = dest_dir("contacts.html")
assert_equal '/contacts.html', @page.url
assert_equal @dest_file, @page.destination(dest_dir)
end
end
context "with custom permalink style with no extension" do
setup do
@site.permalink_style = "/:title"
end
should "return url and destination correctly" do
@page = setup_page('contacts.html')
@dest_file = dest_dir("contacts.html")
assert_equal '/contacts', @page.url
assert_equal @dest_file, @page.destination(dest_dir)
end
end
context "with any other permalink style" do context "with any other permalink style" do
should "return dir correctly" do should "return dir correctly" do
@site.permalink_style = nil @site.permalink_style = nil

View File

@ -143,7 +143,7 @@ class TestSite < JekyllUnitTest
# simulate destination file deletion # simulate destination file deletion
File.unlink dest File.unlink dest
refute File.exists?(dest) refute File.exist?(dest)
sleep 1 sleep 1
@site.process @site.process
@ -369,7 +369,7 @@ class TestSite < JekyllUnitTest
site = Site.new(site_configuration) site = Site.new(site_configuration)
site.process site.process
file_content = site.reader.read_data_file(source_dir('_data', 'members.yaml')) file_content = DataReader.new(site).read_data_file(source_dir('_data', 'members.yaml'))
assert_equal site.data['members'], file_content assert_equal site.data['members'], file_content
assert_equal site.site_payload['site']['data']['members'], file_content assert_equal site.site_payload['site']['data']['members'], file_content

View File

@ -166,4 +166,18 @@ class TestUtils < JekyllUnitTest
end end
end end
context "The \`Utils.add_permalink_suffix\` method" do
should "handle built-in permalink styles" do
assert_equal "/:basename/", Utils.add_permalink_suffix("/:basename", :pretty)
assert_equal "/:basename:output_ext", Utils.add_permalink_suffix("/:basename", :date)
assert_equal "/:basename:output_ext", Utils.add_permalink_suffix("/:basename", :ordinal)
assert_equal "/:basename:output_ext", Utils.add_permalink_suffix("/:basename", :none)
end
should "handle custom permalink styles" do
assert_equal "/:basename/", Utils.add_permalink_suffix("/:basename", "/:title/")
assert_equal "/:basename:output_ext", Utils.add_permalink_suffix("/:basename", "/:title:output_ext")
assert_equal "/:basename", Utils.add_permalink_suffix("/:basename", "/:title")
end
end
end end