abc-backend 0.0.1
Sign up to get free protection for your applications and to get access to all the features.
- data/app/controllers/abc/application_controller.rb +6 -0
- data/app/controllers/abc/backend/base_controller.rb +8 -0
- data/app/presenters/abc/html/menu_entry_presenter.rb +87 -0
- data/app/presenters/abc/html/menu_presenter.rb +68 -0
- data/app/views/abc/backend/base/index.html.erb +1 -0
- data/config/routes.rb +3 -0
- data/lib/abc-backend.rb +2 -0
- data/lib/abc/backend/engine.rb +7 -0
- data/spec/integration/backend_spec.rb +10 -0
- data/spec/integration/menu_spec.rb +18 -0
- data/spec/internal/config/database.yml +3 -0
- data/spec/internal/config/routes.rb +5 -0
- data/spec/internal/db/schema.rb +3 -0
- data/spec/internal/log/test.log +184 -0
- data/spec/internal/public/favicon.ico +0 -0
- data/spec/presenters/html/menu_entry_presenter_spec.rb +49 -0
- data/spec/presenters/html/menu_presenter_spec.rb +74 -0
- data/spec/spec_helper.rb +14 -0
- data/spec/tiny_spec_helper.rb +13 -0
- metadata +175 -0
@@ -0,0 +1,87 @@
|
|
1
|
+
require 'action_view'
|
2
|
+
|
3
|
+
module Abc
|
4
|
+
module Html
|
5
|
+
class MenuEntryPresenter
|
6
|
+
include ActionView::Helpers::TagHelper
|
7
|
+
include ActionView::Context # Nested content_tags
|
8
|
+
|
9
|
+
attr_accessor :menu_entry, :list_element_pair
|
10
|
+
|
11
|
+
def initialize(menu_entry, options = {})
|
12
|
+
options = {:list_element_pair => [:ul, :li]}.merge(options)
|
13
|
+
self.menu_entry = menu_entry
|
14
|
+
self.list_element_pair = options[:list_element_pair]
|
15
|
+
end
|
16
|
+
|
17
|
+
# Renders a menu item in HTML format, and, if it has children, renders those too.
|
18
|
+
#
|
19
|
+
# **A note on HTML safety:**
|
20
|
+
#
|
21
|
+
# It is up to each menu item presenter to check that it is rendering itself safely.
|
22
|
+
# By default, most of the menu has to be declared safe, or else its
|
23
|
+
# constituent tags won't render properly. So we declare vast swaths of the
|
24
|
+
# menu HTML safe, and in truth these parts are. The parts that
|
25
|
+
# need to be especially watched are any spots where you render user input.
|
26
|
+
# By design, that surface is constrained to the `render_as_html` method.
|
27
|
+
# You must, however, return a string marked with html_safe from that method
|
28
|
+
# or else the menu will raise `ActiveSupport::SafeBuffer::SafeConcatError`.
|
29
|
+
#
|
30
|
+
# (This doesn't meant that the entire string must be unsanitized; just that
|
31
|
+
# you must make assurances that your content is appropriately escaped. By
|
32
|
+
# default, ABC uses `ERB::Util#h` to sanitize the user-interpreted parts, but
|
33
|
+
# your derivative classes may have to implement this on their own.)
|
34
|
+
#
|
35
|
+
# @return [SafeBuffer] A safe string containing the MenuEntry and its children.
|
36
|
+
def to_html
|
37
|
+
content = render_as_html
|
38
|
+
raise ActiveSupport::SafeBuffer::SafeConcatError unless content.html_safe?
|
39
|
+
|
40
|
+
content_tag(list_element_tag) do
|
41
|
+
if menu_entry_children.present?
|
42
|
+
render_with_children_as_html content
|
43
|
+
else
|
44
|
+
content
|
45
|
+
end
|
46
|
+
end.html_safe
|
47
|
+
end
|
48
|
+
|
49
|
+
protected
|
50
|
+
|
51
|
+
# Renders this menu item and its children with the assumption it has children.
|
52
|
+
#
|
53
|
+
# @param content [SafeBuffer] A safe string to use as the content of this, the parent {MenuEntry.
|
54
|
+
# @return [SafeBuffer] A safe string to be rendered by the parent {Menu} or {MenuEntry}.
|
55
|
+
def render_with_children_as_html(content)
|
56
|
+
content.safe_concat(
|
57
|
+
content_tag(list_container_tag) do
|
58
|
+
menu_entry_children.reduce(::ActiveSupport::SafeBuffer.new) do |buffer, child|
|
59
|
+
child_presenter = self.class.new(child, :list_element_pair => list_element_pair)
|
60
|
+
buffer.safe_concat child_presenter.to_html
|
61
|
+
end
|
62
|
+
end.html_safe
|
63
|
+
)
|
64
|
+
end
|
65
|
+
|
66
|
+
def list_container_tag
|
67
|
+
list_element_pair.first
|
68
|
+
end
|
69
|
+
|
70
|
+
def list_element_tag
|
71
|
+
list_element_pair.last
|
72
|
+
end
|
73
|
+
|
74
|
+
# Render this {MenuItem} without children.
|
75
|
+
#
|
76
|
+
# **NB**: ERB::Util#h will mark a string as safe.
|
77
|
+
#
|
78
|
+
# @returns [SafeBuffer] A safe string to be rendered or appended with children.
|
79
|
+
def render_as_html
|
80
|
+
ERB::Util.h menu_entry_title
|
81
|
+
end
|
82
|
+
|
83
|
+
delegate :children, :to => :menu_entry, :allow_nil => true, :prefix => true
|
84
|
+
delegate :title, :to => :menu_entry, :prefix => true
|
85
|
+
end
|
86
|
+
end
|
87
|
+
end
|
@@ -0,0 +1,68 @@
|
|
1
|
+
require 'action_view'
|
2
|
+
require 'active_support/core_ext/string'
|
3
|
+
|
4
|
+
module Abc
|
5
|
+
module Html
|
6
|
+
class MenuPresenter
|
7
|
+
include ActionView::Helpers::TagHelper
|
8
|
+
include ActionView::Context
|
9
|
+
|
10
|
+
attr_accessor :menu, :menu_element, :list_element_pair, :menu_entry_presenter_class
|
11
|
+
|
12
|
+
def initialize(menu, options = {})
|
13
|
+
options = default_initialize_options.merge(options)
|
14
|
+
|
15
|
+
self.menu = menu
|
16
|
+
self.menu_element = options[:menu_element]
|
17
|
+
self.list_element_pair = options[:list_element_pair]
|
18
|
+
self.menu_entry_presenter_class = options[:menu_entry_presenter_class]
|
19
|
+
end
|
20
|
+
|
21
|
+
# Outputs the menu in HTML format.
|
22
|
+
#
|
23
|
+
# @return An HTML-safe string containing the markup of the menu in question.
|
24
|
+
def to_html
|
25
|
+
content_tag(menu_element) do
|
26
|
+
content_tag(list_container_tag) do
|
27
|
+
# Reduce will concat into a first SafeBuffer here, so if the first
|
28
|
+
# node is html_safe, this will produce expected outcome. And of course,
|
29
|
+
# MenuEntries are expected to be html_safe.
|
30
|
+
menu_entries.reduce(::ActiveSupport::SafeBuffer.new) do |buffer, child|
|
31
|
+
menu_entry_presenter = menu_entry_presenter_class.new(
|
32
|
+
child, :list_element_pair => list_element_pair
|
33
|
+
)
|
34
|
+
buffer.safe_concat menu_entry_presenter.to_html
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end.html_safe
|
38
|
+
end
|
39
|
+
|
40
|
+
# Set the elements that are used to determine what contains a series of
|
41
|
+
# children and the actual children itself. Defaults to [:ul, :li].
|
42
|
+
# We sometimes refer to the pair as the container and the enumerator.
|
43
|
+
#
|
44
|
+
# @param pair [Array] A pair of HTML element names
|
45
|
+
def list_element_pair=(pair)
|
46
|
+
raise "List element pair must be an array" unless pair.is_a?(Array)
|
47
|
+
raise "List element pair must specify two element types" unless pair.count == 2
|
48
|
+
raise "List element pair should be symbols" unless pair.all? {|e| e.is_a?(Symbol)}
|
49
|
+
@list_element_pair = pair
|
50
|
+
end
|
51
|
+
|
52
|
+
private
|
53
|
+
def default_initialize_options
|
54
|
+
{
|
55
|
+
:menu_element => :nav,
|
56
|
+
:list_element_pair => [:ul, :li],
|
57
|
+
:menu_entry_presenter_class => MenuEntryPresenter
|
58
|
+
}.freeze
|
59
|
+
end
|
60
|
+
|
61
|
+
def list_container_tag
|
62
|
+
list_element_pair.first
|
63
|
+
end
|
64
|
+
|
65
|
+
delegate :entries, :to => :menu, :prefix => true
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
@@ -0,0 +1 @@
|
|
1
|
+
Welcome to Afterburner CMS
|
data/config/routes.rb
ADDED
data/lib/abc-backend.rb
ADDED
@@ -0,0 +1,18 @@
|
|
1
|
+
require 'tiny_spec_helper'
|
2
|
+
require 'interactors/creates_menu'
|
3
|
+
|
4
|
+
describe "Menu" do
|
5
|
+
describe "when using an HTML presenter" do
|
6
|
+
let(:children_for_one) {
|
7
|
+
[{:title => "One first child"}, {:title => "One second child"}]
|
8
|
+
}
|
9
|
+
let(:menu_entries) { [{:title => "One", :children => children_for_one}] }
|
10
|
+
|
11
|
+
let(:menu) { Abc::Interactors::CreatesMenu.call(menu_entries) }
|
12
|
+
let(:present) { Abc::Html::MenuPresenter.new(menu).to_html }
|
13
|
+
|
14
|
+
it "renders properly" do
|
15
|
+
present.should == "<nav><ul><li>One<ul><li>One first child</li><li>One second child</li></ul></li></ul></nav>"
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,184 @@
|
|
1
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-05 16:22:15 -0500
|
2
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
3
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-05 16:33:57 -0500
|
4
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
5
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-05 17:35:03 -0500
|
6
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
7
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.6ms)
|
8
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
9
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-05 22:07:48 -0500
|
10
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
11
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
12
|
+
Completed 200 OK in 3ms (Views: 2.9ms)
|
13
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-05 22:39:55 -0500
|
14
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
15
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
16
|
+
Completed 200 OK in 3ms (Views: 2.6ms)
|
17
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-05 22:40:47 -0500
|
18
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
19
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.6ms)
|
20
|
+
Completed 200 OK in 3ms (Views: 2.9ms)
|
21
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-05 22:42:29 -0500
|
22
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
23
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
24
|
+
Completed 200 OK in 3ms (Views: 2.7ms)
|
25
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-05 23:51:32 -0500
|
26
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
27
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.6ms)
|
28
|
+
Completed 200 OK in 3ms (Views: 2.9ms)
|
29
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-06 00:02:31 -0500
|
30
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
31
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.6ms)
|
32
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
33
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-06 00:06:43 -0500
|
34
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
35
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
36
|
+
Completed 200 OK in 3ms (Views: 2.9ms)
|
37
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-06 00:12:19 -0500
|
38
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
39
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.6ms)
|
40
|
+
Completed 200 OK in 3ms (Views: 2.7ms)
|
41
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-06 00:13:39 -0500
|
42
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
43
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
44
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
45
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-06 00:27:50 -0500
|
46
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
47
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
48
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
49
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-06 00:31:36 -0500
|
50
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
51
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
52
|
+
Completed 200 OK in 3ms (Views: 2.7ms)
|
53
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-06 00:32:25 -0500
|
54
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
55
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
56
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
57
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-06 00:38:07 -0500
|
58
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
59
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.6ms)
|
60
|
+
Completed 200 OK in 3ms (Views: 2.9ms)
|
61
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-06 00:58:40 -0500
|
62
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
63
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
64
|
+
Completed 200 OK in 3ms (Views: 2.7ms)
|
65
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-06 01:04:43 -0500
|
66
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
67
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.6ms)
|
68
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
69
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-07 17:05:26 -0500
|
70
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
71
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
72
|
+
Completed 200 OK in 3ms (Views: 2.6ms)
|
73
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-07 17:05:40 -0500
|
74
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
75
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
76
|
+
Completed 200 OK in 3ms (Views: 2.6ms)
|
77
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-07 17:40:13 -0500
|
78
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
79
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.5ms)
|
80
|
+
Completed 200 OK in 3ms (Views: 2.9ms)
|
81
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-07 17:42:53 -0500
|
82
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
83
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.6ms)
|
84
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
85
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-07 20:00:35 -0500
|
86
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
87
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.6ms)
|
88
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
89
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-08 13:36:54 -0500
|
90
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
91
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.6ms)
|
92
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
93
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-08 13:37:24 -0500
|
94
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
95
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.6ms)
|
96
|
+
Completed 200 OK in 3ms (Views: 2.9ms)
|
97
|
+
Started GET "/backend" for 127.0.0.1 at 2013-03-08 14:02:10 -0500
|
98
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
99
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/rails/app/views/abc/backend/base/index.html.erb (0.6ms)
|
100
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
101
|
+
Started GET "/" for 127.0.0.1 at 2013-03-08 14:29:04 -0500
|
102
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
103
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (0.6ms)
|
104
|
+
Completed 200 OK in 3ms (Views: 2.9ms)
|
105
|
+
Started GET "/" for 127.0.0.1 at 2013-03-08 14:31:37 -0500
|
106
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
107
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (0.5ms)
|
108
|
+
Completed 200 OK in 3ms (Views: 2.9ms)
|
109
|
+
Started GET "/" for 127.0.0.1 at 2013-03-08 14:55:30 -0500
|
110
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
111
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (0.6ms)
|
112
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
113
|
+
Started GET "/" for 127.0.0.1 at 2013-03-08 23:12:44 -0500
|
114
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
115
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (0.6ms)
|
116
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
117
|
+
Started GET "/" for 127.0.0.1 at 2013-03-09 04:17:07 -0500
|
118
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
119
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (0.6ms)
|
120
|
+
Completed 200 OK in 3ms (Views: 2.8ms)
|
121
|
+
Started GET "/" for 127.0.0.1 at 2013-03-09 04:34:19 -0500
|
122
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
123
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (37.5ms)
|
124
|
+
Completed 200 OK in 49ms (Views: 48.5ms)
|
125
|
+
Started GET "/" for 127.0.0.1 at 2013-03-09 04:34:44 -0500
|
126
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
127
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (36.3ms)
|
128
|
+
Completed 200 OK in 47ms (Views: 47.1ms)
|
129
|
+
Started GET "/" for 127.0.0.1 at 2013-03-10 04:27:48 -0400
|
130
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
131
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (2.9ms)
|
132
|
+
Completed 200 OK in 49ms (Views: 48.4ms)
|
133
|
+
Started GET "/" for 127.0.0.1 at 2013-03-11 04:33:11 -0400
|
134
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
135
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (3.0ms)
|
136
|
+
Completed 200 OK in 49ms (Views: 48.5ms)
|
137
|
+
Started GET "/" for 127.0.0.1 at 2013-03-11 05:00:17 -0400
|
138
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
139
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (3.0ms)
|
140
|
+
Completed 200 OK in 48ms (Views: 48.1ms)
|
141
|
+
Started GET "/" for 127.0.0.1 at 2013-03-13 01:33:36 -0400
|
142
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
143
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (3.1ms)
|
144
|
+
Completed 200 OK in 45ms (Views: 45.0ms)
|
145
|
+
Started GET "/" for 127.0.0.1 at 2013-03-13 01:36:51 -0400
|
146
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
147
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (3.2ms)
|
148
|
+
Completed 200 OK in 45ms (Views: 45.0ms)
|
149
|
+
Started GET "/" for 127.0.0.1 at 2013-03-13 03:18:53 -0400
|
150
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
151
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (3.1ms)
|
152
|
+
Completed 200 OK in 48ms (Views: 48.0ms)
|
153
|
+
Started GET "/" for 127.0.0.1 at 2013-03-14 19:44:40 -0400
|
154
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
155
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (3.1ms)
|
156
|
+
Completed 200 OK in 53ms (Views: 52.5ms)
|
157
|
+
Started GET "/" for 127.0.0.1 at 2013-03-16 02:24:31 -0400
|
158
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
159
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (37.4ms)
|
160
|
+
Completed 200 OK in 49ms (Views: 48.8ms)
|
161
|
+
Started GET "/" for 127.0.0.1 at 2013-03-16 02:42:20 -0400
|
162
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
163
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (37.5ms)
|
164
|
+
Completed 200 OK in 49ms (Views: 48.7ms)
|
165
|
+
Started GET "/" for 127.0.0.1 at 2013-03-18 01:19:19 -0400
|
166
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
167
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (33.3ms)
|
168
|
+
Completed 200 OK in 45ms (Views: 44.6ms)
|
169
|
+
Started GET "/" for 127.0.0.1 at 2013-03-18 01:19:47 -0400
|
170
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
171
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (33.7ms)
|
172
|
+
Completed 200 OK in 45ms (Views: 45.1ms)
|
173
|
+
Started GET "/" for 127.0.0.1 at 2013-03-18 01:24:08 -0400
|
174
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
175
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (3.1ms)
|
176
|
+
Completed 200 OK in 46ms (Views: 45.3ms)
|
177
|
+
Started GET "/" for 127.0.0.1 at 2013-03-18 01:24:35 -0400
|
178
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
179
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (3.1ms)
|
180
|
+
Completed 200 OK in 45ms (Views: 44.9ms)
|
181
|
+
Started GET "/" for 127.0.0.1 at 2013-03-18 01:29:56 -0400
|
182
|
+
Processing by Abc::Backend::BaseController#index as HTML
|
183
|
+
Rendered /home/rob/Sites/a/afterburnercms/delivery/backend/app/views/abc/backend/base/index.html.erb (3.1ms)
|
184
|
+
Completed 200 OK in 45ms (Views: 44.7ms)
|
File without changes
|
@@ -0,0 +1,49 @@
|
|
1
|
+
require 'tiny_spec_helper'
|
2
|
+
require 'presenters/abc/html/menu_entry_presenter'
|
3
|
+
|
4
|
+
class MockMenuEntry
|
5
|
+
attr_accessor :children, :title
|
6
|
+
def initialize(opts = {}); @children = opts[:children] || []; @title = opts[:title]; end
|
7
|
+
def list_element_pair=(_); @list_element_pair = _; end
|
8
|
+
end
|
9
|
+
|
10
|
+
module Abc
|
11
|
+
module Html
|
12
|
+
describe MenuEntryPresenter do
|
13
|
+
let(:menu_item) { MockMenuEntry.new(:title => "Root") }
|
14
|
+
let(:child) { MockMenuEntry.new(:title => "Child") }
|
15
|
+
subject { MenuEntryPresenter.new(menu_item) }
|
16
|
+
|
17
|
+
it "renders itself" do
|
18
|
+
subject.to_html.should == "<li>Root</li>"
|
19
|
+
end
|
20
|
+
|
21
|
+
it "renders with the list enumerator of list_element_pair" do
|
22
|
+
subject.list_element_pair = [:nav, :div]
|
23
|
+
subject.to_html.should == "<div>Root</div>"
|
24
|
+
end
|
25
|
+
|
26
|
+
it "raises an error if its content is not marked html_safe" do
|
27
|
+
subject.stub!(:render_as_html).and_return("unsafe string")
|
28
|
+
expect { subject.to_html }.to raise_error(::ActiveSupport::SafeBuffer::SafeConcatError)
|
29
|
+
end
|
30
|
+
|
31
|
+
context "with children" do
|
32
|
+
before(:each) { menu_item.children = [child] }
|
33
|
+
# TODO: Remove this diagnostic spec.
|
34
|
+
it "child count should be one" do
|
35
|
+
subject.menu_entry.children.count.should == 1
|
36
|
+
end
|
37
|
+
|
38
|
+
it "renders its children" do
|
39
|
+
subject.to_html.should == "<li>Root<ul><li>Child</li></ul></li>"
|
40
|
+
end
|
41
|
+
|
42
|
+
it "wraps children in the passed list element" do
|
43
|
+
subject.list_element_pair = [:nav, :div]
|
44
|
+
subject.to_html.should == "<div>Root<nav><div>Child</div></nav></div>"
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
@@ -0,0 +1,74 @@
|
|
1
|
+
require 'tiny_spec_helper'
|
2
|
+
require 'presenters/abc/html/menu_presenter'
|
3
|
+
|
4
|
+
class MenuEntryMock
|
5
|
+
include ActionView::Helpers::TagHelper
|
6
|
+
def initialize(name); @name = name; end
|
7
|
+
def title; @title ||= rand(30).times.map{|i| ('A'..'Z').to_a.sample}.join end
|
8
|
+
attr_accessor :children
|
9
|
+
end
|
10
|
+
|
11
|
+
class MenuEntryPresenterMock
|
12
|
+
attr_accessor :menu_entry, :list_element_pair
|
13
|
+
def initialize(menu_entry, options)
|
14
|
+
@menu_entry = menu_entry
|
15
|
+
@list_element_pair = options[:list_element_pair]
|
16
|
+
end
|
17
|
+
def to_html; "<#{list_element_pair.last}>#{menu_entry.title}</#{list_element_pair.last}>"; end
|
18
|
+
end
|
19
|
+
|
20
|
+
class MenuMock
|
21
|
+
attr_accessor :entries
|
22
|
+
def initialize(options = {}); @entries = options[:entries] || []; end
|
23
|
+
end
|
24
|
+
|
25
|
+
|
26
|
+
module Abc
|
27
|
+
module Html
|
28
|
+
describe MenuPresenter do
|
29
|
+
let(:list_element_pair) { [:ul, :li] }
|
30
|
+
let(:entry1) { MenuEntryMock.new("node 1") }
|
31
|
+
let(:entry1_presenter) { MenuEntryPresenterMock.new(entry1, :list_element_pair => list_element_pair) }
|
32
|
+
let(:entry2) { MenuEntryMock.new("node 2") }
|
33
|
+
let(:entry2_presenter) { MenuEntryPresenterMock.new(entry2, :list_element_pair => list_element_pair) }
|
34
|
+
let(:menu) { MenuMock.new(:entries => [entry1, entry2]) }
|
35
|
+
let(:presenter_options) do
|
36
|
+
{
|
37
|
+
:menu_entry_presenter_class => MenuEntryPresenterMock,
|
38
|
+
:list_element_pair => list_element_pair
|
39
|
+
}
|
40
|
+
end
|
41
|
+
let(:presenter) { MenuPresenter.new(menu, presenter_options) }
|
42
|
+
# TODO: Add specs for list element pair squawks, or refactor these into
|
43
|
+
# two separate param. How do we handle co-dependence, then?
|
44
|
+
# i.e. since this is a ul and an li, what if people change
|
45
|
+
# the ul but not the li? Is this something that our API can make
|
46
|
+
# clearer than it is at the moment?
|
47
|
+
|
48
|
+
it "asks its entries to render themselves" do
|
49
|
+
presenter.to_html
|
50
|
+
end
|
51
|
+
|
52
|
+
it "draws its children in order" do
|
53
|
+
presenter.to_html.should == "<nav><ul>%s%s</ul></nav>" % [entry1_presenter.to_html, entry2_presenter.to_html]
|
54
|
+
end
|
55
|
+
|
56
|
+
it "is considered HTML safe" do
|
57
|
+
presenter.to_html.html_safe?.should be_true
|
58
|
+
end
|
59
|
+
|
60
|
+
it "allows an alternate root element" do
|
61
|
+
presenter.menu_element = :div
|
62
|
+
presenter.to_html.should match(/\A<div/)
|
63
|
+
end
|
64
|
+
|
65
|
+
context 'with alternate list element pair' do
|
66
|
+
let(:list_element_pair) { [:menu, :div] }
|
67
|
+
|
68
|
+
it "uses them properly" do
|
69
|
+
presenter.to_html.should match(/\A<nav><menu><div>/)
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,14 @@
|
|
1
|
+
unless ENV['TRAVIS']
|
2
|
+
require 'simplecov'
|
3
|
+
SimpleCov.start do
|
4
|
+
add_filter "/spec/"
|
5
|
+
end
|
6
|
+
end
|
7
|
+
require 'bundler/setup'
|
8
|
+
|
9
|
+
Bundler.require :default, :test
|
10
|
+
|
11
|
+
require 'capybara/rspec'
|
12
|
+
|
13
|
+
Combustion.initialize! :action_view, :active_model, :action_controller
|
14
|
+
require 'rspec/rails'
|
@@ -0,0 +1,13 @@
|
|
1
|
+
$LOAD_PATH.push File.expand_path('../../app', __FILE__)
|
2
|
+
%w(presenters conductors).each do |pattern|
|
3
|
+
$LOAD_PATH.push File.expand_path("../../app/#{pattern}", __FILE__)
|
4
|
+
end
|
5
|
+
|
6
|
+
unless ENV['TRAVIS']
|
7
|
+
require 'simplecov'
|
8
|
+
SimpleCov.start do
|
9
|
+
add_filter '/spec/'
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
require 'abc-core'
|
metadata
ADDED
@@ -0,0 +1,175 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: abc-backend
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.0.1
|
5
|
+
prerelease:
|
6
|
+
platform: ruby
|
7
|
+
authors:
|
8
|
+
- The Afterburner CMS Team
|
9
|
+
autorequire:
|
10
|
+
bindir: bin
|
11
|
+
cert_chain: []
|
12
|
+
date: 2013-03-18 00:00:00.000000000 Z
|
13
|
+
dependencies:
|
14
|
+
- !ruby/object:Gem::Dependency
|
15
|
+
name: railties
|
16
|
+
requirement: !ruby/object:Gem::Requirement
|
17
|
+
none: false
|
18
|
+
requirements:
|
19
|
+
- - ! '>='
|
20
|
+
- !ruby/object:Gem::Version
|
21
|
+
version: 4.0.0.beta
|
22
|
+
type: :runtime
|
23
|
+
prerelease: false
|
24
|
+
version_requirements: !ruby/object:Gem::Requirement
|
25
|
+
none: false
|
26
|
+
requirements:
|
27
|
+
- - ! '>='
|
28
|
+
- !ruby/object:Gem::Version
|
29
|
+
version: 4.0.0.beta
|
30
|
+
- !ruby/object:Gem::Dependency
|
31
|
+
name: activesupport
|
32
|
+
requirement: !ruby/object:Gem::Requirement
|
33
|
+
none: false
|
34
|
+
requirements:
|
35
|
+
- - ! '>='
|
36
|
+
- !ruby/object:Gem::Version
|
37
|
+
version: 4.0.0.beta
|
38
|
+
type: :runtime
|
39
|
+
prerelease: false
|
40
|
+
version_requirements: !ruby/object:Gem::Requirement
|
41
|
+
none: false
|
42
|
+
requirements:
|
43
|
+
- - ! '>='
|
44
|
+
- !ruby/object:Gem::Version
|
45
|
+
version: 4.0.0.beta
|
46
|
+
- !ruby/object:Gem::Dependency
|
47
|
+
name: actionpack
|
48
|
+
requirement: !ruby/object:Gem::Requirement
|
49
|
+
none: false
|
50
|
+
requirements:
|
51
|
+
- - ! '>='
|
52
|
+
- !ruby/object:Gem::Version
|
53
|
+
version: 4.0.0.beta
|
54
|
+
type: :runtime
|
55
|
+
prerelease: false
|
56
|
+
version_requirements: !ruby/object:Gem::Requirement
|
57
|
+
none: false
|
58
|
+
requirements:
|
59
|
+
- - ! '>='
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: 4.0.0.beta
|
62
|
+
- !ruby/object:Gem::Dependency
|
63
|
+
name: activemodel
|
64
|
+
requirement: !ruby/object:Gem::Requirement
|
65
|
+
none: false
|
66
|
+
requirements:
|
67
|
+
- - ! '>='
|
68
|
+
- !ruby/object:Gem::Version
|
69
|
+
version: 4.0.0.beta
|
70
|
+
type: :runtime
|
71
|
+
prerelease: false
|
72
|
+
version_requirements: !ruby/object:Gem::Requirement
|
73
|
+
none: false
|
74
|
+
requirements:
|
75
|
+
- - ! '>='
|
76
|
+
- !ruby/object:Gem::Version
|
77
|
+
version: 4.0.0.beta
|
78
|
+
- !ruby/object:Gem::Dependency
|
79
|
+
name: abc
|
80
|
+
requirement: !ruby/object:Gem::Requirement
|
81
|
+
none: false
|
82
|
+
requirements:
|
83
|
+
- - '='
|
84
|
+
- !ruby/object:Gem::Version
|
85
|
+
version: 0.0.1
|
86
|
+
type: :runtime
|
87
|
+
prerelease: false
|
88
|
+
version_requirements: !ruby/object:Gem::Requirement
|
89
|
+
none: false
|
90
|
+
requirements:
|
91
|
+
- - '='
|
92
|
+
- !ruby/object:Gem::Version
|
93
|
+
version: 0.0.1
|
94
|
+
- !ruby/object:Gem::Dependency
|
95
|
+
name: abc-core
|
96
|
+
requirement: !ruby/object:Gem::Requirement
|
97
|
+
none: false
|
98
|
+
requirements:
|
99
|
+
- - '='
|
100
|
+
- !ruby/object:Gem::Version
|
101
|
+
version: 0.0.1
|
102
|
+
type: :runtime
|
103
|
+
prerelease: false
|
104
|
+
version_requirements: !ruby/object:Gem::Requirement
|
105
|
+
none: false
|
106
|
+
requirements:
|
107
|
+
- - '='
|
108
|
+
- !ruby/object:Gem::Version
|
109
|
+
version: 0.0.1
|
110
|
+
description: An easy-to-use, easy-to-extend CMS.
|
111
|
+
email:
|
112
|
+
- info@afterburnercms.com
|
113
|
+
executables: []
|
114
|
+
extensions: []
|
115
|
+
extra_rdoc_files: []
|
116
|
+
files:
|
117
|
+
- app/views/abc/backend/base/index.html.erb
|
118
|
+
- app/controllers/abc/backend/base_controller.rb
|
119
|
+
- app/controllers/abc/application_controller.rb
|
120
|
+
- app/presenters/abc/html/menu_presenter.rb
|
121
|
+
- app/presenters/abc/html/menu_entry_presenter.rb
|
122
|
+
- lib/abc-backend.rb
|
123
|
+
- lib/abc/backend/engine.rb
|
124
|
+
- config/routes.rb
|
125
|
+
- spec/tiny_spec_helper.rb
|
126
|
+
- spec/presenters/html/menu_presenter_spec.rb
|
127
|
+
- spec/presenters/html/menu_entry_presenter_spec.rb
|
128
|
+
- spec/spec_helper.rb
|
129
|
+
- spec/integration/backend_spec.rb
|
130
|
+
- spec/integration/menu_spec.rb
|
131
|
+
- spec/internal/log/test.log
|
132
|
+
- spec/internal/public/favicon.ico
|
133
|
+
- spec/internal/db/schema.rb
|
134
|
+
- spec/internal/config/database.yml
|
135
|
+
- spec/internal/config/routes.rb
|
136
|
+
homepage: http://www.afterburnercms.com/
|
137
|
+
licenses: []
|
138
|
+
post_install_message:
|
139
|
+
rdoc_options: []
|
140
|
+
require_paths:
|
141
|
+
- lib
|
142
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
143
|
+
none: false
|
144
|
+
requirements:
|
145
|
+
- - ! '>='
|
146
|
+
- !ruby/object:Gem::Version
|
147
|
+
version: 1.9.3
|
148
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
149
|
+
none: false
|
150
|
+
requirements:
|
151
|
+
- - ! '>='
|
152
|
+
- !ruby/object:Gem::Version
|
153
|
+
version: '0'
|
154
|
+
segments:
|
155
|
+
- 0
|
156
|
+
hash: -3377373757513260239
|
157
|
+
requirements: []
|
158
|
+
rubyforge_project:
|
159
|
+
rubygems_version: 1.8.24
|
160
|
+
signing_key:
|
161
|
+
specification_version: 3
|
162
|
+
summary: An easy-to-use, easy-to-extend CMS.
|
163
|
+
test_files:
|
164
|
+
- spec/tiny_spec_helper.rb
|
165
|
+
- spec/presenters/html/menu_presenter_spec.rb
|
166
|
+
- spec/presenters/html/menu_entry_presenter_spec.rb
|
167
|
+
- spec/spec_helper.rb
|
168
|
+
- spec/integration/backend_spec.rb
|
169
|
+
- spec/integration/menu_spec.rb
|
170
|
+
- spec/internal/log/test.log
|
171
|
+
- spec/internal/public/favicon.ico
|
172
|
+
- spec/internal/db/schema.rb
|
173
|
+
- spec/internal/config/database.yml
|
174
|
+
- spec/internal/config/routes.rb
|
175
|
+
has_rdoc:
|