OMG it's happening ~*Collections*~

This commit is contained in:
Parker Moore 2014-04-01 21:19:10 -04:00
parent a77c92aebe
commit 50b46d7bee
11 changed files with 157 additions and 8 deletions

View File

@ -35,6 +35,7 @@ require 'jekyll/stevenson'
require 'jekyll/deprecator'
require 'jekyll/configuration'
require 'jekyll/document'
require 'jekyll/collection'
require 'jekyll/plugin_manager'
require 'jekyll/site'
require 'jekyll/convertible'

33
lib/jekyll/collection.rb Normal file
View File

@ -0,0 +1,33 @@
module Jekyll
class Collection
attr_reader :site, :label
def initialize(site, label)
@site = site
@label = label
end
def docs
@docs ||= []
end
def read
Dir.glob(File.join(directory, "**", "*.*")).each do |file_path|
if allowed_document?(file_path)
doc = Jekyll::Document.new(file_path, { site: site, collection: self })
docs << doc
end
end
docs
end
def directory
Jekyll.sanitized_path(site.source, "_#{label}")
end
def allowed_document?(path)
!(site.safe && File.symlink?(path))
end
end
end

View File

@ -13,6 +13,7 @@ module Jekyll
'data_source' => '_data',
'keep_files' => ['.git','.svn'],
'gems' => [],
'collections' => nil,
'timezone' => nil, # use the local timezone

View File

@ -1,18 +1,19 @@
module Jekyll
class Document
attr_reader :path
attr_accessor :content
attr_reader :path, :site
attr_accessor :content, :collection
# Create a new Document.
#
# site - the Jekyll::Site instance to which this Document belongs
# shit - the Jekyll::Site instance to which this Document belongs
# path - the path to the file
#
# Returns nothing.
def initialize(site, path)
@site = site
def initialize(path, relations)
@site = relations[:site]
@path = path
@collection = relations[:collection]
end
# Fetch the Document's data.
@ -23,6 +24,10 @@ module Jekyll
@data ||= Hash.new
end
def relative_path
Pathname.new(path).relative_path_from(Pathname.new(site.source)).to_s
end
def extname
File.extname(path)
end

View File

@ -4,7 +4,7 @@ module Jekyll
:exclude, :include, :source, :dest, :lsi, :highlighter,
:permalink_style, :time, :future, :unpublished, :safe, :plugins, :limit_posts,
:show_drafts, :keep_files, :baseurl, :data, :file_read_opts, :gems,
:plugin_manager
:plugin_manager, :collections
attr_accessor :converters, :generators
@ -14,7 +14,9 @@ module Jekyll
def initialize(config)
self.config = config.clone
%w[safe lsi highlighter baseurl exclude include future unpublished show_drafts limit_posts keep_files gems].each do |opt|
%w[
safe lsi highlighter baseurl exclude include future unpublished
show_drafts limit_posts keep_files gems collections].each do |opt|
self.send("#{opt}=", config[opt])
end
@ -90,6 +92,7 @@ module Jekyll
self.layouts = LayoutReader.new(self).read
read_directories
read_data(config['data_source'])
read_collections
end
# Recursively traverse directories to find posts, pages and static files
@ -171,13 +174,24 @@ module Jekyll
entries = Dir.chdir(base) { Dir['*.{yaml,yml}'] }
entries.delete_if { |e| File.directory?(File.join(base, e)) }
data_collection = Jekyll::Collection.new(self, "data")
entries.each do |entry|
path = File.join(source, dir, entry)
next if File.symlink?(path) && safe
key = sanitize_filename(File.basename(entry, '.*'))
(self.data[key] = Jekyll::Document.new(self, path)).read
(self.data[key] = Jekyll::Document.new(path, { site: self, collection: data_collection })).read
end
end
# Read in all collections specified in the configuration
#
# Returns nothing.
def read_collections
if collections
self.collections = Hash[collections.map { |coll| [coll, Jekyll::Collection.new(self, coll)] } ]
collections.each { |_, collection| collection.read }
end
end

View File

@ -0,0 +1,8 @@
---
title: "Jekyll.configuration"
whatever: foo.bar
---
Use `{{ page.title }}` to build a full configuration for use w/Jekyll.
Whatever: {{ page.whatever }}

View File

@ -0,0 +1,5 @@
---
title: "Jekyll.sanitized_path"
---
`{{ page.title }}` is used to make sure your path is in your source.

View File

@ -0,0 +1,5 @@
---
title: "Site#generate"
---
Run your generators!

View File

@ -0,0 +1,5 @@
---
title: "Site#initialize"
---
Create dat site.

View File

@ -0,0 +1 @@
test/source/_methods/sanitized_path.md

71
test/test_collections.rb Normal file
View File

@ -0,0 +1,71 @@
require 'helper'
class TestCollections < Test::Unit::TestCase
context "with no collections specified" do
setup do
@site = Site.new(Jekyll.configuration({
"source" => source_dir,
"destination" => dest_dir
}))
@site.process
end
should "not contain any collections" do
assert_nil @site.collections
end
end
context "with a collection" do
setup do
@site = Site.new(Jekyll.configuration({
"collections" => ["methods"],
"source" => source_dir,
"destination" => dest_dir
}))
@site.process
end
should "create a Hash on Site with the label mapped to the instance of the Collection" do
assert @site.collections.is_a?(Hash)
assert_not_nil @site.collections["methods"]
assert @site.collections["methods"].is_a? Jekyll::Collection
end
should "collects docs in an array on the Collection object" do
assert @site.collections["methods"].docs.is_a? Array
@site.collections["methods"].docs.each do |doc|
assert doc.is_a? Jekyll::Document
assert_include %w[
_methods/configuration.md
_methods/sanitized_path.md
_methods/site/generate.md
_methods/site/initialize.md
_methods/um_hi.md
], doc.relative_path
end
end
end
context "in safe mode" do
setup do
@site = Site.new(Jekyll.configuration({
"collections" => ["methods"],
"safe" => true,
"source" => source_dir,
"destination" => dest_dir
}))
@site.process
@collection = @site.collections["methods"]
end
should "not allow symlinks" do
assert !@collection.allowed_document?(File.join(@collection.directory, "um_hi.md"))
end
should "not include the symlinked file in the list of docs" do
assert_not_include %w[_methods/um_hi.md], @collection.docs.map(&:relative_path)
end
end
end