mook 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/.gitignore +4 -0
- data/Gemfile +4 -0
- data/README.md +98 -0
- data/Rakefile +3 -0
- data/bin/mook +12 -0
- data/lib/mook.rb +15 -0
- data/lib/mook/html.rb +62 -0
- data/lib/mook/model.rb +21 -0
- data/lib/mook/page.rb +33 -0
- data/lib/mook/renderer.rb +30 -0
- data/lib/mook/site.rb +38 -0
- data/lib/mook/version.rb +3 -0
- data/mook.gemspec +23 -0
- metadata +111 -0
data/.gitignore
ADDED
data/Gemfile
ADDED
data/README.md
ADDED
@@ -0,0 +1,98 @@
|
|
1
|
+
# Mook
|
2
|
+
|
3
|
+
Mook is a simple static site generator.
|
4
|
+
|
5
|
+
## Getting Started
|
6
|
+
|
7
|
+
gem install mook
|
8
|
+
|
9
|
+
And you're off.
|
10
|
+
|
11
|
+
|
12
|
+
## Site Layout
|
13
|
+
|
14
|
+
```
|
15
|
+
+ my-site
|
16
|
+
+ pages
|
17
|
+
- index.md
|
18
|
+
- about.md
|
19
|
+
- contact.md
|
20
|
+
+ static
|
21
|
+
+ css
|
22
|
+
- mypage.css
|
23
|
+
+ templates
|
24
|
+
- _toolbar.erb
|
25
|
+
- default.html.erb
|
26
|
+
```
|
27
|
+
|
28
|
+
Pages go in a directory called `pages`, static content goes in a directory called `static`, templates go in `templates`.
|
29
|
+
|
30
|
+
|
31
|
+
## Pages
|
32
|
+
|
33
|
+
[blah](#bloo)
|
34
|
+
|
35
|
+
A page is a Markdown document with some leading metadata:
|
36
|
+
|
37
|
+
Title: About Me
|
38
|
+
Template: default.html.erb
|
39
|
+
Order: 2
|
40
|
+
* * *
|
41
|
+
|
42
|
+
I'm just a simple country [hyperchicken](#more).
|
43
|
+
|
44
|
+
Here's some Ruby code:
|
45
|
+
|
46
|
+
``` ruby
|
47
|
+
Poop.new(:yay => "whee")
|
48
|
+
```
|
49
|
+
|
50
|
+
## Perhaps Some More Stuff. #more
|
51
|
+
|
52
|
+
Also, some other stuff.
|
53
|
+
|
54
|
+
A few things of note:
|
55
|
+
|
56
|
+
* `Title` and `Template` are mandatory, `Order` is optional.
|
57
|
+
* Fenced (i.e., ` ``` `-surrounded) code blocks are OK, and if you add the
|
58
|
+
language name, Mook will syntax highlight the code for you.
|
59
|
+
* Adding a name to a header (i.e., `#more`) created a named anchor above that
|
60
|
+
header with that name so's you can link to it.
|
61
|
+
* Strike-through (`~struckthrough~`) is supported.
|
62
|
+
* Superscript (`2^128` or `this is the 2^(nd) time`) is supported.
|
63
|
+
* URLs are automatically linkified.
|
64
|
+
* Smart quotes, dashes, ellipses, etc. are all supported.
|
65
|
+
|
66
|
+
|
67
|
+
## Templates
|
68
|
+
|
69
|
+
Templates are ERB templates. They've got all the usual features, plus the
|
70
|
+
following stuff in scope:
|
71
|
+
|
72
|
+
* `site`, which wraps the idea of the site you're generating. Has a `#pages`
|
73
|
+
method, which returns an array of all the pages in the site.
|
74
|
+
* `page`, which wraps the idea of the current page being rendered. Has the
|
75
|
+
following methods:
|
76
|
+
* `#name`: the page's name, as defined by the filename
|
77
|
+
* `#title`: the page's title
|
78
|
+
* `#content`: the page's Markdown content, rendered as HTML
|
79
|
+
* `#toc`: a nested `<ul>` list of all the page's headers, with links
|
80
|
+
|
81
|
+
|
82
|
+
## Running
|
83
|
+
|
84
|
+
Run this:
|
85
|
+
|
86
|
+
mook
|
87
|
+
|
88
|
+
Then look in the `target` directory for an awesome surprise.
|
89
|
+
|
90
|
+
|
91
|
+
## But this doesn't do what I want
|
92
|
+
|
93
|
+
Sorry.
|
94
|
+
|
95
|
+
## Licensing
|
96
|
+
|
97
|
+
Copyright 2011 Coda Hale. Licensed to you under the MIT license. Don't screw
|
98
|
+
this up for anyone.
|
data/Rakefile
ADDED
data/bin/mook
ADDED
data/lib/mook.rb
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
require "redcarpet"
|
2
|
+
require "pygments.rb"
|
3
|
+
require "fileutils"
|
4
|
+
require "yaml"
|
5
|
+
require "erb"
|
6
|
+
|
7
|
+
module Mook
|
8
|
+
MARKDOWN_EXTENSIONS = %w{ .md .mdown .markdown }
|
9
|
+
end
|
10
|
+
|
11
|
+
require "mook/site"
|
12
|
+
require "mook/page"
|
13
|
+
require "mook/html"
|
14
|
+
require "mook/renderer"
|
15
|
+
require "mook/model"
|
data/lib/mook/html.rb
ADDED
@@ -0,0 +1,62 @@
|
|
1
|
+
module Mook
|
2
|
+
# Renders Markdown as HTML, Pygmentizing any named code blocks and generating
|
3
|
+
# TOC blocks.
|
4
|
+
class HtmlRenderer < Redcarpet::Render::HTML
|
5
|
+
include Redcarpet::Render::SmartyPants
|
6
|
+
|
7
|
+
def initialize(opts)
|
8
|
+
super(opts)
|
9
|
+
@toc = ""
|
10
|
+
@toc_id = 0
|
11
|
+
@toc_last_level = 0
|
12
|
+
@toc_closed = false
|
13
|
+
end
|
14
|
+
|
15
|
+
def block_code(code, language)
|
16
|
+
if language
|
17
|
+
Pygments.highlight(code, :lexer => language, :options => {:encoding => 'utf-8'})
|
18
|
+
else
|
19
|
+
"<pre>#{code}</pre>"
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
def header(text, header_level)
|
24
|
+
tag = if text =~ / #(.+)$/ then
|
25
|
+
text = text.gsub(/ #(.+)$/, "")
|
26
|
+
$1
|
27
|
+
else
|
28
|
+
nil
|
29
|
+
end
|
30
|
+
|
31
|
+
@toc_id += 1
|
32
|
+
|
33
|
+
id = if tag then tag else "toc_#{@toc_id}" end
|
34
|
+
|
35
|
+
link = "<a href=\"##{id}\">#{text}</a>"
|
36
|
+
|
37
|
+
if @toc_last_level <= 0
|
38
|
+
@toc << "<li>#{link}"
|
39
|
+
else
|
40
|
+
if @toc_last_level == header_level
|
41
|
+
@toc << "</li><li>#{link}"
|
42
|
+
elsif @toc_last_level < header_level
|
43
|
+
@toc << "<ul><li>#{link}"
|
44
|
+
else
|
45
|
+
@toc << "</ul><li>#{link}"
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
@toc_last_level = header_level
|
50
|
+
|
51
|
+
"<a name=\"#{id}\"></a><h#{header_level}>#{text}</h#{header_level}>"
|
52
|
+
end
|
53
|
+
|
54
|
+
def toc
|
55
|
+
unless @toc_closed
|
56
|
+
@toc = "<ul>#{@toc}</li></ul>"
|
57
|
+
@toc_closed = true
|
58
|
+
end
|
59
|
+
@toc
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
data/lib/mook/model.rb
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
module Mook
|
2
|
+
class Model
|
3
|
+
def initialize(site, page)
|
4
|
+
@site = site
|
5
|
+
@page = page
|
6
|
+
end
|
7
|
+
|
8
|
+
def binding
|
9
|
+
super
|
10
|
+
end
|
11
|
+
|
12
|
+
protected
|
13
|
+
|
14
|
+
attr_reader :site, :page
|
15
|
+
|
16
|
+
def partial(name)
|
17
|
+
partial = ERB.new(File.read(File.join("templates", "_#{name}.erb")))
|
18
|
+
partial.result(self.binding)
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
data/lib/mook/page.rb
ADDED
@@ -0,0 +1,33 @@
|
|
1
|
+
class Page
|
2
|
+
METADATA = %w{ title template order }
|
3
|
+
|
4
|
+
def self.load(filename)
|
5
|
+
lines = File.read(filename)
|
6
|
+
m, markdown = lines.split("* * *\n", 2)
|
7
|
+
metadata = Hash[*m.split("\n").map { |s| s.split(": ", 2) }.map { |k, v| [k.downcase, v] }.flatten]
|
8
|
+
|
9
|
+
raise "#{filename} has no title" unless metadata["title"]
|
10
|
+
raise "#{filename} has no template" unless metadata["template"]
|
11
|
+
|
12
|
+
order = (metadata["order"] || 1000).to_i
|
13
|
+
|
14
|
+
Page.new(File.basename(filename), metadata["title"],
|
15
|
+
metadata["template"], order,
|
16
|
+
markdown.strip)
|
17
|
+
end
|
18
|
+
|
19
|
+
attr_reader :name, :title, :template, :order, :markdown
|
20
|
+
attr_accessor :content, :output, :toc
|
21
|
+
|
22
|
+
def initialize(name, title, template, order, markdown)
|
23
|
+
@name = name.gsub(/\.[^\.]+$/, "")
|
24
|
+
@title = title
|
25
|
+
@template = template
|
26
|
+
@order = order
|
27
|
+
@markdown = markdown
|
28
|
+
end
|
29
|
+
|
30
|
+
def url
|
31
|
+
"#{@name}.html"
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,30 @@
|
|
1
|
+
module Mook
|
2
|
+
class Renderer
|
3
|
+
MARKDOWN_OPTIONS = {
|
4
|
+
:strikethrough => true,
|
5
|
+
:fenced_code_blocks => true,
|
6
|
+
:space_after_headers => true,
|
7
|
+
:superscript => true,
|
8
|
+
:autolink => true
|
9
|
+
}
|
10
|
+
HTML_OPTIONS = {
|
11
|
+
|
12
|
+
}
|
13
|
+
|
14
|
+
def initialize(site)
|
15
|
+
@site = site
|
16
|
+
end
|
17
|
+
|
18
|
+
def render!(page)
|
19
|
+
renderer = HtmlRenderer.new(HTML_OPTIONS)
|
20
|
+
md = Redcarpet::Markdown.new(renderer, MARKDOWN_OPTIONS)
|
21
|
+
|
22
|
+
page.content = md.render(page.markdown)
|
23
|
+
page.toc = renderer.toc
|
24
|
+
|
25
|
+
template = ERB.new(File.read(File.join("templates", page.template)))
|
26
|
+
model = Model.new(@site, page)
|
27
|
+
page.output = renderer.postprocess(template.result(model.binding))
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
data/lib/mook/site.rb
ADDED
@@ -0,0 +1,38 @@
|
|
1
|
+
module Mook
|
2
|
+
class Site
|
3
|
+
def self.load(dir)
|
4
|
+
pages = []
|
5
|
+
for page_file in Dir.glob(File.join(dir, "pages", "*"))
|
6
|
+
if MARKDOWN_EXTENSIONS.member?(File.extname(page_file).downcase)
|
7
|
+
pages << Page.load(page_file)
|
8
|
+
end
|
9
|
+
end
|
10
|
+
|
11
|
+
Site.new(pages.sort_by { |p| p.order })
|
12
|
+
end
|
13
|
+
|
14
|
+
attr_reader :pages
|
15
|
+
|
16
|
+
def initialize(pages)
|
17
|
+
@pages = pages
|
18
|
+
end
|
19
|
+
|
20
|
+
def render!
|
21
|
+
renderer = Renderer.new(self)
|
22
|
+
for page in @pages
|
23
|
+
renderer.render!(page)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
def stage!
|
28
|
+
FileUtils.mkdir_p("target")
|
29
|
+
FileUtils.rm_rf(File.join("target", "*"))
|
30
|
+
FileUtils.cp_r(Dir.glob(File.join("static", "*")), "target")
|
31
|
+
for page in @pages
|
32
|
+
File.open(File.join("target", "#{page.name}.html"), "w+") do |f|
|
33
|
+
f << page.output
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
data/lib/mook/version.rb
ADDED
data/mook.gemspec
ADDED
@@ -0,0 +1,23 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
$:.push File.expand_path("../lib", __FILE__)
|
3
|
+
require "mook/version"
|
4
|
+
|
5
|
+
Gem::Specification.new do |s|
|
6
|
+
s.name = "mook"
|
7
|
+
s.version = Mook::VERSION
|
8
|
+
s.platform = Gem::Platform::RUBY
|
9
|
+
s.authors = ["Coda Hale"]
|
10
|
+
s.email = ["coda.hale@gmail.com"]
|
11
|
+
s.homepage = "https://github.com/codahale/mook"
|
12
|
+
s.summary = %q{Yet another damn site generator thing.}
|
13
|
+
s.description = %q{Generates static HTML files from Markdown. But, like, well.}
|
14
|
+
s.add_dependency('redcarpet', '>= 2.1.0')
|
15
|
+
s.add_dependency('pygments.rb', '>= 0.2.4')
|
16
|
+
|
17
|
+
s.rubyforge_project = "mook"
|
18
|
+
|
19
|
+
s.files = `git ls-files`.split("\n")
|
20
|
+
s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
21
|
+
s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
|
22
|
+
s.require_paths = ["lib"]
|
23
|
+
end
|
metadata
ADDED
@@ -0,0 +1,111 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: mook
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
hash: 29
|
5
|
+
prerelease: false
|
6
|
+
segments:
|
7
|
+
- 0
|
8
|
+
- 0
|
9
|
+
- 1
|
10
|
+
version: 0.0.1
|
11
|
+
platform: ruby
|
12
|
+
authors:
|
13
|
+
- Coda Hale
|
14
|
+
autorequire:
|
15
|
+
bindir: bin
|
16
|
+
cert_chain: []
|
17
|
+
|
18
|
+
date: 2012-02-04 00:00:00 -08:00
|
19
|
+
default_executable:
|
20
|
+
dependencies:
|
21
|
+
- !ruby/object:Gem::Dependency
|
22
|
+
name: redcarpet
|
23
|
+
prerelease: false
|
24
|
+
requirement: &id001 !ruby/object:Gem::Requirement
|
25
|
+
none: false
|
26
|
+
requirements:
|
27
|
+
- - ">="
|
28
|
+
- !ruby/object:Gem::Version
|
29
|
+
hash: 11
|
30
|
+
segments:
|
31
|
+
- 2
|
32
|
+
- 1
|
33
|
+
- 0
|
34
|
+
version: 2.1.0
|
35
|
+
type: :runtime
|
36
|
+
version_requirements: *id001
|
37
|
+
- !ruby/object:Gem::Dependency
|
38
|
+
name: pygments.rb
|
39
|
+
prerelease: false
|
40
|
+
requirement: &id002 !ruby/object:Gem::Requirement
|
41
|
+
none: false
|
42
|
+
requirements:
|
43
|
+
- - ">="
|
44
|
+
- !ruby/object:Gem::Version
|
45
|
+
hash: 31
|
46
|
+
segments:
|
47
|
+
- 0
|
48
|
+
- 2
|
49
|
+
- 4
|
50
|
+
version: 0.2.4
|
51
|
+
type: :runtime
|
52
|
+
version_requirements: *id002
|
53
|
+
description: Generates static HTML files from Markdown. But, like, well.
|
54
|
+
email:
|
55
|
+
- coda.hale@gmail.com
|
56
|
+
executables:
|
57
|
+
- mook
|
58
|
+
extensions: []
|
59
|
+
|
60
|
+
extra_rdoc_files: []
|
61
|
+
|
62
|
+
files:
|
63
|
+
- .gitignore
|
64
|
+
- Gemfile
|
65
|
+
- README.md
|
66
|
+
- Rakefile
|
67
|
+
- bin/mook
|
68
|
+
- lib/mook.rb
|
69
|
+
- lib/mook/html.rb
|
70
|
+
- lib/mook/model.rb
|
71
|
+
- lib/mook/page.rb
|
72
|
+
- lib/mook/renderer.rb
|
73
|
+
- lib/mook/site.rb
|
74
|
+
- lib/mook/version.rb
|
75
|
+
- mook.gemspec
|
76
|
+
has_rdoc: true
|
77
|
+
homepage: https://github.com/codahale/mook
|
78
|
+
licenses: []
|
79
|
+
|
80
|
+
post_install_message:
|
81
|
+
rdoc_options: []
|
82
|
+
|
83
|
+
require_paths:
|
84
|
+
- lib
|
85
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
86
|
+
none: false
|
87
|
+
requirements:
|
88
|
+
- - ">="
|
89
|
+
- !ruby/object:Gem::Version
|
90
|
+
hash: 3
|
91
|
+
segments:
|
92
|
+
- 0
|
93
|
+
version: "0"
|
94
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
95
|
+
none: false
|
96
|
+
requirements:
|
97
|
+
- - ">="
|
98
|
+
- !ruby/object:Gem::Version
|
99
|
+
hash: 3
|
100
|
+
segments:
|
101
|
+
- 0
|
102
|
+
version: "0"
|
103
|
+
requirements: []
|
104
|
+
|
105
|
+
rubyforge_project: mook
|
106
|
+
rubygems_version: 1.3.7
|
107
|
+
signing_key:
|
108
|
+
specification_version: 3
|
109
|
+
summary: Yet another damn site generator thing.
|
110
|
+
test_files: []
|
111
|
+
|