rad_kit 0.0.6 → 0.0.7

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.
Files changed (71) hide show
  1. data/lib/components/captcha.rb +24 -0
  2. data/lib/components/captcha.yml +2 -0
  3. data/lib/kit/{http_controller → controller}/authorized.rb +1 -1
  4. data/lib/kit/controller/captcha.rb +23 -0
  5. data/lib/kit/{http_controller → controller}/localized.rb +1 -1
  6. data/lib/kit/controller.rb +5 -0
  7. data/lib/kit/gems.rb +10 -6
  8. data/lib/kit/i18n/locales/ru/pluralization.rb +62 -0
  9. data/lib/kit/i18n.rb +16 -0
  10. data/lib/kit/kit.rb +10 -7
  11. data/lib/kit/kit_text_utils.rb +30 -0
  12. data/lib/kit/misc/prepare_model.rb +16 -0
  13. data/lib/kit/misc/user_error.rb +12 -0
  14. data/lib/kit/models/attachments_uploader_helper.rb +1 -1
  15. data/lib/kit/models/authorized.rb +6 -8
  16. data/lib/kit/models/authorized_object.rb +3 -4
  17. data/lib/kit/models/{micelaneous.rb → miscellaneous.rb} +0 -0
  18. data/lib/kit/models_after.rb +1 -1
  19. data/lib/kit/mongoid/{rad_micelaneous.rb → rad_miscellaneous.rb} +1 -1
  20. data/lib/kit/mongoid/text_processor.rb +1 -1
  21. data/lib/kit/mongoid.rb +2 -2
  22. data/lib/kit/spec.rb +1 -2
  23. data/lib/kit/tasks.rb +1 -1
  24. data/lib/text_utils/code_highlighter.rb +75 -0
  25. data/lib/text_utils/custom_markdown.rb +64 -0
  26. data/lib/text_utils/ensure_utf.rb +14 -0
  27. data/lib/text_utils/format_qualifier.rb +13 -0
  28. data/lib/{kit/text_utils → text_utils}/html_sanitizer.rb +8 -6
  29. data/lib/text_utils/markdown.rb +33 -0
  30. data/lib/text_utils/pipe.rb +16 -0
  31. data/lib/text_utils/processor.rb +14 -0
  32. data/lib/text_utils/support.rb +15 -0
  33. data/lib/text_utils/truncate.rb +30 -0
  34. data/lib/text_utils.rb +23 -0
  35. data/readme.md +1 -8
  36. data/spec/controller/authorization_spec.rb +1 -1
  37. data/spec/controller/captcha_spec.rb +66 -0
  38. data/spec/i18n/i18n_spec/locales/en/general.yml +5 -0
  39. data/spec/i18n/i18n_spec/locales/ru/general.yml +7 -0
  40. data/spec/i18n/i18n_spec.rb +32 -0
  41. data/spec/misc/kit_text_utils_spec.rb +29 -0
  42. data/spec/misc/prepare_model_spec.rb +37 -0
  43. data/spec/misc/user_error_spec.rb +38 -0
  44. data/spec/models/authorized_object_spec.rb +10 -3
  45. data/spec/spec_helper/factories.rb +4 -0
  46. data/spec/spec_helper/user.rb +2 -3
  47. data/spec/spec_helper.rb +0 -5
  48. data/spec/text_utils/code_highlighter_spec.rb +38 -0
  49. data/spec/text_utils/custom_markdown_spec.rb +82 -0
  50. data/spec/text_utils/format_qualifier_spec.rb +37 -0
  51. data/spec/text_utils/html_sanitizer_spec.rb +88 -0
  52. data/spec/text_utils/markdown_spec.rb +114 -0
  53. data/spec/text_utils/pipe_spec.rb +35 -0
  54. data/spec/text_utils/spec_helper.rb +26 -0
  55. data/spec/text_utils/text_processor_shared.rb +9 -0
  56. data/spec/text_utils/truncate_spec.rb +22 -0
  57. metadata +57 -47
  58. data/lib/kit/http_controller.rb +0 -4
  59. data/lib/kit/text_utils/code_highlighter.rb +0 -58
  60. data/lib/kit/text_utils/custom_markdown.rb +0 -90
  61. data/lib/kit/text_utils/ensure_utf.rb +0 -8
  62. data/lib/kit/text_utils/github_flavoured_markdown.rb +0 -32
  63. data/lib/kit/text_utils/image_box.rb +0 -35
  64. data/lib/kit/text_utils/markup.rb +0 -43
  65. data/lib/kit/text_utils/processor.rb +0 -25
  66. data/lib/kit/text_utils/tag_shortcuts.rb +0 -14
  67. data/lib/kit/text_utils/truncate.rb +0 -29
  68. data/lib/kit/text_utils/truncator.rb +0 -15
  69. data/lib/kit/text_utils/urls.rb +0 -13
  70. data/lib/kit/text_utils.rb +0 -43
  71. data/spec/utils/text_utils_spec.rb +0 -280
@@ -1,43 +0,0 @@
1
- class Rad::TextUtils::Markup < Rad::TextUtils::Processor
2
-
3
- def initialize processor = nil
4
- super
5
-
6
- @markup = build_from(
7
- Rad::TextUtils::EnsureUtf,
8
- Rad::TextUtils::HtmlSanitizer,
9
-
10
- Rad::TextUtils::CodeHighlighter,
11
-
12
- Rad::TextUtils::CustomMarkdown,
13
-
14
- Rad::TextUtils::Urls,
15
- Rad::TextUtils::TagShortcuts
16
- )
17
-
18
- @html = build_from(
19
- Rad::TextUtils::EnsureUtf,
20
- Rad::TextUtils::HtmlSanitizer,
21
- Rad::TextUtils::CodeHighlighter
22
- )
23
- end
24
-
25
- def process text, env
26
- return text if text.blank?
27
-
28
- if text =~ /\A\[html\]/i
29
- text = text.sub(/\A\[html\][\s\n\r]*/i, '')
30
- chain = @html
31
- else
32
- chain = @markup
33
- end
34
-
35
- text = chain.process text, env
36
-
37
- unless text.encoding == Encoding::UTF_8
38
- raise "something wrong happens, invalid encoding (#{text.encoding} instead of utf-8)!"
39
- end
40
-
41
- call_next text, env
42
- end
43
- end
@@ -1,25 +0,0 @@
1
- class Rad::TextUtils::Processor
2
- def initialize next_processor = nil
3
- @next_processor = next_processor
4
- end
5
-
6
- protected
7
- def call_next data, env
8
- if @next_processor
9
- @next_processor.process data, env
10
- else
11
- data
12
- end
13
- end
14
-
15
- def build_from *processors
16
- processors.reverse.inject nil do |next_processor, meta|
17
- klass, args = if meta.is_a? Array
18
- [meta[0], meta[1..-1]]
19
- else
20
- [meta, []]
21
- end
22
- klass.new next_processor, *args
23
- end
24
- end
25
- end
@@ -1,14 +0,0 @@
1
- class Rad::TextUtils::TagShortcuts < Rad::TextUtils::Processor
2
- TAGS = {
3
- /\[clear\]/ => lambda{|match| "<div class='clear'></div>"},
4
- /\[space\]/ => lambda{|match| "<div class='space'></div>"}
5
- }
6
-
7
- def process markdown, env
8
- TAGS.each do |k, v|
9
- markdown.gsub!(k, &v)
10
- end
11
-
12
- call_next markdown, env
13
- end
14
- end
@@ -1,29 +0,0 @@
1
- class Rad::TextUtils::Truncate < Rad::TextUtils::Processor
2
- def initialize processor, length
3
- super(processor)
4
- @length = length
5
- end
6
-
7
- def process str_or_html, env
8
- str_or_html ||= ""
9
-
10
- # Strip from HTML tags
11
- str_or_html = str_or_html.gsub("<br", " <br").gsub("<p", " <p") # to preserve space in place of <> html elements
12
- doc = Nokogiri::XML("<div class='root'>#{str_or_html}</div>")
13
- str = doc.css('.root').first.content
14
-
15
- str = str.gsub(/\s+/, ' ')
16
-
17
- # Truncate with no broken words
18
- str = if str.length >= @length
19
- shortened = str[0, @length]
20
- splitted = shortened.split(/\s/)
21
- words = splitted.length
22
- splitted[0, words-1].join(" ") + ' ...'
23
- else
24
- str
25
- end
26
-
27
- call_next str, env
28
- end
29
- end
@@ -1,15 +0,0 @@
1
- class Rad::TextUtils::Truncator < Rad::TextUtils::Processor
2
- def initialize processor, length
3
- super(processor)
4
-
5
- @chain = build_from(
6
- Rad::TextUtils::EnsureUtf,
7
- [Rad::TextUtils::Truncate, length]
8
- )
9
- end
10
-
11
- def process text_or_html, env
12
- text_or_html = @chain.process text_or_html, env
13
- call_next text_or_html, env
14
- end
15
- end
@@ -1,13 +0,0 @@
1
- class Rad::TextUtils::Urls < Rad::TextUtils::Processor
2
- # Creates <a> tags for all urls.
3
- # IMPORTANT: make sure you've used #urls_to_images method first
4
- # if you wanted all images urls to become <img> tags.
5
- def process html, env
6
- # becouse it finds only one url in such string "http://some_domain.com http://some_domain.com" we need to aply it twice
7
- regexp, sub = /(\s|^|\A|\n|\t|\r)(http:\/\/.*?)([,.])?(\s|$|\n|\Z|\t|\r|<)/, '\1<a href="\2">\2</a>\3\4'
8
- html = html.gsub regexp, sub
9
- html.gsub regexp, sub
10
-
11
- call_next html, env
12
- end
13
- end
@@ -1,43 +0,0 @@
1
- require 'digest/md5'
2
-
3
- require 'nokogiri'
4
- require 'bluecloth'
5
- require 'sanitize'
6
-
7
- module Rad::TextUtils; end
8
-
9
- %w(
10
- processor
11
-
12
- github_flavoured_markdown
13
- image_box
14
- custom_markdown
15
- urls
16
- tag_shortcuts
17
- html_sanitizer
18
- ensure_utf
19
- truncate
20
- code_highlighter
21
- truncator
22
-
23
- markup
24
- ).each{|f| require "kit/text_utils/#{f}"}
25
-
26
- module Rad::TextUtils
27
- class << self
28
- def markup text
29
- Rad::TextUtils::Markup.new.process text, {}
30
- end
31
-
32
- def random_string length = 3
33
- @digits ||= ('a'..'z').to_a + (0..9).to_a
34
- (0..(length-1)).map{@digits[rand(@digits.size)]}.join
35
- end
36
-
37
- def truncate str_or_html, length
38
- Rad::TextUtils::Truncator.new(nil, length).process str_or_html, {}
39
- # str_or_html = HtmlSanitizer.new.process str_or_html, {}
40
- # Truncator.new(length).process str_or_html
41
- end
42
- end
43
- end
@@ -1,280 +0,0 @@
1
- require 'spec_helper'
2
-
3
- # require 'kit/utils/text_utils.rb'
4
-
5
- describe "TextUtils" do
6
- def to_doc markup
7
- Nokogiri::HTML(to_html(markup))
8
- end
9
-
10
- def to_html markup
11
- Rad::TextUtils.markup(markup)
12
- end
13
-
14
- ::Nokogiri::XML::Node.class_eval do
15
- def should_be_fuzzy_equal_to attributes
16
- attributes.stringify_keys!
17
- self.content.should == content if content = attributes.delete('content')
18
-
19
- attributes.each do |attr_name, value|
20
- self[attr_name].to_s.should == value.to_s
21
- end
22
- end
23
- end
24
-
25
- describe "code highlighting" do
26
- it "basic" do
27
- to_html(%{<p> text </p><code lang='ruby'>class A; p "Hello World" end</code><p> text </p>}).should =~ /span/i
28
- to_html(%{<p> text </p><code language='ruby'>class A; p "Hello World" end</code><p> text </p>}).should =~ /span/i
29
- to_html(%{<code lang='ruby'>\nclass A \n def p\n 10\n end\nend \n</code>}).should =~ /span/i
30
- end
31
-
32
- it "should works with < and > in code" do
33
- to_html(%{<code lang='ruby'>class A < ClassB; end</code>}).should include('ClassB')
34
- end
35
-
36
- it 'should preserve custom classes in <code>' do
37
- to_html(%{<code lang='ruby' class='my_code'>\nclass A \n def p\n 10\n end\nend \n</code>}).should =~ /my_code/i
38
- end
39
- end
40
-
41
- it "should not raise error on empty string" do
42
- to_html('').should == ''
43
- end
44
-
45
- describe "MarkdDown" do
46
-
47
-
48
- it "should do basic markup" do
49
- doc = to_doc "**text**"
50
- doc.css("p b, p strong").first.should_be_fuzzy_equal_to content: 'text'
51
- end
52
-
53
- it "should guess urls" do
54
- doc = to_doc "This is a http://www.some.com/some link"
55
- doc.content.strip.should == "This is a http://www.some.com/some link"
56
- doc.css("p a").first.should_be_fuzzy_equal_to href: "http://www.some.com/some"
57
-
58
- # from error
59
- doc = to_doc "http://www.some.com/some"
60
- doc.content.strip.should == "http://www.some.com/some"
61
- doc.css("p a").first.should_be_fuzzy_equal_to href: "http://www.some.com/some"
62
-
63
- # from error
64
- # http://mastertalk.ru/topic111478.html
65
- end
66
-
67
- it "should allow 'a' elements" do
68
- html = <<HTML
69
- <a href="http://www.some.com/some">Absolute Link</a>
70
- <a href="/some">Relative Link</a>
71
- HTML
72
-
73
- doc = to_doc html
74
- doc.css("a").first[:href].should == "http://www.some.com/some"
75
- doc.css("a").last[:href].should == "/some"
76
- end
77
-
78
- it "should embed YouTube Videos" do
79
- html =<<HTML
80
- <object width="425" height="344">
81
- <param name="movie" value="http://www.youtube.com/v/s8hYKKXV5wU&hl=en_US&fs=1&"></param>
82
- <param name="allowFullScreen" value="true"></param>
83
- <param name="allowscriptaccess" value="always"></param>
84
- <embed src="http://www.youtube.com/v/s8hYKKXV5wU&hl=en_US&fs=1&" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="425" height="344"></embed>
85
- </object>
86
- HTML
87
-
88
- doc = to_doc html
89
- obj = doc.css("object").first.should_be_fuzzy_equal_to width: 425, height: 344
90
- p1, p2, p3, embed = doc.css("object *")
91
- p1.should_be_fuzzy_equal_to name: "movie", value: "http://www.youtube.com/v/s8hYKKXV5wU&hl=en_US&fs=1&"
92
- p2.should_be_fuzzy_equal_to name: "allowFullScreen", value: "true"
93
- p3.should_be_fuzzy_equal_to name: "allowscriptaccess", value: "always"
94
- embed.should_be_fuzzy_equal_to src: "http://www.youtube.com/v/s8hYKKXV5wU&hl=en_US&fs=1&",
95
- type: "application/x-shockwave-flash", allowscriptaccess: "always",
96
- allowfullscreen: "true", width: "425", height: "344"
97
- end
98
-
99
- it "should skip empty paragraphs" do
100
- html = "line 1\n\nline 2\n\n\n\nline 3"
101
- to_html(html).should =~ /<p>\s*line 1<\/p>\n<p>line 2<\/p>\n<p>line 3\s*<\/p>.?/
102
- end
103
-
104
- it "should convert \n to <br/>" do
105
- to_doc("foo\nbar").css('br').size.should == 1
106
- end
107
-
108
- it "should not touch single underscores inside words" do
109
- to_html("foo_bar").should include("foo_bar")
110
- end
111
-
112
- it "should works with unicode" do
113
- html = %{Юникод <a href="http://www.some.com/" class="_image_box">Юникод</a>}
114
- doc = to_doc html
115
- doc.css('p').first.content.should =~ /Юникод/
116
- doc.css('p a').first.should_be_fuzzy_equal_to href: "http://www.some.com/", class: "_image_box", content: "Юникод"
117
- end
118
-
119
- it 'should allow class and rel attribute' do
120
- html = %{<a href="http://www.some.com/" class="_image_box" rel="nofollow">Some</a>}
121
- doc = to_doc html
122
- doc.css('a').first.should_be_fuzzy_equal_to href: "http://www.some.com/", class: "_image_box", rel: "nofollow"
123
- end
124
-
125
- it "should allow image inside of link" do
126
- html = <<HTML
127
- <a rel="article_images" class="_image_box" href="/some_image">
128
- <img src="/some_image"></img>
129
- </a>
130
- HTML
131
-
132
- doc = to_doc html
133
- doc.css('a').first.should_be_fuzzy_equal_to href: "/some_image", class: "_image_box"
134
- doc.css('a img').first.should_be_fuzzy_equal_to src: "/some_image"
135
- end
136
-
137
- it "should use simplifyed syntax for image boxes (!![img_thumb] => [![img_thumb]][img_full_version])" do
138
- html = <<HTML
139
- !![img]
140
- ![img]
141
-
142
- !![img_2]
143
- ![img_2]
144
-
145
- [img]: /some_prefix/image_name.png
146
- [img_2]: /some_prefix/image_name2.icon.png
147
- HTML
148
-
149
- doc = to_doc html
150
- doc.css('a').first.should_be_fuzzy_equal_to href: "/some_prefix/image_name.png"
151
- doc.css('a img').first.should_be_fuzzy_equal_to src: "/some_prefix/image_name.thumb.png"
152
-
153
- doc.css('a').last.should_be_fuzzy_equal_to href: "/some_prefix/image_name2.png"
154
- doc.css('a img').last.should_be_fuzzy_equal_to src: "/some_prefix/image_name2.icon.png"
155
-
156
- doc.css('img').size.should == 4
157
- end
158
-
159
- it "simplifyed syntax for image boxes should be robust (from error)" do
160
- html = "!![img] " # without resolved reference
161
- to_html(html)
162
- lambda{to_html(html)}.should_not raise_error
163
- end
164
-
165
- it "should create teaser from text" do
166
- text = %{Hi there, I have a page that will list news articles}
167
- Rad::TextUtils.truncate(text, 20).should == "Hi there, I have a ..."
168
- end
169
-
170
- it "should create teaser from html" do
171
- text = %{Hi <div><b>there</b>, I have a page that will list news articles</div>}
172
- Rad::TextUtils.truncate(text, 20).should == "Hi there, I have a ..."
173
-
174
- Rad::TextUtils.truncate(%{a<br/>b}, 20).should == "a b" # from error
175
- end
176
-
177
- # it "embed metaweb.com wiget" do
178
- # html = <<HTML
179
- # <div itemtype="http://www.freebase.com/id/computer/software" itemid="http://www.freebase.com/id/en/google_web_toolkit" itemscope="" style="border: 0pt none; outline: 0pt none; padding: 0pt; margin: 0pt; position: relative;" id="fbtb-6ffc2545598340cbbc7945f43ebd45de" class="fb-widget">
180
- # <iframe frameborder="0" scrolling="no" src="http://www.freebase.com/widget/topic?track=topicblocks_homepage&amp;mode=content&amp;id=%2Fen%2Fgoogle_web_toolkit" style="height: 285px; width: 413px; border: 0pt none; outline: 0pt none; padding: 0pt; margin: 0pt;" classname="fb-widget-iframe" allowtransparency="true" class=" "></iframe>
181
- # <script defer="" type="text/javascript" src="http://freebaselibs.com/static/widgets/2/widget.js"></script>
182
- # </div>
183
- # HTML
184
- #
185
- # text = "{metaweb:google_web_toolkit}"
186
- # to_html(text).should include(html)
187
- # end
188
-
189
- it "should correctly insert newline (from error)" do
190
- html = <<HTML
191
- ![img] Open Design.
192
- http://oomps.com
193
-
194
- [img]: /some_link
195
- HTML
196
-
197
- to_doc(html).css('br').size.should == 1
198
- end
199
-
200
- it "clear div" do
201
- html = "[clear]"
202
-
203
- doc = to_doc html
204
- doc.css('div.clear').size.should == 1
205
- end
206
-
207
- it "space div" do
208
- html = "[space]"
209
-
210
- doc = to_doc html
211
- doc.css('div.space').size.should == 1
212
- end
213
-
214
- it "should correctly guess links (from error)" do
215
- to_doc("http://some_domain.com http://some_domain.com").css('a').size == 2
216
- end
217
-
218
- it "should leave existing links intact" do
219
- doc = to_doc(%{<a href="http://some_domain.com">http://some_domain.com</a>})
220
- doc.css('a').size.should == 1
221
- doc.css('a').first['href'].should == "http://some_domain.com"
222
- end
223
-
224
- it "should leave existing links intact" do
225
- md = %{\
226
- [Download Page][dl]
227
- [dl]: http://www.mozilla.org/products/firefox/}
228
-
229
- to_doc(md).css('a').first['href'].should == 'http://www.mozilla.org/products/firefox/'
230
- end
231
-
232
- it "should allow div with any classes (from error)" do
233
- html = %{<div class="col3 left"><a href='#'>text</a></div>}
234
- to_doc(html).css("div.col3.left a").size.should == 1
235
- end
236
-
237
- it "should apply markup inside of html elements (from error)" do
238
- html = <<HTML
239
- <div class='right'>
240
- ![img]
241
- </div>
242
-
243
- [img]: /some_link
244
- HTML
245
-
246
- to_doc(html).css('.right img').size.should == 1
247
- end
248
-
249
- it "shouldn't create newline after > sign (from error)" do
250
- html = %{\
251
- <div>text</div>
252
- text}
253
- to_doc(html).css('br').size.should == 0
254
- end
255
-
256
- it "shouldn't add empty <p> before first line (from error)" do
257
- to_html("<span>text</span>text").should_not =~ /<p>\s*<\/p>/
258
- end
259
- end
260
-
261
- it "should not aply markdown if document specified as [html]" do
262
- html = %{\
263
- [html]
264
- first line
265
- **text**
266
- second line}
267
-
268
- r = to_html(html)
269
- r.should_not include('<')
270
- r.should_not include('[html]')
271
- end
272
-
273
- it "should still escape input in [html] mode" do
274
- html = %{\
275
- [html]
276
- <script>some dangerous code</script>}
277
-
278
- to_html(html).should_not include('script')
279
- end
280
- end