lesstile 0.3 → 1.0.0
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +3 -0
- data/History.txt +6 -0
- data/README.txt +8 -3
- data/Rakefile +2 -19
- data/lib/lesstile.rb +26 -24
- data/spec/spec_lesstile.rb +53 -13
- metadata +35 -27
data/.gitignore
ADDED
data/History.txt
CHANGED
data/README.txt
CHANGED
@@ -3,7 +3,7 @@ by Xavier Shay (http://rhnh.net)
|
|
3
3
|
|
4
4
|
== DESCRIPTION:
|
5
5
|
|
6
|
-
Converts text formatted with an exceedingly simple markup language into
|
6
|
+
Converts text formatted with an exceedingly simple markup language into valid HTML (iron clad guarantee!) - perfect for comments on your blog. Textile isn't good for this because not only does it do too much (do commenters really need subscript?), but it can also output invalid HTML (try a <b> tag over multiple lines...). Whitelisting HTML is another option, but you still need some sort of parsing if you want syntax highlighting.
|
7
7
|
|
8
8
|
Integrates with CodeRay for sexy syntax highlighting.
|
9
9
|
|
@@ -28,9 +28,12 @@ Integrates with CodeRay for sexy syntax highlighting.
|
|
28
28
|
---
|
29
29
|
EOS
|
30
30
|
|
31
|
+
Lesstile.format_as_html(comment)
|
32
|
+
Lesstile.format_as_html(comment, :code_formatter => Lesstile::CodeRayFormatter) # Requires code ray
|
33
|
+
Lesstile.format_as_html(comment, :code_formatter => lambda {|code, lang| "Code in #{lang}: #{code}" })
|
34
|
+
|
35
|
+
# Also XHTML, for the old schoolers
|
31
36
|
Lesstile.format_as_xhtml(comment)
|
32
|
-
Lesstile.format_as_xhtml(comment, :code_formatter => Lesstile::CodeRayFormatter) # Requires code ray
|
33
|
-
Lesstile.format_as_xhtml(comment, :code_formatter => lambda {|code, lang| "Code in #{lang}: #{code}" })
|
34
37
|
|
35
38
|
== REQUIREMENTS:
|
36
39
|
|
@@ -41,6 +44,8 @@ Integrates with CodeRay for sexy syntax highlighting.
|
|
41
44
|
sudo gem install lesstile # gem install
|
42
45
|
git clone git://github.com/xaviershay/lesstile.git # go from source
|
43
46
|
|
47
|
+
Tested on ruby 1.8.6-339, 1.8.7-160, 1.9.1-rc2, and 1.9.2-p0
|
48
|
+
|
44
49
|
== LICENSE:
|
45
50
|
|
46
51
|
(The MIT License)
|
data/Rakefile
CHANGED
@@ -1,26 +1,9 @@
|
|
1
|
-
# -*- ruby -*-
|
2
|
-
|
3
|
-
require 'rubygems'
|
4
|
-
require 'hoe'
|
5
1
|
require 'spec/rake/spectask'
|
6
|
-
require './lib/lesstile.rb'
|
7
|
-
|
8
|
-
Hoe.new('lesstile', Lesstile::VERSION) do |p|
|
9
|
-
p.rubyforge_name = 'lesstile'
|
10
|
-
p.author = 'Xavier Shay'
|
11
|
-
p.email = 'xavier@rhnh.net'
|
12
|
-
p.summary = 'Format text using an exceedingly simple markup language - perfect for comments on your blog'
|
13
|
-
p.description = p.paragraphs_of('README.txt', 2..5).join("\n\n")
|
14
|
-
p.url = p.paragraphs_of('README.txt', 0).first.split(/\n/)[1..-1]
|
15
|
-
p.changes = p.paragraphs_of('History.txt', 0..1).join("\n\n")
|
16
|
-
p.remote_rdoc_dir = ""
|
17
|
-
end
|
18
|
-
|
19
2
|
Spec::Rake::SpecTask.new do |t|
|
20
3
|
t.warning = false
|
21
4
|
t.rcov = false
|
22
5
|
t.spec_files = FileList['spec/spec_*.rb']
|
23
6
|
end
|
24
7
|
|
25
|
-
task :test
|
26
|
-
|
8
|
+
task :test => :spec
|
9
|
+
task :default => :spec
|
data/lib/lesstile.rb
CHANGED
@@ -2,7 +2,9 @@ require 'cgi'
|
|
2
2
|
require 'uri'
|
3
3
|
|
4
4
|
class Lesstile
|
5
|
-
VERSION = '0
|
5
|
+
VERSION = '1.0'
|
6
|
+
|
7
|
+
CodeDetectionRegex = /---\s*?([\w\s\._+()-]*?)\s*?\n(.*?)---\n/m
|
6
8
|
|
7
9
|
class << self
|
8
10
|
# Returns lesstile formatted text as valid XHTML
|
@@ -17,44 +19,42 @@ class Lesstile
|
|
17
19
|
text.gsub!(/\r\n/, "\n")
|
18
20
|
text = CGI::escapeHTML(text)
|
19
21
|
|
20
|
-
code_regex = /---\s*?(\w*?)\s*?\n(.*?)---\n/m
|
21
22
|
output = ""
|
22
23
|
|
23
|
-
while match = text.match(
|
24
|
+
while match = text.match(CodeDetectionRegex)
|
24
25
|
captures = match.captures
|
25
26
|
code = captures[1]
|
26
|
-
lang = blank?(captures[0]) ? nil : captures[0].downcase.intern
|
27
|
+
lang = blank?(captures[0]) ? nil : captures[0].downcase.strip.intern
|
28
|
+
|
29
|
+
output +=
|
30
|
+
options[:text_formatter][match.pre_match] +
|
31
|
+
options[:code_formatter][code, lang]
|
27
32
|
|
28
|
-
output += options[:text_formatter][match.pre_match] + options[:code_formatter][code, lang]
|
29
33
|
text = match.post_match
|
30
34
|
end
|
31
35
|
|
32
36
|
output += options[:text_formatter][text.chomp]
|
33
37
|
output
|
34
38
|
end
|
39
|
+
|
40
|
+
# Returns lesstile formatted text as valid HTML5
|
41
|
+
#
|
42
|
+
# options (all optional):
|
43
|
+
# * <tt>text_formatter</tt>: A callback function used to format text.
|
44
|
+
# * <tt>code_formatter</tt>: A callback function used to format code. Typically used for syntax highlighting.
|
45
|
+
def format_as_html(text, options = {})
|
46
|
+
format_as_xhtml(text, options)
|
47
|
+
end
|
35
48
|
|
36
49
|
def default_options
|
37
50
|
{
|
38
51
|
:code_formatter => lambda {|code, lang| "<pre><code>#{code}</code></pre>" },
|
39
52
|
:text_formatter => lambda {|text|
|
40
|
-
text = text.
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
pivot = text.index(uri)
|
46
|
-
pre = text[0..pivot-1]
|
47
|
-
m = pre.match(/"(.*)":$/)
|
48
|
-
link = m ? m.captures.first : nil
|
49
|
-
if link
|
50
|
-
buffer += m.pre_match + "<a href='#{uri.to_s}'>#{link}</a>"
|
51
|
-
else
|
52
|
-
buffer += pre + uri
|
53
|
-
end
|
54
|
-
text = text[pivot+uri.length..-1]
|
55
|
-
end
|
56
|
-
buffer += text
|
57
|
-
buffer
|
53
|
+
text = text.dup
|
54
|
+
text.gsub!(/\n/, "<br />\n")
|
55
|
+
text.gsub!('"', '"')
|
56
|
+
text.gsub!(Regexp.new('"([^"]+)":(' + URI.regexp.to_s + ')'), '<a href="\2">\1</a>')
|
57
|
+
text
|
58
58
|
}
|
59
59
|
}
|
60
60
|
end
|
@@ -74,5 +74,7 @@ class Lesstile
|
|
74
74
|
end
|
75
75
|
|
76
76
|
# A formatter that syntax highlights code using CodeRay
|
77
|
-
CodeRayFormatter = lambda {|code, lang|
|
77
|
+
CodeRayFormatter = lambda {|code, lang|
|
78
|
+
CodeRay.scan(CGI::unescapeHTML(code), lang).html(:line_numbers => :table).div
|
79
|
+
}
|
78
80
|
end
|
data/spec/spec_lesstile.rb
CHANGED
@@ -1,17 +1,8 @@
|
|
1
|
+
require 'rubygems'
|
1
2
|
require 'spec'
|
2
3
|
require File.dirname(__FILE__) + '/../lib/lesstile'
|
3
4
|
|
4
|
-
describe
|
5
|
-
before(:all) do
|
6
|
-
@lesstile = Lesstile
|
7
|
-
@format = lambda {|text|
|
8
|
-
@lesstile.format_as_xhtml(text,
|
9
|
-
:code_formatter => lambda {|code, lang| "|#{code}|" },
|
10
|
-
:text_formatter => lambda {|text| text }
|
11
|
-
)
|
12
|
-
}
|
13
|
-
end
|
14
|
-
|
5
|
+
describe 'an html formatter', :shared => true do
|
15
6
|
it "normal text unchanged" do
|
16
7
|
@format["hello"].should == "hello"
|
17
8
|
end
|
@@ -25,6 +16,18 @@ describe "Lesstile#format_as_xhtml" do
|
|
25
16
|
it "surrounds code blocks in appropriate tags" do
|
26
17
|
@format["---\nhello\n---\n"].should == "|hello\n|"
|
27
18
|
end
|
19
|
+
|
20
|
+
it "parses code blocks with language specified" do
|
21
|
+
@format["--- abc\nhello\n---\n"].should == "|(abc)hello\n|"
|
22
|
+
end
|
23
|
+
|
24
|
+
# spaces, dashes, plusses, normal, underscore, brackets, numbers, dots
|
25
|
+
["Ruby on Rails", "Objective-C", "Objective-C++",
|
26
|
+
"Python", "_SQL_", "(X)HTML", "CSS3", "Javascript1.2"].each do |language|
|
27
|
+
it "parses code blocks with language #{language}" do
|
28
|
+
@format["--- #{language}\nhello\n---\n"].should == "|(#{language.downcase})hello\n|"
|
29
|
+
end
|
30
|
+
end
|
28
31
|
|
29
32
|
it "parses code blocks at end of input" do
|
30
33
|
@format["---\nhello\n---"].should == "|hello\n|"
|
@@ -50,14 +53,51 @@ describe "Lesstile#format_as_xhtml" do
|
|
50
53
|
end
|
51
54
|
end
|
52
55
|
|
56
|
+
describe "Lesstile#format_as_xhtml" do
|
57
|
+
before(:all) do
|
58
|
+
@lesstile = Lesstile
|
59
|
+
@format = lambda {|text|
|
60
|
+
@lesstile.format_as_xhtml(text,
|
61
|
+
:code_formatter => lambda {|code, lang| "|#{"(#{lang})" if lang}#{code}|" },
|
62
|
+
:text_formatter => lambda {|text| text }
|
63
|
+
)
|
64
|
+
}
|
65
|
+
end
|
66
|
+
|
67
|
+
it_should_behave_like 'an html formatter'
|
68
|
+
end
|
69
|
+
|
70
|
+
describe "Lesstile#format_as_html" do
|
71
|
+
before(:all) do
|
72
|
+
@lesstile = Lesstile
|
73
|
+
@format = lambda {|text|
|
74
|
+
@lesstile.format_as_html(text,
|
75
|
+
:code_formatter => lambda {|code, lang| "|#{"(#{lang})" if lang}#{code}|" },
|
76
|
+
:text_formatter => lambda {|text| text }
|
77
|
+
)
|
78
|
+
}
|
79
|
+
end
|
80
|
+
|
81
|
+
it_should_behave_like 'an html formatter'
|
82
|
+
end
|
83
|
+
|
53
84
|
describe 'Lesstile default text formatter' do
|
54
85
|
before(:all) do
|
55
86
|
@format = lambda {|text| Lesstile.default_options[:text_formatter][text] }
|
56
87
|
end
|
57
88
|
|
58
89
|
it 'recognises links in text' do
|
59
|
-
@format['
|
60
|
-
|
90
|
+
@format[CGI::escapeHTML('"a link":http://example.com "<link":http://example.com linkage')].should ==
|
91
|
+
'<a href="http://example.com">a link</a> <a href="http://example.com"><link</a> linkage'
|
92
|
+
end
|
93
|
+
|
94
|
+
it 'does not recognise blank links' do
|
95
|
+
text = '"":http://example.com'
|
96
|
+
@format[CGI::escapeHTML(text)].should == text
|
97
|
+
end
|
98
|
+
|
99
|
+
it 'unescapes " since it is not dangerous in plain text and allows us to use a simple regex for link formatting' do
|
100
|
+
@format["""].should == '"'
|
61
101
|
end
|
62
102
|
end
|
63
103
|
|
metadata
CHANGED
@@ -1,37 +1,38 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: lesstile
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
|
5
|
-
|
4
|
+
hash: 23
|
5
|
+
prerelease: false
|
6
|
+
segments:
|
7
|
+
- 1
|
8
|
+
- 0
|
9
|
+
- 0
|
10
|
+
version: 1.0.0
|
11
|
+
platform: ruby
|
6
12
|
authors:
|
7
13
|
- Xavier Shay
|
8
14
|
autorequire:
|
9
15
|
bindir: bin
|
10
16
|
cert_chain: []
|
11
17
|
|
12
|
-
date:
|
18
|
+
date: 2010-09-15 00:00:00 +01:00
|
13
19
|
default_executable:
|
14
|
-
dependencies:
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
version: 1.5.1
|
23
|
-
version:
|
24
|
-
description: "Integrates with CodeRay for sexy syntax highlighting. == SYNOPSIS: comment = <<-EOS \"Ego Link\":http://rhnh.net Wow, this post is awesome. I'd implement it like this: --- Ruby def hello_world puts \"hello world!\" end ---"
|
25
|
-
email: xavier@rhnh.net
|
20
|
+
dependencies: []
|
21
|
+
|
22
|
+
description: |
|
23
|
+
Converts text formatted with an exceedingly simple markup language into valid HTML (iron clad guarantee!) - perfect for comments on your blog. Textile isn't good for this because not only does it do too much (do commenters really need subscript?), but it can also output invalid HTML (try a <b> tag over multiple lines...). Whitelisting HTML is another option, but you still need some sort of parsing if you want syntax highlighting.
|
24
|
+
|
25
|
+
Integrates with CodeRay for sexy syntax highlighting.
|
26
|
+
|
27
|
+
email: contact@rhnh.net
|
26
28
|
executables: []
|
27
29
|
|
28
30
|
extensions: []
|
29
31
|
|
30
32
|
extra_rdoc_files:
|
31
|
-
- History.txt
|
32
|
-
- Manifest.txt
|
33
33
|
- README.txt
|
34
34
|
files:
|
35
|
+
- .gitignore
|
35
36
|
- History.txt
|
36
37
|
- Manifest.txt
|
37
38
|
- README.txt
|
@@ -39,31 +40,38 @@ files:
|
|
39
40
|
- lib/lesstile.rb
|
40
41
|
- spec/spec_lesstile.rb
|
41
42
|
has_rdoc: true
|
42
|
-
homepage:
|
43
|
+
homepage: http://github.com/xaviershay/lesstile
|
44
|
+
licenses: []
|
45
|
+
|
43
46
|
post_install_message:
|
44
47
|
rdoc_options:
|
45
|
-
- --
|
46
|
-
- README.txt
|
48
|
+
- --charset=UTF-8
|
47
49
|
require_paths:
|
48
50
|
- lib
|
49
51
|
required_ruby_version: !ruby/object:Gem::Requirement
|
52
|
+
none: false
|
50
53
|
requirements:
|
51
54
|
- - ">="
|
52
55
|
- !ruby/object:Gem::Version
|
56
|
+
hash: 3
|
57
|
+
segments:
|
58
|
+
- 0
|
53
59
|
version: "0"
|
54
|
-
version:
|
55
60
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
61
|
+
none: false
|
56
62
|
requirements:
|
57
63
|
- - ">="
|
58
64
|
- !ruby/object:Gem::Version
|
65
|
+
hash: 3
|
66
|
+
segments:
|
67
|
+
- 0
|
59
68
|
version: "0"
|
60
|
-
version:
|
61
69
|
requirements: []
|
62
70
|
|
63
|
-
rubyforge_project:
|
64
|
-
rubygems_version:
|
71
|
+
rubyforge_project:
|
72
|
+
rubygems_version: 1.3.7
|
65
73
|
signing_key:
|
66
|
-
specification_version:
|
74
|
+
specification_version: 3
|
67
75
|
summary: Format text using an exceedingly simple markup language - perfect for comments on your blog
|
68
|
-
test_files:
|
69
|
-
|
76
|
+
test_files:
|
77
|
+
- spec/spec_lesstile.rb
|