slack-go / slack Goto Github PK
View Code? Open in Web Editor NEWSlack API in Go, originally by @nlopes; Maintainers needed, contact @parsley42
Home Page: https://pkg.go.dev/github.com/slack-go/slack
License: BSD 2-Clause "Simplified" License
Slack API in Go, originally by @nlopes; Maintainers needed, contact @parsley42
Home Page: https://pkg.go.dev/github.com/slack-go/slack
License: BSD 2-Clause "Simplified" License
I need to see what user the token was granted for. Slack has the users.identity endpoint for that, but it does not seem to be implemented here
May have missed it but I didn't see a method for posting to a webhook url. Ended up just generating a token to use but support and/or docs for webhook integration would be great!
Hi,
I just noticed an inconsistency where the UserChangeEvent
includes a User
(https://github.com/nlopes/slack/blob/master/websocket_misc.go#L40) whereas TeamJoinEvent
uses a *User
(https://github.com/nlopes/slack/blob/master/websocket_teams.go#L5). Not sure which is better but it'd be great if it was consistent! :)
Hi, and thanks for this cool library. I have a small issue sending messages to channels by using name ('#general'). Using the channel id works just fine, but it's kind of tedious to maintain.
The RTM example on https://github.com/nlopes/slack/blob/master/examples/websocket/websocket.go uses #general (alltough it says to replace that name with the channel id). Is this library supposed to work with channel names, or do I have to lookup the channel id by name, when creating the client? Sorry to open a new issue for this.. :-)
I'm working with this lib in a project using it for the websockets RTM API implementation, and when receiving an error response from the api this line https://github.com/nlopes/slack/blob/master/websocket.go#L184 Is making the app crash.
The error responses from slack are also going here and I think it should handle the error gracefully.
For instance when sending a message with empty text, slacks answer is: {"ok":false,"reply_to":1,"error":{"code":2,"msg":"message text is missing"}}
Making the Unmarshal fail and exiting the app.
I think that the unmarshal error could be relaxed and at least reach https://github.com/nlopes/slack/blob/master/websocket.go#L194-L195
Said that, agree that error should not end up in that bucket.
First off, thanks for the pkg. I was originally using hal, but have moved over to using your api and a tiny custom framework, and it's a real pleasure so far.
My bot is periodically dying, I suspect possibly due to something int he latency response code, I'll take a look soon, but thought I'd report it here just incase:
json: cannot unmarshal number into Go value of type slack.JSONTimeString
I've not got a definitive way of triggering the problem yet. Will send a PR if I work it out.
I'm somewhat unsure if this error even pertains directly to this package, but I think it might. Please correct me if I'm wrong in that assumption.
I'm currently using slick, which builds on top of this. For a number of messages I'm trying to send, I'm receiving OutgoingErrorEvents. A quickly hacked together debug event listener spits out that the description of these are write tcp my_ip:54821->slack_ip:443: i/o timeout
. From reading other issues and PRs, I'm hoping this has something to do with https://github.com/nlopes/slack/pull/102. But I really don't have a clue... And if it doesn't, is there anything I could do to fix this?
Any help would be much appreciated ๐
Ideally these two should have compatible interfaces to reduce the friction in sending messages.
Slack's JSON escapes /
such that it is emitted as \/
. This Unmarshals correctly but json.Marshal
doesn't re-escape this character by default. It may be worth adding a custom encoder to handle this scenario correctly.
I want to call chat.update
with parse=full
or some of the other optional arguments here: https://api.slack.com/methods/chat.update#formatting
The current UpdateMessage function doesn't allow us to do that. I was wondering, would we:
UpdateMessageEx()
?! so we feel in Windowzland somehowI need to use this library from an AppEngine frontend, which necessitates the use of Google's urlfetch API, which provides a custom *http.Client
. I have it patched on my end (slack.Slack
gets an extra config *http.Client
field that's initialized in slack.New()
), but I wanted to be sure you were receptive to such a change before submitting a patch.
slackApi = slack.New("a-wrong-key")
slackApi.SetDebug(true)
_, err := slackApi.StartRTM("", "http://example.com")
if err != nil {
log.Printf("Error starting RTM: %s", err)
}
2015/05/13 12:15:26 {"ok":false,"error":"invalid_auth"}
2015/05/13 12:15:26 Error starting RTM: json: cannot unmarshal string into Go value of type slack.SlackWSError
The response returned by Slack is {"ok":false,"error":"not_authed"}
This line then tries to parse that as a infoResponseFull
and fails, which causes the error above.
Hi, great library, I'm using it for developing a bot, and yesterday he suddenly stopped with this error message:
json: cannot unmarshal number into Go value of type slack.JSONTimeString
I'm sorry that I cant' provide more information for now, but I'll try to catch this error later (the main problem is that it happened only once yet). I've taken a brief look at the code, and looks like there is a lot of JSONTimeString
's everywhere, so probably, Slack guys started changing protocol a bit.
there are plenty of log.Fatal
, log.Panic
in the code, especially regarding disconnection...
My bot handles reconnecting after disconnection.. but this API makes it hard to recover as it kills the whole thing at many points.
Anyone using the websocket stream ? I'd like to either make it reconnection-handling friendly, or maybe implement the reconnection right into this lib. what do you think ?
I'm trying to get a history of messages for a channel.
`package main
import (
"fmt"
"github.com/nlopes/slack"
"io/ioutil"
"strings"
)
func main() {
token, err := ioutil.ReadFile("bot_token")
check(err)
str_token := strings.TrimSpace(string(token))
fmt.Printf("Token: %s\n", string(str_token))
api := slack.New(string(str_token))
channels, err := api.GetChannels(true)
check(err)
bot_id := getChannelIDFromName(channels, "bot")
fmt.Println(bot_id)
// msg_params := slack.PostMessageParameters{}
hst_params := slack.HistoryParameters{}
history, err := api.GetChannelHistory(bot_id, hst_params)
check(err)
fmt.Println(history)
for _, message := range history.Messages {
fmt.Println(message.Text)
}
}
func getChannelIDFromName(channels []slack.Channel, name string) string {
for _, channel := range channels {
if channel.Name == name {
return channel.ID
}
}
return ""
}
func check(e error) {
if e != nil {
panic(e)
}
}
`
The output from fmt.Println(history):
'&{ [{{message U17RLSCLA Hello World 1487703863.000191 false [] [] false [] false 0 []} }] true}`
This is despite the fact that there is actually a long history, and running the example command from the slack api doc returns many more messages.
Am I setting something up incorrectly?
Announced yesterday and described here:
https://api.slack.com/docs/message-buttons
I'll be working on that if you don't mind.. if you want to pitch in, notify me.. I really want that for https://github.com/abourget/slick :)
It would be ultra-convenient if RTMEvent implemented json.Unmarshaler so I could decode and replay RTMEvents from my Slackbot RTM event log for unit testing.
It seems the event mapping is not exported so this can't be done externally to the package without quite a bit of unnecessary overhead (unless I'm missing something.)
Slack announced a new Events API which provides similiar functionality to the Real-time message API (RTM) but with a simpler webhook interface.
Auto send invite for user?
Suggestion: Travis or Wecker.
Rationale: We need to run tests to verify we're not introducing regressions in PRs.
I believe (new to golang so pardon if I'm just being stupid), that now that "ts" in the Attachment struct is of type json.Number, you can no longer pass a PostMessageParamaters struct that contains attachments with the ts field to the post message call. It will fail on unmarshalling the attachments.
Illustrative go playground on what I am seeing (simplified):
https://play.golang.org/p/R5EivlvQRn
The method GetReactions
doesn't return message object but slack api support. So how do I get total message when i receive a reaction_added
event ? Any other method can do this ?
Would be nice if some of the logging could be cleaned up.
It would be great if you either setup a public *log.Logger so the user can tweak the settings without messing with their own log or at least only log when the Slack struct has debug on.
Returned the error when tried to start the application, the second try worked.
[signal SIGSEGV: segmentation violation code=0x1 addr=0x18 pc=0x55fa094141d5]
goroutine 12 [running]:
panic(0x55fa099da220, 0xc42000c050)
/usr/lib/go/src/runtime/panic.go:500 +0x1a5
github.com/golang.org/x/net/websocket.(*Conn).SetWriteDeadline(0x0, 0xecfaec8ba, 0x55fa1492367a, 0x55fa09db18e0, 0xc4203f1900, 0x0)
/go/src/github.com/golang.org/x/net/websocket/websocket.go:279 +0x45
github.com/github.com/nlopes/slack.(*RTM).connect(0xc4201c6900, 0x1, 0x8, 0x55fa096229ac, 0xb, 0x0)
/go/src/github.com/github.com/nlopes/slack/websocket_managed_conn.go:94 +0x268
github.com/github.com/nlopes/slack.(*RTM).ManageConnection(0xc4201c6900)
/go/src/github.com/github.com/nlopes/slack/websocket_managed_conn.go:32 +0x46
Searching I also found this issue in other project that uses the slack lib:
jpbruinsslot/slack-term#36
Just noticed that Slack does not expose a num_members
(maybe they used to?) but slack.Channel
has that field so it's always set to 0 which is surprising. Can we remove it?
To send a message using the rtm protocol, I need the channel ID, it seems it does not work just using "#channelname".
Then, the problem is how to obtain that ID, as GetChannelInfo does not return it. I think it is returned bu the API, so it should be easy to return from GetChannelInfo
https://github.com/nlopes/slack/blob/master/slack.go#L50
in code comment, i.e. here's how to get your token...
I am currently in the process of merging some really great changes from @abourget slack branch and a couple more from @mlbvsnba.
I would love to start moving towards merging naming for some things in the library but I thought asking what people prefer wouldn't harm anyone.
The ones I see so far are:
RTM vs WS
Client vs Slack
@joefitzgerald @abourget @mlbvsnba: would you guys mind chiming in on this if you feel strongly either way?
Thanks!
Disclaimer: I'm very new to go, and also to the Slack API.
There's an rtm.Disconnect() available, which does appear to disconnect. However, if I use something starting with the websocket example, there's no obvious indication given to the client waiting on IncomingEvents that the disconnection has succeeded.
So, say I want to implement a "quit" command for the bot. I want the bot to say "Okay, fine" or something, then leave. If I break out of the event loop immediately after sending the message, the message never actually gets sent, because concurrency. If I call Disconnect, I do indeed disconnect and stop processing things, but... the program just sits there waiting for an event. It seems like maybe the channel should be closed once the disconnection is complete, since reconnect isn't implemented/available?
https://github.com/nlopes/slack/blob/master/groups.go#L232
The argument should be "channel" instead of "user" as described in the Slack doc:
https://api.slack.com/methods/groups.open
hi, i'm wondering how to map a channel name (#general
) to an ID or vice-versa.
in my code i would like to be able to write e.g. JoinChannel("#general")
but to do that i need to get the channel id.
Channel
type does not expose ID or name, so i am confused about how GetChannels
or GetChannelInfo
is useful...
How stable is the current API? v0.0.1
is over a year old at this point - will the current code be tagged at some point soon?
Thanks
currently running into an issue we're trying to test some for that is looping over the IncomingEvents
and part of that is filtering out events from the bot user.
trying to test this code requires setting up a working connection even though none of the code actually needs a connection to be tested except for the fact there is no way of populating the Info structure without handshaking with slack.
Would be nice if we could manually set it (honestly I don't generally see the benefit in the GetInfo() call vs just exposing the field as you still have to check for nil since it may or may not be populated depending when you call it)
no desktop_notification at eventMapping
Hello @nlopes,
First of all, great work with this client, seems pretty nice ๐.
I'm opening this issue because I'm interested in extend the API for example of channels, creating a method getCurrentChannels
or methods build on top of the Slack API.
In order to increase the usability and keep all the "module" the pure operations that you can do to get info of Slack.
What do you think?
Thanks!
to reproduce: revoke authorization from within slack ui for a bot, then try to invoke rtm.Disconnect().
it deadlocks. Adding a deadline to ping fixes the issue. it appears to be deadlocking during a force ping.
but the underlying cause is the websocket.JSON.Send(rtm.conn, msg) never returning. adding a deadline solves it. but it seems there is an underlying issue in the websocket library w/ regards to connections being closed.
func (rtm *RTM) ping() error {
id := rtm.idGen.Next()
rtm.Debugln("Sending PING ", id)
rtm.pings[id] = time.Now()
msg := &Ping{ID: id, Type: "ping"}
// adding a deadline here prevents ping from potentially blocking forever on send.
rtm.conn.SetWriteDeadline(time.Now().Add(1 * time.Second))
err := websocket.JSON.Send(rtm.conn, msg)
if err != nil {
rtm.Debugf("RTM Error sending 'PING %d': %s", id, err.Error())
return err
}
return nil
}
will provide a PR tomorrow.
So either I'm dumb or something's not working.
I've implemented a smallish bot using the lib that's supposed to respond to messages.
But after running for a while all incoming messages are processes, but once it tries to send a message I hit the following:
Unexpected: write tcp 10.249.126.60:58189->52.90.4.230:443: i/o timeout
Unexpected: write tcp 10.249.126.60:58189->52.90.4.230:443: i/o timeout
nlopes/slack2016/09/01 12:55:45 slack.go:86: Sending PING 20
nlopes/slack2016/09/01 12:55:45 slack.go:80: RTM Error sending 'PING 20': write tcp 10.249.126.60:58189->52.90.4.230:443: i/o timeout
nlopes/slack2016/09/01 12:55:45 slack.go:86: killing connection
Unexpected: &{false}
Unexpected: &{1 3}
Unexpected: read tcp 10.249.126.60:58189->52.90.4.230:443: use of closed network connection
Message is also not being re-sent on reconnect. Any ideas what I'm doing wrong? I saw that sendOutgoingMessage
doesn't handle connection drops, but...
It appears on the slack API documentation it talks about subscribing to channels to get information, however, when I run this package, doing the examples/websocket/websocket.go code with minor modifications, I never see the case *slack.MessageEvent:
line trigger. I'm trying to figure out if there's a step to make this happen.. you can't make a bot join the channel.. So..
I tried dumping messages from direct chats today and with one particular message I got an error:
json: cannot unmarshal string into Go value of type int64
After investigation I found that one message has the ts
field for attachment as a string. I tired replacing the data type for attachment from int64
to string
but it started crashing on another user, which means that this field can be both int64 and string.
I'm not fluent in Go to figure out a solution, so here's json of a response that crashes the script (changed names etc. for privacy):
{
"ok": true,
"latest": "1461156109.000043",
"messages": [
{
"type": "message",
"user": "U025QS77U",
"text": "<https://something.slack.com/archives/lunch/p1461060720000152>",
"attachments": [
{
"color": "4D394B",
"from_url": "https://something.slack.com/archives/lunch/p1461060720000152",
"fallback": "[April 19th, 2016 3:12 AM] someone: > 12 1234 1234 1234 1234 1234 1234",
"author_subname": "someone",
"ts": "1461060720.000152",
"text": "> 12 1234 1234 1234 1234 1234 1234",
"author_name": "Some User",
"author_link": "https://something.slack.com/team/someone",
"author_icon": "https://avatars.slack-edge.com/2015-04-17/12312312312231.jpg",
"mrkdwn_in": [
"text"
],
"id": 1
}
],
"ts": "1461156085.000041"
}
],
"has_more": true
}
I'm writing a slackbot service, and I noticed that when a user disconnects my slack app, even after I call rtm.Disconnect()
my call to go rtm.ManageConnection()
is continually attempting to reconnect with exponential backoff, and I have no way to tell it to stop running.
Is this a known issue? It looks like, from the code, that the unexported function rtm.connect
doesn't listen to the killChannel
until after it establishes the connection to slack, which won't ever happen if the error is because the user's token is invalid.
Hi
The code panics when trying to calling the Error()
method on a AckErrorEvent
instance (looks like the underlying ErrorObj error
is nil):
panic: value method slack.RTMError.Error called using nil *RTMError pointer
goroutine 18 [running]:
panic(0x988720, 0xc420433980)
/usr/local/Cellar/go/1.7.3/libexec/src/runtime/panic.go:500 +0x1a1
github.com/nlopes/slack.(*RTMError).Error(0x0, 0x1, 0xffffffffffff0101)
<autogenerated>:112 +0xc5
github.com/nlopes/slack.(*AckErrorEvent).Error(0xc42040aa10, 0x9, 0xa509f4)
/Users/marc/dev/abitbot/vendor/src/github.com/nlopes/slack/websocket_internals.go:91 +0x33
abitbot/source.(*SlackSource).Run(0xc4201c0190)
/Users/marc/dev/abitbot/src/abitbot/source/slack.go:361 +0x9ae
created by main.main
/Users/marc/dev/abitbot/src/cmd/george/main.go:134 +0x950
Maybe it would be better for the Error()
method to return directly the error
value instead of a string representation, or at least check that the ErrorObj error
is non-nil before calling the Error()
method on it?
Multi-party DM methods! All prefixed with mpim and include:.close, .history, .list, .mark, and .open
https://github.com/nlopes/slack/blob/master/admin.go#L21 is a good example of bad errors.
That returns an error if something goes wrong, or it returns an error if the API gives a error. How do we differentiate between those two states? I can't show the API error to a user, because if it's a JSON Unmarshal error that's not a good idea. And currently the only way of checking would be to check if the error message contains a string, which is a bad idea.
Dave Cheney has a good set of examples on his blog http://dave.cheney.net/2016/04/27/dont-just-check-errors-handle-them-gracefully and has also made a very nice package that fits what he is saying https://github.com/pkg/errors
What do you think?
Edit: I accidentally the wrong dfc.
Currently when a file is uploaded and the json can't be unmarshelled the lib class log.fatal instead it should panic so the code calling it can recover and does not need to manuall restart since log.Fatal calls os.Exit(1)
When a bot joins a channel, would be good to have this event type:
https://api.slack.com/events/channel_joined
more info coming soon, but get that after calling GetGroupHistory
for 1 specific group and then looping thru:
for _, message := range history.Messages
NewOutgoingMessage("@someone")
doesn't properly tag someone
in the message. What's the best way to accomplish this?
Compare:
Is there a way I can use your API to find Slack channel membership? How about its Name?
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.