pith 0.2.0 → 0.2.1

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,74 +0,0 @@
1
- require "pathname"
2
-
3
- module Pith
4
- module Input
5
-
6
- class Abstract
7
-
8
- def initialize(project, path)
9
- @project = project
10
- @path = path
11
- end
12
-
13
- attr_reader :project, :path
14
-
15
- # Public: Get the file-system location of this input.
16
- #
17
- # Returns a fully-qualified Pathname.
18
- #
19
- def file
20
- project.input_dir + path
21
- end
22
-
23
- def output_file
24
- project.output_dir + output_path
25
- end
26
-
27
- # Public: Generate a corresponding output file.
28
- #
29
- def build
30
- return false if ignorable? || uptodate?
31
- logger.info("%-14s%s" % ["--(#{type})-->", output_path])
32
- generate_output
33
- end
34
-
35
- # Public: Resolve a reference relative to this input.
36
- #
37
- # ref - a String referencing another asset
38
- #
39
- # A ref starting with "/" is resolved relative to the project root;
40
- # anything else is resolved relative to this input.
41
- #
42
- # Returns a fully-qualified Pathname of the asset.
43
- #
44
- def resolve_path(ref)
45
- ref = ref.to_str
46
- if ref[0,1] == "/"
47
- Pathname(ref[1..-1])
48
- else
49
- path.parent + ref
50
- end
51
- end
52
-
53
- # Consider whether this input can be ignored.
54
- #
55
- # Returns true if it can.
56
- #
57
- def ignorable?
58
- path.to_s.split("/").any? { |component| component.to_s[0,1] == "_" }
59
- end
60
-
61
- protected
62
-
63
- def default_title
64
- path.to_s.sub(/\..*/, '').tr('_-', ' ').capitalize
65
- end
66
-
67
- def logger
68
- project.logger
69
- end
70
-
71
- end
72
-
73
- end
74
- end
@@ -1,74 +0,0 @@
1
- require "pathname"
2
-
3
- module Pith
4
- module Input
5
-
6
- class Abstract
7
-
8
- def initialize(project, path)
9
- @project = project
10
- @path = path
11
- end
12
-
13
- attr_reader :project, :path
14
-
15
- # Public: Get the file-system location of this input.
16
- #
17
- # Returns a fully-qualified Pathname.
18
- #
19
- def file
20
- project.input_dir + path
21
- end
22
-
23
- # Public: Get the file-system location of the corresponding output file.
24
- #
25
- # Returns a fully-qualified Pathname.
26
- #
27
- def output_file
28
- project.output_dir + output_path
29
- end
30
-
31
- # Public: Generate an output file.
32
- #
33
- def build
34
- return false if ignorable? || uptodate?
35
- logger.info("%-16s%s" % ["--(#{type})-->", output_path])
36
- generate_output
37
- end
38
-
39
- # Public: Resolve a reference relative to this input.
40
- #
41
- # ref - a String referencing another asset
42
- #
43
- # A ref starting with "/" is resolved relative to the project root;
44
- # anything else is resolved relative to this input.
45
- #
46
- # Returns a fully-qualified Pathname of the asset.
47
- #
48
- def resolve_path(ref)
49
- ref = ref.to_str
50
- if ref[0,1] == "/"
51
- Pathname(ref[1..-1])
52
- else
53
- path.parent + ref
54
- end
55
- end
56
-
57
- # Consider whether this input can be ignored.
58
- #
59
- # Returns true if it can.
60
- #
61
- def ignorable?
62
- path.to_s.split("/").any? { |component| component.to_s[0,1] == "_" }
63
- end
64
-
65
- protected
66
-
67
- def logger
68
- project.logger
69
- end
70
-
71
- end
72
-
73
- end
74
- end
@@ -1,39 +0,0 @@
1
- require "fileutils"
2
- require "pith/input/abstract"
3
-
4
- module Pith
5
- module Input
6
-
7
- # Represents a non-template input.
8
- #
9
- class Resource < Abstract
10
-
11
- def output_path
12
- path
13
- end
14
-
15
- def uptodate?
16
- FileUtils.uptodate?(output_file, [file])
17
- end
18
-
19
- # Copy this input verbatim into the output directory
20
- #
21
- def generate_output
22
- output_file.parent.mkpath
23
- FileUtils.copy(file, output_file)
24
- end
25
-
26
- # Render this input, for inclusion within templates
27
- #
28
- def render(context, locals = {})
29
- file.read
30
- end
31
-
32
- def meta
33
- {}
34
- end
35
-
36
- end
37
-
38
- end
39
- end
@@ -1,41 +0,0 @@
1
- require "fileutils"
2
- require "pith/input/abstract"
3
-
4
- module Pith
5
- module Input
6
-
7
- class Resource < Abstract
8
-
9
- def output_path
10
- path
11
- end
12
-
13
- def type
14
- "copy"
15
- end
16
-
17
- def uptodate?
18
- FileUtils.uptodate?(output_file, [file])
19
- end
20
-
21
- # Copy this input verbatim into the output directory
22
- #
23
- def generate_output
24
- output_file.parent.mkpath
25
- FileUtils.copy(file, output_file)
26
- end
27
-
28
- # Render this input, for inclusion within templates
29
- #
30
- def render(context, locals = {})
31
- file.read
32
- end
33
-
34
- def meta
35
- {}
36
- end
37
-
38
- end
39
-
40
- end
41
- end
@@ -1,159 +0,0 @@
1
- require "fileutils"
2
- require "pathname"
3
- require "pith/exception_ext"
4
- require "pith/input/abstract"
5
- require "pith/render_context"
6
- require "tilt"
7
- require "yaml"
8
-
9
- module Pith
10
- module Input
11
-
12
- # Represents an input that should be evaluated as a template.
13
- #
14
- class Template < Abstract
15
-
16
- def self.can_handle?(path)
17
- !!Tilt[path.to_s]
18
- end
19
-
20
- def initialize(project, path)
21
- raise(ArgumentError, "#{path} is not a template") unless Template.can_handle?(path)
22
- super(project, path)
23
- determine_pipeline
24
- load
25
- end
26
-
27
- attr_reader :output_path
28
-
29
- # Check whether output is up-to-date.
30
- #
31
- # Return true unless output needs to be re-generated.
32
- #
33
- def uptodate?
34
- dependencies && FileUtils.uptodate?(output_file, dependencies)
35
- end
36
-
37
- # Generate output for this template
38
- #
39
- def generate_output
40
- output_file.parent.mkpath
41
- render_context = RenderContext.new(project)
42
- output_file.open("w") do |out|
43
- begin
44
- out.puts(render_context.render(self))
45
- rescue StandardError, SyntaxError => e
46
- logger.warn e.summary(:max_backtrace => 5)
47
- out.puts "<pre>"
48
- out.puts e.summary
49
- end
50
- end
51
- @dependencies = render_context.dependencies
52
- end
53
-
54
- # Render this input using Tilt
55
- #
56
- def render(context, locals = {}, &block)
57
- @pipeline.inject(@template_text) do |text, processor|
58
- template = processor.new(file.to_s, @template_start_line) { text }
59
- template.render(context, locals, &block)
60
- end
61
- end
62
-
63
- # Public: Get YAML metadata declared in the header of of a template.
64
- #
65
- # If the first line of the template starts with "---" it is considered to be
66
- # the start of a YAML 'document', which is loaded and returned.
67
- #
68
- # Examples
69
- #
70
- # Given input starting with:
71
- #
72
- # ---
73
- # published: 2008-09-15
74
- # ...
75
- # OTHER STUFF
76
- #
77
- # input.meta
78
- # #=> { "published" => "2008-09-15" }
79
- #
80
- # Returns a Hash.
81
- #
82
- def meta
83
- @meta
84
- end
85
-
86
- # Public: Get page title.
87
- #
88
- # The default title is based on the input file-name, sans-extension, capitalised,
89
- # but can be overridden by providing a "title" in the metadata block.
90
- #
91
- # Examples
92
- #
93
- # input.path.to_s
94
- # #=> "some_page.html.haml"
95
- # input.title
96
- # #=> "Some page"
97
- #
98
- def title
99
- meta["title"] || default_title
100
- end
101
-
102
- private
103
-
104
- def default_title
105
- path.basename.to_s.sub(/\..*/, '').tr('_-', ' ').capitalize
106
- end
107
-
108
- def determine_pipeline
109
- @pipeline = []
110
- remaining_path = path.to_s
111
- while remaining_path =~ /^(.+)\.(.+)$/
112
- if Tilt[$2]
113
- remaining_path = $1
114
- @pipeline << Tilt[$2]
115
- else
116
- break
117
- end
118
- end
119
- @output_path = Pathname(remaining_path)
120
- end
121
-
122
- # Read input file, extracting YAML meta-data header, and template content.
123
- #
124
- def load
125
- file.open do |input|
126
- load_meta(input)
127
- load_template(input)
128
- end
129
- end
130
-
131
- def load_meta(input)
132
- @meta = {}
133
- header = input.gets
134
- if header =~ /^---/
135
- while line = input.gets
136
- break if line =~ /^(---|\.\.\.)/
137
- header << line
138
- end
139
- begin
140
- @meta = YAML.load(header)
141
- rescue ArgumentError, SyntaxError
142
- logger.warn "#{file}:1: badly-formed YAML header"
143
- end
144
- else
145
- input.rewind
146
- end
147
- end
148
-
149
- def load_template(input)
150
- @template_start_line = input.lineno + 1
151
- @template_text = input.read
152
- end
153
-
154
- attr_accessor :dependencies
155
-
156
- end
157
-
158
- end
159
- end
@@ -1,126 +0,0 @@
1
- require "fileutils"
2
- require "pathname"
3
- require "pith/input/abstract"
4
- require "pith/render_context"
5
- require "tilt"
6
- require "yaml"
7
-
8
- module Pith
9
- module Input
10
-
11
- class Template < Abstract
12
-
13
- def self.can_handle?(path)
14
- path.to_str =~ /\.([^.]+)$/ && Tilt.registered?($1)
15
- end
16
-
17
- def initialize(project, path)
18
- raise(ArgumentError, "#{path} is not a template") unless Template.can_handle?(path)
19
- super(project, path)
20
- path.to_str =~ /^(.+)\.(.+)$/ || raise("huh?")
21
- @output_path = Pathname($1)
22
- @type = $2
23
- load
24
- end
25
-
26
- attr_reader :output_path, :type
27
-
28
- # Check whether output is up-to-date.
29
- #
30
- # Return true unless output needs to be re-generated.
31
- #
32
- def uptodate?
33
- dependencies && FileUtils.uptodate?(output_file, dependencies)
34
- end
35
-
36
- # Generate output for this template
37
- #
38
- def generate_output
39
- output_file.parent.mkpath
40
- render_context = RenderContext.new(project)
41
- output_file.open("w") do |out|
42
- out.puts(render_context.render(self))
43
- end
44
- @dependencies = render_context.dependencies
45
- end
46
-
47
- # Render this input using Tilt
48
- #
49
- def render(context, locals = {}, &block)
50
- @tilt_template.render(context, locals, &block)
51
- end
52
-
53
- # Public: Get YAML metadata declared in the header of of a template.
54
- #
55
- # If the first line of the template starts with "---" it is considered to be
56
- # the start of a YAML 'document', which is loaded and returned.
57
- #
58
- # Examples
59
- #
60
- # Given input starting with:
61
- #
62
- # ---
63
- # published: 2008-09-15
64
- # ...
65
- # OTHER STUFF
66
- #
67
- # input.meta
68
- # #=> { "published" => "2008-09-15" }
69
- #
70
- # Returns a Hash.
71
- #
72
- def meta
73
- @meta
74
- end
75
-
76
- # Public: Get page title.
77
- #
78
- # The default title is based on the input file-name, sans-extension, capitalised,
79
- # but can be overridden by providing a "title" in the metadata block.
80
- #
81
- # Examples
82
- #
83
- # input.path.to_s
84
- # #=> "some_page.html.haml"
85
- # input.title
86
- # #=> "Some page"
87
- #
88
- def title
89
- meta["title"] || default_title
90
- end
91
-
92
- private
93
-
94
- def default_title
95
- path.basename.to_s.sub(/\..*/, '').tr('_-', ' ').capitalize
96
- end
97
-
98
- # Read input file, extracting YAML meta-data header, and template content.
99
- #
100
- def load
101
- @meta = {}
102
- file.open do |input|
103
- header = input.gets
104
- if header =~ /^---/
105
- while line = input.gets
106
- break if line =~ /^(---|\.\.\.)/
107
- header << line
108
- end
109
- begin
110
- @meta = YAML.load(header)
111
- rescue
112
- logger.warn "#{file}:1: badly-formed YAML header"
113
- end
114
- else
115
- input.rewind
116
- end
117
- @tilt_template = Tilt.new(file, input.lineno + 1) { input.read }
118
- end
119
- end
120
-
121
- attr_accessor :dependencies
122
-
123
- end
124
-
125
- end
126
- end