Skip to content

feat(analytics): support explicit count values in Count method#3619

Draft
wolf-06 wants to merge 2 commits intohatchet-dev:mainfrom
wolf-06:feat/analytics/count
Draft

feat(analytics): support explicit count values in Count method#3619
wolf-06 wants to merge 2 commits intohatchet-dev:mainfrom
wolf-06:feat/analytics/count

Conversation

@wolf-06
Copy link
Copy Markdown

@wolf-06 wolf-06 commented Apr 14, 2026

Description

Adds support for explicit count values in analytics.Count() by extracting int64 values from the last Properties argument when multiple are provided.

What's Changed

  • Extract count from last Properties argument if multiple provided, summing all int64 values
  • Fall back to count=1 when no explicit count is provided
  • Add tests covering default, explicit, sum, and fallback behavior
  • Update comment to explain the feature

Type of change

  • New feature (non-breaking change which adds functionality)
  • Test changes (add, refactor, improve or change a test)

FIXES #3382

wolf-06 added 2 commits April 15, 2026 03:38
Signed-off-by: wolf-06 <Uajjawal.06@gmail.com>
Signed-off-by: wolf-06 <Uajjawal.06@gmail.com>
@vercel
Copy link
Copy Markdown

vercel bot commented Apr 14, 2026

@wolf-06 is attempting to deploy a commit to the Hatchet Team on Vercel.

A member of the Team first needs to authorize it.

Copy link
Copy Markdown
Collaborator

@gregfurman gregfurman left a comment

Choose a reason for hiding this comment

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

Thanks for picking this up! I think the current approach needs some more consideration since (IMO) it's prone to incorrect usage and is not very self-documenting.

Wdyt of the approach outlined in #3382 that extends the analytics.Properties and uses a more explicit (and structured) typing system to determine values?

Comment on lines +151 to +152
// Extract count from last properties arg if multiple are provided.
// Allows passing aggregated counts instead of always using 1.
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Tbh I still think we should be passing in a structured type to determine/override this value, where necessary instead of relying on a positional arg in the varadic params.

Like, it's more explicit that way i.e

a.Count(ctx, analytics.Log, analytics.Get, analytics.Properties{}, analytics.Increment(5))

versus:

a.Count(ctx, analytics.Log, analytics.Get, analytics.Properties{}, analytics.Properties{"": 5})

where the latter could be error prone as well since it means we'd need to document this positional behaviour.

This typed-approach also means we can extend supported operations i.e

a.Count(ctx, analytics.Log, analytics.Get, analytics.Properties{}, analytics.Decrement(5))
a.Count(ctx, analytics.Log, analytics.Get, analytics.Properties{}, analytics.Set(0)) // or maybe .Reset() ?

Then if we have other metric types (i.e a gauge or whatever) we can extend this approach to suit.

Copy link
Copy Markdown
Author

@wolf-06 wolf-06 Apr 15, 2026

Choose a reason for hiding this comment

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

Fair enough,
will move with original approach of using structured property, which ig will also solve to other concerns automatically.

// Allows passing aggregated counts instead of always using 1.
var n int64
if len(props) > 1 && props[len(props)-1] != nil {
for _, v := range props[len(props)-1] {
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Unsure this is desirable due to the typing of analytics.Properties.

Like, analytics.Properties is a map[string]any which means (in the case of your changes) the last arg would still have to be correctly typed as such. So if I wanted to increment the count by 5 I'd need to pass a contrived map type where the keys will be ignored i.e

a.Count(ctx, analytics.Log, analytics.Get, analytics.Properties{},  analytics.Properties{"foo": 5}))

Also, if we pass in two (or more) properties, the caller has no way of knowing the final arg will have all of its values used for incrementing. This ambigious behaviour could lead to unintentionally passing props in that we expect to be included as tags/labels but get used to increment metrics.

var n int64
if len(props) > 1 && props[len(props)-1] != nil {
for _, v := range props[len(props)-1] {
if value, ok := v.(int64); ok {
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

This conversion means we're only ever supporting an int64 being explicitly passed in, meaning other numeric types being used would get skipped over.

i.e

a.Count(ctx, analytics.Log, analytics.Get, analytics.Properties{},  analytics.Properties{"foo": uint64(5)}))

Would see 1 being added since a uint64 is not an int64 -- hence it's skipped as type-checking fails.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[FEAT] Extend Analytics Interface

2 participants