Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
20 commits
Select commit Hold shift + click to select a range
228aa80
Added .env to .gitignore.
dev-elle-up Mar 19, 2019
731b4ae
completes wave 1 but without class structure yet
kaseea Mar 20, 2019
fa070bb
completes coding requirements for wave 1 and adds a slack class
kaseea Mar 20, 2019
b45546e
Merge branch 'master' of https://github.com/Mello-Cello/slack-cli
dev-elle-up Mar 20, 2019
8089c88
Updated the test file to require dotenv and to set up VCR.configure.
dev-elle-up Mar 20, 2019
1b667e5
Set up tests for list channels. Addressed some bugs with linking file…
dev-elle-up Mar 21, 2019
474d458
some small changes from lecture
kaseea Mar 21, 2019
04b715a
adds wave 2 functionalities, and splits methods into different classes
kaseea Mar 21, 2019
99e66c3
Wrote and stemmed out more tests for selecting channels and users.
dev-elle-up Mar 21, 2019
e1e3ec6
Wrote and stemmed out more tests for selecting channels and users.
dev-elle-up Mar 21, 2019
18e25dc
Added tests for selecting users and channels. Currently not working.
dev-elle-up Mar 22, 2019
87f5a28
changes the format of some of the test files to match class structure
kaseea Mar 22, 2019
92be44b
merges better
kaseea Mar 22, 2019
ca1b2fc
fixes bug with downcase, better matching for selection methods
kaseea Mar 22, 2019
4767ec0
stopping point for Friday
kaseea Mar 22, 2019
d8a3ca1
fixes send message and comepletes wave 3
kaseea Mar 25, 2019
22b9e57
Cleaned up user interface. Fixed 'show details when no user/channel i…
dev-elle-up Mar 26, 2019
c3a8892
Fixed the 'send_msg' method. Can now send a message to a channel.
dev-elle-up Mar 26, 2019
57beebd
Got 'send_msg' working for user. Added an if/else to check for which …
dev-elle-up Mar 26, 2019
f778e37
Removed unnecessary comments in spec file and tests that were unused …
dev-elle-up Mar 26, 2019
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,10 @@
/test/tmp/
/test/version_tmp/
/tmp/
temp-auth-check.rb

# Used by dotenv library to load environment variables.
# .env
.env

## Specific to RubyMotion:
.dat*
Expand Down
6 changes: 3 additions & 3 deletions Rakefile
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
require 'rake/testtask'
require "rake/testtask"

Rake::TestTask.new do |t|
t.libs = ["lib"]
t.warning = true
t.test_files = FileList['specs/*_spec.rb']
# t.warning = false # <-- Scarlet added this to eleminate our minitest circular warnings
t.test_files = FileList["specs/*_spec.rb"]
end

task default: :test
25 changes: 25 additions & 0 deletions lib/channel.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
# require_relative "slack"
require "httparty"
require "dotenv"
require "table_print"
Dotenv.load

class Channel
attr_reader :name, :topic, :num_members, :slack_id

def initialize(name, topic, num_members, slack_id)
@name = name
@topic = topic
@num_members = num_members
@slack_id = slack_id
end

def details
puts "
Name: #{name}
Topic: #{topic}
Number of members: #{num_members}
Slack ID: #{slack_id}
---"
end
end
155 changes: 151 additions & 4 deletions lib/slack.rb
Original file line number Diff line number Diff line change
@@ -1,11 +1,158 @@
#!/usr/bin/env ruby
require "pry"

require_relative "channel"
require_relative "user"
require "httparty"
require "dotenv"
Dotenv.load

class SlackError < StandardError; end

class Slack

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This class would be better named SlackWorkspace since slack can include multiple workspaces.

Also it would be good to wrap everything in a module

attr_reader :channels, :users

def initialize()
@channels = []
@users = []
get_lists
end

def get_lists()

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just notice here how the loops look almost identical. This is a good indication that you can dry things up using duck typing / polymorphism.

query_parameters = {
token: ENV["SLACK_API_TOKEN"],
pretty: 1,
}
url = "https://slack.com/api/conversations.list?"
response = HTTParty.get(url, query: query_parameters)
response["channels"].each do |x|

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

.map could also be used here to give you an array of Channel instances

@channels << Channel.new(x["name"], x["topic"]["value"], x["num_members"], x["id"])
end
url2 = "https://slack.com/api/users.list?"
response2 = HTTParty.get(url2, query: query_parameters)
response2["members"].each do |x|
@users << User.new(x["name"], x["id"], x["real_name"])
end
end

def lists_channels
puts "\nHere are the channels:"
@channels.each do |x|
puts " - #{x.name}"
end
puts "---\n"
end

def lists_users
puts "\nHere are the users:"
@users.each do |x|
puts " - #{x.user_name}"
end
puts "---\n"
end

def select_user(search)
user = @users.find { |x| x.user_name.downcase == search.downcase || x.user_id.downcase == search.downcase }
end

def select_channel(search)
channel = @channels.find { |x| x.name.downcase == search.downcase || x.slack_id.downcase == search.downcase }
end

def self.send_msg(recipient, text)
if recipient == nil
puts "Please select a channel or user first."
main
end

url = "https://slack.com/api/chat.postMessage"
if recipient.class == Channel

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The if and elsif here are identical, so you just need to check to see if recipient is not nil.

query_parameters = {
token: ENV["SLACK_API_TOKEN"],
channel: recipient.slack_id,
text: text,
}
elsif recipient.class == User
query_parameters = {
token: ENV["SLACK_API_TOKEN"],
channel: recipient.user_id,
text: text,
# as_user: true, <-- use this in the future for allowing to send as a user
}
end

response = HTTParty.post(url,
headers: {"Content-Type" => "application/x-www-form-urlencoded"},
query: query_parameters)
if response["ok"]
return true
else
raise SlackError, "Error when posting '#{text}' to #{recipient}, error: #{response["error"]}"
end
end
end

def main
puts "Welcome to the Ada Slack CLI!"
slack = Slack.new

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would be better to have main and the Slack class in separate files.


puts "Welcome to the Kasey-Elle Slack CLI!
There are #{slack.channels.length} channels and #{slack.users.length} members in this instance of Slack."

# TODO project
def name_checker(who)
while who == ""
puts "Please enter a valid name/ID."
who = gets.chomp
end
end

puts "Thank you for using the Ada Slack CLI"
def options
puts "What should we do next? You can:
list channels / list users / select user / select channel / show details / send message / quit"
return gets.chomp
end

continue = true

chosen_user = ""
while (continue)
response = options
case response
when "list channels"
slack.lists_channels
when "list users"
slack.lists_users
when "select user"
puts "Enter the name or ID of the user you wish to select."
who = gets.chomp
name_checker(who)
chosen_user = slack.select_user(who)
puts "That user was not found. Please check your spelling or try another selection." if chosen_user == nil
when "select channel"
puts "Enter the name or ID of the channel you wish to select."
who = gets.chomp
name_checker(who)
chosen_user = slack.select_channel(who)
puts "That channel was not found. Please try again." if chosen_user == nil
when "show details"
if chosen_user == "" || chosen_user == nil
puts "Please select a channel or user first."
else
chosen_user.details
end
when "send message"
puts "What message would you like to send?"
text = gets.chomp
Slack.send_msg(chosen_user, text)
when "quit"
continue = false
else
puts "Oops! That is not a valid option. Please try again."
end
end

puts "Thank you for using the Kasey-Elle Slack CLI"
end

main if __FILE__ == $PROGRAM_NAME
main if __FILE__ == $PROGRAM_NAME

# NOTE for Elle: Run ruby lib/slack.rb from slack-cli folder to run the CLI program.
23 changes: 23 additions & 0 deletions lib/user.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
# require_relative "slack"
require "httparty"
require "dotenv"
require "table_print"
Dotenv.load

class User
attr_reader :user_name, :user_id, :real_name

def initialize(user_name, user_id, real_name)
@user_name = user_name
@user_id = user_id
@real_name = real_name
end

def details
puts "
Name: #{user_name}
ID: #{user_id}
Real Name: #{real_name}
---"
end
end
80 changes: 80 additions & 0 deletions notes_to_do.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
types of tests:

add one for invalid tokens

check for 200? basically, "ok" is true or false

3 tests for send messaging
describe Slack do
describe "send_msg" do
it "can send a valid message" do
VCR.use_cassette("slack_message") do
return_value = SlackApi.send_msg("Test message", "apiiiii")

expect(return_value).must_equal true
end
end
end
end

BASE_URL = https://slack.com/api/

def self.send_msg(text, channel)
response = HTTParty.post(
"#{BASE_URL}chat.postMessage"
headers: { 'Content-Type' => 'application/x-www-form-urlencoded' },
body: {
token: SLACK_API_TOKEN,
channel: channel,
text: message,
},
)

if response["ok"]
return true
else
raise SlackError, "Error when posting #{message} to #{channel}, error: #{response["error"]}"
end

end

class SlackError < StandardError; end

it "generates an error if given an invalid channel" do

VCR.use_cassette("slack_message") do
expect {
return_value = SlackApiWrapper.send_msg("Test message", "bogus")
}.must_raise SlackError
end

it "will raise an error if given an empty message" do

end

notes:

above, the def self.send_msg
was in

module SlackApi
BASE_URL =
API_KEY = ENV["token"]

then slack error line
then send_msg

end


Add the following test to specs/slack_api_wrapper_spec.rb.

it "will raise an error when given an invalid channel" do
VCR.use_cassette("slack-posts") do
exception = expect {
SlackApi.send_msg("This post should not work", "invalid-channel")
}.must_raise SlackApiWrapper::SlackApiError

expect(exception.message).must_equal 'Error when posting This post should not work to invalid-channel, error: channel_not_found'
end
end
Loading