actionmailbox 6.0.0.beta1

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 (55) hide show
  1. checksums.yaml +7 -0
  2. data/CHANGELOG.md +5 -0
  3. data/MIT-LICENSE +21 -0
  4. data/README.md +13 -0
  5. data/app/controllers/action_mailbox/base_controller.rb +38 -0
  6. data/app/controllers/action_mailbox/ingresses/amazon/inbound_emails_controller.rb +54 -0
  7. data/app/controllers/action_mailbox/ingresses/mailgun/inbound_emails_controller.rb +103 -0
  8. data/app/controllers/action_mailbox/ingresses/mandrill/inbound_emails_controller.rb +82 -0
  9. data/app/controllers/action_mailbox/ingresses/postmark/inbound_emails_controller.rb +62 -0
  10. data/app/controllers/action_mailbox/ingresses/relay/inbound_emails_controller.rb +65 -0
  11. data/app/controllers/action_mailbox/ingresses/sendgrid/inbound_emails_controller.rb +54 -0
  12. data/app/controllers/rails/conductor/action_mailbox/inbound_emails_controller.rb +34 -0
  13. data/app/controllers/rails/conductor/action_mailbox/reroutes_controller.rb +19 -0
  14. data/app/controllers/rails/conductor/base_controller.rb +14 -0
  15. data/app/jobs/action_mailbox/incineration_job.rb +22 -0
  16. data/app/jobs/action_mailbox/routing_job.rb +13 -0
  17. data/app/models/action_mailbox/inbound_email.rb +49 -0
  18. data/app/models/action_mailbox/inbound_email/incineratable.rb +20 -0
  19. data/app/models/action_mailbox/inbound_email/incineratable/incineration.rb +26 -0
  20. data/app/models/action_mailbox/inbound_email/message_id.rb +38 -0
  21. data/app/models/action_mailbox/inbound_email/routable.rb +24 -0
  22. data/app/views/layouts/rails/conductor.html.erb +7 -0
  23. data/app/views/rails/conductor/action_mailbox/inbound_emails/index.html.erb +15 -0
  24. data/app/views/rails/conductor/action_mailbox/inbound_emails/new.html.erb +47 -0
  25. data/app/views/rails/conductor/action_mailbox/inbound_emails/show.html.erb +15 -0
  26. data/config/routes.rb +20 -0
  27. data/db/migrate/20180917164000_create_action_mailbox_tables.rb +17 -0
  28. data/lib/action_mailbox.rb +16 -0
  29. data/lib/action_mailbox/base.rb +118 -0
  30. data/lib/action_mailbox/callbacks.rb +34 -0
  31. data/lib/action_mailbox/engine.rb +42 -0
  32. data/lib/action_mailbox/gem_version.rb +17 -0
  33. data/lib/action_mailbox/mail_ext.rb +6 -0
  34. data/lib/action_mailbox/mail_ext/address_equality.rb +9 -0
  35. data/lib/action_mailbox/mail_ext/address_wrapping.rb +9 -0
  36. data/lib/action_mailbox/mail_ext/addresses.rb +29 -0
  37. data/lib/action_mailbox/mail_ext/from_source.rb +7 -0
  38. data/lib/action_mailbox/mail_ext/recipients.rb +9 -0
  39. data/lib/action_mailbox/relayer.rb +75 -0
  40. data/lib/action_mailbox/router.rb +42 -0
  41. data/lib/action_mailbox/router/route.rb +42 -0
  42. data/lib/action_mailbox/routing.rb +22 -0
  43. data/lib/action_mailbox/test_case.rb +12 -0
  44. data/lib/action_mailbox/test_helper.rb +44 -0
  45. data/lib/action_mailbox/version.rb +10 -0
  46. data/lib/rails/generators/installer.rb +10 -0
  47. data/lib/rails/generators/mailbox/USAGE +12 -0
  48. data/lib/rails/generators/mailbox/mailbox_generator.rb +32 -0
  49. data/lib/rails/generators/mailbox/templates/application_mailbox.rb.tt +3 -0
  50. data/lib/rails/generators/mailbox/templates/mailbox.rb.tt +4 -0
  51. data/lib/rails/generators/test_unit/mailbox_generator.rb +20 -0
  52. data/lib/rails/generators/test_unit/templates/mailbox_test.rb.tt +13 -0
  53. data/lib/tasks/ingress.rake +72 -0
  54. data/lib/tasks/install.rake +20 -0
  55. metadata +184 -0
@@ -0,0 +1,22 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ActionMailbox
4
+ # See +ActionMailbox::Base+ for how to specify routing.
5
+ module Routing
6
+ extend ActiveSupport::Concern
7
+
8
+ included do
9
+ cattr_accessor :router, default: ActionMailbox::Router.new
10
+ end
11
+
12
+ class_methods do
13
+ def routing(routes)
14
+ router.add_routes(routes)
15
+ end
16
+
17
+ def route(inbound_email)
18
+ router.route(inbound_email)
19
+ end
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,12 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "action_mailbox/test_helper"
4
+ require "active_support/test_case"
5
+
6
+ module ActionMailbox
7
+ class TestCase < ActiveSupport::TestCase
8
+ include ActionMailbox::TestHelper
9
+ end
10
+ end
11
+
12
+ ActiveSupport.run_load_hooks :action_mailbox_test_case, ActionMailbox::TestCase
@@ -0,0 +1,44 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "mail"
4
+
5
+ module ActionMailbox
6
+ module TestHelper
7
+ # Create an +InboundEmail+ record using an eml fixture in the format of message/rfc822
8
+ # referenced with +fixture_name+ located in +test/fixtures/files/fixture_name+.
9
+ def create_inbound_email_from_fixture(fixture_name, status: :processing)
10
+ create_inbound_email_from_source file_fixture(fixture_name).read, status: status
11
+ end
12
+
13
+ # Create an +InboundEmail+ by specifying it using +Mail.new+ options. Example:
14
+ #
15
+ # create_inbound_email_from_mail(from: "david@loudthinking.com", subject: "Hello!")
16
+ def create_inbound_email_from_mail(status: :processing, **mail_options)
17
+ create_inbound_email_from_source Mail.new(mail_options).to_s, status: status
18
+ end
19
+
20
+ # Create an +InboundEmail+ using the raw rfc822 +source+ as text.
21
+ def create_inbound_email_from_source(source, status: :processing)
22
+ ActionMailbox::InboundEmail.create_and_extract_message_id! source, status: status
23
+ end
24
+
25
+
26
+ # Create an +InboundEmail+ from fixture using the same arguments as +create_inbound_email_from_fixture+
27
+ # and immediately route it to processing.
28
+ def receive_inbound_email_from_fixture(*args)
29
+ create_inbound_email_from_fixture(*args).tap(&:route)
30
+ end
31
+
32
+ # Create an +InboundEmail+ from fixture using the same arguments as +create_inbound_email_from_mail+
33
+ # and immediately route it to processing.
34
+ def receive_inbound_email_from_mail(**kwargs)
35
+ create_inbound_email_from_mail(**kwargs).tap(&:route)
36
+ end
37
+
38
+ # Create an +InboundEmail+ from fixture using the same arguments as +create_inbound_email_from_source+
39
+ # and immediately route it to processing.
40
+ def receive_inbound_email_from_source(**kwargs)
41
+ create_inbound_email_from_source(**kwargs).tap(&:route)
42
+ end
43
+ end
44
+ end
@@ -0,0 +1,10 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative "gem_version"
4
+
5
+ module ActionMailbox
6
+ # Returns the currently-loaded version of Action Mailbox as a <tt>Gem::Version</tt>.
7
+ def self.version
8
+ gem_version
9
+ end
10
+ end
@@ -0,0 +1,10 @@
1
+ # frozen_string_literal: true
2
+
3
+ say "Copying application_mailbox.rb to app/mailboxes"
4
+ copy_file "#{__dir__}/mailbox/templates/application_mailbox.rb", "app/mailboxes/application_mailbox.rb"
5
+
6
+ environment <<~end_of_config, env: "production"
7
+ # Prepare the ingress controller used to receive mail
8
+ # config.action_mailbox.ingress = :amazon
9
+
10
+ end_of_config
@@ -0,0 +1,12 @@
1
+ Description:
2
+ ============
3
+ Stubs out a new mailbox class in app/mailboxes and invokes your template
4
+ engine and test framework generators.
5
+
6
+ Example:
7
+ ========
8
+ rails generate mailbox inbox
9
+
10
+ creates a InboxMailbox class and test:
11
+ Mailbox: app/mailboxes/inbox_mailbox.rb
12
+ Test: test/mailboxes/inbox_mailbox_test.rb
@@ -0,0 +1,32 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Rails
4
+ module Generators
5
+ class MailboxGenerator < NamedBase
6
+ source_root File.expand_path("templates", __dir__)
7
+
8
+ check_class_collision suffix: "Mailbox"
9
+
10
+ def create_mailbox_file
11
+ template "mailbox.rb", File.join("app/mailboxes", class_path, "#{file_name}_mailbox.rb")
12
+
13
+ in_root do
14
+ if behavior == :invoke && !File.exist?(application_mailbox_file_name)
15
+ template "application_mailbox.rb", application_mailbox_file_name
16
+ end
17
+ end
18
+ end
19
+
20
+ hook_for :test_framework
21
+
22
+ private
23
+ def file_name # :doc:
24
+ @_file_name ||= super.sub(/_mailbox\z/i, "")
25
+ end
26
+
27
+ def application_mailbox_file_name
28
+ "app/mailboxes/application_mailbox.rb"
29
+ end
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,3 @@
1
+ class ApplicationMailbox < ActionMailbox::Base
2
+ # routing /something/i => :somewhere
3
+ end
@@ -0,0 +1,4 @@
1
+ class <%= class_name %>Mailbox < ApplicationMailbox
2
+ def process
3
+ end
4
+ end
@@ -0,0 +1,20 @@
1
+ # frozen_string_literal: true
2
+
3
+ module TestUnit
4
+ module Generators
5
+ class MailboxGenerator < ::Rails::Generators::NamedBase
6
+ source_root File.expand_path("templates", __dir__)
7
+
8
+ check_class_collision suffix: "MailboxTest"
9
+
10
+ def create_test_files
11
+ template "mailbox_test.rb", File.join("test/mailboxes", class_path, "#{file_name}_mailbox_test.rb")
12
+ end
13
+
14
+ private
15
+ def file_name # :doc:
16
+ @_file_name ||= super.sub(/_mailbox\z/i, "")
17
+ end
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,13 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "test_helper"
4
+
5
+ class <%= class_name %>MailboxTest < ActionMailbox::TestCase
6
+ # test "receive mail" do
7
+ # receive_inbound_email_from_mail \
8
+ # to: '"someone" <someone@example.com>',
9
+ # from: '"else" <else@example.com>',
10
+ # subject: "Hello world!",
11
+ # body: "Hello?"
12
+ # end
13
+ end
@@ -0,0 +1,72 @@
1
+ # frozen_string_literal: true
2
+
3
+ namespace :action_mailbox do
4
+ namespace :ingress do
5
+ task :environment do
6
+ require "active_support"
7
+ require "active_support/core_ext/object/blank"
8
+ require "action_mailbox/relayer"
9
+ end
10
+
11
+ desc "Relay an inbound email from Exim to Action Mailbox (URL and INGRESS_PASSWORD required)"
12
+ task exim: "action_mailbox:ingress:environment" do
13
+ url, password = ENV.values_at("URL", "INGRESS_PASSWORD")
14
+
15
+ if url.blank? || password.blank?
16
+ print "URL and INGRESS_PASSWORD are required"
17
+ exit 64 # EX_USAGE
18
+ end
19
+
20
+ ActionMailbox::Relayer.new(url: url, password: password).relay(STDIN.read).tap do |result|
21
+ print result.message
22
+
23
+ case
24
+ when result.success?
25
+ exit 0
26
+ when result.transient_failure?
27
+ exit 75 # EX_TEMPFAIL
28
+ else
29
+ exit 69 # EX_UNAVAILABLE
30
+ end
31
+ end
32
+ end
33
+
34
+ desc "Relay an inbound email from Postfix to Action Mailbox (URL and INGRESS_PASSWORD required)"
35
+ task postfix: "action_mailbox:ingress:environment" do
36
+ url, password = ENV.values_at("URL", "INGRESS_PASSWORD")
37
+
38
+ if url.blank? || password.blank?
39
+ print "4.3.5 URL and INGRESS_PASSWORD are required"
40
+ exit 1
41
+ end
42
+
43
+ ActionMailbox::Relayer.new(url: url, password: password).relay(STDIN.read).tap do |result|
44
+ print "#{result.status_code} #{result.message}"
45
+ exit result.success?
46
+ end
47
+ end
48
+
49
+ desc "Relay an inbound email from Qmail to Action Mailbox (URL and INGRESS_PASSWORD required)"
50
+ task qmail: "action_mailbox:ingress:environment" do
51
+ url, password = ENV.values_at("URL", "INGRESS_PASSWORD")
52
+
53
+ if url.blank? || password.blank?
54
+ print "URL and INGRESS_PASSWORD are required"
55
+ exit 111
56
+ end
57
+
58
+ ActionMailbox::Relayer.new(url: url, password: password).relay(STDIN.read).tap do |result|
59
+ print result.message
60
+
61
+ case
62
+ when result.success?
63
+ exit 0
64
+ when result.transient_failure?
65
+ exit 111
66
+ else
67
+ exit 100
68
+ end
69
+ end
70
+ end
71
+ end
72
+ end
@@ -0,0 +1,20 @@
1
+ # frozen_string_literal: true
2
+
3
+ namespace :action_mailbox do
4
+ # Prevent migration installation task from showing up twice.
5
+ Rake::Task["install:migrations"].clear_comments
6
+
7
+ desc "Copy over the migration"
8
+ task install: %w[ environment run_installer copy_migrations ]
9
+
10
+ task :run_installer do
11
+ installer_template = File.expand_path("../rails/generators/installer.rb", __dir__)
12
+ system "#{RbConfig.ruby} ./bin/rails app:template LOCATION=#{installer_template}"
13
+ end
14
+
15
+ task :copy_migrations do
16
+ Rake::Task["active_storage:install:migrations"].invoke
17
+ Rake::Task["railties:install:migrations"].reenable # Otherwise you can't run 2 migration copy tasks in one invocation
18
+ Rake::Task["action_mailbox:install:migrations"].invoke
19
+ end
20
+ end
metadata ADDED
@@ -0,0 +1,184 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: actionmailbox
3
+ version: !ruby/object:Gem::Version
4
+ version: 6.0.0.beta1
5
+ platform: ruby
6
+ authors:
7
+ - David Heinemeier Hansson
8
+ - George Claghorn
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2019-01-18 00:00:00.000000000 Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: activesupport
16
+ requirement: !ruby/object:Gem::Requirement
17
+ requirements:
18
+ - - '='
19
+ - !ruby/object:Gem::Version
20
+ version: 6.0.0.beta1
21
+ type: :runtime
22
+ prerelease: false
23
+ version_requirements: !ruby/object:Gem::Requirement
24
+ requirements:
25
+ - - '='
26
+ - !ruby/object:Gem::Version
27
+ version: 6.0.0.beta1
28
+ - !ruby/object:Gem::Dependency
29
+ name: activerecord
30
+ requirement: !ruby/object:Gem::Requirement
31
+ requirements:
32
+ - - '='
33
+ - !ruby/object:Gem::Version
34
+ version: 6.0.0.beta1
35
+ type: :runtime
36
+ prerelease: false
37
+ version_requirements: !ruby/object:Gem::Requirement
38
+ requirements:
39
+ - - '='
40
+ - !ruby/object:Gem::Version
41
+ version: 6.0.0.beta1
42
+ - !ruby/object:Gem::Dependency
43
+ name: activestorage
44
+ requirement: !ruby/object:Gem::Requirement
45
+ requirements:
46
+ - - '='
47
+ - !ruby/object:Gem::Version
48
+ version: 6.0.0.beta1
49
+ type: :runtime
50
+ prerelease: false
51
+ version_requirements: !ruby/object:Gem::Requirement
52
+ requirements:
53
+ - - '='
54
+ - !ruby/object:Gem::Version
55
+ version: 6.0.0.beta1
56
+ - !ruby/object:Gem::Dependency
57
+ name: activejob
58
+ requirement: !ruby/object:Gem::Requirement
59
+ requirements:
60
+ - - '='
61
+ - !ruby/object:Gem::Version
62
+ version: 6.0.0.beta1
63
+ type: :runtime
64
+ prerelease: false
65
+ version_requirements: !ruby/object:Gem::Requirement
66
+ requirements:
67
+ - - '='
68
+ - !ruby/object:Gem::Version
69
+ version: 6.0.0.beta1
70
+ - !ruby/object:Gem::Dependency
71
+ name: actionpack
72
+ requirement: !ruby/object:Gem::Requirement
73
+ requirements:
74
+ - - '='
75
+ - !ruby/object:Gem::Version
76
+ version: 6.0.0.beta1
77
+ type: :runtime
78
+ prerelease: false
79
+ version_requirements: !ruby/object:Gem::Requirement
80
+ requirements:
81
+ - - '='
82
+ - !ruby/object:Gem::Version
83
+ version: 6.0.0.beta1
84
+ - !ruby/object:Gem::Dependency
85
+ name: mail
86
+ requirement: !ruby/object:Gem::Requirement
87
+ requirements:
88
+ - - ">="
89
+ - !ruby/object:Gem::Version
90
+ version: 2.7.1
91
+ type: :runtime
92
+ prerelease: false
93
+ version_requirements: !ruby/object:Gem::Requirement
94
+ requirements:
95
+ - - ">="
96
+ - !ruby/object:Gem::Version
97
+ version: 2.7.1
98
+ description: Receive and process incoming emails in Rails applications.
99
+ email:
100
+ - david@loudthinking.com
101
+ - george@basecamp.com
102
+ executables: []
103
+ extensions: []
104
+ extra_rdoc_files: []
105
+ files:
106
+ - CHANGELOG.md
107
+ - MIT-LICENSE
108
+ - README.md
109
+ - app/controllers/action_mailbox/base_controller.rb
110
+ - app/controllers/action_mailbox/ingresses/amazon/inbound_emails_controller.rb
111
+ - app/controllers/action_mailbox/ingresses/mailgun/inbound_emails_controller.rb
112
+ - app/controllers/action_mailbox/ingresses/mandrill/inbound_emails_controller.rb
113
+ - app/controllers/action_mailbox/ingresses/postmark/inbound_emails_controller.rb
114
+ - app/controllers/action_mailbox/ingresses/relay/inbound_emails_controller.rb
115
+ - app/controllers/action_mailbox/ingresses/sendgrid/inbound_emails_controller.rb
116
+ - app/controllers/rails/conductor/action_mailbox/inbound_emails_controller.rb
117
+ - app/controllers/rails/conductor/action_mailbox/reroutes_controller.rb
118
+ - app/controllers/rails/conductor/base_controller.rb
119
+ - app/jobs/action_mailbox/incineration_job.rb
120
+ - app/jobs/action_mailbox/routing_job.rb
121
+ - app/models/action_mailbox/inbound_email.rb
122
+ - app/models/action_mailbox/inbound_email/incineratable.rb
123
+ - app/models/action_mailbox/inbound_email/incineratable/incineration.rb
124
+ - app/models/action_mailbox/inbound_email/message_id.rb
125
+ - app/models/action_mailbox/inbound_email/routable.rb
126
+ - app/views/layouts/rails/conductor.html.erb
127
+ - app/views/rails/conductor/action_mailbox/inbound_emails/index.html.erb
128
+ - app/views/rails/conductor/action_mailbox/inbound_emails/new.html.erb
129
+ - app/views/rails/conductor/action_mailbox/inbound_emails/show.html.erb
130
+ - config/routes.rb
131
+ - db/migrate/20180917164000_create_action_mailbox_tables.rb
132
+ - lib/action_mailbox.rb
133
+ - lib/action_mailbox/base.rb
134
+ - lib/action_mailbox/callbacks.rb
135
+ - lib/action_mailbox/engine.rb
136
+ - lib/action_mailbox/gem_version.rb
137
+ - lib/action_mailbox/mail_ext.rb
138
+ - lib/action_mailbox/mail_ext/address_equality.rb
139
+ - lib/action_mailbox/mail_ext/address_wrapping.rb
140
+ - lib/action_mailbox/mail_ext/addresses.rb
141
+ - lib/action_mailbox/mail_ext/from_source.rb
142
+ - lib/action_mailbox/mail_ext/recipients.rb
143
+ - lib/action_mailbox/relayer.rb
144
+ - lib/action_mailbox/router.rb
145
+ - lib/action_mailbox/router/route.rb
146
+ - lib/action_mailbox/routing.rb
147
+ - lib/action_mailbox/test_case.rb
148
+ - lib/action_mailbox/test_helper.rb
149
+ - lib/action_mailbox/version.rb
150
+ - lib/rails/generators/installer.rb
151
+ - lib/rails/generators/mailbox/USAGE
152
+ - lib/rails/generators/mailbox/mailbox_generator.rb
153
+ - lib/rails/generators/mailbox/templates/application_mailbox.rb.tt
154
+ - lib/rails/generators/mailbox/templates/mailbox.rb.tt
155
+ - lib/rails/generators/test_unit/mailbox_generator.rb
156
+ - lib/rails/generators/test_unit/templates/mailbox_test.rb.tt
157
+ - lib/tasks/ingress.rake
158
+ - lib/tasks/install.rake
159
+ homepage: https://rubyonrails.org
160
+ licenses:
161
+ - MIT
162
+ metadata:
163
+ source_code_uri: https://github.com/rails/rails/tree/v6.0.0.beta1/actionmailbox
164
+ changelog_uri: https://github.com/rails/rails/blob/v6.0.0.beta1/actionmailbox/CHANGELOG.md
165
+ post_install_message:
166
+ rdoc_options: []
167
+ require_paths:
168
+ - lib
169
+ required_ruby_version: !ruby/object:Gem::Requirement
170
+ requirements:
171
+ - - ">="
172
+ - !ruby/object:Gem::Version
173
+ version: 2.5.0
174
+ required_rubygems_version: !ruby/object:Gem::Requirement
175
+ requirements:
176
+ - - ">"
177
+ - !ruby/object:Gem::Version
178
+ version: 1.3.1
179
+ requirements: []
180
+ rubygems_version: 3.0.1
181
+ signing_key:
182
+ specification_version: 4
183
+ summary: Inbound email handling framework.
184
+ test_files: []