slack_neuralyzer 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.codeclimate.yml +16 -0
- data/.gitignore +9 -0
- data/.rspec +2 -0
- data/.travis.yml +6 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +21 -0
- data/README.md +216 -0
- data/Rakefile +6 -0
- data/bin/console +14 -0
- data/bin/setup +8 -0
- data/bin/slack_neuralyzer +13 -0
- data/lib/slack_api/errors/not_found.rb +9 -0
- data/lib/slack_api/errors/response.rb +9 -0
- data/lib/slack_api/slack_api.rb +1 -0
- data/lib/slack_neuralyzer.rb +26 -0
- data/lib/slack_neuralyzer/args_parser.rb +98 -0
- data/lib/slack_neuralyzer/cleaner/base.rb +73 -0
- data/lib/slack_neuralyzer/cleaner/files.rb +41 -0
- data/lib/slack_neuralyzer/cleaner/messages.rb +83 -0
- data/lib/slack_neuralyzer/cli.rb +23 -0
- data/lib/slack_neuralyzer/colorizable.rb +16 -0
- data/lib/slack_neuralyzer/dict.rb +118 -0
- data/lib/slack_neuralyzer/errors/mutually_exclusive_arguments.rb +9 -0
- data/lib/slack_neuralyzer/errors/required_arguments.rb +9 -0
- data/lib/slack_neuralyzer/helper.rb +23 -0
- data/lib/slack_neuralyzer/logger.rb +23 -0
- data/lib/slack_neuralyzer/multi_io.rb +34 -0
- data/lib/slack_neuralyzer/version.rb +3 -0
- data/screenshots/general_test_token.png +0 -0
- data/screenshots/neuralyzer.gif +0 -0
- data/screenshots/slack_neuralyzer_demo.gif +0 -0
- data/slack_neuralyzer.gemspec +28 -0
- metadata +161 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: f34f12786efe803fc3109712824067b26c27e228
|
4
|
+
data.tar.gz: 9e84e469278787d33e1438b8306110ce7c2b0c41
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: 9d2c9932289e8bdbbee6e12318eaf4192b8466eac8fe6f9037acfe764a530c8a1bd1c823d1841c23302f16c39a7edb45d740f3a9978bf93b55a38316c85c267b
|
7
|
+
data.tar.gz: d88b648cc1f468161e75477b37c6265a44b72a2b02ac7c929299f7a61f72c2ce18e596621b37379f712cf38d16a1b2c5c1ab55cba369d659e88b534cb025bcba
|
data/.codeclimate.yml
ADDED
data/.gitignore
ADDED
data/.rspec
ADDED
data/.travis.yml
ADDED
data/Gemfile
ADDED
data/LICENSE.txt
ADDED
@@ -0,0 +1,21 @@
|
|
1
|
+
The MIT License (MIT)
|
2
|
+
|
3
|
+
Copyright (c) 2016 Leon Ji
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
7
|
+
in the Software without restriction, including without limitation the rights
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
10
|
+
furnished to do so, subject to the following conditions:
|
11
|
+
|
12
|
+
The above copyright notice and this permission notice shall be included in
|
13
|
+
all copies or substantial portions of the Software.
|
14
|
+
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
21
|
+
THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,216 @@
|
|
1
|
+
# Slack Neuralyzer
|
2
|
+
|
3
|
+
[![Build Status](https://travis-ci.org/mgleon08/slack_neuralyzer.svg?branch=master)](https://travis-ci.org/mgleon08/slack_neuralyzer)
|
4
|
+
[![Coverage Status](https://coveralls.io/repos/github/mgleon08/slack_neuralyzer/badge.svg?branch=master)](https://coveralls.io/github/mgleon08/slack_neuralyzer?branch=master)
|
5
|
+
[![Code Climate](https://codeclimate.com/github/mgleon08/slack_neuralyzer/badges/gpa.svg)](https://codeclimate.com/github/mgleon08/slack_neuralyzer)
|
6
|
+
[![security](https://hakiri.io/github/mgleon08/slack_neuralyzer/master.svg)](https://hakiri.io/github/mgleon08/slack_neuralyzer/master)
|
7
|
+
[![MIT licensed](https://img.shields.io/badge/license-MIT-blue.svg)](https://github.com/mgleon08/slack_neuralyzer/blob/master/LICENSE.txt)
|
8
|
+
|
9
|
+
Slack Neuralyzer is a ruby gem for bulk delete messages and files on Slack channels.
|
10
|
+
|
11
|
+
The easiest way to clean up messages and files on Slack.
|
12
|
+
|
13
|
+
![](https://media.giphy.com/media/65NO1TrKrJUT6/giphy.gif)
|
14
|
+
|
15
|
+
## Installation
|
16
|
+
|
17
|
+
```
|
18
|
+
$ gem install slack_neuralyzer
|
19
|
+
```
|
20
|
+
|
21
|
+
## Slack token
|
22
|
+
|
23
|
+
<a href='https://api.slack.com/web' target='_blank'><img src='screenshots/general_test_token.png' alt='general_test_token' width = '20%' /></a>
|
24
|
+
|
25
|
+
##Getting Started
|
26
|
+
|
27
|
+
![](screenshots/slack_neuralyzer_demo.gif)
|
28
|
+
|
29
|
+
### Show all channel names
|
30
|
+
|
31
|
+
`slack_neuralyzer -t <TOKEN> -s`
|
32
|
+
|
33
|
+
```ruby
|
34
|
+
All user direct:
|
35
|
+
001. leon
|
36
|
+
002. slackbot
|
37
|
+
003. cleanerbot
|
38
|
+
|
39
|
+
All channels (public):
|
40
|
+
001. general
|
41
|
+
002. random
|
42
|
+
|
43
|
+
All groups (private):
|
44
|
+
001. private_channel
|
45
|
+
|
46
|
+
All multiparty direct:
|
47
|
+
001. mpdm-leon--cleanerbot-1
|
48
|
+
002. mpdm-leon--slackbot-1
|
49
|
+
```
|
50
|
+
|
51
|
+
### Delete message(s)
|
52
|
+
|
53
|
+
>Rerun below command and use `-e | --execute` to actually delete the message(s).
|
54
|
+
|
55
|
+
* Channel
|
56
|
+
|
57
|
+
`-C | --channel` `-D | --direct` `-G | --group` `-M | --mpdirect`
|
58
|
+
|
59
|
+
```ruby
|
60
|
+
# Delete all user messages in general channel
|
61
|
+
slack_neuralyzer -t <TOKEN> -m -C general -u all
|
62
|
+
|
63
|
+
# Delete all user messages in leon direct channel
|
64
|
+
slack_neuralyzer -t <TOKEN> -m -D leon -u all
|
65
|
+
|
66
|
+
# Delete all user messages in private_channel groups channel
|
67
|
+
slack_neuralyzer -t <TOKEN> -m -G private_channel -u all
|
68
|
+
|
69
|
+
# Delete all user messages in mpdm-leon--cleanerbot-1 multiparty direct channel
|
70
|
+
# (can `use slack_neuralyzer -t <TOKEN> -s` to see mpdirect channle name)
|
71
|
+
slack_neuralyzer -t <TOKEN> -m -M mpdm-leon--cleanerbot-1 -u all
|
72
|
+
```
|
73
|
+
|
74
|
+
* Specific user
|
75
|
+
|
76
|
+
`-u | --user`
|
77
|
+
|
78
|
+
```ruby
|
79
|
+
# Delete leon messages in general channel
|
80
|
+
slack_neuralyzer -t <TOKEN> -m -C general -u leon
|
81
|
+
|
82
|
+
# if you want to specific all users, you can type 'all'
|
83
|
+
slack_neuralyzer -t <TOKEN> -m -C general -u all
|
84
|
+
```
|
85
|
+
|
86
|
+
* Specific Bot
|
87
|
+
|
88
|
+
`-b | --bot`
|
89
|
+
|
90
|
+
```ruby
|
91
|
+
# Delete bots messages in general channel
|
92
|
+
slack_neuralyzer -t <TOKEN> -m -C general -b cleanerbot
|
93
|
+
|
94
|
+
# if you want to specific all bots, you can type 'all' (not bot users)
|
95
|
+
slack_neuralyzer -t <TOKEN> -m -C general -b all
|
96
|
+
```
|
97
|
+
|
98
|
+
* Delete message(s) between two dates
|
99
|
+
|
100
|
+
`-A | --after` `-B | --before`
|
101
|
+
|
102
|
+
```ruby
|
103
|
+
# Delete all user messages in general channel at 20160101 to 20161212
|
104
|
+
slack_neuralyzer -t <TOKEN> -m -C general -u all -A 20160101 -B 20161212
|
105
|
+
```
|
106
|
+
|
107
|
+
* Delete message(s) with specified text
|
108
|
+
|
109
|
+
`-R | --regex`
|
110
|
+
|
111
|
+
```ruby
|
112
|
+
# Delete all user messages with hello string in general channel
|
113
|
+
slack_neuralyzer -t <TOKEN> -m -C general -u all -R hello
|
114
|
+
```
|
115
|
+
|
116
|
+
### Delete file(s)
|
117
|
+
|
118
|
+
> File types: all, spaces, snippets, images, gdocs, docs, zips, pdfs
|
119
|
+
|
120
|
+
>Rerun below command and use `-e | --execute` to actually delete the message(s).
|
121
|
+
|
122
|
+
* Channel
|
123
|
+
|
124
|
+
`-C | --channel` `-D | --direct` `-G | --group` `-M | --mpdirect`
|
125
|
+
|
126
|
+
```ruby
|
127
|
+
# Delete all user upload all type file in general channel
|
128
|
+
slack_neuralyzer -t <TOKEN> -f all -C general -u all
|
129
|
+
|
130
|
+
# Delete leon upload all images file in leon direct channel
|
131
|
+
slack_neuralyzer -t <TOKEN> -f images -D leon -u leon
|
132
|
+
|
133
|
+
# Delete all user upload all pdfs file in private_channel groups channel
|
134
|
+
slack_neuralyzer -t <TOKEN> -f pdfs -G private_channel -u all
|
135
|
+
|
136
|
+
# Delete all user upload all zips file in mpdm-leon--cleanerbot-1 multiparty direct channel
|
137
|
+
# (can `use slack_neuralyzer -t <TOKEN> -s` to see mpdirect channle name)
|
138
|
+
slack_neuralyzer -t <TOKEN> -f zips -M mpdm-leon--cleanerbot-1 -u all
|
139
|
+
```
|
140
|
+
|
141
|
+
* Specific user and file type
|
142
|
+
|
143
|
+
`-u | --user` `-f | --file`
|
144
|
+
|
145
|
+
```ruby
|
146
|
+
# Delete leon upload images file in general channel
|
147
|
+
slack_neuralyzer -t <TOKEN> -f images -C general -u leon
|
148
|
+
```
|
149
|
+
|
150
|
+
* Delete file between two dates
|
151
|
+
|
152
|
+
`-A | --after` `-B | --before`
|
153
|
+
|
154
|
+
```ruby
|
155
|
+
# Delete all user upload all type file in general channel at 20160101 to 20161212
|
156
|
+
slack_neuralyzer -t <TOKEN> -f all -C general -u all -A 20160101 -B 20161212
|
157
|
+
```
|
158
|
+
|
159
|
+
### Generate log file
|
160
|
+
|
161
|
+
`-l | --log`
|
162
|
+
|
163
|
+
```ruby
|
164
|
+
# Generate a log file in the current directory in ./slack_neuralyzer/YYYY-MM-DDTHH:MM:SS
|
165
|
+
slack_neuralyzer -t <TOKEN> -m -C general -u all -A 20160101 -B 20161212 -l
|
166
|
+
```
|
167
|
+
|
168
|
+
|
169
|
+
### Rate
|
170
|
+
|
171
|
+
`-r | --rate`
|
172
|
+
|
173
|
+
```ruby
|
174
|
+
# Delay between API calls in seconds (default:0.05)
|
175
|
+
slack_neuralyzer -t <TOKEN> -m -C general -u all -r 0.01
|
176
|
+
```
|
177
|
+
|
178
|
+
|
179
|
+
### Help
|
180
|
+
|
181
|
+
`-h | --help`
|
182
|
+
|
183
|
+
```
|
184
|
+
usage:
|
185
|
+
slack_neuralyzer [options]
|
186
|
+
See https://github.com/mgleon08/slack_neuralyzer for more information.
|
187
|
+
|
188
|
+
options:
|
189
|
+
-t, --token TOKEN Slack API token (https://api.slack.com/web)
|
190
|
+
-s, --show Show all users, channels, groups and multiparty direct names
|
191
|
+
-m, --message Specifies that the delete object is messages
|
192
|
+
-f, --file TYPE Specifies that the delete object is files of a certain type (Type: all, spaces, snippets, images, gdocs, docs, zips, pdfs)
|
193
|
+
-C, --channel CHANNEL Public channel name (e.g., general, random)
|
194
|
+
-D, --direct DIRECT Direct messages channel name (e.g., leon)
|
195
|
+
-G, --group GROUP Private groups channel name
|
196
|
+
-M, --mpdirect MPDIRECT Multiparty direct messages channel name (e.g., mpdm-leon--bot-1 [--show option to see name])
|
197
|
+
-u, --user USER Delete messages/files from the specific user (if you want to specific all users, you can type 'all')
|
198
|
+
-b, --bot BOT Delete messages from the specific bot (not bot users, if you want to specific all bots, you can type 'all')
|
199
|
+
-A, --after DATE Delete messages/files after than this time (YYYYMMDD)
|
200
|
+
-B, --before DATE Delete messages/files before than this time (YYYYMMDD)
|
201
|
+
-R, --regex TEXT Delete messages with specified text (regular expression)
|
202
|
+
-e, --execute Execute the delete task
|
203
|
+
-l, --log Generate a log file in the current directory
|
204
|
+
-r, --rate RATE Delay between API calls in seconds (default:0.1)
|
205
|
+
-v, --version Show the SlackNeuralyzer version
|
206
|
+
-h, --help Show this message
|
207
|
+
```
|
208
|
+
|
209
|
+
## Contributing
|
210
|
+
|
211
|
+
Bug reports and pull requests are welcome on GitHub at [`https://github.com/mgleon08/slack_neuralyzer/pulls`](https://github.com/mgleon08/slack_neuralyzer/pulls)
|
212
|
+
|
213
|
+
## Copyright & License
|
214
|
+
|
215
|
+
* Copyright (c) 2016 Leon Ji. See [LICENSE.txt](https://github.com/mgleon08/slack_neuralyzer/blob/master/LICENSE.txt) for further details.
|
216
|
+
* The gem is available as open source under the terms of the [MIT License](http://opensource.org/licenses/MIT).
|
data/Rakefile
ADDED
data/bin/console
ADDED
@@ -0,0 +1,14 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
require "bundler/setup"
|
4
|
+
require "slack_neuralyzer"
|
5
|
+
|
6
|
+
# You can add fixtures and/or initialization code here to make experimenting
|
7
|
+
# with your gem easier. You can also use a different console, if you like.
|
8
|
+
|
9
|
+
# (If you use this, don't forget to add pry to your Gemfile!)
|
10
|
+
# require "pry"
|
11
|
+
# Pry.start
|
12
|
+
|
13
|
+
require "irb"
|
14
|
+
IRB.start
|
data/bin/setup
ADDED
@@ -0,0 +1,13 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
require_relative '../lib/slack_neuralyzer'
|
3
|
+
|
4
|
+
begin
|
5
|
+
args = SlackNeuralyzer::ArgsParser.new(ARGV)
|
6
|
+
logger = SlackNeuralyzer::Logger.default(args.log)
|
7
|
+
dict = SlackNeuralyzer::Dict.new(args.token)
|
8
|
+
cli = SlackNeuralyzer::Cli.new(args, dict, logger)
|
9
|
+
cli.run
|
10
|
+
rescue => e
|
11
|
+
$stderr.puts e.message
|
12
|
+
exit
|
13
|
+
end
|
@@ -0,0 +1 @@
|
|
1
|
+
require 'slack'
|
@@ -0,0 +1,26 @@
|
|
1
|
+
$LOAD_PATH << File.dirname(__FILE__)
|
2
|
+
|
3
|
+
require 'optparse'
|
4
|
+
require 'time'
|
5
|
+
require 'colorize'
|
6
|
+
require 'logger'
|
7
|
+
|
8
|
+
require 'slack_api/slack_api'
|
9
|
+
require 'slack_api/errors/not_found'
|
10
|
+
require 'slack_api/errors/response'
|
11
|
+
|
12
|
+
require 'slack_neuralyzer/logger'
|
13
|
+
require 'slack_neuralyzer/multi_io'
|
14
|
+
|
15
|
+
require 'slack_neuralyzer/helper'
|
16
|
+
require 'slack_neuralyzer/colorizable'
|
17
|
+
require 'slack_neuralyzer/args_parser'
|
18
|
+
require 'slack_neuralyzer/dict'
|
19
|
+
require 'slack_neuralyzer/cli'
|
20
|
+
require 'slack_neuralyzer/cleaner/base'
|
21
|
+
require 'slack_neuralyzer/cleaner/messages'
|
22
|
+
require 'slack_neuralyzer/cleaner/files'
|
23
|
+
require 'slack_neuralyzer/errors/mutually_exclusive_arguments'
|
24
|
+
require 'slack_neuralyzer/errors/required_arguments'
|
25
|
+
|
26
|
+
require 'slack_neuralyzer/version'
|
@@ -0,0 +1,98 @@
|
|
1
|
+
module SlackNeuralyzer
|
2
|
+
class ArgsParser
|
3
|
+
attr_accessor :token, :show, :message, :file, :channel, :direct,
|
4
|
+
:group, :mpdirect, :user, :bot, :after, :before,
|
5
|
+
:execute, :log, :rate, :regex
|
6
|
+
|
7
|
+
def initialize(args)
|
8
|
+
@args = args
|
9
|
+
init_arg_groups
|
10
|
+
parse_args
|
11
|
+
validates_mutex_args
|
12
|
+
validates_required_args
|
13
|
+
end
|
14
|
+
|
15
|
+
def init_arg_groups
|
16
|
+
@arg_groups = {
|
17
|
+
'required': [
|
18
|
+
[:token],
|
19
|
+
[:message, :file],
|
20
|
+
[:channel, :direct, :group, :mpdirect],
|
21
|
+
[:user, :bot]
|
22
|
+
],
|
23
|
+
'mutex': [
|
24
|
+
[:message, :file],
|
25
|
+
[:channel, :direct, :group, :mpdirect],
|
26
|
+
[:file, :bot],
|
27
|
+
[:file, :regex]
|
28
|
+
]
|
29
|
+
}
|
30
|
+
end
|
31
|
+
|
32
|
+
def rate_limit
|
33
|
+
rate || 0.05
|
34
|
+
end
|
35
|
+
|
36
|
+
private
|
37
|
+
|
38
|
+
def parse_args
|
39
|
+
opts = OptionParser.new
|
40
|
+
opts.banner = usage_msg
|
41
|
+
opts.separator ''
|
42
|
+
opts.separator 'options:'
|
43
|
+
opts.on('-t', '--token TOKEN', 'Slack API token (https://api.slack.com/web)') { |token| self.token = token }
|
44
|
+
opts.on('-s', '--show', 'Show all users, channels, groups and multiparty direct names') { self.show = true }
|
45
|
+
|
46
|
+
opts.on('-m', '--message', 'Specifies that the delete object is messages') { self.message = true }
|
47
|
+
opts.on('-f', '--file TYPE', "Specifies that the delete object is files of a certain type (Type: all, spaces, snippets, images, gdocs, docs, zips, pdfs)") { |file| self.file = file }
|
48
|
+
|
49
|
+
opts.on('-C', '--channel CHANNEL', 'Public channel name (e.g., general, random)') { |channel| self.channel = channel }
|
50
|
+
opts.on('-D', '--direct DIRECT', 'Direct messages channel name (e.g., leon)') { |direct| self.direct = direct }
|
51
|
+
opts.on('-G', '--group GROUP', 'Private groups channel name') { |group| self.group = group }
|
52
|
+
opts.on('-M', '--mpdirect MPDIRECT', 'Multiparty direct messages channel name (e.g., mpdm-leon--bot-1 [--show option to see name])') { |mpdirect| self.mpdirect = mpdirect }
|
53
|
+
|
54
|
+
opts.on('-u', '--user USER', "Delete messages/files from the specific user (if you want to specific all users, you can type 'all')") { |user| self.user = user }
|
55
|
+
opts.on('-b', '--bot BOT', "Delete messages from the specific bot (not bot users, if you want to specific all bots, you can type 'all')") { |bot| self.bot = bot }
|
56
|
+
|
57
|
+
opts.on('-A', '--after DATE', 'Delete messages/files after than this time (YYYYMMDD)') { |after| self.after = after }
|
58
|
+
opts.on('-B', '--before DATE', 'Delete messages/files before than this time (YYYYMMDD)') { |before| self.before = before }
|
59
|
+
|
60
|
+
opts.on('-R', '--regex TEXT', 'Delete messages with specified text (regular expression)') { |regex| self.regex = regex }
|
61
|
+
|
62
|
+
opts.on('-e', '--execute', 'Execute the delete task') { self.execute = true }
|
63
|
+
opts.on('-l', '--log', 'Generate a log file in the current directory') { self.log = true }
|
64
|
+
opts.on('-r', '--rate RATE', Float, 'Delay between API calls in seconds (default:0.1)') { |rate| self.rate = rate }
|
65
|
+
opts.on('-v', '--version', 'Show the SlackNeuralyzer version') { puts("slack_neuralyzer #{SlackNeuralyzer::VERSION}"); exit }
|
66
|
+
opts.on('-h', '--help', 'Show this message') { puts(opts); exit }
|
67
|
+
opts.parse!(@args)
|
68
|
+
end
|
69
|
+
|
70
|
+
def usage_msg
|
71
|
+
<<-USAGE.freeze
|
72
|
+
usage:
|
73
|
+
slack_neuralyzer [options]
|
74
|
+
See https://github.com/mgleon08/slack_neuralyzer for more information.
|
75
|
+
USAGE
|
76
|
+
end
|
77
|
+
|
78
|
+
def validates_required_args
|
79
|
+
@arg_groups[:required].each do |opts|
|
80
|
+
filters = opts.select{ |opt| !self.public_send(opt).nil? }
|
81
|
+
raise SlackNeuralyzer::Errors::RequiredArgumentsError.new(double_dash(opts).join(', ')) if filters.empty?
|
82
|
+
return unless self.show.nil?
|
83
|
+
end
|
84
|
+
end
|
85
|
+
|
86
|
+
def validates_mutex_args
|
87
|
+
@arg_groups[:mutex].each do |opts|
|
88
|
+
return unless self.show.nil?
|
89
|
+
filters = opts.select{ |opt| !self.public_send(opt).nil? }
|
90
|
+
raise SlackNeuralyzer::Errors::MutuallyExclusiveArgumentsError.new(double_dash(filters).join(', ')) if filters.size > 1
|
91
|
+
end
|
92
|
+
end
|
93
|
+
|
94
|
+
def double_dash(arrays)
|
95
|
+
arrays.map{ |array| array.to_s.prepend('--') }
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
@@ -0,0 +1,73 @@
|
|
1
|
+
module SlackNeuralyzer
|
2
|
+
module Cleaner
|
3
|
+
class Base
|
4
|
+
include Helper
|
5
|
+
include Colorizable
|
6
|
+
attr_reader :args, :dict, :channel_type, :logger
|
7
|
+
|
8
|
+
def initialize(args, dict, logger)
|
9
|
+
@args = args
|
10
|
+
@dict = dict
|
11
|
+
@logger = logger
|
12
|
+
reset_counter
|
13
|
+
parse_to_ts(args.after, args.before)
|
14
|
+
end
|
15
|
+
|
16
|
+
private
|
17
|
+
|
18
|
+
def get_user_id
|
19
|
+
user_id = args.user == 'all' ? -1 : dict.find_user_id(args.user)
|
20
|
+
raise SlackApi::Errors::NotFoundError, "#{args.user} not found." unless args.bot || user_id
|
21
|
+
user_id
|
22
|
+
end
|
23
|
+
|
24
|
+
def get_channel_id
|
25
|
+
if args.channel
|
26
|
+
@channel_type = 'channel'
|
27
|
+
channel_id = dict.find_channel_id(args.channel)
|
28
|
+
elsif args.direct
|
29
|
+
@channel_type = 'direct'
|
30
|
+
user_id = dict.find_user_id(args.direct)
|
31
|
+
channel_id = dict.find_im_id(user_id)
|
32
|
+
elsif args.group
|
33
|
+
@channel_type = 'group'
|
34
|
+
channel_id = dict.find_group_id(args.group)
|
35
|
+
elsif args.mpdirect
|
36
|
+
@channel_type = 'mpdirect'
|
37
|
+
channel_id = dict.find_mpim_id(args.mpdirect)
|
38
|
+
end
|
39
|
+
raise SlackApi::Errors::NotFoundError, "#{current_channel} not found." unless channel_id
|
40
|
+
channel_id
|
41
|
+
end
|
42
|
+
|
43
|
+
def current_channel
|
44
|
+
light_green("#{args.public_send(channel_type)} #{channel_type}")
|
45
|
+
end
|
46
|
+
|
47
|
+
def time_format(time)
|
48
|
+
light_cyan("[#{parse_to_date(time)}]")
|
49
|
+
end
|
50
|
+
|
51
|
+
def delete_format
|
52
|
+
args.execute ? '(delete) '.light_red : ''
|
53
|
+
end
|
54
|
+
|
55
|
+
def not_have_any(type)
|
56
|
+
logger.info "#{current_channel} does not have any #{type}(s)"
|
57
|
+
exit
|
58
|
+
end
|
59
|
+
|
60
|
+
def finish_text(type)
|
61
|
+
text = "\n#{light_green(counter)} #{type}(s) in #{current_channel} "
|
62
|
+
if args.execute.nil? && counter.nonzero?
|
63
|
+
text << 'will be deleted.'
|
64
|
+
text << light_red("\nNow, you can rerun the command and use `-e | --execute` to actually delete the #{type}(s).")
|
65
|
+
else
|
66
|
+
text << 'have been deleted.'
|
67
|
+
end
|
68
|
+
text << light_blue("\nThe log file has been generated in the current directory") if args.log
|
69
|
+
text
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|
@@ -0,0 +1,41 @@
|
|
1
|
+
module SlackNeuralyzer
|
2
|
+
module Cleaner
|
3
|
+
class Files < Base
|
4
|
+
def clean
|
5
|
+
user_id = get_user_id
|
6
|
+
channel_id = get_channel_id
|
7
|
+
clean_channel_file(channel_id, user_id)
|
8
|
+
end
|
9
|
+
|
10
|
+
private
|
11
|
+
|
12
|
+
def clean_channel_file(channel_id, user_id)
|
13
|
+
page, total_page = 0, nil
|
14
|
+
until page == total_page
|
15
|
+
page += 1
|
16
|
+
res = Slack.files_list(page: page, channel: channel_id, types: args.file, ts_from: start_time, ts_to: end_time)
|
17
|
+
raise SlackApi::Errors::ResponseError, res['error'] unless res['ok']
|
18
|
+
total_page = res['paging']['pages']
|
19
|
+
not_have_any('file') if total_page.zero?
|
20
|
+
res['files'].each do |file|
|
21
|
+
if args.user && (file['user'] == user_id || user_id == -1)
|
22
|
+
delete_file(file)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
logger.info finish_text('file')
|
28
|
+
end
|
29
|
+
|
30
|
+
def delete_file(file)
|
31
|
+
file_time = time_format(file['timestamp'])
|
32
|
+
file_url = light_magenta("(#{file['permalink']})")
|
33
|
+
delete = delete_format
|
34
|
+
Slack.files_delete(file: file['id']) if args.execute
|
35
|
+
logger.info "#{delete}#{file_time} #{dict.find_user_name(file['user'])}: #{file['name']} #{file_url}"
|
36
|
+
increase_counter
|
37
|
+
sleep(args.rate_limit)
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
@@ -0,0 +1,83 @@
|
|
1
|
+
module SlackNeuralyzer
|
2
|
+
module Cleaner
|
3
|
+
class Messages < Base
|
4
|
+
def clean
|
5
|
+
user_id = get_user_id
|
6
|
+
channel_id = get_channel_id
|
7
|
+
end_point = get_history_end_point
|
8
|
+
clean_channel_messages(channel_id, user_id, end_point)
|
9
|
+
end
|
10
|
+
|
11
|
+
private
|
12
|
+
|
13
|
+
def clean_channel_messages(channel_id, user_id, end_point)
|
14
|
+
has_more = true
|
15
|
+
|
16
|
+
while has_more
|
17
|
+
res = Slack.public_send(end_point, channel: channel_id, oldest: start_time, latest: end_time)
|
18
|
+
raise SlackApi::Errors::ResponseError, res['error'] unless res['ok']
|
19
|
+
has_more = res['has_more']
|
20
|
+
messages = res['messages']
|
21
|
+
not_have_any('message') if messages.empty?
|
22
|
+
|
23
|
+
messages.each do |msg|
|
24
|
+
@end_time = msg['ts']
|
25
|
+
dict.scan_user_id_to_transform(msg['text'])
|
26
|
+
next unless msg['type'] == 'message'
|
27
|
+
next if args.regex && !match_regex(msg['text'])
|
28
|
+
|
29
|
+
if args.user && user_msg?(msg, user_id)
|
30
|
+
name = dict.find_user_name(msg['user'])
|
31
|
+
delete_message(channel_id, msg, name)
|
32
|
+
end
|
33
|
+
|
34
|
+
next unless args.bot && bot_msg?(msg)
|
35
|
+
|
36
|
+
name = dict.find_bot_name(msg['bot_id'])
|
37
|
+
if args.bot == name || args.bot == 'all'
|
38
|
+
delete_message(channel_id, msg, name)
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
42
|
+
|
43
|
+
logger.info finish_text('message')
|
44
|
+
end
|
45
|
+
|
46
|
+
def user_msg?(msg, user_id)
|
47
|
+
!bot_msg?(msg) && (msg['user'] == user_id || user_id == -1)
|
48
|
+
end
|
49
|
+
|
50
|
+
def bot_msg?(msg)
|
51
|
+
msg['subtype'] == 'bot_message'
|
52
|
+
end
|
53
|
+
|
54
|
+
def delete_message(channel_id, msg, name)
|
55
|
+
Slack.chat_delete(channel: channel_id, ts: msg['ts']) if args.execute
|
56
|
+
logger.info "#{delete_format}#{time_format(msg['ts'])} #{name}: #{msg['text']}"
|
57
|
+
increase_counter
|
58
|
+
sleep(args.rate_limit)
|
59
|
+
end
|
60
|
+
|
61
|
+
def get_history_end_point
|
62
|
+
if args.channel
|
63
|
+
:channels_history
|
64
|
+
elsif args.direct
|
65
|
+
:im_history
|
66
|
+
elsif args.group
|
67
|
+
:groups_history
|
68
|
+
elsif args.mpdirect
|
69
|
+
:mpim_history
|
70
|
+
end
|
71
|
+
end
|
72
|
+
|
73
|
+
def match_regex(text)
|
74
|
+
match_word = text.scan(/#{args.regex}/).flatten
|
75
|
+
return false if match_word.empty?
|
76
|
+
match_word.uniq.each do |word|
|
77
|
+
text.gsub!(/#{word}/, light_magenta(word.to_s))
|
78
|
+
end
|
79
|
+
text
|
80
|
+
end
|
81
|
+
end
|
82
|
+
end
|
83
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module SlackNeuralyzer
|
2
|
+
class Cli
|
3
|
+
attr_reader :args, :dict, :logger
|
4
|
+
|
5
|
+
def initialize(args, dict, logger)
|
6
|
+
@args = args
|
7
|
+
@dict = dict
|
8
|
+
@logger = logger
|
9
|
+
end
|
10
|
+
|
11
|
+
def run
|
12
|
+
logger.info "Running slack_neuralyzer v#{SlackNeuralyzer::VERSION}\n"
|
13
|
+
sleep(1)
|
14
|
+
if args.show
|
15
|
+
puts dict.show_all_channels
|
16
|
+
elsif args.message
|
17
|
+
Cleaner::Messages.new(args, dict, logger).clean
|
18
|
+
elsif args.file
|
19
|
+
Cleaner::Files.new(args, dict, logger).clean
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
module SlackNeuralyzer
|
2
|
+
module Colorizable
|
3
|
+
[
|
4
|
+
:light_green,
|
5
|
+
:light_cyan,
|
6
|
+
:light_red,
|
7
|
+
:light_blue,
|
8
|
+
:light_yellow,
|
9
|
+
:light_magenta
|
10
|
+
].each do |color|
|
11
|
+
define_method(color) do |text|
|
12
|
+
text.to_s.public_send(color)
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,118 @@
|
|
1
|
+
module SlackNeuralyzer
|
2
|
+
class Dict
|
3
|
+
include Colorizable
|
4
|
+
attr_reader :channels, :ims, :groups, :mpims, :users, :bots
|
5
|
+
|
6
|
+
def initialize(token)
|
7
|
+
Slack.token = token
|
8
|
+
@users = {}
|
9
|
+
@channels = {}
|
10
|
+
@groups = {}
|
11
|
+
@ims = {}
|
12
|
+
@mpims = {}
|
13
|
+
@bots = {}
|
14
|
+
init_all_dict
|
15
|
+
end
|
16
|
+
|
17
|
+
def show_all_channels
|
18
|
+
text = ''
|
19
|
+
text << light_blue("All user direct:\n")
|
20
|
+
text << list_names(users)
|
21
|
+
text << light_blue("\nAll channels (public):\n")
|
22
|
+
text << list_names(channels)
|
23
|
+
text << light_blue("\nAll groups (private):\n")
|
24
|
+
text << list_names(groups)
|
25
|
+
text << light_blue("\nAll multiparty direct:\n")
|
26
|
+
text << list_names(mpims)
|
27
|
+
end
|
28
|
+
|
29
|
+
[:channel, :im, :group, :mpim, :user].each do |channel|
|
30
|
+
define_method("find_#{channel}_id".to_sym) do |name|
|
31
|
+
public_send("#{channel}s").key(name)
|
32
|
+
end
|
33
|
+
|
34
|
+
define_method("find_#{channel}_name".to_sym) do |name|
|
35
|
+
public_send("#{channel}s").invert.key(name)
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
def scan_user_id_to_transform(text)
|
40
|
+
return text if text.nil?
|
41
|
+
scan_id = text.scan(/<@(?<bot>[[:alnum:][:punct:]]*)>/i).flatten
|
42
|
+
if scan_id.any?
|
43
|
+
scan_id.uniq.each do |id|
|
44
|
+
name = find_user_name(id)
|
45
|
+
text.gsub!(/<@#{id}>/, light_yellow("@#{name}"))
|
46
|
+
end
|
47
|
+
end
|
48
|
+
text
|
49
|
+
end
|
50
|
+
|
51
|
+
def find_bot_name(bot_id)
|
52
|
+
build_bot_name(bot_id) unless bots.invert.key(bot_id)
|
53
|
+
bots.invert.key(bot_id)
|
54
|
+
end
|
55
|
+
|
56
|
+
def build_bot_name(bot_id)
|
57
|
+
res = Slack.bots_info(bot: bot_id)
|
58
|
+
raise SlackApi::Errors::ResponseError, res['error'] unless res['ok']
|
59
|
+
@bots[bot_id] = res['bot']['name']
|
60
|
+
end
|
61
|
+
|
62
|
+
private
|
63
|
+
|
64
|
+
def init_all_dict
|
65
|
+
init_users_dict
|
66
|
+
init_channels_dict
|
67
|
+
init_groups_dict
|
68
|
+
init_ims_dict
|
69
|
+
init_mpims_dict
|
70
|
+
end
|
71
|
+
|
72
|
+
def init_users_dict
|
73
|
+
res = Slack.users_list
|
74
|
+
raise SlackApi::Errors::ResponseError, res['error'] unless res['ok']
|
75
|
+
members = res['members']
|
76
|
+
members.each { |member| @users[member['id']] = member['name'] }
|
77
|
+
end
|
78
|
+
|
79
|
+
def init_channels_dict
|
80
|
+
res = Slack.channels_list
|
81
|
+
raise SlackApi::Errors::ResponseError, res['error'] unless res['ok']
|
82
|
+
channels = res['channels']
|
83
|
+
channels.each { |channel| @channels[channel['id']] = channel['name'] }
|
84
|
+
end
|
85
|
+
|
86
|
+
def init_groups_dict
|
87
|
+
res = Slack.groups_list
|
88
|
+
raise SlackApi::Errors::ResponseError, res['error'] unless res['ok']
|
89
|
+
groups = res['groups']
|
90
|
+
groups.each do |group|
|
91
|
+
next if group['is_mpim'] != false
|
92
|
+
@groups[group['id']] = group['name']
|
93
|
+
end
|
94
|
+
end
|
95
|
+
|
96
|
+
def init_ims_dict
|
97
|
+
res = Slack.im_list
|
98
|
+
raise SlackApi::Errors::ResponseError, res['error'] unless res['ok']
|
99
|
+
ims = res['ims']
|
100
|
+
ims.each { |im| @ims[im['id']] = im['user'] }
|
101
|
+
end
|
102
|
+
|
103
|
+
def init_mpims_dict
|
104
|
+
res = Slack.mpim_list
|
105
|
+
raise SlackApi::Errors::ResponseError, res['error'] unless res['ok']
|
106
|
+
mpims = res['groups']
|
107
|
+
mpims.each { |mpim| @mpims[mpim['id']] = mpim['name'] }
|
108
|
+
end
|
109
|
+
|
110
|
+
def list_names(names)
|
111
|
+
''.tap do |text|
|
112
|
+
names.values.each.with_index(1) do |name, index|
|
113
|
+
text << " #{index.to_s.rjust(3, '0')}. #{name}\n"
|
114
|
+
end
|
115
|
+
end
|
116
|
+
end
|
117
|
+
end
|
118
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module SlackNeuralyzer
|
2
|
+
module Helper
|
3
|
+
attr_reader :counter, :start_time, :end_time
|
4
|
+
|
5
|
+
def parse_to_ts(start_time, end_time)
|
6
|
+
end_time ||= Time.now.to_s
|
7
|
+
@start_time = Time.parse(start_time).to_f if start_time
|
8
|
+
@end_time = Time.parse(end_time).to_f
|
9
|
+
end
|
10
|
+
|
11
|
+
def parse_to_date(ts)
|
12
|
+
Time.at(ts.to_f).strftime('%Y-%m-%d %H:%M')
|
13
|
+
end
|
14
|
+
|
15
|
+
def reset_counter
|
16
|
+
@counter = 0
|
17
|
+
end
|
18
|
+
|
19
|
+
def increase_counter
|
20
|
+
@counter += 1
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module SlackNeuralyzer
|
2
|
+
class Logger < ::Logger
|
3
|
+
class << self
|
4
|
+
def default(log)
|
5
|
+
io = [STDOUT]
|
6
|
+
io << log_file if log
|
7
|
+
logger = Logger.new(MultiIO.new(*io))
|
8
|
+
logger.level = Logger::INFO
|
9
|
+
logger.formatter = proc do |_severity, _datetime, _progname, msg|
|
10
|
+
"#{msg}\n"
|
11
|
+
end
|
12
|
+
logger
|
13
|
+
end
|
14
|
+
|
15
|
+
def log_file
|
16
|
+
time = Time.now.strftime('%Y-%m-%dT%H:%M:%S')
|
17
|
+
FileUtils.mkdir_p('./slack_neuralyzer')
|
18
|
+
log_file = File.open("./slack_neuralyzer/#{time}.log", 'a')
|
19
|
+
log_file
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,34 @@
|
|
1
|
+
module SlackNeuralyzer
|
2
|
+
class MultiIO
|
3
|
+
def initialize(*targets)
|
4
|
+
@targets = targets
|
5
|
+
@shell_colors = {
|
6
|
+
light_red: '\\e\\[0;91;49m',
|
7
|
+
light_green: '\\e\\[0;92;49m',
|
8
|
+
light_yellow: '\\e\\[0;93;49m',
|
9
|
+
light_blue: '\\e\\[0;94;49m',
|
10
|
+
light_magenta: '\\e\\[0;95;49m',
|
11
|
+
light_cyan: '\\e\\[0;96;49m',
|
12
|
+
out_put: '\\e\\[0m'
|
13
|
+
}
|
14
|
+
end
|
15
|
+
|
16
|
+
def write(args)
|
17
|
+
@targets.each do |target|
|
18
|
+
pretty_file_text(args) if target.is_a? File
|
19
|
+
target.write(args)
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
def close
|
24
|
+
@targets.each(&:close)
|
25
|
+
end
|
26
|
+
|
27
|
+
def pretty_file_text(args)
|
28
|
+
@shell_colors.values.each do |color|
|
29
|
+
args.gsub!(/#{color}/, '')
|
30
|
+
end
|
31
|
+
args
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
Binary file
|
Binary file
|
Binary file
|
@@ -0,0 +1,28 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
lib = File.expand_path('../lib', __FILE__)
|
3
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
+
require 'slack_neuralyzer/version'
|
5
|
+
|
6
|
+
Gem::Specification.new do |spec|
|
7
|
+
spec.name = "slack_neuralyzer"
|
8
|
+
spec.version = SlackNeuralyzer::VERSION
|
9
|
+
spec.authors = ["Leon Ji"]
|
10
|
+
spec.email = ["mgleon08@gmail.com"]
|
11
|
+
|
12
|
+
spec.summary = %q{The easiest way to clean up messages and files on Slack.}
|
13
|
+
spec.description = %q{This is a ruby gem for bulk delete messages and files on Slack channels.}
|
14
|
+
spec.homepage = "https://github.com/mgleon08/slack_neuralyzer"
|
15
|
+
spec.license = "MIT"
|
16
|
+
|
17
|
+
spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
|
18
|
+
spec.bindir = "bin"
|
19
|
+
spec.require_paths = ["lib"]
|
20
|
+
spec.executables = ["slack_neuralyzer"]
|
21
|
+
|
22
|
+
spec.add_development_dependency "bundler", "~> 1.11"
|
23
|
+
spec.add_development_dependency "rake", "~> 10.0"
|
24
|
+
spec.add_development_dependency "rspec", "~> 3.0"
|
25
|
+
spec.add_development_dependency "coveralls", "~> 0.8.1"
|
26
|
+
spec.add_runtime_dependency "slack-api", "~> 1.2"
|
27
|
+
spec.add_runtime_dependency "colorize", "~> 0.8"
|
28
|
+
end
|
metadata
ADDED
@@ -0,0 +1,161 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: slack_neuralyzer
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.1.0
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Leon Ji
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2016-10-18 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: bundler
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '1.11'
|
20
|
+
type: :development
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '1.11'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: rake
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - "~>"
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '10.0'
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - "~>"
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '10.0'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: rspec
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - "~>"
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '3.0'
|
48
|
+
type: :development
|
49
|
+
prerelease: false
|
50
|
+
version_requirements: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - "~>"
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '3.0'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: coveralls
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - "~>"
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: 0.8.1
|
62
|
+
type: :development
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - "~>"
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: 0.8.1
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: slack-api
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
72
|
+
requirements:
|
73
|
+
- - "~>"
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
version: '1.2'
|
76
|
+
type: :runtime
|
77
|
+
prerelease: false
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
79
|
+
requirements:
|
80
|
+
- - "~>"
|
81
|
+
- !ruby/object:Gem::Version
|
82
|
+
version: '1.2'
|
83
|
+
- !ruby/object:Gem::Dependency
|
84
|
+
name: colorize
|
85
|
+
requirement: !ruby/object:Gem::Requirement
|
86
|
+
requirements:
|
87
|
+
- - "~>"
|
88
|
+
- !ruby/object:Gem::Version
|
89
|
+
version: '0.8'
|
90
|
+
type: :runtime
|
91
|
+
prerelease: false
|
92
|
+
version_requirements: !ruby/object:Gem::Requirement
|
93
|
+
requirements:
|
94
|
+
- - "~>"
|
95
|
+
- !ruby/object:Gem::Version
|
96
|
+
version: '0.8'
|
97
|
+
description: This is a ruby gem for bulk delete messages and files on Slack channels.
|
98
|
+
email:
|
99
|
+
- mgleon08@gmail.com
|
100
|
+
executables:
|
101
|
+
- slack_neuralyzer
|
102
|
+
extensions: []
|
103
|
+
extra_rdoc_files: []
|
104
|
+
files:
|
105
|
+
- ".codeclimate.yml"
|
106
|
+
- ".gitignore"
|
107
|
+
- ".rspec"
|
108
|
+
- ".travis.yml"
|
109
|
+
- Gemfile
|
110
|
+
- LICENSE.txt
|
111
|
+
- README.md
|
112
|
+
- Rakefile
|
113
|
+
- bin/console
|
114
|
+
- bin/setup
|
115
|
+
- bin/slack_neuralyzer
|
116
|
+
- lib/slack_api/errors/not_found.rb
|
117
|
+
- lib/slack_api/errors/response.rb
|
118
|
+
- lib/slack_api/slack_api.rb
|
119
|
+
- lib/slack_neuralyzer.rb
|
120
|
+
- lib/slack_neuralyzer/args_parser.rb
|
121
|
+
- lib/slack_neuralyzer/cleaner/base.rb
|
122
|
+
- lib/slack_neuralyzer/cleaner/files.rb
|
123
|
+
- lib/slack_neuralyzer/cleaner/messages.rb
|
124
|
+
- lib/slack_neuralyzer/cli.rb
|
125
|
+
- lib/slack_neuralyzer/colorizable.rb
|
126
|
+
- lib/slack_neuralyzer/dict.rb
|
127
|
+
- lib/slack_neuralyzer/errors/mutually_exclusive_arguments.rb
|
128
|
+
- lib/slack_neuralyzer/errors/required_arguments.rb
|
129
|
+
- lib/slack_neuralyzer/helper.rb
|
130
|
+
- lib/slack_neuralyzer/logger.rb
|
131
|
+
- lib/slack_neuralyzer/multi_io.rb
|
132
|
+
- lib/slack_neuralyzer/version.rb
|
133
|
+
- screenshots/general_test_token.png
|
134
|
+
- screenshots/neuralyzer.gif
|
135
|
+
- screenshots/slack_neuralyzer_demo.gif
|
136
|
+
- slack_neuralyzer.gemspec
|
137
|
+
homepage: https://github.com/mgleon08/slack_neuralyzer
|
138
|
+
licenses:
|
139
|
+
- MIT
|
140
|
+
metadata: {}
|
141
|
+
post_install_message:
|
142
|
+
rdoc_options: []
|
143
|
+
require_paths:
|
144
|
+
- lib
|
145
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
146
|
+
requirements:
|
147
|
+
- - ">="
|
148
|
+
- !ruby/object:Gem::Version
|
149
|
+
version: '0'
|
150
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
151
|
+
requirements:
|
152
|
+
- - ">="
|
153
|
+
- !ruby/object:Gem::Version
|
154
|
+
version: '0'
|
155
|
+
requirements: []
|
156
|
+
rubyforge_project:
|
157
|
+
rubygems_version: 2.4.8
|
158
|
+
signing_key:
|
159
|
+
specification_version: 4
|
160
|
+
summary: The easiest way to clean up messages and files on Slack.
|
161
|
+
test_files: []
|