mail_view 1.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (3) hide show
  1. data/lib/mail_view.rb +91 -0
  2. data/test/test_mail_view.rb +123 -0
  3. metadata +46 -0
@@ -0,0 +1,91 @@
1
+ require 'erb'
2
+ require 'tilt'
3
+
4
+ require 'rack/mime'
5
+
6
+ class MailView
7
+ autoload :Mapper, 'mail_view/mapper'
8
+
9
+ class << self
10
+ def default_email_template_path
11
+ File.expand_path('../mail_view/email.html.erb', __FILE__)
12
+ end
13
+
14
+ def default_index_template_path
15
+ File.expand_path('../mail_view/index.html.erb', __FILE__)
16
+ end
17
+
18
+ def call(env)
19
+ new.call(env)
20
+ end
21
+ end
22
+
23
+ def call(env)
24
+ path_info = env["PATH_INFO"]
25
+
26
+ if path_info == "" || path_info == "/"
27
+ links = self.actions.inject({}) { |h, action|
28
+ h[action] = "#{env["SCRIPT_NAME"]}/#{action}"
29
+ h
30
+ }
31
+
32
+ ok index_template.render(Object.new, :links => links)
33
+ elsif path_info =~ /([\w_]+)(\.\w+)?$/
34
+ name = $1
35
+ format = $2 || ".html"
36
+
37
+ if actions.include?(name)
38
+ ok render_mail(name, send(name), format)
39
+ else
40
+ not_found
41
+ end
42
+ else
43
+ not_found(true)
44
+ end
45
+ end
46
+
47
+ protected
48
+ def actions
49
+ public_methods(false).map(&:to_s) - ['call']
50
+ end
51
+
52
+ def email_template
53
+ Tilt.new(email_template_path)
54
+ end
55
+
56
+ def email_template_path
57
+ self.class.default_email_template_path
58
+ end
59
+
60
+ def index_template
61
+ Tilt.new(index_template_path)
62
+ end
63
+
64
+ def index_template_path
65
+ self.class.default_index_template_path
66
+ end
67
+
68
+ private
69
+ def ok(body)
70
+ [200, {"Content-Type" => "text/html"}, [body]]
71
+ end
72
+
73
+ def not_found(pass = false)
74
+ if pass
75
+ [404, {"Content-Type" => "text/html", "X-Cascade" => "pass"}, ["Not Found"]]
76
+ else
77
+ [404, {"Content-Type" => "text/html"}, ["Not Found"]]
78
+ end
79
+ end
80
+
81
+ def render_mail(name, mail, format = nil)
82
+ body_part = mail
83
+
84
+ if mail.multipart?
85
+ content_type = Rack::Mime.mime_type(format)
86
+ body_part = mail.parts.find { |part| part.content_type.match(content_type) } || mail.parts.first
87
+ end
88
+
89
+ email_template.render(Object.new, :name => name, :mail => mail, :body_part => body_part)
90
+ end
91
+ end
@@ -0,0 +1,123 @@
1
+ require 'test/unit'
2
+ require 'rack/test'
3
+
4
+ require 'mail_view'
5
+ require 'mail'
6
+
7
+ require 'tmail'
8
+
9
+ class TestMailView < Test::Unit::TestCase
10
+ include Rack::Test::Methods
11
+
12
+ class Preview < MailView
13
+ def plain_text_message
14
+ Mail.new do
15
+ to 'josh@37signals.com'
16
+ body 'Hello'
17
+ end
18
+ end
19
+
20
+ def html_message
21
+ Mail.new do
22
+ to 'josh@37signals.com'
23
+
24
+ content_type 'text/html; charset=UTF-8'
25
+ body '<h1>Hello</h1>'
26
+ end
27
+ end
28
+
29
+ def tmail_html_message
30
+ TMail::Mail.parse(html_message.to_s)
31
+ end
32
+
33
+ def multipart_alternative
34
+ Mail.new do
35
+ to 'josh@37signals.com'
36
+
37
+ text_part do
38
+ body 'This is plain text'
39
+ end
40
+
41
+ html_part do
42
+ content_type 'text/html; charset=UTF-8'
43
+ body '<h1>This is HTML</h1>'
44
+ end
45
+ end
46
+ end
47
+
48
+ def tmail_multipart_alternative
49
+ TMail::Mail.parse(multipart_alternative.to_s)
50
+ end
51
+ end
52
+
53
+ def app
54
+ Preview
55
+ end
56
+
57
+ def test_index
58
+ get '/'
59
+ assert last_response.ok?
60
+
61
+ assert_match(/plain_text_message/, last_response.body)
62
+ assert_match(/html_message/, last_response.body)
63
+ assert_match(/multipart_alternative/, last_response.body)
64
+ end
65
+
66
+ def test_not_found
67
+ get '/missing'
68
+ assert last_response.not_found?
69
+ end
70
+
71
+ def test_plain_text_message
72
+ get '/plain_text_message'
73
+ assert last_response.ok?
74
+
75
+ assert_match(/Hello/, last_response.body)
76
+ end
77
+
78
+ def test_html_message
79
+ get '/html_message'
80
+ assert last_response.ok?
81
+
82
+ assert_match(/<h1>Hello<\/h1>/, last_response.body)
83
+ end
84
+
85
+ def test_multipart_alternative
86
+ get '/multipart_alternative'
87
+ assert last_response.ok?
88
+
89
+ assert_match(/<h1>This is HTML<\/h1>/, last_response.body)
90
+ assert_match(/View plain text version/, last_response.body)
91
+ end
92
+
93
+ def test_multipart_alternative_as_html
94
+ get '/multipart_alternative.html'
95
+ assert last_response.ok?
96
+
97
+ assert_match(/<h1>This is HTML<\/h1>/, last_response.body)
98
+ assert_match(/View plain text version/, last_response.body)
99
+ end
100
+
101
+ def test_multipart_alternative_as_text
102
+ get '/multipart_alternative.txt'
103
+ assert last_response.ok?
104
+
105
+ assert_match(/This is plain text/, last_response.body)
106
+ assert_match(/View HTML version/, last_response.body)
107
+ end
108
+
109
+ def test_tmail_html_message
110
+ get '/tmail_html_message'
111
+ assert last_response.ok?
112
+
113
+ assert_match(/<h1>Hello<\/h1>/, last_response.body)
114
+ end
115
+
116
+ def test_tmail_multipart_alternative
117
+ get '/tmail_multipart_alternative'
118
+ assert last_response.ok?
119
+
120
+ assert_match(/<h1>This is HTML<\/h1>/, last_response.body)
121
+ assert_match(/View plain text version/, last_response.body)
122
+ end
123
+ end
metadata ADDED
@@ -0,0 +1,46 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: mail_view
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.1
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Josh Peek
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2011-11-07 00:00:00.000000000 Z
13
+ dependencies: []
14
+ description:
15
+ email: josh@joshpeek.com
16
+ executables: []
17
+ extensions: []
18
+ extra_rdoc_files: []
19
+ files:
20
+ - ./lib/mail_view.rb
21
+ - ./test/test_mail_view.rb
22
+ homepage: https://github.com/37signals/mail_view
23
+ licenses: []
24
+ post_install_message:
25
+ rdoc_options: []
26
+ require_paths:
27
+ - lib
28
+ required_ruby_version: !ruby/object:Gem::Requirement
29
+ none: false
30
+ requirements:
31
+ - - ! '>='
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ required_rubygems_version: !ruby/object:Gem::Requirement
35
+ none: false
36
+ requirements:
37
+ - - ! '>='
38
+ - !ruby/object:Gem::Version
39
+ version: '0'
40
+ requirements: []
41
+ rubyforge_project:
42
+ rubygems_version: 1.8.11
43
+ signing_key:
44
+ specification_version: 3
45
+ summary: Visual email testing
46
+ test_files: []