hotmailer 1.0.0

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 (3) hide show
  1. data/README +98 -0
  2. data/lib/hotmailer.rb +263 -0
  3. metadata +63 -0
data/README ADDED
@@ -0,0 +1,98 @@
1
+ Hotmailer Library v0.1
2
+
3
+ The hotmailer library is used to programatically access your hotmail account. It depends on the 'mechanize' (and by extension 'hpricot') libraries.
4
+
5
+ The Hotmailer library contains two objects:
6
+
7
+ 1. WWW::Hotmailer - this is descended from WWW::Mechanize, but has been specialised for hotmail.
8
+ 2. Hotmailer::Message - This is the class for hotmail messages.
9
+
10
+
11
+ === WWW::Hotmailer
12
+
13
+ This contains the following methods.
14
+
15
+ - new(username,password) - Used for creating a new hotmailer object. Note that this will not login for you, but only initialize the object.
16
+
17
+ eg. zaphod = Hotmailer.new('zaphod@hotmail.com','chunkybacon')
18
+
19
+ - login - This logs in a hotmailer object to hotmail.
20
+
21
+ eg. zaphod.login
22
+
23
+ - contacts(reload=false) : this gets a list of your hotmail contacts, in the form of a list of hashes, each hash containing a :name, and an :email for that contact. The first time it gets the contacts it caches them to save time - passing reload=true to the function forces it to reload the contacts from hotmail.
24
+
25
+ eg. contacts = zaphod.contacts
26
+
27
+ contacts is now [{:name => "Ford Prefect",:email => "fprefect@bt.net"},{:name => "Trishia Macmillan",:email => "trillian@gmail.com"}]
28
+
29
+
30
+ - compose(to,subject,body) : This sends an email to the 'to' address, using subject and body.
31
+
32
+ - messages(reload=false) : This gets all the messages in your hotmail inbox. It returns an array of Hotmailer::Message objects. The first time it gets them it caches them and returns this cache on subsequent calls, unless you specify reload=true.
33
+
34
+ eg. messages = zaphod.messages(true)
35
+
36
+ - add_contact(quickname,email,fname='',lname='') : This adds a contact to your hotmail address book. Only quickname and email are obligatory - fname (First Name) and lname (Last Name) can be left blank.
37
+
38
+ eg. zaphod.add_contact('barty','slartibartfast@fjord.net','Slarti','Bartfast')
39
+
40
+
41
+ Any of these methods will raise an error if there is a problem - you therefore should capture these errors in your program if you want to recover from them somehow.
42
+
43
+
44
+ === Hotmailer::Message
45
+
46
+ This is the hotmail message class, and it contains the following (read only) attributes:
47
+
48
+ - from_email : The sender's email address.
49
+ - from_name : The sender's name.
50
+ - status : One of "Read", "Unread", and "Forwarded", describing the status of the message
51
+ - subject : The subject of the message
52
+ - date : The date it was sent
53
+ - size - The message's size (eg. '4 KB')
54
+ - body - The text of the message (in plain text)
55
+
56
+
57
+ In addition the following methods are also available:
58
+
59
+ - read : This returns the body of the message (in plain text). This is the same as the body attribute.
60
+ - delete : This deletes the message from the user's inbox, and places it in trash (where it will automatically disappear into the great void after a few days).
61
+ - forward(to) - This forwards a message to the to email address specified.
62
+
63
+
64
+
65
+
66
+ === Example Run
67
+
68
+ require 'hotmailer'
69
+
70
+ #Create object and login
71
+ zaphod = Hotmailer.new('zaphod@hotmail.com','chunkybacon')
72
+ zaphod.login
73
+
74
+
75
+ #Get messages
76
+ messages = zaphod.messages
77
+
78
+ #Get details of first message
79
+ puts messages[0].from_email
80
+ puts messages[0].from_name
81
+ puts messages[0].subject
82
+ puts messages[0].body
83
+
84
+
85
+ #Forward first message to Arhur
86
+ messages[0].forward('dentarthurdent@gmail.com')
87
+
88
+ #Delete first message
89
+ messages[0].delete
90
+
91
+ #Add Arthur's contact details
92
+ zaphod.add_contact('arthur','dentarthurdent@hotmail.com','Arthur','Dent')
93
+
94
+ #Get contacts list
95
+ contacts = zaphod.contacts
96
+
97
+
98
+
@@ -0,0 +1,263 @@
1
+ require 'rubygems'
2
+ require 'mechanize'
3
+
4
+
5
+ class Hotmailer < WWW::Mechanize
6
+
7
+ attr_accessor :username, :passwd
8
+ attr_reader :inbox, :logged_in
9
+
10
+ def initialize(username,passwd)
11
+ super()
12
+ self.user_agent_alias = "Windows IE 6"
13
+ @username = username
14
+ @passwd = passwd
15
+ @inbox = ''
16
+ @contacts = []
17
+ @messages = []
18
+ end
19
+
20
+ def login
21
+ #Logs in the user
22
+ first_page = self.get('http://hotmail.com')
23
+ login_form = first_page.form('f1')
24
+ login_form.login = self.username
25
+ login_form.passwd = self.passwd
26
+
27
+ login_page = self.submit(login_form)
28
+
29
+ if login_page.body =~ /window\.location\.replace\(\"([^"]+)\"/
30
+ new_loc = $1
31
+ else
32
+ raise "Error logging in - check username and password and try again"
33
+ end
34
+
35
+ main_page = self.get(new_loc)
36
+
37
+ if main_page.body =~ /_UM\s*=\s*"([^"]+)";?/
38
+ @inbox = $1
39
+ else
40
+ raise "Error getting mailbox - hotmail format may have changed! (Please try logging in manually using your web browser, then retry this)."
41
+ end
42
+
43
+ @logged_in = true
44
+
45
+ end
46
+
47
+ def contacts(reload=false)
48
+ #Get user's contact list (returns an array of hashes, each has a record for one
49
+ # user, and contains :name and :email keys)
50
+
51
+ unless reload
52
+ return @contacts unless @contacts.empty?
53
+ end
54
+
55
+ self.login unless self.logged_in
56
+
57
+ #The URL to use to get contacts in printable view
58
+ contacts_url = "/cgi-bin/addresses?fti=yes&PrintView=1&"+self.inbox
59
+
60
+ all_contacts = self.get(contacts_url)
61
+
62
+ #Get separate contacts [those within trs within trs]
63
+ scontacts = all_contacts/"tr/tr"
64
+
65
+ scontacts.each do |c|
66
+ #Get each contact's name and email, and append it to @contacts
67
+ details = (c/"td")
68
+ name = details[0].inner_html
69
+ email = (details[1]/"span")[0].inner_html
70
+ @contacts << {:name => name,:email => email}
71
+ end
72
+
73
+ return @contacts
74
+
75
+ end
76
+
77
+ def compose(to,subject,body)
78
+ #Sends an email
79
+
80
+ self.login unless self.logged_in
81
+
82
+ compose_url ="/cgi-bin/compose?"+self.inbox
83
+ comp_page = self.get(compose_url)
84
+
85
+ comp_form = comp_page.form("composeform")
86
+ comp_form.to = to
87
+ comp_form.subject = subject
88
+ comp_form.body = body
89
+
90
+ res_page = self.submit(comp_form)
91
+
92
+ unless res_page.body =~ /Your message has been sent/
93
+ raise "There was an error sending the message"
94
+ end
95
+
96
+ return true
97
+
98
+ end
99
+
100
+ def messages(reload=false)
101
+
102
+ unless reload
103
+ return @messages unless @messages.empty?
104
+ end
105
+
106
+ self.login unless self.logged_in
107
+
108
+ page = 1
109
+ last_page = 1
110
+ raw_messages = []
111
+ messages = []
112
+
113
+ while page <= last_page.to_i
114
+ msg_url = "/cgi-bin/HoTMaiL?&Sort=rDate&page=#{page}&"+self.inbox
115
+ msg_page = self.get(msg_url)
116
+
117
+ #Get last page
118
+ lastp = (msg_page/"a[@title='Last Page']")[0]
119
+ if lastp
120
+ lastp.attributes['href'] =~ /HM\('page=(\d+)/
121
+ last_page = $1
122
+ end
123
+
124
+ msgs = msg_page/"tr[@name]"
125
+ raw_messages += msgs
126
+
127
+ page+=1
128
+ end
129
+
130
+ for msg in raw_messages
131
+ fname = (msg/"a")[0].inner_html
132
+ femail = msg.attributes['name']
133
+ status = (msg/"img")[0].attributes['alt']
134
+
135
+ mlink = (msg/"a")[0].attributes['href']
136
+ mlink =~ /G\('([^']+)'/
137
+ mlink = $1
138
+
139
+ subject = (msg/"td")[6].inner_html
140
+ date = (msg/"td")[7].inner_html
141
+ size = (msg/"td")[8].inner_html
142
+
143
+ m = Hotmailer::Message.new(self,:from_name=> fname, :from_email => femail, :status => status, :link => mlink, :subject => subject, :date => date, :size => size)
144
+
145
+ messages << m
146
+ end
147
+
148
+ @messages = messages
149
+ return @messages
150
+ end
151
+
152
+ def add_contact(quickname,email,fname='',lname='')
153
+ #To add a contact
154
+
155
+ self.login unless self.logged_in
156
+
157
+ main_url = '/cgi-bin/hmhome?'+self.inbox
158
+ main_page = self.get(main_url)
159
+
160
+ c_link = (main_page/"a[@href=#]").find {|c| c.inner_html == "New Contact"}
161
+ unless c_link['onclick'] =~ /G\('([^']+)'/
162
+ raise "Error adding contact - hotmail format may have changed"
163
+ end
164
+
165
+ c_href = $1
166
+ contact_page = self.get(c_href+"&"+self.inbox)
167
+ contact_form = contact_page.form('addr')
168
+
169
+ contact_form.alias = quickname
170
+ contact_form.addrlist = email
171
+
172
+ contact_form.aliasfname = fname
173
+ contact_form.aliaslname = lname
174
+
175
+ res_page = self.submit(contact_form)
176
+
177
+ unless res_page.body =~ /Contact/
178
+ raise "Error adding contact"
179
+ end
180
+
181
+ return true
182
+ end
183
+
184
+ end
185
+
186
+
187
+ class Hotmailer::Message
188
+ attr_reader :from_email, :from_name, :status, :link, :subject, :date, :size, :parent, :id
189
+
190
+
191
+ def initialize(parent,opts = {})
192
+ @from_email = opts[:from_email]
193
+ @from_name = opts[:from_name]
194
+ @status = opts[:status]
195
+ @link = opts[:link]
196
+ @subject = opts[:subject]
197
+ @date = opts[:date]
198
+ @size = opts[:size]
199
+ @body = ''
200
+ @parent = parent
201
+ #Get message id
202
+ @link =~ /msg=(.+)/
203
+ @id = $1
204
+ end
205
+
206
+ def read
207
+ #Used to read the message's contents (in plain text)
208
+ return @body unless @body.empty?
209
+
210
+ msg_link = self.link+"&raw=0&"+@parent.inbox
211
+ msg_page = @parent.get(msg_link)
212
+ raw_text = (msg_page/"pre")[0].inner_html
213
+
214
+ if raw_text =~ /\n\n(.+)/m
215
+ msg_text = $1
216
+ else
217
+ msg_text = ''
218
+ end
219
+
220
+ @body = msg_text
221
+ return @body
222
+ end
223
+
224
+ alias :body :read
225
+
226
+ def delete
227
+ #Used to delete the message
228
+ #Get message page, and all links on page
229
+ msg_page = parent.get(self.link)
230
+ links = (msg_page/"a")
231
+
232
+ #Get delete link
233
+ del_a = links.find {|a| a.inner_html == 'Delete' }
234
+ if del_a.attributes['onclick'] =~ /G\('([^']+)'/
235
+ del_link = $1
236
+ else
237
+ raise "Could not find delete link - hotmail layout changed?"
238
+ end
239
+
240
+ res_page = parent.get(del_link)
241
+ #Remove self from parent's messages array
242
+ parent.messages.delete(self)
243
+ return true if res_page.body =~ /Mail/
244
+
245
+ end
246
+
247
+ def forward(to)
248
+ #Forward this message
249
+ f_url = "/cgi-bin/compose?type=f&msg=#{self.id}&"+parent.inbox
250
+ f_page = parent.get(f_url)
251
+
252
+ fwd_form = f_page.form('composeform')
253
+ fwd_form.to = to
254
+ res_page = parent.submit(fwd_form)
255
+
256
+ if res_page.body =~ /Your message has been sent/
257
+ return true
258
+ else
259
+ raise "Error forwarding message"
260
+ end
261
+
262
+ end
263
+ end
metadata ADDED
@@ -0,0 +1,63 @@
1
+ --- !ruby/object:Gem::Specification
2
+ rubygems_version: 0.8.11
3
+ specification_version: 1
4
+ name: hotmailer
5
+ version: !ruby/object:Gem::Version
6
+ version: 1.0.0
7
+ date: 2006-11-15 00:00:00 +00:00
8
+ summary: Package for programatically accessing hotmail accounts
9
+ require_paths:
10
+ - lib
11
+ email: amrangaye@gmail.com
12
+ homepage:
13
+ rubyforge_project:
14
+ description:
15
+ autorequire: hotmailer
16
+ default_executable:
17
+ bindir: bin
18
+ has_rdoc: true
19
+ required_ruby_version: !ruby/object:Gem::Version::Requirement
20
+ requirements:
21
+ - - ">"
22
+ - !ruby/object:Gem::Version
23
+ version: 0.0.0
24
+ version:
25
+ platform: ruby
26
+ signing_key:
27
+ cert_chain:
28
+ authors:
29
+ - Amran Gaye
30
+ files:
31
+ - lib/hotmailer.rb
32
+ - README
33
+ test_files: []
34
+
35
+ rdoc_options: []
36
+
37
+ extra_rdoc_files:
38
+ - README
39
+ executables: []
40
+
41
+ extensions: []
42
+
43
+ requirements: []
44
+
45
+ dependencies:
46
+ - !ruby/object:Gem::Dependency
47
+ name: mechanize
48
+ version_requirement:
49
+ version_requirements: !ruby/object:Gem::Version::Requirement
50
+ requirements:
51
+ - - ">"
52
+ - !ruby/object:Gem::Version
53
+ version: 0.0.0
54
+ version:
55
+ - !ruby/object:Gem::Dependency
56
+ name: hpricot
57
+ version_requirement:
58
+ version_requirements: !ruby/object:Gem::Version::Requirement
59
+ requirements:
60
+ - - ">"
61
+ - !ruby/object:Gem::Version
62
+ version: 0.0.0
63
+ version: