fake_friends 1.0.1 → 1.0.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/README.md +25 -15
- data/Rakefile +14 -1
- data/dev/fetch_from_twitter.rb +42 -33
- data/dev/usernames.yml +0 -2
- data/fake_friends.gemspec +12 -18
- data/lib/fake_friends/users.yml +9559 -6567
- data/lib/fake_friends/version.rb +1 -1
- data/lib/fake_friends.rb +30 -24
- data/spec/fake_friends_spec.rb +28 -29
- data/spec/spec_helper.rb +3 -5
- metadata +12 -13
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 7fa347b02b31c2cda971456e866fff0c9050cab3
|
4
|
+
data.tar.gz: c93a5bd06c8fc75a765a909a3ea8d897b223207b
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 7f9b02a59830956ed2be01dd9ec8634f6a407816432c6d70f364fca54ec641b9505b40e498504dff7a1b8d2ba0348824848328ca792e42034b1b60416edc0df7
|
7
|
+
data.tar.gz: fd363a0e634549019d7ac362981342d48c3fea158c3801c503c7d76d4b1b9f899cf4e2046c8bdd613e2de0a898ded71568c4437510035ccd7b30e686b9eab435
|
data/.gitignore
CHANGED
data/README.md
CHANGED
@@ -1,14 +1,21 @@
|
|
1
1
|
# FakeFriends
|
2
2
|
|
3
3
|
[![Gem Version](https://badge.fury.io/rb/fake_friends.png)](http://badge.fury.io/rb/fake_friends)
|
4
|
-
[![Code Climate](https://codeclimate.com/github/
|
5
|
-
[![
|
6
|
-
[![
|
4
|
+
[![Code Climate](https://codeclimate.com/github/jkrmr/fake_friends.png)](https://codeclimate.com/github/jkrmr/fake_friends)
|
5
|
+
[![Build Status](https://travis-ci.org/jkrmr/fake_friends.png?branch=master)](https://travis-ci.org/jkrmr/fake_friends)
|
6
|
+
[![Dependency Status](https://gemnasium.com/jkrmr/fake_friends.svg)](https://gemnasium.com/jkrmr/fake_friends)
|
7
7
|
|
8
|
-
|
8
|
+
|
9
|
+
A simple [ruby gem](https://rubygems.org/gems/fake_friends) to generate
|
10
|
+
consistent and realistic fake user data for demoing social networking apps
|
11
|
+
(e.g., user names match their avatars, fake posts are pulled from actual Twitter
|
12
|
+
posts rather than lorem text, etc), modeled on the popular
|
13
|
+
[faker](https://github.com/stympy/faker) gem.
|
9
14
|
|
10
15
|
|
11
16
|
## Release Notes
|
17
|
+
**1.0.2** Refreshes user library contents, goes back to 100 users, makes `::all` public<br>
|
18
|
+
**1.0.1** Clarifies documentation, updates dependencies, fixes gemspec typos<br>
|
12
19
|
**1.0.0** Rewrites fetch script and updates it for Twitter API v1.1 (backwards incompatible), minor bug fixed<br>
|
13
20
|
**0.1.6** Adds tests in RSpec<br>
|
14
21
|
**0.1.5** Inital release<br>
|
@@ -24,17 +31,18 @@ Or install it yourself as: `$ gem install fake_friends`<br>
|
|
24
31
|
## The FakeFriend class
|
25
32
|
|
26
33
|
#### class methods
|
27
|
-
* `::gather(n)
|
34
|
+
* `::gather(n)`<br>
|
28
35
|
`n`: int (number of user objects to create)
|
29
|
-
* `::find_by(options)
|
30
|
-
`options`: { `username:` string (twitter username) } or { `id:` int (from 1 to
|
36
|
+
* `::find_by(options)`<br>
|
37
|
+
`options`: { `username:` string (twitter username) } or { `id:` int (from 1 to 100) }
|
38
|
+
* `::all`
|
31
39
|
|
32
40
|
#### instance methods
|
33
41
|
* `#username`
|
34
42
|
* `#name`
|
35
43
|
* `#description`
|
36
44
|
* `#avatar_url(size)`
|
37
|
-
`size`: requested size of image. Available in 128, 73, 48, and 24 px
|
45
|
+
`size`: requested size of image. Available in 128, 73, 48, and 24 px.<br>
|
38
46
|
Returns a url to an image in the closest available size.
|
39
47
|
* `#url`
|
40
48
|
* `#posts`
|
@@ -49,11 +57,13 @@ to return an array of 5 `FakeFriend` objects.
|
|
49
57
|
|
50
58
|
user = FakeFriend.find_by(id: 5)
|
51
59
|
|
52
|
-
returns the fifth user in the library and assigns it to `user
|
60
|
+
returns the fifth user in the library and assigns it to `user`, and use
|
61
|
+
|
62
|
+
FakeFriend.all
|
63
|
+
|
64
|
+
to return all the users in the library.
|
53
65
|
|
54
|
-
`user.avatar_url(size)` pulls an avatar from uiFaces.com, where Twitter users have contributed their profile photos.
|
55
|
-
The available sizes (in pixels) are 128, 73, 48, and 24. The method will choose the image closest in size
|
56
|
-
to the requested `size`.
|
66
|
+
`user.avatar_url(size)` pulls an avatar from uiFaces.com, where Twitter users have contributed their profile photos. The available sizes (in pixels) are 128, 73, 48, and 24. The method will choose the image closest in size to the requested `size`.
|
57
67
|
|
58
68
|
`user.url` returns a hash with an `:expanded` url (e.g. `http://www.google.com`) and a `:display` url (e.g. `google.com`).
|
59
69
|
|
@@ -62,11 +72,11 @@ to the requested `size`.
|
|
62
72
|
|
63
73
|
## Data
|
64
74
|
|
65
|
-
The library currently holds
|
75
|
+
The library currently holds 100 users with associated status updates. Associated image urls are generated from the username.
|
66
76
|
|
67
77
|
## Source
|
68
|
-
Images come from user contributions on uiFaces.com
|
69
|
-
Posts are non-retweet tweets from the associated twitter profiles (all public)
|
78
|
+
Images come from user contributions on uiFaces.com.<br>
|
79
|
+
Posts are non-retweet tweets from the associated twitter profiles (all public).<br>
|
70
80
|
Many thanks to these users for their contributions.
|
71
81
|
|
72
82
|
|
data/Rakefile
CHANGED
@@ -1,5 +1,18 @@
|
|
1
|
-
require
|
1
|
+
require 'bundler/gem_tasks'
|
2
2
|
require 'rspec/core/rake_task'
|
3
|
+
require 'yaml'
|
3
4
|
|
4
5
|
RSpec::Core::RakeTask.new('spec')
|
5
6
|
task default: :spec
|
7
|
+
|
8
|
+
|
9
|
+
namespace :fake_friends do
|
10
|
+
desc 'Re-generates library with fresh data from twitter'
|
11
|
+
task :refresh do
|
12
|
+
credentials = YAML.load_file('application.yml')
|
13
|
+
credentials.each_pair{ |key, val| ENV[key] = val }
|
14
|
+
ruby "dev/fetch_from_twitter.rb"
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
|
data/dev/fetch_from_twitter.rb
CHANGED
@@ -1,13 +1,15 @@
|
|
1
1
|
require 'twitter'
|
2
2
|
require 'yaml'
|
3
3
|
|
4
|
+
PROJ_ROOT = File.expand_path("../../", __FILE__)
|
5
|
+
|
4
6
|
class TweetFetcher
|
5
7
|
attr_reader :twitter_client, :number_of_users, :max_posts_per_user,
|
6
8
|
:avail_users, :output_file_rel_path, :fake_friends
|
7
9
|
|
8
|
-
def initialize(opt={ users: 100, max_posts_per_user:
|
9
|
-
user_list:
|
10
|
-
output_file:
|
10
|
+
def initialize(opt={ users: 100, max_posts_per_user: 60,
|
11
|
+
user_list: "#{PROJ_ROOT}/dev/usernames.yml",
|
12
|
+
output_file: "#{PROJ_ROOT}/lib/fake_friends/users.yml" } )
|
11
13
|
|
12
14
|
@number_of_users = opt[:users]
|
13
15
|
@max_posts_per_user = opt[:max_posts_per_user]
|
@@ -16,23 +18,19 @@ class TweetFetcher
|
|
16
18
|
|
17
19
|
@fake_friends = {} # users to be stored as FakeFriend objects
|
18
20
|
@twitter_client = initialize_twitter_api_client
|
21
|
+
puts "\nTwitter API credentials set."
|
19
22
|
end
|
20
23
|
|
21
24
|
# ---
|
22
25
|
# prompts for twitter api credentials and returns a client
|
23
26
|
# ---
|
24
27
|
def initialize_twitter_api_client
|
25
|
-
puts
|
26
|
-
|
28
|
+
puts "\nEnter your Twitter API credentials (get some @ dev.twitter.com)."
|
27
29
|
Twitter::REST::Client.new do |config|
|
28
|
-
|
29
|
-
config.
|
30
|
-
|
31
|
-
config.
|
32
|
-
print 'oauth token: '
|
33
|
-
config.oauth_token = gets.chomp
|
34
|
-
print 'oauth token secret: '
|
35
|
-
config.oauth_token_secret = gets.chomp
|
30
|
+
config.consumer_key = ENV["API_KEY"] || prompt_for('api key')
|
31
|
+
config.consumer_secret = ENV["API_SEC"] || prompt_for('api secret')
|
32
|
+
config.access_token = ENV["TOKEN"] || prompt_for('access token')
|
33
|
+
config.access_token_secret = ENV["TOKEN_SEC"] || prompt_for('access token secret')
|
36
34
|
end
|
37
35
|
end
|
38
36
|
|
@@ -51,13 +49,19 @@ class TweetFetcher
|
|
51
49
|
# Fetches users and their tweets, iteratively saves them to file as YAML
|
52
50
|
# ---
|
53
51
|
def fetch_users_and_their_tweets
|
54
|
-
users = avail_users.
|
52
|
+
users = avail_users.take(number_of_users)
|
55
53
|
|
56
|
-
puts ""
|
57
54
|
users.each_with_index do |username, user_num|
|
58
|
-
|
59
|
-
|
60
|
-
|
55
|
+
begin
|
56
|
+
if user_exists_and_tweets_are_public?(username)
|
57
|
+
fake_friends[username] = create_user_hash_for(username)
|
58
|
+
update_output_file_with(username, user_num)
|
59
|
+
else
|
60
|
+
puts "user #{username} no longer exists or does not have a public account."
|
61
|
+
end
|
62
|
+
rescue Twitter::Error::RequestTimeout
|
63
|
+
countdown_minutes(1)
|
64
|
+
retry
|
61
65
|
end
|
62
66
|
end
|
63
67
|
|
@@ -67,38 +71,43 @@ class TweetFetcher
|
|
67
71
|
private
|
68
72
|
|
69
73
|
# ---
|
70
|
-
#
|
74
|
+
# Prompts for user input, returns string
|
75
|
+
# ---
|
76
|
+
def prompt_for(string)
|
77
|
+
print "#{string}: "
|
78
|
+
gets.chomp
|
79
|
+
end
|
80
|
+
|
81
|
+
# ---
|
82
|
+
# Returns true only if the requested account exists and is public
|
71
83
|
# ---
|
72
84
|
def user_exists_and_tweets_are_public?(u)
|
73
85
|
twitter_client.user?(u) && !twitter_client.user(u).protected?
|
86
|
+
rescue Twitter::Error::Forbidden
|
87
|
+
false
|
74
88
|
end
|
75
89
|
|
76
90
|
# ---
|
77
91
|
# For a given Twitter user, returns a hash with the following strings:
|
78
92
|
# name, location, description, url[:expanded], url[:display], image url
|
79
|
-
# and an array containing the desired number of tweets
|
93
|
+
# and an array containing the desired maximum number of tweets
|
80
94
|
# ---
|
81
95
|
def create_user_hash_for(u)
|
82
96
|
user = twitter_client.user(u) # load user
|
83
|
-
posts = posts(u, max_posts_per_user) # fetch 100 posts
|
97
|
+
posts = posts(u, max_posts_per_user) # fetch <= 100 posts
|
84
98
|
|
85
|
-
begin # get
|
99
|
+
begin # get urls if they exist
|
86
100
|
expanded_url = user.attrs[:entities][:url][:urls].first[:expanded_url]
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
begin # get display url if it exists
|
92
|
-
display_url = user.attrs[:entities][:url][:urls].first[:display_url]
|
93
|
-
rescue
|
94
|
-
display_url = nil
|
101
|
+
display_url = user.attrs[:entities][:url][:urls].first[:display_url]
|
102
|
+
rescue NoMethodError
|
103
|
+
expanded_url = display_url = nil
|
95
104
|
end
|
96
105
|
|
97
106
|
{
|
98
107
|
name: user.name, location: user.location,
|
99
108
|
description: user.description,
|
100
109
|
url: { expanded: expanded_url, display: display_url },
|
101
|
-
image: user.profile_image_url, posts: posts
|
110
|
+
image: user.profile_image_url.to_s, posts: posts
|
102
111
|
}
|
103
112
|
end
|
104
113
|
|
@@ -111,7 +120,7 @@ class TweetFetcher
|
|
111
120
|
f.write(fake_friends.to_yaml)
|
112
121
|
end
|
113
122
|
|
114
|
-
puts "
|
123
|
+
puts "\nfetched and saved user #{number+1}: #{user}"
|
115
124
|
|
116
125
|
if number_of_users <= 75
|
117
126
|
# small number fetched in batches, rest every 15th user
|
@@ -130,7 +139,7 @@ class TweetFetcher
|
|
130
139
|
puts "taking a #{min}-minute power nap to stay within Twitter API rate limits..."
|
131
140
|
seconds = (min * 60).to_i
|
132
141
|
|
133
|
-
|
142
|
+
seconds.downto 0 do |sec|
|
134
143
|
print "\r%02d:%02d:%02d" % [ sec / 3600, sec / 60, sec % 60 ]
|
135
144
|
$stdout.flush
|
136
145
|
sleep 1
|
data/dev/usernames.yml
CHANGED
data/fake_friends.gemspec
CHANGED
@@ -4,27 +4,21 @@ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
|
4
4
|
require 'fake_friends/version'
|
5
5
|
|
6
6
|
Gem::Specification.new do |spec|
|
7
|
-
spec.name =
|
7
|
+
spec.name = 'fake_friends'
|
8
8
|
spec.version = FakeFriends::VERSION
|
9
|
-
spec.authors = [
|
10
|
-
spec.email = [
|
11
|
-
spec.description =
|
12
|
-
spec.summary =
|
13
|
-
|
14
|
-
|
15
|
-
spec.homepage = "http://github.com/jmromer/FakeFriends"
|
16
|
-
spec.license = "MIT"
|
9
|
+
spec.authors = ['Jake Romer']
|
10
|
+
spec.email = ['jacob.romer@icloud.com']
|
11
|
+
spec.description = 'A simple fake user generator'
|
12
|
+
spec.summary = 'Generates fake users with consistent attributes from public Twitter accounts and image urls from uiFaces.com.'
|
13
|
+
spec.homepage = 'http://github.com/jkrmr/fake_friends'
|
14
|
+
spec.license = 'MIT'
|
17
15
|
spec.files = `git ls-files`.split($/)
|
18
16
|
spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
|
19
17
|
spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
|
20
|
-
spec.require_paths = [
|
18
|
+
spec.require_paths = ['lib']
|
21
19
|
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
spec.add_development_dependency
|
26
|
-
spec.add_development_dependency "rspec", "~> 2.14.1"
|
27
|
-
|
28
|
-
spec.add_development_dependency "bundler", "~> 1.5.2"
|
29
|
-
spec.add_development_dependency "rake", "~> 10.1.0"
|
20
|
+
spec.add_development_dependency 'twitter', '~> 5.6'
|
21
|
+
spec.add_development_dependency 'rspec', '~> 2.14'
|
22
|
+
spec.add_development_dependency 'bundler', '~> 1.5'
|
23
|
+
spec.add_development_dependency 'rake', '~> 10.1'
|
30
24
|
end
|