Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Return response metadata with chat errors #939

Closed
StupidScience opened this issue May 19, 2021 · 8 comments
Closed

Return response metadata with chat errors #939

StupidScience opened this issue May 19, 2021 · 8 comments

Comments

@StupidScience
Copy link
Contributor

Description

Currently with methods like SendMessageContext there is no way to get info about error like it is possible for OpenViewContext as example. So it leads that you just get errors like invalid_blocks without any additional information while in real response can be something like

{
    "ok": false,
    "error": "invalid_blocks",
    "errors": [
        "failed to match all allowed schemas [json-pointer:/blocks/1/elements/0/text]",
        "invalid additional property: verbatim [json-pointer:/blocks/1/elements/0/text]"
    ],
    "response_metadata": {
        "messages": [
            "[ERROR] failed to match all allowed schemas [json-pointer:/blocks/1/elements/0/text]",
            "[ERROR] invalid additional property: verbatim [json-pointer:/blocks/1/elements/0/text]"
        ]
    }
}

I've tested it with invocation like this:

s.SendMessageContext(
    context.TODO(),
    channelID,
    slack.MsgOptionText("", false),
    slack.MsgOptionBlocks(
	  slack.NewSectionBlock(
		  slack.NewTextBlockObject(slack.MarkdownType, "test", true, true),
		  nil,
		  nil,
	  ),
  ),
)

So it is really annoying to debug this issues in semi-manual way to understand what is going on in real.

May be there is some option to create some kind of error wrapper type like the following to avoid breaking the compatibility:

type Error struct {
	Err             string
	Messages []string
}

Or return response from specified function so it would be possible to get this information?

(Optional) Slack's documentation

https://api.slack.com/changelog/2016-09-28-response-metadata-is-on-the-way

@StupidScience
Copy link
Contributor Author

@kanata2 sorry for bothering. what do you think about this?

@kanata2
Copy link
Member

kanata2 commented Sep 6, 2021

Sorry for my slow response 😩
I'll confirm later.

@abustany
Copy link
Contributor

abustany commented Oct 6, 2021

one could imagine a SlackErrorResponse, which would basically be a SlackResponse with Ok == false. That struct would implement the error interface returning its Error field as the current code does, but could also be casted using errors.As to get access to ResponseMetadata. Something like

// SlackErrorResponse is a SlackResponse with an error set
type SlackErrorResponse struct {
  Error string
  ResponseMetadata ResponseMetadata
}

func (r SlackErrorResponse) Error() string { return r.Error } // keeps the same behavior as before

// we'd change this method
func (t SlackResponse) Err() {
  if t.Ok { return nil } // unchanged
  if strings.TrimSpace(t.Error) == "" { return nil } // unchanged
  return SlackErrorResponse{Error: t.Error, ResponseMetadata: t.ResponseMetadata}
}

I'm happy to work on implementing this if you think it makes sense.

@abourget
Copy link
Contributor

yes please please, same issue here!

@abourget
Copy link
Contributor

Another option:

type SlackErrorResponse struct {
  Response SlackResponse
}
func (e SlackErrorResponse) Error() string {
  return e.Response.Error
}

and we could even add a few newer fields to SlackResponse:

type SlackResponse struct {
	Ok               bool             `json:"ok"`
	Error            string           `json:"error"`
	Errors []string `json:"errors"`
        Warnings []string `json:"warnings"`
	ResponseMetadata ResponseMetadata `json:"response_metadata"`
}

That would future-proof the returned Error object.

@abourget
Copy link
Contributor

Yet another option: append the ResponseMetadata.Messages array, joined with a ", " to the currently returned errors.New() here:

func (t SlackResponse) Err() error {
	if t.Ok {
		return nil
	}
...
	return errors.New(t.Error)
}

This way, everyone benefits from clearer messages.

@abourget
Copy link
Contributor

Third option, a mix of both two previous options: return a clearer error message on the SlackErrorResponse's proposed Error() string function. Get the best of all the worlds.

@kanata2
Copy link
Member

kanata2 commented Oct 29, 2021

Sorry for delay.
I generally agree with @abustany's original suggestion.
I would like to prioritize the review of other pull requests,
so if possible, could you please submit a pull request the proposal here?

@abourget @abustany
Thank you for your great suggestions.

abourget added a commit to abourget/slack that referenced this issue Oct 29, 2021
@kanata2 kanata2 closed this as completed Oct 30, 2021
ghost pushed a commit to range-labs/slack that referenced this issue Apr 19, 2022
* Change ActionType to public

* Changed type of GetConversationsParameters.ExcludeArchived to bool instead of string.

* Make possible to get authorized user's profile providing empty userID to GetUserProfileContext

* Added coverage for audit API endpoint

* Added all of the other possible entity types for completeness

* Update audit.go

Just cleaning up a comment

* Changed field Ua to UA to better match Go standard

* Add support for "channel_created" in the Events API.

* add thread_ts to container

* restore go.mod and go.sum

* refact: missing attachement fields

* Make UserID optional in GetUserProfile()

`users.profile.get` API takes user parameter as optional.
https://api.slack.com/methods/users.profile.get

This change breaks GetUserProfile interface.
The current interface does not allow the bot to retrieve
its own user profile.

* Handle token_revoked event

This is a critical event and the client should stop trying to reconnect.

Signed-off-by: Andrea Barberio <[email protected]>

* Add ReplyTo information to ack error events.

This allows clients to better handle ack errors by linking them
to the original outbound message.

* Make more examples directly runnable

* add the condition to the validation func for TextBlockObject

* Seems the token was missing from the request.

* Token is also added to URL parameters

* Update slackevents/inner_events.go

* Remove deprecated methods

Related issues:

- slack-go#748
- slack-go#876

More details:

- https://api.slack.com/changelog/2020-01-deprecating-antecedents-to-the-conversations-api

* slacktest: Save thread_ts to message

* Add timepicker to UnmarshalJSON

* Fix authorization on methods which uses get requests

* [socketmode] Add methods with passing context

- added socketmode.Client.RunContext
- added socketmode.Client.OpenContext
- changed socketmode.Client.openAndDial to pass context
- added test coverage for socketmode.Client.openAndDial
- added test coverage for socketmode.Client.RunContext
- added test coverage for socketmode.Client.OpenContext

* [socketmode] Use DialContext instead of Dial

* [socketmode] Graceful shutdown websocket.Conn

websocket connection freeze on conn.ReadJSON

- returned context errors to stop reconnect
- closed channel of messages when exit from Client.run
- closed websocket connection when context canceled

* [socketmode] mark test only for go 1.13 and higher

* [socketmode] fix typo in json tag

* Drop support of Go 1.12

* Remove travis badge

* Fix broken examples

* Add support for Go1.16

* [skip-ci] Replace badge

* feat: support response_urls field for view_submission payload

view_submission payload includes response_urls field when specific blocks have
a special parameter(response_url_enabled paramter = true).

See the following Slack docs for more details:

* https://api.slack.com/surfaces/modals/using#modal_response_url
* https://api.slack.com/reference/interaction-payloads/views#view_submission

* add missing token values

* added `external` data_source for dynamic data

`external` kind of input was missing in the slack api
but makes sense to pass this as option rather than separating into
two funcs; also makes sense to pass Optional as option but not hardcoded

* fix: renamed from dynamic to external for dialog input

* slacktest: Fix broken json if newline in text

* support team id param

* Trivial typo fix in the bug reporting template

* Updating audit.go 

Updated audit api code to use the updated getMethod w/ token function

* fix button sample

* fix limit url param

This should be "limit" not "count" according to the current
API docs: https://api.slack.com/admins/audit-logs#monitoring-workspace-events-with-the-audit-logs-api__how-to-call-the-audit-logs-api__audit-logs-endpoints

* Don't include secrets in url

* replace deprecated method

I believe this GetGroups was deleted as a part of this commit:
slack-go@9152ed0

* Rename the member socketmode.Client.apiClient to Client, and be an embedded structure for compatibility

* Fix path

* New events (WIP)

* New events (WIP)

* New events (WIP)

* fix block_context.go doc link

* New events (WIP)

* New events (WIP)

* Restore original paths

* Restore original intents

* Add test setup for Go1.17 environment to CI

* Add Enterprise property

* Fixed LinkSharedEvent and added context aware UnfurlMessage

The MessageTimeStamp was incorrectly marked as a number. It should be
a string as any other timestamp, and it required for Unfurl to work

* Revert conversion to string for now

* Add expires_in and refresh token handling

* Update users example with input examples

* Add Dispatch Action Config to InputBlock

* use pointer

* add TeamJoinEvent

* Update socketmode.go

* webhooks: add additional fields

no issue

These fields allow users to replace original messages sent by bots

eg first sending a ephemeral message and replacing it with one thats in-channel

* add message subType constants from https://api.slack.com/events/message

* Allow wrapping of error metadata. Addresses issue slack-go#939

* Support Rich Text blocks

* Update CHANGELOG.md

* Update bug report template

* fix: don't add API token as a query string in users.setPhoto method

resolve slack-go#992

* sometimes the message_ts isn't a json.Number

* add a new test with the payload from link_shared docs re: unfurls in the message composer

* add a comment for why MessageTimeStamp is a string, not json.Number

* [ci-skip] doc: guide to Slack channel

* [skip-ci] slacktest: fix license issue

Resolved: slack-go#625, slack-go#948, slack-go#979

* add socket mode example link to README

As mentioned in the documentation in https://api.slack.com/rtm:
"For most applications, Socket Mode is a better way to communicate with Slack."

(Personally I got confused between RTM and Socket Mode, and I think this might help future developers)

* Update README.md

* add empty line to be consistent

* add latest_reply property to Msg struct

* introduce workflow step app functionality

* tests for workflowStep added

* example workflowStep app added

* readme improved

* unused variable in example removed, switch line indention to tabulator

* using snake case for new directory and file

* Add refresh_token and token_type to OAuthV2Response fields

* all: add new //go:build lines

$ go version
go version go1.17.7 darwin/amd64

$ make fmt

Signed-off-by: Koichi Shiraishi <[email protected]>

* all: remove github.com/pkg/errors dependency

The github.com/pkg/errors package has been deprecated.

Signed-off-by: Koichi Shiraishi <[email protected]>

* vendor: run go mod vendor

Signed-off-by: Koichi Shiraishi <[email protected]>

* messageID: add benchmark for NewSafeID

Signed-off-by: Koichi Shiraishi <[email protected]>

* messageID: optimize NewSafeID using atomic instead of mutex lock

name                  old time/op    new time/op    delta
NewSafeID-20            13.9ns ± 2%     7.5ns ± 1%  -46.16%  (p=0.008 n=5+5)
NewSafeIDParallel-20    24.2ns ± 6%    22.1ns ± 1%   -9.06%  (p=0.008 n=5+5)

name                  old alloc/op   new alloc/op   delta
NewSafeID-20             0.00B          0.00B          ~     (all equal)
NewSafeIDParallel-20     8.00B ± 0%     8.00B ± 0%     ~     (all equal)

name                  old allocs/op  new allocs/op  delta
NewSafeID-20              0.00           0.00          ~     (all equal)
NewSafeIDParallel-20      1.00 ± 0%      1.00 ± 0%     ~     (all equal)

Signed-off-by: Koichi Shiraishi <[email protected]>

* messageID: add NewSafeID testcase

Signed-off-by: Koichi Shiraishi <[email protected]>

* switch go code style for imports from gofmt to goimports

* all: support pass context.Context to all methods

Signed-off-by: Koichi Shiraishi <[email protected]>

* webhooks: remove go1.12 support

Signed-off-by: Koichi Shiraishi <[email protected]>

* misc: use NewRequestWithContext

Signed-off-by: Koichi Shiraishi <[email protected]>

* misc: use http.MethodXXX constant

Signed-off-by: Koichi Shiraishi <[email protected]>

* messageID: fix atomic operation suggested by brainexe

name                  old time/op    new time/op    delta
NewSafeID-20            7.60ns ± 1%    5.93ns ± 1%  -21.97%  (p=0.008 n=5+5)
NewSafeIDParallel-20    21.0ns ± 1%    21.0ns ± 2%     ~     (p=0.952 n=5+5)

name                  old alloc/op   new alloc/op   delta
NewSafeID-20             0.00B          0.00B          ~     (all equal)
NewSafeIDParallel-20     8.00B ± 0%     8.00B ± 0%     ~     (all equal)

name                  old allocs/op  new allocs/op  delta
NewSafeID-20              0.00           0.00          ~     (all equal)
NewSafeIDParallel-20      1.00 ± 0%      1.00 ± 0%     ~     (all equal)

See also:
- slack-go#1035 (review)

Signed-off-by: Koichi Shiraishi <[email protected]>

* messageID: add documentation

Signed-off-by: Koichi Shiraishi <[email protected]>

* chat: add some BuildRequestContext methods for backwards compatibility

Signed-off-by: Koichi Shiraishi <[email protected]>

* webhook: remove unnecessary PostWebhookContextCustomHTTP function

Signed-off-by: Koichi Shiraishi <[email protected]>

* introduce workflow step app functionality

* tests for workflowStep added

* example workflowStep app added

* readme improved

* unused variable in example removed, switch line indention to tabulator

* using snake case for new directory and file

* switch go code style for imports from gofmt to goimports

* optimize slackutilsx.EscapeMessage function

* workflow_step: add SaveWorkflowStepConfigurationConetxt & fix return err

Signed-off-by: Koichi Shiraishi <[email protected]>

* workflow_step: fix typo on SaveWorkflowStepConfigurationContext

Signed-off-by: Koichi Shiraishi <[email protected]>

* github/workflow: drop go1.15 and add go1.18 (slack-go#1048)

* github/workflow: drop go1.15 and add go1.18

* all: run goimports

* WithStyle should be fluent

* Add a fluent WithConfirm for buttons

Co-authored-by: GLOFonseca <[email protected]>
Co-authored-by: mzduke <[email protected]>
Co-authored-by: Alexander Tunik <[email protected]>
Co-authored-by: Justin Judd <[email protected]>
Co-authored-by: Ward Vandewege <[email protected]>
Co-authored-by: Ian Hall <[email protected]>
Co-authored-by: xnok <[email protected]>
Co-authored-by: Takuya Kosugiyama <[email protected]>
Co-authored-by: Andrea Barberio <[email protected]>
Co-authored-by: Nolan Lum <[email protected]>
Co-authored-by: David Parsley <[email protected]>
Co-authored-by: sryoya <[email protected]>
Co-authored-by: Naoki Kanatani <[email protected]>
Co-authored-by: arran <[email protected]>
Co-authored-by: “Anton <[email protected]>
Co-authored-by: Hiroshi Muraoka <[email protected]>
Co-authored-by: Aleksandr Kozlov <[email protected]>
Co-authored-by: Evgeniy Kulikov <[email protected]>
Co-authored-by: Takayuki WATANABE <[email protected]>
Co-authored-by: Chris Lee <[email protected]>
Co-authored-by: Myroslav Gavryliak <[email protected]>
Co-authored-by: Daniel Metz <[email protected]>
Co-authored-by: Justin Clift <[email protected]>
Co-authored-by: Justin Judd <[email protected]>
Co-authored-by: sivchari <[email protected]>
Co-authored-by: Henry Foster <ahoy>
Co-authored-by: thorntonmc <[email protected]>
Co-authored-by: Yoshio HANAWA <[email protected]>
Co-authored-by: Valerian Saliou <[email protected]>
Co-authored-by: Pavel Lakosnikov <[email protected]>
Co-authored-by: norabal <[email protected]>
Co-authored-by: Peter Kristensen <[email protected]>
Co-authored-by: Ryota <[email protected]>
Co-authored-by: Karl-Johan Grahn <[email protected]>
Co-authored-by: Karl-Johan Grahn <[email protected]>
Co-authored-by: Karl Keefer <[email protected]>
Co-authored-by: Rafael Almeida <[email protected]>
Co-authored-by: James Loh <[email protected]>
Co-authored-by: Alexandre Bourget <[email protected]>
Co-authored-by: Chris Toshok <[email protected]>
Co-authored-by: Itay Donanhirsh <[email protected]>
Co-authored-by: amelia gapin <[email protected]>
Co-authored-by: Steffen Mahler <[email protected]>
Co-authored-by: hidenami-i <[email protected]>
Co-authored-by: Koichi Shiraishi <[email protected]>
Co-authored-by: Matthias Dötsch <[email protected]>
Co-authored-by: Leo Zhang <[email protected]>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

4 participants