mailhandler 1.0.18 → 1.0.19
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.
- checksums.yaml +4 -4
- data/lib/mailhandler/receiving/base.rb +6 -0
- data/lib/mailhandler/receiving/file_filter/base.rb +32 -31
- data/lib/mailhandler/receiving/file_filter/filter.rb +59 -91
- data/lib/mailhandler/receiving/folder.rb +8 -8
- data/lib/mailhandler/version.rb +1 -1
- data/readme.md +7 -5
- data/spec/unit/mailhandler/receiving/folder_spec.rb +4 -5
- data/spec/unit/mailhandler/receiving/imap_spec.rb +2 -2
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: ecef71152a0c0d0fe88836302a0a1d21943aa982
|
4
|
+
data.tar.gz: cad86ec06626c41396a2c5cc62c458cc1206b28a
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 969fd41cda3bd806293f955545b8b424cbb3da04bbab0353267de32ecc3db2f06f7e09bf4c557e96c8ad03bc1244558582fb2a624002ad57d7b4c6668199d43d
|
7
|
+
data.tar.gz: 129595a692c4e5bed2cc34f6bba7099f419cec6ae76ffde2049a0e658867b432391b9059ef9eb97efad0f7f714fd3433faa16b00a608004e3124c430d905e9b9
|
@@ -87,6 +87,12 @@ module MailHandler
|
|
87
87
|
|
88
88
|
end
|
89
89
|
|
90
|
+
if options[:by_recipient]
|
91
|
+
|
92
|
+
raise MailHandler::Error, "Incorrect option options[:by_recipient]=#{options[:by_recipient]}." unless options[:by_recipient].is_a?(Hash)
|
93
|
+
|
94
|
+
end
|
95
|
+
|
90
96
|
end
|
91
97
|
|
92
98
|
def validate_used_options(options)
|
@@ -5,58 +5,59 @@ module MailHandler
|
|
5
5
|
|
6
6
|
module Receiving
|
7
7
|
|
8
|
-
|
8
|
+
class FileList
|
9
9
|
|
10
|
-
|
10
|
+
def self.get(pattern)
|
11
11
|
|
12
|
-
|
12
|
+
Dir.glob(pattern).map { |file| File.absolute_path(file) }
|
13
13
|
|
14
|
-
|
15
|
-
|
14
|
+
end
|
15
|
+
|
16
|
+
def self.sort(files)
|
16
17
|
|
17
|
-
|
18
|
+
swapped = true
|
19
|
+
j = 0
|
18
20
|
|
19
|
-
|
20
|
-
j+=1
|
21
|
+
while swapped do
|
21
22
|
|
22
|
-
|
23
|
+
swapped = false
|
24
|
+
j+=1
|
23
25
|
|
24
|
-
|
25
|
-
tmp = files[i]
|
26
|
-
files[i] = files[i + 1]
|
27
|
-
files[i + 1] = tmp
|
28
|
-
swapped = true
|
26
|
+
(files.size - j).times do |i|
|
29
27
|
|
30
|
-
|
28
|
+
if File.new(files[i]).ctime < File.new(files[i + 1]).ctime
|
29
|
+
tmp = files[i]
|
30
|
+
files[i] = files[i + 1]
|
31
|
+
files[i + 1] = tmp
|
32
|
+
swapped = true
|
31
33
|
|
32
34
|
end
|
33
35
|
|
34
36
|
end
|
35
37
|
|
36
|
-
files
|
37
|
-
|
38
38
|
end
|
39
39
|
|
40
|
-
|
41
|
-
|
42
|
-
files = []
|
43
|
-
Dir.glob(pattern).each { |file| files << File.absolute_path(file) }
|
44
|
-
files
|
40
|
+
files
|
45
41
|
|
46
|
-
|
42
|
+
end
|
47
43
|
|
48
|
-
|
44
|
+
end
|
49
45
|
|
50
|
-
|
46
|
+
end
|
51
47
|
|
52
|
-
|
48
|
+
end
|
53
49
|
|
54
|
-
|
50
|
+
=begin
|
55
51
|
|
56
|
-
|
52
|
+
TEST EXAMPLE
|
57
53
|
|
58
|
-
|
54
|
+
FileList.get('*.*')
|
55
|
+
FileList::Filter::ByEmailSubject.new(files,'subject').get
|
56
|
+
FileList::Filter::ByEmailContent.new(files,'content').get
|
57
|
+
FileList::Filter::ByEmailDate.new(files, date).get
|
58
|
+
FileList::Filter::ByEmailRecipient.new(files, recipient).get
|
59
59
|
|
60
|
-
|
60
|
+
f = FileList::Filter::ByEmailSubject.new(FileList.get("*.*"), "binding")
|
61
|
+
puts f.get
|
61
62
|
|
62
|
-
end
|
63
|
+
=end
|
@@ -5,166 +5,134 @@ module MailHandler
|
|
5
5
|
|
6
6
|
module Receiving
|
7
7
|
|
8
|
-
|
8
|
+
class FileList
|
9
9
|
|
10
|
-
|
10
|
+
module Filter
|
11
11
|
|
12
|
-
|
12
|
+
class Base
|
13
13
|
|
14
|
-
|
14
|
+
attr_accessor :files
|
15
15
|
|
16
|
-
|
17
|
-
|
18
|
-
end
|
19
|
-
|
20
|
-
class ContentBase < Base
|
21
|
-
|
22
|
-
def initialize(content)
|
23
|
-
|
24
|
-
@content = content.to_s
|
16
|
+
def initialize(files)
|
25
17
|
|
26
|
-
|
27
|
-
|
28
|
-
protected
|
18
|
+
@files=files
|
29
19
|
|
30
|
-
|
20
|
+
end
|
31
21
|
|
32
|
-
|
22
|
+
def get
|
33
23
|
|
34
|
-
|
24
|
+
files.select { |file| ignore_exception { meets_expectation?(file) } }
|
35
25
|
|
36
|
-
|
26
|
+
end
|
37
27
|
|
38
|
-
|
28
|
+
protected
|
39
29
|
|
40
|
-
|
41
|
-
false
|
30
|
+
def meet_expectation?(file)
|
42
31
|
|
43
|
-
|
32
|
+
raise StandardError, 'Needs to be implemented.'
|
44
33
|
|
45
34
|
end
|
46
35
|
|
47
|
-
|
36
|
+
def read_file(file)
|
48
37
|
|
49
|
-
|
38
|
+
# TODO: add UTF support
|
39
|
+
# string need to be read and converted
|
40
|
+
# read_email(file_content).subject.include?(@content) - 10x slower, use something else for reading
|
41
|
+
# Mail::Encodings.unquote_and_convert_to(content, "UTF-8") - 6x slower
|
42
|
+
File.read(file)
|
50
43
|
|
51
|
-
|
44
|
+
end
|
52
45
|
|
53
|
-
|
46
|
+
private
|
54
47
|
|
55
|
-
|
48
|
+
def ignore_exception
|
56
49
|
|
57
|
-
|
50
|
+
begin
|
58
51
|
|
59
|
-
|
52
|
+
yield
|
60
53
|
|
61
|
-
|
54
|
+
rescue
|
62
55
|
|
63
|
-
|
56
|
+
false
|
64
57
|
|
65
|
-
|
58
|
+
end
|
66
59
|
|
67
|
-
|
68
|
-
filter_files(files)
|
60
|
+
end
|
69
61
|
|
70
62
|
end
|
71
63
|
|
72
|
-
|
73
|
-
|
74
|
-
def file_match_filter?(file)
|
75
|
-
|
76
|
-
# TODO: add UTF support
|
77
|
-
# string need to be read and converted
|
78
|
-
# read_email(file_content).subject.include?(@content) - 10x slower, use something else for reading
|
79
|
-
# Mail::Encodings.unquote_and_convert_to(content, "UTF-8") - 6x slower
|
80
|
-
File.read(file).include? @content
|
64
|
+
class ByDate < Base
|
81
65
|
|
82
|
-
|
83
|
-
|
84
|
-
end
|
66
|
+
def initialize(files, date)
|
85
67
|
|
86
|
-
|
68
|
+
super(files)
|
69
|
+
@date = date
|
87
70
|
|
88
|
-
|
71
|
+
end
|
89
72
|
|
90
|
-
|
73
|
+
private
|
91
74
|
|
92
|
-
|
75
|
+
def meets_expectation?(file)
|
93
76
|
|
94
|
-
|
77
|
+
(File.exists? file)? (File.ctime file) > @date : false
|
95
78
|
|
96
|
-
|
97
|
-
filter_files(files)
|
79
|
+
end
|
98
80
|
|
99
81
|
end
|
100
82
|
|
101
|
-
|
83
|
+
class Email < Base
|
102
84
|
|
103
|
-
|
85
|
+
def initialize(files)
|
104
86
|
|
105
|
-
|
87
|
+
super(files)
|
106
88
|
|
107
|
-
|
89
|
+
end
|
108
90
|
|
109
|
-
|
91
|
+
protected
|
110
92
|
|
111
|
-
|
93
|
+
def read_email_from_file(file)
|
112
94
|
|
113
|
-
|
95
|
+
Mail.read(file)
|
114
96
|
|
115
|
-
|
97
|
+
end
|
116
98
|
|
117
99
|
end
|
118
100
|
|
119
|
-
|
120
|
-
|
121
|
-
files = super(pattern)
|
122
|
-
filter_files(files)
|
101
|
+
class ByEmailContent < Email
|
123
102
|
|
124
|
-
|
125
|
-
|
126
|
-
private
|
103
|
+
def initialize(files, content)
|
127
104
|
|
128
|
-
|
105
|
+
super(files)
|
106
|
+
@content = content
|
129
107
|
|
130
|
-
|
131
|
-
if file != nil
|
108
|
+
end
|
132
109
|
|
133
|
-
|
110
|
+
protected
|
134
111
|
|
135
|
-
|
112
|
+
def meets_expectation?(file)
|
136
113
|
|
137
|
-
|
114
|
+
read_file(file).include? @content
|
138
115
|
|
139
116
|
end
|
140
117
|
|
141
118
|
end
|
142
119
|
|
143
|
-
|
144
|
-
|
145
|
-
module Email
|
120
|
+
class ByEmailSubject < ByEmailContent ; end
|
146
121
|
|
147
|
-
class
|
122
|
+
class ByEmailRecipient < Email
|
148
123
|
|
149
|
-
def initialize(recipient)
|
124
|
+
def initialize(files, recipient)
|
150
125
|
|
126
|
+
super(files)
|
151
127
|
@recipient = recipient
|
152
128
|
|
153
129
|
end
|
154
130
|
|
155
|
-
def get(pattern)
|
156
|
-
|
157
|
-
files = super(pattern)
|
158
|
-
filter_files(files)
|
159
|
-
|
160
|
-
end
|
161
|
-
|
162
131
|
private
|
163
132
|
|
164
|
-
def
|
133
|
+
def meets_expectation?(file)
|
165
134
|
|
166
|
-
|
167
|
-
email[@recipient.keys.first].to_s.include? @recipient.values.first
|
135
|
+
read_email_from_file(file)[@recipient.keys.first].to_s.include? @recipient.values.first
|
168
136
|
|
169
137
|
end
|
170
138
|
|
@@ -45,10 +45,10 @@ module MailHandler
|
|
45
45
|
# filter options which need to be done by searching files
|
46
46
|
FILE_SEARCH_CLASSES = {
|
47
47
|
|
48
|
-
:by_subject => Filter::
|
49
|
-
:by_content => Filter::
|
50
|
-
:since => Filter::ByDate,
|
51
|
-
:by_recipient => Filter::
|
48
|
+
:by_subject => FileList::Filter::ByEmailSubject,
|
49
|
+
:by_content => FileList::Filter::ByEmailContent,
|
50
|
+
:since => FileList::Filter::ByDate,
|
51
|
+
:by_recipient => FileList::Filter::ByEmailRecipient
|
52
52
|
}
|
53
53
|
|
54
54
|
def search_pattern
|
@@ -59,7 +59,7 @@ module MailHandler
|
|
59
59
|
|
60
60
|
def read_found_emails(files, count)
|
61
61
|
|
62
|
-
files.first(count).map { |file| Mail.
|
62
|
+
files.first(count).map { |file| Mail.read(file ) }
|
63
63
|
|
64
64
|
end
|
65
65
|
|
@@ -67,15 +67,15 @@ module MailHandler
|
|
67
67
|
# this will ignore filter criteria options which can't be done on files directly
|
68
68
|
def find_files(options)
|
69
69
|
|
70
|
-
files =
|
70
|
+
files = FileList.get(search_pattern)
|
71
71
|
|
72
72
|
options.each do |key, value|
|
73
73
|
|
74
|
-
files =
|
74
|
+
files = FILE_SEARCH_CLASSES[key].new(files, value).get if FILE_SEARCH_CLASSES[key] != nil
|
75
75
|
|
76
76
|
end
|
77
77
|
|
78
|
-
|
78
|
+
FileList.sort(files)
|
79
79
|
|
80
80
|
end
|
81
81
|
|
data/lib/mailhandler/version.rb
CHANGED
data/readme.md
CHANGED
@@ -1,11 +1,13 @@
|
|
1
|
+
<img src="http://assets.wildbit.com/postmark/blog/images/mailhandler-logo.png" alt="MailHandler Logo" title="MailHandler" width="148" height="149">
|
2
|
+
|
1
3
|
# MailHandler Gem
|
2
4
|
|
3
5
|
[](https://travis-ci.org/wildbit/mailhandler)
|
4
6
|
|
5
|
-
MailHandler is a simple wrapper on top of [
|
7
|
+
MailHandler is a simple wrapper on top of [Mail gem](https://github.com/mikel/mail) and [Postmark gem](https://github.com/wildbit/postmark-gem) libraries. It allows you to send and retrieve emails and at the same time get details on how long these operations took.
|
6
8
|
Main purpose of the gem is easier email sending/delivery testing with notifications if sending or retrieving email is taking too long.
|
7
9
|
|
8
|
-
The library supports sending email by SMTP and Postmark API and checking email delivery by IMAP protocol, or by folder
|
10
|
+
The library supports sending email by SMTP and Postmark API and checking email delivery by IMAP protocol, or by folder if you have a local mailbox.
|
9
11
|
|
10
12
|
# Install the gem
|
11
13
|
|
@@ -32,8 +34,8 @@ Folders can be the same if you don't plan to archive found emails. Retrieving em
|
|
32
34
|
|
33
35
|
``` ruby
|
34
36
|
email_receiver = MailHandler.receiver(:folder) do |checker|
|
35
|
-
checker.inbox_folder =
|
36
|
-
checker.archive_folder =
|
37
|
+
checker.inbox_folder = '/folder/mailbox/'
|
38
|
+
checker.archive_folder = '/folder/mailbox/archive/'
|
37
39
|
end
|
38
40
|
```
|
39
41
|
|
@@ -126,7 +128,7 @@ email_sender = MailHandler.sender(type) do |dispatcher|
|
|
126
128
|
end
|
127
129
|
```
|
128
130
|
|
129
|
-
* `:type` - type can be `:postmark_api` or
|
131
|
+
* `:type` - type can be `:postmark_api` or `:postmark_batch_api`
|
130
132
|
* `:api_token` - api token of one of your Postmark sending servers
|
131
133
|
|
132
134
|
### Sending email by SMTP
|
@@ -22,14 +22,14 @@ describe MailHandler::Receiving::FolderChecker do
|
|
22
22
|
it 'by multiple search options' do
|
23
23
|
|
24
24
|
time = Time.now
|
25
|
-
checker.find({:by_subject => 'test', :by_content => 'test', :since => time, :by_recipient => 'igor@example.com'})
|
25
|
+
checker.find({:by_subject => 'test', :by_content => 'test', :since => time, :by_recipient => { :to => 'igor@example.com'}})
|
26
26
|
expect(checker.search_options).to eq(
|
27
27
|
{:count=>50,
|
28
28
|
:archive=>false,
|
29
29
|
:by_subject => 'test',
|
30
30
|
:by_content => 'test',
|
31
31
|
:since => time,
|
32
|
-
:by_recipient => 'igor@example.com'})
|
32
|
+
:by_recipient => {:to => 'igor@example.com'}})
|
33
33
|
|
34
34
|
end
|
35
35
|
|
@@ -78,8 +78,8 @@ describe MailHandler::Receiving::FolderChecker do
|
|
78
78
|
|
79
79
|
it 'by_recipient' do
|
80
80
|
|
81
|
-
checker.find({:by_recipient => 'igor@example.com'})
|
82
|
-
expect(checker.search_options).to eq({:count=>50, :archive=>false, :by_recipient => 'igor@example.com' })
|
81
|
+
checker.find({:by_recipient => {:to => 'igor@example.com'}})
|
82
|
+
expect(checker.search_options).to eq({:count=>50, :archive=>false, :by_recipient => {:to => 'igor@example.com' }})
|
83
83
|
|
84
84
|
end
|
85
85
|
|
@@ -321,5 +321,4 @@ describe MailHandler::Receiving::FolderChecker do
|
|
321
321
|
|
322
322
|
end
|
323
323
|
|
324
|
-
|
325
324
|
end
|
@@ -28,13 +28,13 @@ describe MailHandler::Receiving::IMAPChecker do
|
|
28
28
|
|
29
29
|
it 'by multiple search options' do
|
30
30
|
|
31
|
-
checker.find({:by_subject => 'test', :by_content => 'test', :by_recipient => 'igor@example.com'})
|
31
|
+
checker.find({:by_subject => 'test', :by_content => 'test', :by_recipient => {:to => 'igor@example.com'}})
|
32
32
|
expect(checker.search_options).to eq(
|
33
33
|
{:count=>50,
|
34
34
|
:archive=>false,
|
35
35
|
:by_subject => 'test',
|
36
36
|
:by_content => 'test',
|
37
|
-
:by_recipient => 'igor@example.com'})
|
37
|
+
:by_recipient => {:to => 'igor@example.com'}})
|
38
38
|
|
39
39
|
end
|
40
40
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: mailhandler
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.0.
|
4
|
+
version: 1.0.19
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Igor Balos
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2016-01-28 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: mail
|