pp-contacts 1.5.1 → 1.5.2
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +7 -0
- data/Gemfile +16 -0
- data/Gemfile.lock +27 -0
- data/contacts.gemspec +16 -0
- data/cruise_config.rb +22 -0
- data/geminstaller.yml +8 -0
- data/lib/contacts/base.rb +0 -1
- data/lib/contacts/outlook.rb +59 -0
- data/lib/contacts/vcf.rb +25 -0
- data/test/example_accounts.yml +40 -0
- data/test/outlook_fullname.csv +3 -0
- data/test/outlook_splitname.csv +3 -0
- data/test/test_helper.rb +32 -0
- data/test/test_suite.rb +4 -0
- data/test/unit/aol_contact_importer_test.rb +33 -0
- data/test/unit/gmail_contact_importer_test.rb +39 -0
- data/test/unit/hotmail_contact_importer_test.rb +41 -0
- data/test/unit/outlook_test.rb +23 -0
- data/test/unit/test_accounts_test.rb +23 -0
- data/test/unit/vcf_test.rb +17 -0
- data/test/unit/yahoo_csv_contact_importer_test.rb +35 -0
- data/test/vCards.vcf +16 -0
- metadata +35 -14
data/.gitignore
ADDED
data/Gemfile
ADDED
@@ -0,0 +1,16 @@
|
|
1
|
+
# A sample Gemfile
|
2
|
+
source "http://rubygems.org"
|
3
|
+
|
4
|
+
gem "rake"
|
5
|
+
gem 'gdata19', :git => 'git://github.com/paperlesspost/gdata.git'
|
6
|
+
gem 'hpricot'
|
7
|
+
gem 'nokogiri'
|
8
|
+
gem "json", '> 0.4.1'
|
9
|
+
|
10
|
+
group :development do
|
11
|
+
gem 'gem-release'
|
12
|
+
end
|
13
|
+
|
14
|
+
group :test do
|
15
|
+
gem 'shoulda'
|
16
|
+
end
|
data/Gemfile.lock
ADDED
@@ -0,0 +1,27 @@
|
|
1
|
+
GIT
|
2
|
+
remote: git://github.com/paperlesspost/gdata.git
|
3
|
+
revision: 91f3a5b2e701c879ae5dfcb48dec5bb039e37a7b
|
4
|
+
specs:
|
5
|
+
gdata19 (0.1.9.2)
|
6
|
+
|
7
|
+
GEM
|
8
|
+
remote: http://rubygems.org/
|
9
|
+
specs:
|
10
|
+
gem-release (0.3.1)
|
11
|
+
hpricot (0.8.4)
|
12
|
+
json (1.5.3)
|
13
|
+
nokogiri (1.5.2)
|
14
|
+
rake (0.9.2)
|
15
|
+
shoulda (2.11.3)
|
16
|
+
|
17
|
+
PLATFORMS
|
18
|
+
ruby
|
19
|
+
|
20
|
+
DEPENDENCIES
|
21
|
+
gdata19!
|
22
|
+
gem-release
|
23
|
+
hpricot
|
24
|
+
json (> 0.4.1)
|
25
|
+
nokogiri
|
26
|
+
rake
|
27
|
+
shoulda
|
data/contacts.gemspec
ADDED
@@ -0,0 +1,16 @@
|
|
1
|
+
Gem::Specification.new do |s|
|
2
|
+
s.name = "pp-contacts"
|
3
|
+
s.version = "1.5.2"
|
4
|
+
s.date = "2012-04-26"
|
5
|
+
s.summary = "A universal interface to grab contact list information from various providers including Outlook, Address Book, Yahoo, AOL, Gmail, Hotmail, and Plaxo."
|
6
|
+
s.homepage = "http://github.com/paperlesspost/contacts"
|
7
|
+
s.description = "A universal interface to grab contact list information from various providers including Outlook, Address Book, Yahoo, AOL, Gmail, Hotmail, and Plaxo."
|
8
|
+
s.has_rdoc = false
|
9
|
+
s.authors = ["Lucas Carlson", "Paperless"]
|
10
|
+
s.files = `git ls-files`.split($\)
|
11
|
+
s.add_dependency("json", ">= 1.1.1")
|
12
|
+
s.add_dependency('gdata19')
|
13
|
+
s.add_dependency('hpricot')
|
14
|
+
s.add_dependency('nokogiri')
|
15
|
+
s.add_dependency('encryptor')
|
16
|
+
end
|
data/cruise_config.rb
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
# Project-specific configuration for CruiseControl.rb
|
2
|
+
|
3
|
+
Project.configure do |project|
|
4
|
+
|
5
|
+
# Send email notifications about broken and fixed builds to email1@your.site, email2@your.site (default: send to nobody)
|
6
|
+
# if building this on your own CI box, please remove!
|
7
|
+
project.email_notifier.emails = ['opensource@pivotallabs.com']
|
8
|
+
|
9
|
+
# Set email 'from' field to john@doe.com:
|
10
|
+
# project.email_notifier.from = 'john@doe.com'
|
11
|
+
|
12
|
+
# Build the project by invoking rake task 'custom'
|
13
|
+
# project.rake_task = 'custom'
|
14
|
+
|
15
|
+
# Build the project by invoking shell script "build_my_app.sh". Keep in mind that when the script is invoked, current working directory is
|
16
|
+
# [cruise]/projects/your_project/work, so if you do not keep build_my_app.sh in version control, it should be '../build_my_app.sh' instead
|
17
|
+
# project.build_command = 'build_my_app.sh'
|
18
|
+
|
19
|
+
# Ping Subversion for new revisions every 5 minutes (default: 30 seconds)
|
20
|
+
# project.scheduler.polling_interval = 5.minutes
|
21
|
+
|
22
|
+
end
|
data/geminstaller.yml
ADDED
data/lib/contacts/base.rb
CHANGED
@@ -0,0 +1,59 @@
|
|
1
|
+
require 'csv'
|
2
|
+
|
3
|
+
class Contacts
|
4
|
+
class Outlook < Base
|
5
|
+
|
6
|
+
def initialize(file)
|
7
|
+
@contact_file = Array.new
|
8
|
+
file = file.respond_to?(:read) ? file.read : file
|
9
|
+
file.each_line do |line|
|
10
|
+
@contact_file << CSV.parse(line)[0]
|
11
|
+
end
|
12
|
+
@full_name = false
|
13
|
+
@header_indexes = Hash.new
|
14
|
+
@header_indexes[:email_address] = Array.new
|
15
|
+
|
16
|
+
headers = @contact_file[0]
|
17
|
+
|
18
|
+
@contact_file = @contact_file[1, @contact_file.length]
|
19
|
+
|
20
|
+
headers.each_with_index do |header, i|
|
21
|
+
if header.match(/^Name$/)
|
22
|
+
@full_name = true
|
23
|
+
@header_indexes[:full_name] = i
|
24
|
+
elsif header.match(/^First Name/)
|
25
|
+
@header_indexes[:first_name] = i
|
26
|
+
elsif header.match(/^Last Name/)
|
27
|
+
@header_indexes[:last_name] = i
|
28
|
+
elsif header.match(/E-mail/)
|
29
|
+
@header_indexes[:email_address] << i
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
def contacts
|
35
|
+
|
36
|
+
contacts = Array.new
|
37
|
+
|
38
|
+
@contact_file.each_with_index do |line, i|
|
39
|
+
contacts[i] = Array.new unless contacts[i]
|
40
|
+
if(@full_name)
|
41
|
+
contacts[i][0] = line[@header_indexes[:full_name]]
|
42
|
+
else
|
43
|
+
contacts[i][0] = "#{line[@header_indexes[:first_name]]} #{line[@header_indexes[:last_name]]}"
|
44
|
+
end
|
45
|
+
@header_indexes[:email_address].each do |index|
|
46
|
+
if line[index] && !contacts[i][1]
|
47
|
+
contacts[i][1] = line[index]
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
52
|
+
contacts
|
53
|
+
end
|
54
|
+
|
55
|
+
end
|
56
|
+
|
57
|
+
private
|
58
|
+
FILETYPES[:outlook] = Outlook
|
59
|
+
end
|
data/lib/contacts/vcf.rb
ADDED
@@ -0,0 +1,25 @@
|
|
1
|
+
class Contacts
|
2
|
+
class Vcf < Base
|
3
|
+
|
4
|
+
def initialize(file)
|
5
|
+
@contact_file = file
|
6
|
+
end
|
7
|
+
|
8
|
+
def contacts
|
9
|
+
contacts = Array.new
|
10
|
+
i = 0
|
11
|
+
@contact_file.each do |line|
|
12
|
+
contacts[i] = Array.new unless contacts[i]
|
13
|
+
if line.match(/FN:/)
|
14
|
+
contacts[i] << line.gsub(/FN:/, '').strip
|
15
|
+
elsif line.match(/EMAIL;/)
|
16
|
+
contacts[i] << line.gsub(/^.*:/, '').strip
|
17
|
+
elsif line.match(/END:VCARD/)
|
18
|
+
i += 1
|
19
|
+
end
|
20
|
+
end
|
21
|
+
contacts
|
22
|
+
end
|
23
|
+
end
|
24
|
+
FILETYPES[:vcf] = Vcf
|
25
|
+
end
|
@@ -0,0 +1,40 @@
|
|
1
|
+
gmail:
|
2
|
+
username: <changeme>
|
3
|
+
password: <changeme>
|
4
|
+
contacts:
|
5
|
+
-
|
6
|
+
name: "FirstName1 LastName1"
|
7
|
+
email_address: "firstname1@example.com"
|
8
|
+
-
|
9
|
+
name: "FirstName2 LastName2"
|
10
|
+
email_address: "firstname2@example.com"
|
11
|
+
yahoo:
|
12
|
+
username: <changeme>
|
13
|
+
password: <changeme>
|
14
|
+
contacts:
|
15
|
+
-
|
16
|
+
name: "FirstName1 LastName1"
|
17
|
+
email_address: "firstname1@example.com"
|
18
|
+
-
|
19
|
+
name: "FirstName2 LastName2"
|
20
|
+
email_address: "firstname2@example.com"
|
21
|
+
hotmail:
|
22
|
+
username: <changeme>
|
23
|
+
password: <changeme>
|
24
|
+
contacts:
|
25
|
+
-
|
26
|
+
name: "FirstName1 LastName1"
|
27
|
+
email_address: "firstname1@example.com"
|
28
|
+
-
|
29
|
+
name: "FirstName2 LastName2"
|
30
|
+
email_address: "firstname2@example.com"
|
31
|
+
aol:
|
32
|
+
username: <changeme>
|
33
|
+
password: <changeme>
|
34
|
+
contacts:
|
35
|
+
-
|
36
|
+
name: "FirstName1 LastName1"
|
37
|
+
email_address: "firstname1@example.com"
|
38
|
+
-
|
39
|
+
name: "FirstName2 LastName2"
|
40
|
+
email_address: "firstname2@example.com"
|
data/test/test_helper.rb
ADDED
@@ -0,0 +1,32 @@
|
|
1
|
+
dir = File.dirname(__FILE__)
|
2
|
+
$LOAD_PATH.unshift(dir + "/../lib/")
|
3
|
+
require 'test/unit'
|
4
|
+
require 'contacts'
|
5
|
+
require 'yaml'
|
6
|
+
require 'shoulda'
|
7
|
+
|
8
|
+
class ContactImporterTestCase < Test::Unit::TestCase
|
9
|
+
# Add more helper methods to be used by all tests here...
|
10
|
+
def default_test
|
11
|
+
assert true
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
class TestAccounts
|
16
|
+
def self.[](type)
|
17
|
+
load[type]
|
18
|
+
end
|
19
|
+
|
20
|
+
def self.load(file = File.dirname(__FILE__) + "/accounts.yml")
|
21
|
+
raise "/test/accounts.yml file not found, please create, see /test/example_accounts.yml for information" unless File.exist?(file)
|
22
|
+
|
23
|
+
accounts = {}
|
24
|
+
YAML::load(File.open(file)).each do |type, contents|
|
25
|
+
contacts = contents["contacts"].collect {|contact| [contact["name"], contact["email_address"]]}
|
26
|
+
accounts[type.to_sym] = Account.new(type.to_sym, contents["username"], contents["password"], contacts)
|
27
|
+
end
|
28
|
+
accounts
|
29
|
+
end
|
30
|
+
|
31
|
+
Account = Struct.new :type, :username, :password, :contacts
|
32
|
+
end
|
data/test/test_suite.rb
ADDED
@@ -0,0 +1,33 @@
|
|
1
|
+
dir = File.dirname(__FILE__)
|
2
|
+
require "#{dir}/../test_helper"
|
3
|
+
require 'contacts'
|
4
|
+
|
5
|
+
class AolContactImporterTest < ContactImporterTestCase
|
6
|
+
def setup
|
7
|
+
super
|
8
|
+
@account = TestAccounts[:aol]
|
9
|
+
end
|
10
|
+
|
11
|
+
def test_successful_login
|
12
|
+
Contacts.new(:aolImporter, @account.username, @account.password)
|
13
|
+
end
|
14
|
+
|
15
|
+
def test_importer_fails_with_blank_password
|
16
|
+
assert_raise(Contacts::AuthenticationError) do
|
17
|
+
Contacts.new(:aolImporter, @account.username, "")
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
def test_importer_fails_with_blank_username
|
22
|
+
assert_raise(Contacts::AuthenticationError) do
|
23
|
+
Contacts.new(:aolImporter, "", @account.password)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
def test_fetch_contacts
|
28
|
+
contacts = Contacts.new(:aolImporter, @account.username, @account.password).contacts
|
29
|
+
@account.contacts.each do |contact|
|
30
|
+
assert contacts.include?(contact), "Could not find: #{contact.inspect} in #{contacts.inspect}"
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,39 @@
|
|
1
|
+
dir = File.dirname(__FILE__)
|
2
|
+
require "#{dir}/../test_helper"
|
3
|
+
require 'contacts'
|
4
|
+
|
5
|
+
class GmailContactImporterTest < ContactImporterTestCase
|
6
|
+
def setup
|
7
|
+
super
|
8
|
+
@account = TestAccounts[:gmail]
|
9
|
+
end
|
10
|
+
|
11
|
+
def test_successful_login
|
12
|
+
Contacts.new(:gmail, @account.username, @account.password)
|
13
|
+
end
|
14
|
+
|
15
|
+
def test_importer_fails_with_invalid_password
|
16
|
+
assert_raise(Contacts::AuthenticationError) do
|
17
|
+
Contacts.new(:gmail, @account.username, "wrong_password")
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
def test_importer_fails_with_blank_password
|
22
|
+
assert_raise(Contacts::AuthenticationError) do
|
23
|
+
Contacts.new(:gmail, @account.username, "")
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
def test_importer_fails_with_blank_username
|
28
|
+
assert_raise(Contacts::AuthenticationError) do
|
29
|
+
Contacts.new(:gmail, "", @account.password)
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
def test_fetch_contacts
|
34
|
+
contacts = Contacts.new(:gmail, @account.username, @account.password).contacts
|
35
|
+
@account.contacts.each do |contact|
|
36
|
+
assert contacts.include?(contact), "Could not find: #{contact.inspect} in #{contacts.inspect}"
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
@@ -0,0 +1,41 @@
|
|
1
|
+
dir = File.dirname(__FILE__)
|
2
|
+
require "#{dir}/../test_helper"
|
3
|
+
require 'contacts'
|
4
|
+
|
5
|
+
class HotmailContactImporterTest < ContactImporterTestCase
|
6
|
+
def setup
|
7
|
+
super
|
8
|
+
@account = TestAccounts[:hotmail]
|
9
|
+
end
|
10
|
+
|
11
|
+
def test_successful_login
|
12
|
+
Contacts.new(:hotmail, @account.username, @account.password)
|
13
|
+
end
|
14
|
+
|
15
|
+
def test_importer_fails_with_invalid_msn_password
|
16
|
+
assert_raise(Contacts::AuthenticationError) do
|
17
|
+
Contacts.new(:hotmail, "test@msn.com","wrong_password")
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
def test_importer_fails_with_invalid_password
|
22
|
+
assert_raise(Contacts::AuthenticationError) do
|
23
|
+
Contacts.new(:hotmail, @account.username,"wrong_password")
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
def test_fetch_contacts
|
28
|
+
contacts = Contacts.new(:hotmail, @account.username, @account.password).contacts
|
29
|
+
@account.contacts.each do |contact|
|
30
|
+
assert contacts.include?(contact), "Could not find: #{contact.inspect} in #{contacts.inspect}"
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
# Since the hotmail scraper doesn't read names, test email
|
35
|
+
def test_fetch_email
|
36
|
+
contacts = Contacts.new(:hotmail, @account.username, @account.password).contacts
|
37
|
+
@account.contacts.each do |contact|
|
38
|
+
assert contacts.any?{|book_contact| book_contact.last == contact.last }, "Could not find: #{contact.inspect} in #{contacts.inspect}"
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
dir = File.dirname(__FILE__)
|
2
|
+
require "#{dir}/../test_helper"
|
3
|
+
|
4
|
+
class OutlookTest < ContactImporterTestCase
|
5
|
+
context 'An instance of Outlook' do
|
6
|
+
should 'open file properly' do
|
7
|
+
outlookobject = Contacts.new(:outlook, File.open(File.dirname(__FILE__) + '/../outlook_fullname.csv'))
|
8
|
+
assert_not_nil outlookobject
|
9
|
+
end
|
10
|
+
|
11
|
+
should 'get contacts from file with Full Name' do
|
12
|
+
outlookobject = Contacts.new(:outlook, File.open(File.dirname(__FILE__) + '/../outlook_fullname.csv'))
|
13
|
+
contacts = outlookobject.contacts
|
14
|
+
assert_not_nil contacts
|
15
|
+
end
|
16
|
+
|
17
|
+
should 'get contacts from file with split up names' do
|
18
|
+
outlookobject = Contacts.new(:outlook, File.open(File.dirname(__FILE__) + '/../outlook_splitname.csv'))
|
19
|
+
contacts = outlookobject.contacts
|
20
|
+
assert_not_nil contacts
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
dir = File.dirname(__FILE__)
|
2
|
+
require "#{dir}/../test_helper"
|
3
|
+
|
4
|
+
class TestAccountsTest < ContactImporterTestCase
|
5
|
+
def test_test_accounts_loads_data_from_example_accounts_file
|
6
|
+
account = TestAccounts.load(File.dirname(__FILE__) + "/../example_accounts.yml")[:gmail]
|
7
|
+
|
8
|
+
assert_equal :gmail, account.type
|
9
|
+
assert_equal "<changeme>", account.username
|
10
|
+
assert_equal "<changeme>", account.password
|
11
|
+
assert_equal [["FirstName1 LastName1", "firstname1@example.com"], ["FirstName2 LastName2", "firstname2@example.com"]], account.contacts
|
12
|
+
end
|
13
|
+
|
14
|
+
def test_test_accounts_blows_up_if_file_doesnt_exist
|
15
|
+
assert_raise(RuntimeError) do
|
16
|
+
TestAccounts.load("file_that_does_not_exist.yml")
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
def test_we_can_load_from_account_file
|
21
|
+
assert_not_nil TestAccounts[:gmail].username
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
dir = File.dirname(__FILE__)
|
2
|
+
require "#{dir}/../test_helper"
|
3
|
+
|
4
|
+
class VcfTest < ContactImporterTestCase
|
5
|
+
context 'An instance of Vcf' do
|
6
|
+
should 'open file properly' do
|
7
|
+
vcfobject = Contacts.new(:vcf, File.open(File.dirname(__FILE__) + '/../vCards.vcf'))
|
8
|
+
assert_not_nil vcfobject
|
9
|
+
end
|
10
|
+
|
11
|
+
should 'get contacts from file' do
|
12
|
+
vcfobject = Contacts.new(:vcf, File.open(File.dirname(__FILE__) + '/../vCards.vcf'))
|
13
|
+
contacts = vcfobject.contacts
|
14
|
+
assert_not_nil contacts
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
dir = File.dirname(__FILE__)
|
2
|
+
require "#{dir}/../test_helper"
|
3
|
+
require 'contacts'
|
4
|
+
|
5
|
+
class YahooContactImporterTest < ContactImporterTestCase
|
6
|
+
def setup
|
7
|
+
super
|
8
|
+
@account = TestAccounts[:yahoo]
|
9
|
+
end
|
10
|
+
|
11
|
+
def test_a_successful_login
|
12
|
+
Contacts.new(:yahoo, @account.username, @account.password)
|
13
|
+
end
|
14
|
+
|
15
|
+
def test_importer_fails_with_invalid_password
|
16
|
+
assert_raise(Contacts::AuthenticationError) do
|
17
|
+
Contacts.new(:yahoo, @account.username, "wrong_password")
|
18
|
+
end
|
19
|
+
# run the "successful" login test to ensure we reset yahoo's failed login lockout counter
|
20
|
+
# See http://www.pivotaltracker.com/story/show/138210
|
21
|
+
# yahoo needs some time to unset the failed login state, apparently...
|
22
|
+
# ...1 sec and 5 secs still failed sporadically
|
23
|
+
sleep 10
|
24
|
+
assert_nothing_raised do
|
25
|
+
Contacts.new(:yahoo, @account.username, @account.password)
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
def test_a_fetch_contacts
|
30
|
+
contacts = Contacts.new(:yahoo, @account.username, @account.password).contacts
|
31
|
+
@account.contacts.each do |contact|
|
32
|
+
assert contacts.include?(contact), "Could not find: #{contact.inspect} in #{contacts.inspect}"
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
data/test/vCards.vcf
ADDED
@@ -0,0 +1,16 @@
|
|
1
|
+
BEGIN:VCARD
|
2
|
+
VERSION:3.0
|
3
|
+
N:LastName1;FirstName1;;;
|
4
|
+
FN:FirstName1 LastName1
|
5
|
+
EMAIL;type=INTERNET;type=WORK;type=pref:firstname1@example.com
|
6
|
+
CATEGORIES:test
|
7
|
+
X-ABUID:3BCA01C2-3EF7-4BB8-BFD4-08ED31416C8F\:ABPerson
|
8
|
+
END:VCARD
|
9
|
+
BEGIN:VCARD
|
10
|
+
VERSION:3.0
|
11
|
+
N:LastName2;FirstName2;;;
|
12
|
+
FN:FirstName2 LastName2
|
13
|
+
EMAIL;type=INTERNET;type=WORK;type=pref:firstname2@example.com
|
14
|
+
CATEGORIES:test
|
15
|
+
X-ABUID:53F6702D-D2B6-4B46-8C41-CD31F743260B\:ABPerson
|
16
|
+
END:VCARD
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: pp-contacts
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.5.
|
4
|
+
version: 1.5.2
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -14,7 +14,7 @@ date: 2012-04-26 00:00:00.000000000Z
|
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: json
|
17
|
-
requirement: &
|
17
|
+
requirement: &70303491442280 !ruby/object:Gem::Requirement
|
18
18
|
none: false
|
19
19
|
requirements:
|
20
20
|
- - ! '>='
|
@@ -22,10 +22,10 @@ dependencies:
|
|
22
22
|
version: 1.1.1
|
23
23
|
type: :runtime
|
24
24
|
prerelease: false
|
25
|
-
version_requirements: *
|
25
|
+
version_requirements: *70303491442280
|
26
26
|
- !ruby/object:Gem::Dependency
|
27
27
|
name: gdata19
|
28
|
-
requirement: &
|
28
|
+
requirement: &70303491441860 !ruby/object:Gem::Requirement
|
29
29
|
none: false
|
30
30
|
requirements:
|
31
31
|
- - ! '>='
|
@@ -33,10 +33,10 @@ dependencies:
|
|
33
33
|
version: '0'
|
34
34
|
type: :runtime
|
35
35
|
prerelease: false
|
36
|
-
version_requirements: *
|
36
|
+
version_requirements: *70303491441860
|
37
37
|
- !ruby/object:Gem::Dependency
|
38
38
|
name: hpricot
|
39
|
-
requirement: &
|
39
|
+
requirement: &70303491441400 !ruby/object:Gem::Requirement
|
40
40
|
none: false
|
41
41
|
requirements:
|
42
42
|
- - ! '>='
|
@@ -44,10 +44,10 @@ dependencies:
|
|
44
44
|
version: '0'
|
45
45
|
type: :runtime
|
46
46
|
prerelease: false
|
47
|
-
version_requirements: *
|
47
|
+
version_requirements: *70303491441400
|
48
48
|
- !ruby/object:Gem::Dependency
|
49
49
|
name: nokogiri
|
50
|
-
requirement: &
|
50
|
+
requirement: &70303491440980 !ruby/object:Gem::Requirement
|
51
51
|
none: false
|
52
52
|
requirements:
|
53
53
|
- - ! '>='
|
@@ -55,10 +55,10 @@ dependencies:
|
|
55
55
|
version: '0'
|
56
56
|
type: :runtime
|
57
57
|
prerelease: false
|
58
|
-
version_requirements: *
|
58
|
+
version_requirements: *70303491440980
|
59
59
|
- !ruby/object:Gem::Dependency
|
60
60
|
name: encryptor
|
61
|
-
requirement: &
|
61
|
+
requirement: &70303491440560 !ruby/object:Gem::Requirement
|
62
62
|
none: false
|
63
63
|
requirements:
|
64
64
|
- - ! '>='
|
@@ -66,7 +66,7 @@ dependencies:
|
|
66
66
|
version: '0'
|
67
67
|
type: :runtime
|
68
68
|
prerelease: false
|
69
|
-
version_requirements: *
|
69
|
+
version_requirements: *70303491440560
|
70
70
|
description: A universal interface to grab contact list information from various providers
|
71
71
|
including Outlook, Address Book, Yahoo, AOL, Gmail, Hotmail, and Plaxo.
|
72
72
|
email:
|
@@ -74,18 +74,39 @@ executables: []
|
|
74
74
|
extensions: []
|
75
75
|
extra_rdoc_files: []
|
76
76
|
files:
|
77
|
+
- .gitignore
|
78
|
+
- Gemfile
|
79
|
+
- Gemfile.lock
|
77
80
|
- LICENSE
|
78
|
-
- Rakefile
|
79
81
|
- README.md
|
82
|
+
- Rakefile
|
83
|
+
- contacts.gemspec
|
84
|
+
- cruise_config.rb
|
80
85
|
- examples/grab_contacts.rb
|
86
|
+
- geminstaller.yml
|
81
87
|
- lib/contacts.rb
|
88
|
+
- lib/contacts/aol_importer.rb
|
82
89
|
- lib/contacts/base.rb
|
83
|
-
- lib/contacts/json_picker.rb
|
84
90
|
- lib/contacts/gmail.rb
|
85
|
-
- lib/contacts/aol_importer.rb
|
86
91
|
- lib/contacts/hotmail.rb
|
92
|
+
- lib/contacts/json_picker.rb
|
93
|
+
- lib/contacts/outlook.rb
|
87
94
|
- lib/contacts/plaxo.rb
|
95
|
+
- lib/contacts/vcf.rb
|
88
96
|
- lib/contacts/yahoo.rb
|
97
|
+
- test/example_accounts.yml
|
98
|
+
- test/outlook_fullname.csv
|
99
|
+
- test/outlook_splitname.csv
|
100
|
+
- test/test_helper.rb
|
101
|
+
- test/test_suite.rb
|
102
|
+
- test/unit/aol_contact_importer_test.rb
|
103
|
+
- test/unit/gmail_contact_importer_test.rb
|
104
|
+
- test/unit/hotmail_contact_importer_test.rb
|
105
|
+
- test/unit/outlook_test.rb
|
106
|
+
- test/unit/test_accounts_test.rb
|
107
|
+
- test/unit/vcf_test.rb
|
108
|
+
- test/unit/yahoo_csv_contact_importer_test.rb
|
109
|
+
- test/vCards.vcf
|
89
110
|
homepage: http://github.com/paperlesspost/contacts
|
90
111
|
licenses: []
|
91
112
|
post_install_message:
|