aboutsummaryrefslogtreecommitdiff
path: root/plugins
diff options
context:
space:
mode:
Diffstat (limited to 'plugins')
-rw-r--r--plugins/date.rb8
-rw-r--r--plugins/octopress_filters.rb7
-rw-r--r--plugins/pagination.rb121
-rw-r--r--plugins/post_filters.rb176
-rw-r--r--plugins/preview_unpublished.rb48
-rw-r--r--plugins/sitemap_generator.rb312
6 files changed, 8 insertions, 664 deletions
diff --git a/plugins/date.rb b/plugins/date.rb
index 01d94737..031e6736 100644
--- a/plugins/date.rb
+++ b/plugins/date.rb
@@ -63,8 +63,8 @@ module Jekyll
# Convert this Convertible's data to a Hash suitable for use by Liquid.
# Overrides the default return data and adds any date-specific liquid attributes
alias :super_to_liquid :to_liquid
- def to_liquid
- super_to_liquid.deep_merge(liquid_date_attributes)
+ def to_liquid(attrs = nil)
+ Utils.deep_merge_hashes super_to_liquid(attrs), liquid_date_attributes
end
end
@@ -74,8 +74,8 @@ module Jekyll
# Convert this Convertible's data to a Hash suitable for use by Liquid.
# Overrides the default return data and adds any date-specific liquid attributes
alias :super_to_liquid :to_liquid
- def to_liquid
- super_to_liquid.deep_merge(liquid_date_attributes)
+ def to_liquid(attrs = nil)
+ Utils.deep_merge_hashes super_to_liquid(attrs), liquid_date_attributes
end
end
end
diff --git a/plugins/octopress_filters.rb b/plugins/octopress_filters.rb
index a2ed71f8..d88cd639 100644
--- a/plugins/octopress_filters.rb
+++ b/plugins/octopress_filters.rb
@@ -1,8 +1,9 @@
#custom filters for Octopress
require './plugins/backtick_code_block'
-require './plugins/post_filters'
+require 'jekyll-page-hooks'
+require 'jekyll-sitemap'
+require 'jekyll-date-format'
require './plugins/raw'
-require './plugins/date'
require 'rubypants'
module OctopressFilters
@@ -21,7 +22,7 @@ module OctopressFilters
end
module Jekyll
- class ContentFilters < PostFilter
+ class ContentFilters < PageHooks
include OctopressFilters
def pre_render(post)
if post.ext.match('html|textile|markdown|md|haml|slim|xml')
diff --git a/plugins/pagination.rb b/plugins/pagination.rb
deleted file mode 100644
index a318754e..00000000
--- a/plugins/pagination.rb
+++ /dev/null
@@ -1,121 +0,0 @@
-module Jekyll
-
- class Pagination < Generator
- # This generator is safe from arbitrary code execution.
- safe true
-
- # Generate paginated pages if necessary.
- #
- # site - The Site.
- #
- # Returns nothing.
- def generate(site)
- site.pages.dup.each do |page|
- paginate(site, page) if Pager.pagination_enabled?(site.config, page)
- end
- end
-
- # Paginates the blog's posts. Renders the index.html file into paginated
- # directories, e.g.: page2/index.html, page3/index.html, etc and adds more
- # site-wide data.
- #
- # site - The Site.
- # page - The index.html Page that requires pagination.
- #
- # {"paginator" => { "page" => <Number>,
- # "per_page" => <Number>,
- # "posts" => [<Post>],
- # "total_posts" => <Number>,
- # "total_pages" => <Number>,
- # "previous_page" => <Number>,
- # "next_page" => <Number> }}
- def paginate(site, page)
- all_posts = site.site_payload['site']['posts']
- pages = Pager.calculate_pages(all_posts, site.config['paginate'].to_i)
- page_dir = page.destination('').sub(/\/[^\/]+$/, '')
- page_dir_config = site.config['pagination_dir']
- dir = ((page_dir_config || page_dir) + '/').sub(/^\/+/, '')
-
- (1..pages).each do |num_page|
- pager = Pager.new(site.config, num_page, all_posts, page_dir+'/', '/'+dir, pages)
- if num_page > 1
- newpage = Page.new(site, site.source, page_dir, page.name)
- newpage.pager = pager
- newpage.dir = File.join(page.dir, "#{dir}page/#{num_page}")
- site.pages << newpage
- else
- page.pager = pager
- end
- end
- end
- end
-
- class Pager
- attr_reader :page, :per_page, :posts, :total_posts, :total_pages, :previous_page, :next_page
-
- # Calculate the number of pages.
- #
- # all_posts - The Array of all Posts.
- # per_page - The Integer of entries per page.
- #
- # Returns the Integer number of pages.
- def self.calculate_pages(all_posts, per_page)
- (all_posts.size.to_f / per_page.to_i).ceil
- end
-
- # Determine if pagination is enabled for a given file.
- #
- # config - The configuration Hash.
- # file - The String filename of the file.
- #
- # Returns true if pagination is enabled, false otherwise.
- def self.pagination_enabled?(config, file)
- file.name == 'index.html' && !config['paginate'].nil? && file.content =~ /paginator\./
- end
-
- # Initialize a new Pager.
- #
- # config - The Hash configuration of the site.
- # page - The Integer page number.
- # all_posts - The Array of all the site's Posts.
- # num_pages - The Integer number of pages or nil if you'd like the number
- # of pages calculated.
- def initialize(config, page, all_posts, index_dir, pagination_dir, num_pages = nil)
- @page = page
- @per_page = config['paginate'].to_i
- @page_dir = pagination_dir + 'page/'
- @total_pages = num_pages || Pager.calculate_pages(all_posts, @per_page)
- @previous_page = nil
-
- if @page > @total_pages
- raise RuntimeError, "page number can't be greater than total pages: #{@page} > #{@total_pages}"
- end
-
- init = (@page - 1) * @per_page
- offset = (init + @per_page - 1) >= all_posts.size ? all_posts.size : (init + @per_page - 1)
-
- @total_posts = all_posts.size
- @posts = all_posts[init..offset]
- @previous_page = @page != 1 ? @page_dir + (@page - 1).to_s + '/' : nil
- @previous_page = index_dir if @page - 1 == 1
- @next_page = @page != @total_pages ? @page_dir + (@page + 1).to_s + '/' : nil
- end
-
- # Convert this Pager's data to a Hash suitable for use by Liquid.
- #
- # Returns the Hash representation of this Pager.
- def to_liquid
- {
- 'page' => page,
- 'per_page' => per_page,
- 'posts' => posts,
- 'total_posts' => total_posts,
- 'total_pages' => total_pages,
- 'previous_page' => previous_page,
- 'next_page' => next_page
- }
- end
- end
-
-end
-
diff --git a/plugins/post_filters.rb b/plugins/post_filters.rb
deleted file mode 100644
index 08626802..00000000
--- a/plugins/post_filters.rb
+++ /dev/null
@@ -1,176 +0,0 @@
-module Jekyll
-
- # Extended plugin type that allows the plugin
- # to be called on varous callback methods.
- #
- # Examples:
- # https://github.com/tedkulp/octopress/blob/master/plugins/post_metaweblog.rb
- # https://github.com/tedkulp/octopress/blob/master/plugins/post_twitter.rb
- class PostFilter < Plugin
-
- #Called before post is sent to the converter. Allows
- #you to modify the post object before the converter
- #does it's thing
- def pre_render(post)
- end
-
- #Called after the post is rendered with the converter.
- #Use the post object to modify it's contents before the
- #post is inserted into the template.
- def post_render(post)
- end
-
- #Called after the post is written to the disk.
- #Use the post object to read it's contents to do something
- #after the post is safely written.
- def post_write(post)
- end
- end
-
- # Monkey patch for the Jekyll Site class. For the original class,
- # see: https://github.com/mojombo/jekyll/blob/master/lib/jekyll/site.rb
- class Site
-
- # Instance variable to store the various post_filter
- # plugins that are loaded.
- attr_accessor :post_filters
-
- # Instantiates all of the post_filter plugins. This is basically
- # a duplication of the other loaders in Site#setup.
- def load_post_filters
- self.post_filters = Jekyll::PostFilter.subclasses.select do |c|
- !self.safe || c.safe
- end.map do |c|
- c.new(self.config)
- end
- end
- end
-
- # Monkey patch for the Jekyll Post class. For the original class,
- # see: https://github.com/mojombo/jekyll/blob/master/lib/jekyll/post.rb
- class Post
-
- # Copy the #write method to #old_write, so we can redefine #write
- # method.
- alias_method :old_write, :write
-
- # Write the generated post file to the destination directory. It
- # then calls any post_write methods that may exist.
- # +dest+ is the String path to the destination dir
- #
- # Returns nothing
- def write(dest)
- old_write(dest)
- post_write if respond_to?(:post_write)
- end
- end
-
- # Monkey patch for the Jekyll Page class. For the original class,
- # see: https://github.com/mojombo/jekyll/blob/master/lib/jekyll/page.rb
- class Page
-
- # Copy the #write method to #old_write, so we can redefine #write
- # method.
- alias_method :old_write, :write
-
- # Write the generated post file to the destination directory. It
- # then calls any post_write methods that may exist.
- # +dest+ is the String path to the destination dir
- #
- # Returns nothing
- def write(dest)
- old_write(dest)
- post_write if respond_to?(:post_write)
- end
- end
-
- # Monkey patch for the Jekyll Convertible module. For the original class,
- # see: https://github.com/mojombo/jekyll/blob/master/lib/jekyll/convertible.rb
- module Convertible
-
- def is_post?
- self.class.to_s == 'Jekyll::Post'
- end
-
- def is_page?
- self.class.to_s == 'Jekyll::Page'
- end
-
- def is_filterable?
- is_post? or is_page?
- end
-
- # Call the #pre_render methods on all of the loaded
- # post_filter plugins.
- #
- # Returns nothing
- def pre_render
- self.site.load_post_filters unless self.site.post_filters
-
- if self.site.post_filters and is_filterable?
- self.site.post_filters.each do |filter|
- filter.pre_render(self)
- end
- end
- end
-
- # Call the #post_render methods on all of the loaded
- # post_filter plugins.
- #
- # Returns nothing
- def post_render
- if self.site.post_filters and is_filterable?
- self.site.post_filters.each do |filter|
- filter.post_render(self)
- end
- end
- end
-
- # Call the #post_write methods on all of the loaded
- # post_filter plugins.
- #
- # Returns nothing
- def post_write
- if self.site.post_filters and is_filterable?
- self.site.post_filters.each do |filter|
- filter.post_write(self)
- end
- end
- end
-
- # Copy the #transform method to #old_transform, so we can
- # redefine #transform method.
- alias_method :old_transform, :transform
-
- # Transform the contents based on the content type. Then calls the
- # #post_render method if it exists
- #
- # Returns nothing.
- def transform
- old_transform
- post_render if respond_to?(:post_render)
- end
-
- # Copy the #do_layout method to #old_do_layout, so we can
- # redefine #do_layout method.
- alias_method :old_do_layout, :do_layout
-
- # Calls the pre_render method if it exists and then adds any necessary
- # layouts to this convertible document.
- #
- # payload - The site payload Hash.
- # layouts - A Hash of {"name" => "layout"}.
- #
- # Returns nothing.
- def do_layout(payload, layouts)
- pre_render if respond_to?(:pre_render)
- old_do_layout(payload, layouts)
- end
-
- # Returns the full url of the post, including the
- # configured url
- def full_url
- self.site.config['url'] + self.url
- end
- end
-end
diff --git a/plugins/preview_unpublished.rb b/plugins/preview_unpublished.rb
deleted file mode 100644
index 28cbdfe7..00000000
--- a/plugins/preview_unpublished.rb
+++ /dev/null
@@ -1,48 +0,0 @@
-# Monkeypatch for Jekyll
-# Introduce distinction between preview/productive site generation
-# so posts with YAML attribute `published: false` can be previewed
-# on localhost without being published to the productive environment.
-
-module Jekyll
-
- class Site
- # 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_posts(dir)
- base = File.join(self.source, dir, '_posts')
- return unless File.exists?(base)
- entries = Dir.chdir(base) { filter_entries(Dir['**/*']) }
-
- # first pass processes, but does not yet render post content
- entries.each do |f|
- if Post.valid?(f)
- post = Post.new(self, self.source, dir, f)
-
- # Monkeypatch:
- # On preview environment (localhost), publish all posts
- if ENV.has_key?('OCTOPRESS_ENV') && ENV['OCTOPRESS_ENV'] == 'preview' && post.data.has_key?('published') && post.data['published'] == false
- post.published = true
- # Set preview mode flag (if necessary), `rake generate` will check for it
- # to prevent pushing preview posts to productive environment
- File.open(".preview-mode", "w") {}
- end
-
- if post.published && (self.future || post.date <= self.time)
- self.posts << post
- post.categories.each { |c| self.categories[c] << post }
- post.tags.each { |c| self.tags[c] << post }
- end
- end
- end
-
- self.posts.sort!
-
- # limit the posts if :limit_posts option is set
- self.posts = self.posts[-limit_posts, limit_posts] if limit_posts
- end
- end
-end
diff --git a/plugins/sitemap_generator.rb b/plugins/sitemap_generator.rb
deleted file mode 100644
index a08590bf..00000000
--- a/plugins/sitemap_generator.rb
+++ /dev/null
@@ -1,312 +0,0 @@
-# Sitemap.xml Generator is a Jekyll plugin that generates a sitemap.xml file by
-# traversing all of the available posts and pages.
-#
-# How To Use:
-# 1) Copy source file into your _plugins folder within your Jekyll project.
-# 2) Change modify the url variable in _config.yml to reflect your domain name.
-# 3) Run Jekyll: jekyll --server to re-generate your site.
-#
-# Variables:
-# * Change SITEMAP_FILE_NAME if you want your sitemap to be called something
-# other than sitemap.xml.
-# * Change the PAGES_INCLUDE_POSTS list to include any pages that are looping
-# through your posts (e.g. "index.html", "archive.html", etc.). This will
-# ensure that right after you make a new post, the last modified date will
-# be updated to reflect the new post.
-# * A sitemap.xml should be included in your _site folder.
-# * If there are any files you don't want included in the sitemap, add them
-# to the EXCLUDED_FILES list. The name should match the name of the source
-# file.
-# * If you want to include the optional changefreq and priority attributes,
-# simply include custom variables in the YAML Front Matter of that file.
-# The names of these custom variables are defined below in the
-# CHANGE_FREQUENCY_CUSTOM_VARIABLE_NAME and PRIORITY_CUSTOM_VARIABLE_NAME
-# constants.
-#
-# Notes:
-# * The last modified date is determined by the latest from the following:
-# system modified date of the page or post, system modified date of
-# included layout, system modified date of included layout within that
-# layout, ...
-#
-# Author: Michael Levin
-# Site: http://www.kinnetica.com
-# Distributed Under A Creative Commons License
-# - http://creativecommons.org/licenses/by/3.0/
-#
-# Modified for Octopress by John W. Long
-#
-require 'rexml/document'
-require 'fileutils'
-
-module Jekyll
-
- # Change SITEMAP_FILE_NAME if you would like your sitemap file
- # to be called something else
- SITEMAP_FILE_NAME = "sitemap.xml"
-
- # Any files to exclude from being included in the sitemap.xml
- EXCLUDED_FILES = ["atom.xml"]
-
- # Any files that include posts, so that when a new post is added, the last
- # modified date of these pages should take that into account
- PAGES_INCLUDE_POSTS = ["index.html"]
-
- # Custom variable names for changefreq and priority elements
- # These names are used within the YAML Front Matter of pages or posts
- # for which you want to include these properties
- CHANGE_FREQUENCY_CUSTOM_VARIABLE_NAME = "change_frequency"
- PRIORITY_CUSTOM_VARIABLE_NAME = "priority"
-
- class Post
- attr_accessor :name
-
- def full_path_to_source
- File.join(@base, @name)
- end
-
- def location_on_server
- "#{site.config['url']}#{url}"
- end
- end
-
- class Page
- attr_accessor :name
-
- def full_path_to_source
- File.join(@base, @dir, @name)
- end
-
- def location_on_server
- location = "#{site.config['url']}#{@dir}#{url}"
- location.gsub(/index.html$/, "")
- end
- end
-
- class Layout
- def full_path_to_source
- File.join(@base, @name)
- end
- end
-
- # Recover from strange exception when starting server without --auto
- class SitemapFile < StaticFile
- def write(dest)
- begin
- super(dest)
- rescue
- end
-
- true
- end
- end
-
- class SitemapGenerator < Generator
-
- # Valid values allowed by sitemap.xml spec for change frequencies
- VALID_CHANGE_FREQUENCY_VALUES = ["always", "hourly", "daily", "weekly",
- "monthly", "yearly", "never"]
-
- # Goes through pages and posts and generates sitemap.xml file
- #
- # Returns nothing
- def generate(site)
- sitemap = REXML::Document.new << REXML::XMLDecl.new("1.0", "UTF-8")
-
- urlset = REXML::Element.new "urlset"
- urlset.add_attribute("xmlns",
- "http://www.sitemaps.org/schemas/sitemap/0.9")
-
- @last_modified_post_date = fill_posts(site, urlset)
- fill_pages(site, urlset)
-
- sitemap.add_element(urlset)
-
- # File I/O: create sitemap.xml file and write out pretty-printed XML
- unless File.exists?(site.dest)
- FileUtils.mkdir_p(site.dest)
- end
- file = File.new(File.join(site.dest, SITEMAP_FILE_NAME), "w")
- formatter = REXML::Formatters::Pretty.new(4)
- formatter.compact = true
- formatter.write(sitemap, file)
- file.close
-
- # Keep the sitemap.xml file from being cleaned by Jekyll
- site.static_files << Jekyll::SitemapFile.new(site, site.dest, "/", SITEMAP_FILE_NAME)
- end
-
- # Create url elements for all the posts and find the date of the latest one
- #
- # Returns last_modified_date of latest post
- def fill_posts(site, urlset)
- last_modified_date = nil
- site.posts.each do |post|
- if !excluded?(post.name)
- url = fill_url(site, post)
- urlset.add_element(url)
- end
-
- path = post.full_path_to_source
- date = File.mtime(path)
- last_modified_date = date if last_modified_date == nil or date > last_modified_date
- end
-
- last_modified_date
- end
-
- # Create url elements for all the normal pages and find the date of the
- # index to use with the pagination pages
- #
- # Returns last_modified_date of index page
- def fill_pages(site, urlset)
- site.pages.each do |page|
- if !excluded?(page.name)
- path = page.full_path_to_source
- if File.exists?(path)
- url = fill_url(site, page)
- urlset.add_element(url)
- end
- end
- end
- end
-
- # Fill data of each URL element: location, last modified,
- # change frequency (optional), and priority.
- #
- # Returns url REXML::Element
- def fill_url(site, page_or_post)
- url = REXML::Element.new "url"
-
- loc = fill_location(page_or_post)
- url.add_element(loc)
-
- lastmod = fill_last_modified(site, page_or_post)
- url.add_element(lastmod) if lastmod
-
- if (page_or_post.data[CHANGE_FREQUENCY_CUSTOM_VARIABLE_NAME])
- change_frequency =
- page_or_post.data[CHANGE_FREQUENCY_CUSTOM_VARIABLE_NAME].downcase
-
- if (valid_change_frequency?(change_frequency))
- changefreq = REXML::Element.new "changefreq"
- changefreq.text = change_frequency
- url.add_element(changefreq)
- else
- puts "ERROR: Invalid Change Frequency In #{page_or_post.name}"
- end
- end
-
- if (page_or_post.data[PRIORITY_CUSTOM_VARIABLE_NAME])
- priority_value = page_or_post.data[PRIORITY_CUSTOM_VARIABLE_NAME]
- if valid_priority?(priority_value)
- priority = REXML::Element.new "priority"
- priority.text = page_or_post.data[PRIORITY_CUSTOM_VARIABLE_NAME]
- url.add_element(priority)
- else
- puts "ERROR: Invalid Priority In #{page_or_post.name}"
- end
- end
-
- url
- end
-
- # Get URL location of page or post
- #
- # Returns the location of the page or post
- def fill_location(page_or_post)
- loc = REXML::Element.new "loc"
- loc.text = page_or_post.location_on_server
-
- loc
- end
-
- # Fill lastmod XML element with the last modified date for the page or post.
- #
- # Returns lastmod REXML::Element or nil
- def fill_last_modified(site, page_or_post)
- path = page_or_post.full_path_to_source
-
- lastmod = REXML::Element.new "lastmod"
- date = File.mtime(path)
- latest_date = find_latest_date(date, site, page_or_post)
-
- if @last_modified_post_date == nil
- # This is a post
- lastmod.text = latest_date.iso8601
- else
- # This is a page
- if posts_included?(page_or_post.name)
- # We want to take into account the last post date
- final_date = greater_date(latest_date, @last_modified_post_date)
- lastmod.text = final_date.iso8601
- else
- lastmod.text = latest_date.iso8601
- end
- end
- lastmod
- end
-
- # Go through the page/post and any implemented layouts and get the latest
- # modified date
- #
- # Returns formatted output of latest date of page/post and any used layouts
- def find_latest_date(latest_date, site, page_or_post)
- layouts = site.layouts
- layout = layouts[page_or_post.data["layout"]]
- while layout
- path = layout.full_path_to_source
- date = File.mtime(path)
-
- latest_date = date if (date > latest_date)
-
- layout = layouts[layout.data["layout"]]
- end
-
- latest_date
- end
-
- # Which of the two dates is later
- #
- # Returns latest of two dates
- def greater_date(date1, date2)
- if (date1 >= date2)
- date1
- else
- date2
- end
- end
-
- # Is the page or post listed as something we want to exclude?
- #
- # Returns boolean
- def excluded?(name)
- EXCLUDED_FILES.include? name
- end
-
- def posts_included?(name)
- PAGES_INCLUDE_POSTS.include? name
- end
-
- # Is the change frequency value provided valid according to the spec
- #
- # Returns boolean
- def valid_change_frequency?(change_frequency)
- VALID_CHANGE_FREQUENCY_VALUES.include? change_frequency
- end
-
- # Is the priority value provided valid according to the spec
- #
- # Returns boolean
- def valid_priority?(priority)
- begin
- priority_val = Float(priority)
- return true if priority_val >= 0.0 and priority_val <= 1.0
- rescue ArgumentError
- end
-
- false
- end
- end
-end
-