twterm 1.0.1 → 1.0.2
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/bin/twterm +1 -1
- data/lib/twterm.rb +2 -1
- data/lib/twterm/app.rb +13 -0
- data/lib/twterm/auth.rb +7 -2
- data/lib/twterm/client.rb +15 -4
- data/lib/twterm/status.rb +24 -8
- data/lib/twterm/tab/new/start.rb +13 -2
- data/lib/twterm/tab/new/user.rb +60 -0
- data/lib/twterm/tab/statuses_tab.rb +27 -12
- data/lib/twterm/tab/user_tab.rb +4 -0
- data/lib/twterm/tweetbox.rb +5 -1
- data/lib/twterm/version.rb +1 -1
- metadata +3 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: b83f1b22f92cf279b15fdb70358d86dca32a00d9
|
4
|
+
data.tar.gz: ea0d20227e837aa606fa27d73aaa0cad87e2d0ba
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: aad2fda4667c871c79b556360280a160ee4bbbced590bc5bb6e18938c9e0949bd2f454e65c2c97e5c1a99bc016ee80e348426544d8bc50ccc5276dee89784af7
|
7
|
+
data.tar.gz: e90142ebc46ec3c38ed1bb9e7a8ea5f09030b6c1306e2823865ae916aee5cca6c65a1a0fe9220aaa9c812d85fda982b4a22213de7056159059996e313f8f75d7
|
data/bin/twterm
CHANGED
data/lib/twterm.rb
CHANGED
@@ -36,6 +36,7 @@ require 'twterm/tab/mentions_tab'
|
|
36
36
|
require 'twterm/tab/new/start'
|
37
37
|
require 'twterm/tab/new/list'
|
38
38
|
require 'twterm/tab/new/search'
|
39
|
+
require 'twterm/tab/new/user'
|
39
40
|
require 'twterm/tab/search_tab'
|
40
41
|
require 'twterm/tab/timeline_tab'
|
41
42
|
require 'twterm/tab/user_tab'
|
@@ -46,6 +47,6 @@ require 'twterm/version'
|
|
46
47
|
|
47
48
|
module Twterm
|
48
49
|
class Conf
|
49
|
-
REQUIRE_VERSION = '1.0.
|
50
|
+
REQUIRE_VERSION = '1.0.2'
|
50
51
|
end
|
51
52
|
end
|
data/lib/twterm/app.rb
CHANGED
@@ -25,6 +25,8 @@ module Twterm
|
|
25
25
|
end
|
26
26
|
|
27
27
|
def run
|
28
|
+
run_periodic_cleanup
|
29
|
+
|
28
30
|
Screen.instance.wait
|
29
31
|
Screen.instance.refresh
|
30
32
|
end
|
@@ -41,5 +43,16 @@ module Twterm
|
|
41
43
|
exit
|
42
44
|
end
|
43
45
|
end
|
46
|
+
|
47
|
+
private
|
48
|
+
|
49
|
+
def run_periodic_cleanup
|
50
|
+
Thread.new do
|
51
|
+
loop do
|
52
|
+
sleep 300
|
53
|
+
Status.cleanup
|
54
|
+
end
|
55
|
+
end
|
56
|
+
end
|
44
57
|
end
|
45
58
|
end
|
data/lib/twterm/auth.rb
CHANGED
@@ -7,8 +7,13 @@ module Twterm
|
|
7
7
|
site: 'https://api.twitter.com'
|
8
8
|
)
|
9
9
|
request_token = consumer.get_request_token
|
10
|
-
|
11
|
-
|
10
|
+
url = request_token.authorize_url
|
11
|
+
begin
|
12
|
+
Launchy.open(url)
|
13
|
+
rescue Launchy::CommandNotFoundError
|
14
|
+
puts "Open the following URL to authorize yourself: #{url}"
|
15
|
+
end
|
16
|
+
print 'Input PIN: '
|
12
17
|
pin = (STDIN.gets || '').strip
|
13
18
|
access_token = request_token.get_access_token(oauth_verifier: pin)
|
14
19
|
|
data/lib/twterm/client.rb
CHANGED
@@ -85,19 +85,19 @@ module Twterm
|
|
85
85
|
|
86
86
|
def home_timeline
|
87
87
|
send_request do
|
88
|
-
yield @rest_client.home_timeline(count:
|
88
|
+
yield @rest_client.home_timeline(count: 100).map(&CREATE_STATUS_PROC)
|
89
89
|
end
|
90
90
|
end
|
91
91
|
|
92
92
|
def mentions
|
93
93
|
send_request do
|
94
|
-
yield @rest_client.mentions(count:
|
94
|
+
yield @rest_client.mentions(count: 100).map(&CREATE_STATUS_PROC)
|
95
95
|
end
|
96
96
|
end
|
97
97
|
|
98
98
|
def user_timeline(user_id)
|
99
99
|
send_request do
|
100
|
-
yield @rest_client.user_timeline(user_id, count:
|
100
|
+
yield @rest_client.user_timeline(user_id, count: 100).map(&CREATE_STATUS_PROC)
|
101
101
|
end
|
102
102
|
end
|
103
103
|
|
@@ -110,7 +110,7 @@ module Twterm
|
|
110
110
|
def list(list)
|
111
111
|
fail ArgumentError, 'argument must be an instance of List class' unless list.is_a? List
|
112
112
|
send_request do
|
113
|
-
yield @rest_client.list_timeline(list.id, count:
|
113
|
+
yield @rest_client.list_timeline(list.id, count: 100).map(&CREATE_STATUS_PROC)
|
114
114
|
end
|
115
115
|
end
|
116
116
|
|
@@ -126,6 +126,17 @@ module Twterm
|
|
126
126
|
end
|
127
127
|
end
|
128
128
|
|
129
|
+
def show_user(query)
|
130
|
+
send_request do
|
131
|
+
begin
|
132
|
+
user = User.new(@rest_client.user(query))
|
133
|
+
rescue Twitter::Error::NotFound
|
134
|
+
user = nil
|
135
|
+
end
|
136
|
+
yield user
|
137
|
+
end
|
138
|
+
end
|
139
|
+
|
129
140
|
def favorite(status)
|
130
141
|
return false unless status.is_a? Status
|
131
142
|
|
data/lib/twterm/status.rb
CHANGED
@@ -1,14 +1,15 @@
|
|
1
1
|
module Twterm
|
2
2
|
class Status
|
3
|
-
|
3
|
+
MAX_CACHED_STATUSES_COUNT = 1000
|
4
|
+
|
5
|
+
attr_reader :id, :text, :created_at, :created_at_for_sort, :retweet_count, :favorite_count, :in_reply_to_status_id, :favorited, :retweeted, :user, :retweeted_by, :urls, :media, :touched_at
|
4
6
|
alias_method :favorited?, :favorited
|
5
7
|
alias_method :retweeted?, :retweeted
|
6
8
|
|
7
|
-
@@instances =
|
9
|
+
@@instances = {}
|
8
10
|
|
9
11
|
def self.new(tweet)
|
10
|
-
|
11
|
-
instance = @@instances.find(&detector)
|
12
|
+
instance = find(tweet.id)
|
12
13
|
instance.nil? ? super : instance.update!(tweet)
|
13
14
|
end
|
14
15
|
|
@@ -39,7 +40,9 @@ module Twterm
|
|
39
40
|
|
40
41
|
expand_url!
|
41
42
|
|
42
|
-
|
43
|
+
@touched_at = Time.now
|
44
|
+
|
45
|
+
@@instances[id] = self
|
43
46
|
end
|
44
47
|
|
45
48
|
def update!(tweet)
|
@@ -79,24 +82,37 @@ module Twterm
|
|
79
82
|
def in_reply_to_status(&block)
|
80
83
|
block.call(nil) if @in_reply_to_status_id.nil?
|
81
84
|
|
82
|
-
status = Status.
|
85
|
+
status = Status.find(@in_reply_to_status_id)
|
83
86
|
block.call(status) unless status.nil?
|
84
87
|
|
85
88
|
Client.current.show_status(@in_reply_to_status_id, &block)
|
86
89
|
end
|
87
90
|
|
91
|
+
def touch!
|
92
|
+
@touched_at = Time.now
|
93
|
+
end
|
94
|
+
|
88
95
|
def ==(other)
|
89
96
|
other.is_a?(self.class) && id == other.id
|
90
97
|
end
|
91
98
|
|
92
99
|
class << self
|
93
|
-
def
|
94
|
-
@@instances
|
100
|
+
def find(id)
|
101
|
+
@@instances[id]
|
95
102
|
end
|
96
103
|
|
97
104
|
def parse_time(time)
|
98
105
|
(time.is_a?(String) ? Time.parse(time) : time.dup).localtime
|
99
106
|
end
|
107
|
+
|
108
|
+
def cleanup
|
109
|
+
count = MAX_CACHED_STATUSES_COUNT
|
110
|
+
return if @@instances.count < count
|
111
|
+
|
112
|
+
statuses = @@instances.values.sort_by(&:touched_at).take(count)
|
113
|
+
status_ids = statuses.map(&:id)
|
114
|
+
@@instances = status_ids.zip(statuses).to_h
|
115
|
+
end
|
100
116
|
end
|
101
117
|
end
|
102
118
|
end
|
data/lib/twterm/tab/new/start.rb
CHANGED
@@ -19,6 +19,10 @@ module Twterm
|
|
19
19
|
tab = Tab::New::Search.new
|
20
20
|
TabManager.instance.switch(tab)
|
21
21
|
tab.invoke_input
|
22
|
+
when 'U'
|
23
|
+
tab = Tab::New::User.new
|
24
|
+
TabManager.instance.switch(tab)
|
25
|
+
tab.invoke_input
|
22
26
|
else
|
23
27
|
return false
|
24
28
|
end
|
@@ -53,10 +57,17 @@ module Twterm
|
|
53
57
|
@window.addstr('[S]')
|
54
58
|
end
|
55
59
|
|
56
|
-
@window.setpos(
|
60
|
+
@window.setpos(8, 5)
|
61
|
+
@window.addstr('- [U] Open user tab')
|
62
|
+
@window.bold do
|
63
|
+
@window.setpos(8, 7)
|
64
|
+
@window.addstr('[U]')
|
65
|
+
end
|
66
|
+
|
67
|
+
@window.setpos(11, 3)
|
57
68
|
@window.addstr('To cancel opening a new tab, just press [w] to close this tab.')
|
58
69
|
@window.bold do
|
59
|
-
@window.setpos(
|
70
|
+
@window.setpos(11, 43)
|
60
71
|
@window.addstr('[w]')
|
61
72
|
end
|
62
73
|
@window.refresh
|
@@ -0,0 +1,60 @@
|
|
1
|
+
module Twterm
|
2
|
+
module Tab
|
3
|
+
module New
|
4
|
+
class User
|
5
|
+
include Base
|
6
|
+
include Readline
|
7
|
+
|
8
|
+
def initialize
|
9
|
+
super
|
10
|
+
|
11
|
+
@title = 'New tab'
|
12
|
+
@window.refresh
|
13
|
+
end
|
14
|
+
|
15
|
+
def respond_to_key(_)
|
16
|
+
false
|
17
|
+
end
|
18
|
+
|
19
|
+
def invoke_input
|
20
|
+
resetter = proc do
|
21
|
+
reset_prog_mode
|
22
|
+
sleep 0.1
|
23
|
+
Screen.instance.refresh
|
24
|
+
end
|
25
|
+
|
26
|
+
input_thread = Thread.new do
|
27
|
+
close_screen
|
28
|
+
puts "\nSearch user"
|
29
|
+
screen_name = readline('> @').strip
|
30
|
+
resetter.call
|
31
|
+
|
32
|
+
Client.current.show_user(screen_name) do |user|
|
33
|
+
if screen_name.nil? || screen_name.empty? || user.nil?
|
34
|
+
Notifier.instance.show_error 'User not found' if user.nil?
|
35
|
+
tab = Tab::New::Start.new
|
36
|
+
else
|
37
|
+
tab = Tab::UserTab.new(user)
|
38
|
+
end
|
39
|
+
|
40
|
+
TabManager.instance.switch(tab)
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
App.instance.register_interruption_handler do
|
45
|
+
input_thread.kill
|
46
|
+
resetter.call
|
47
|
+
tab = Tab::New::Start.new
|
48
|
+
TabManager.instance.switch(tab)
|
49
|
+
end
|
50
|
+
|
51
|
+
input_thread.join
|
52
|
+
end
|
53
|
+
|
54
|
+
private
|
55
|
+
|
56
|
+
def update; end
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
@@ -8,16 +8,30 @@ module Twterm
|
|
8
8
|
def initialize
|
9
9
|
super
|
10
10
|
|
11
|
-
@
|
11
|
+
@status_ids = []
|
12
|
+
|
13
|
+
Thread.new do
|
14
|
+
loop do
|
15
|
+
statuses.take(100).each(&:touch!)
|
16
|
+
sleep 60
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
def statuses
|
22
|
+
statuses = @status_ids.map { |id| Status.find(id) }.reject(&:nil?)
|
23
|
+
@status_ids = statuses.map(&:id)
|
24
|
+
statuses
|
12
25
|
end
|
13
26
|
|
14
27
|
def prepend(status)
|
15
28
|
fail unless status.is_a? Status
|
16
29
|
|
17
|
-
return if @
|
30
|
+
return if @status_ids.include?(status.id)
|
18
31
|
|
19
|
-
@
|
32
|
+
@status_ids << status.id
|
20
33
|
status.split(@window.maxx - 4)
|
34
|
+
status.touch!
|
21
35
|
item_prepended
|
22
36
|
refresh
|
23
37
|
end
|
@@ -25,10 +39,11 @@ module Twterm
|
|
25
39
|
def append(status)
|
26
40
|
fail ArgumentError, 'argument must be an instance of Status class' unless status.is_a? Status
|
27
41
|
|
28
|
-
return if @
|
42
|
+
return if @status_ids.include?(status.id)
|
29
43
|
|
30
|
-
@
|
44
|
+
@status_ids.unshift(status.id)
|
31
45
|
status.split(@window.maxx - 4)
|
46
|
+
status.touch!
|
32
47
|
item_appended
|
33
48
|
refresh
|
34
49
|
end
|
@@ -59,8 +74,7 @@ module Twterm
|
|
59
74
|
end
|
60
75
|
|
61
76
|
def delete_status(status_id)
|
62
|
-
|
63
|
-
@statuses.delete_if(&detector)
|
77
|
+
@status_ids.delete(status_id)
|
64
78
|
refresh
|
65
79
|
end
|
66
80
|
|
@@ -93,7 +107,7 @@ module Twterm
|
|
93
107
|
|
94
108
|
@window.clear
|
95
109
|
|
96
|
-
|
110
|
+
statuses.reverse.drop(offset).each.with_index(offset) do |status, i|
|
97
111
|
formatted_lines = status.split(@window.maxx - 4).count
|
98
112
|
if current_line + formatted_lines + 2 > @window.maxy
|
99
113
|
@scrollable_last = i
|
@@ -202,18 +216,19 @@ module Twterm
|
|
202
216
|
private
|
203
217
|
|
204
218
|
def highlighted_status
|
205
|
-
@
|
219
|
+
id = @status_ids[count - index - 1]
|
220
|
+
Status.find(id)
|
206
221
|
end
|
207
222
|
|
208
223
|
def count
|
209
|
-
@
|
224
|
+
@status_ids.count
|
210
225
|
end
|
211
226
|
|
212
227
|
def offset_from_bottom
|
213
228
|
return @offset_from_bottom unless @offset_from_bottom.nil?
|
214
229
|
|
215
230
|
height = 0
|
216
|
-
|
231
|
+
statuses.each.with_index(-1) do |status, i|
|
217
232
|
height += status.split(@window.maxx - 4).count + 2
|
218
233
|
if height >= @window.maxy
|
219
234
|
@offset_from_bottom = i
|
@@ -224,7 +239,7 @@ module Twterm
|
|
224
239
|
end
|
225
240
|
|
226
241
|
def sort
|
227
|
-
@
|
242
|
+
@status_ids.sort_by! { |id| Status.find(id).created_at_for_sort }
|
228
243
|
end
|
229
244
|
|
230
245
|
def show_help
|
data/lib/twterm/tab/user_tab.rb
CHANGED
data/lib/twterm/tweetbox.rb
CHANGED
@@ -23,7 +23,11 @@ module Twterm
|
|
23
23
|
|
24
24
|
thread = Thread.new do
|
25
25
|
close_screen
|
26
|
-
|
26
|
+
if @in_reply_to.nil?
|
27
|
+
puts "\nCompose new tweet:"
|
28
|
+
else
|
29
|
+
puts "\nReply to @#{@in_reply_to.user.screen_name}'s tweet: \"#{@in_reply_to.text}\""
|
30
|
+
end
|
27
31
|
@status = readline(@in_reply_to.nil? ? '> ' : " @#{in_reply_to.user.screen_name} ", true)
|
28
32
|
resetter.call
|
29
33
|
post
|
data/lib/twterm/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: twterm
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.0.
|
4
|
+
version: 1.0.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Ryota Kameoka
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-03-
|
11
|
+
date: 2015-03-23 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: curses
|
@@ -146,6 +146,7 @@ files:
|
|
146
146
|
- lib/twterm/tab/new/list.rb
|
147
147
|
- lib/twterm/tab/new/search.rb
|
148
148
|
- lib/twterm/tab/new/start.rb
|
149
|
+
- lib/twterm/tab/new/user.rb
|
149
150
|
- lib/twterm/tab/scrollable.rb
|
150
151
|
- lib/twterm/tab/search_tab.rb
|
151
152
|
- lib/twterm/tab/statuses_tab.rb
|