[marker] Add marker info to actor result

in order to enable rules to access i.e. the position of the marker

Signed-off-by: Knut Ahlers <knut@ahlers.me>
This commit is contained in:
Knut Ahlers 2024-09-11 14:23:42 +02:00
parent e0a8ce3684
commit 740a71a173
Signed by: luzifer
SSH key fingerprint: SHA256:/xtE5lCgiRDQr8SLxHMS92ZBlACmATUmF1crK16Ks4E
3 changed files with 24 additions and 8 deletions

View file

@ -86,7 +86,7 @@ Triggers the creation of a Clip from the given channel owned by the creator (sub
## Create Marker ## Create Marker
Creates a marker on the currently running stream of the given channel. The marker will be created on behalf of the channel owner and requires matching scope. Creates a marker on the currently running stream of the given channel. The marker will be created on behalf of the channel owner and requires matching scope. (Subsequent actions can use variable `marker` to access marker details.)
```yaml ```yaml
- type: marker - type: marker

View file

@ -31,7 +31,7 @@ func Register(args plugins.RegistrationArguments) error {
args.RegisterActor(actorName, func() plugins.Actor { return &actor{} }) args.RegisterActor(actorName, func() plugins.Actor { return &actor{} })
args.RegisterActorDocumentation(plugins.ActionDocumentation{ args.RegisterActorDocumentation(plugins.ActionDocumentation{
Description: "Creates a marker on the currently running stream of the given channel. The marker will be created on behalf of the channel owner and requires matching scope.", Description: "Creates a marker on the currently running stream of the given channel. The marker will be created on behalf of the channel owner and requires matching scope. (Subsequent actions can use variable `marker` to access marker details.)",
Name: "Create Marker", Name: "Create Marker",
Type: actorName, Type: actorName,
Fields: []plugins.ActionDocumentationField{ Fields: []plugins.ActionDocumentationField{
@ -86,10 +86,13 @@ func (actor) Execute(_ *irc.Client, m *irc.Message, r *plugins.Rule, eventData *
return false, fmt.Errorf("getting Twitch client for %q: %w", channel, err) return false, fmt.Errorf("getting Twitch client for %q: %w", channel, err)
} }
if err = tc.CreateStreamMarker(context.TODO(), description); err != nil { var marker twitch.StreamMarkerInfo
if marker, err = tc.CreateStreamMarker(context.TODO(), description); err != nil {
return false, fmt.Errorf("creating marker: %w", err) return false, fmt.Errorf("creating marker: %w", err)
} }
eventData.Set("marker", marker)
return false, nil return false, nil
} }

View file

@ -29,6 +29,14 @@ type (
TagIds []string `json:"tag_ids"` //revive:disable-line:var-naming // Disabled to prevent breaking change TagIds []string `json:"tag_ids"` //revive:disable-line:var-naming // Disabled to prevent breaking change
IsMature bool `json:"is_mature"` IsMature bool `json:"is_mature"`
} }
// StreamMarkerInfo contains information about a marker on a stream
StreamMarkerInfo struct {
ID int64 `json:"id"`
CreatedAt time.Time `json:"created_at"`
Description string `json:"description"`
PositionSeconds int64 `json:"position_seconds"`
}
) )
// ErrNoStreamsFound allows to differntiate between an HTTP error and // ErrNoStreamsFound allows to differntiate between an HTTP error and
@ -38,12 +46,12 @@ var ErrNoStreamsFound = errors.New("no streams found")
// CreateStreamMarker creates a marker for the currently running stream. // CreateStreamMarker creates a marker for the currently running stream.
// The stream must be live, no VoD, no upload and no re-run. // The stream must be live, no VoD, no upload and no re-run.
// The description may be up to 140 chars and can be omitted. // The description may be up to 140 chars and can be omitted.
func (c *Client) CreateStreamMarker(ctx context.Context, description string) (err error) { func (c *Client) CreateStreamMarker(ctx context.Context, description string) (marker StreamMarkerInfo, err error) {
body := new(bytes.Buffer) body := new(bytes.Buffer)
userID, _, err := c.GetAuthorizedUser(ctx) userID, _, err := c.GetAuthorizedUser(ctx)
if err != nil { if err != nil {
return fmt.Errorf("getting ID for current user: %w", err) return marker, fmt.Errorf("getting ID for current user: %w", err)
} }
if err = json.NewEncoder(body).Encode(struct { if err = json.NewEncoder(body).Encode(struct {
@ -53,7 +61,11 @@ func (c *Client) CreateStreamMarker(ctx context.Context, description string) (er
UserID: userID, UserID: userID,
Description: description, Description: description,
}); err != nil { }); err != nil {
return fmt.Errorf("encoding payload: %w", err) return marker, fmt.Errorf("encoding payload: %w", err)
}
var payload struct {
Data []StreamMarkerInfo `json:"data"`
} }
if err := c.Request(ctx, ClientRequestOpts{ if err := c.Request(ctx, ClientRequestOpts{
@ -61,12 +73,13 @@ func (c *Client) CreateStreamMarker(ctx context.Context, description string) (er
Body: body, Body: body,
Method: http.MethodPost, Method: http.MethodPost,
OKStatus: http.StatusOK, OKStatus: http.StatusOK,
Out: &payload,
URL: "https://api.twitch.tv/helix/streams/markers", URL: "https://api.twitch.tv/helix/streams/markers",
}); err != nil { }); err != nil {
return fmt.Errorf("creating marker: %w", err) return marker, fmt.Errorf("creating marker: %w", err)
} }
return nil return payload.Data[0], nil
} }
// GetCurrentStreamInfo returns the StreamInfo of the currently running // GetCurrentStreamInfo returns the StreamInfo of the currently running