-
Notifications
You must be signed in to change notification settings - Fork 77
Description
From the documentation
From https://customer.io/docs/journeys/events/#deduplicating-events
You can provide an id with your events, to deduplicate events—if there’s a possibility that your integration might send duplicate events. The id must be a ULID. If two events contain the same id, we won’t process the event multiple times.
Deduplicating events helps you accurately represent people’s activity; can prevent people from accidentally entering or leaving campaigns based on the number of times that a person performed an event; and prevents duplicate events from impacting your workspace’s performance.
{
"name": "my event",
"id": "01BX5ZZKBKACTAV9WEVGEMMVRY",
"data": {
"prop1": "value"
}
}Relevant code
customerio-ruby/lib/customerio/client.rb
Lines 160 to 166 in f9984a7
| def create_customer_event(customer_id, event_name, attributes = {}) | |
| create_event( | |
| url: "#{customer_path(customer_id)}/events", | |
| event_name: event_name, | |
| attributes: attributes | |
| ) | |
| end |
customerio-ruby/lib/customerio/client.rb
Lines 186 to 193 in f9984a7
| def create_event(url:, event_name:, anonymous_id: nil, event_type: nil, attributes: {}) | |
| body = { :name => event_name, :data => attributes } | |
| body[:timestamp] = attributes[:timestamp] if valid_timestamp?(attributes[:timestamp]) | |
| body[:anonymous_id] = anonymous_id unless is_empty?(anonymous_id) | |
| body[:type] = event_type unless is_empty?(event_type) | |
| @client.request_and_verify_response(:post, url, body) | |
| end |
customerio-ruby/lib/customerio/client.rb
Lines 47 to 52 in f9984a7
| def track(customer_id, event_name, attributes = {}) | |
| raise ParamError.new("customer_id must be a non-empty string") if is_empty?(customer_id) | |
| raise ParamError.new("event_name must be a non-empty string") if is_empty?(event_name) | |
| create_customer_event(customer_id, event_name, attributes) | |
| end |
Problem
As you can see, the expected JSON has a top-level id attribute. However, the existing code doesn't allow for this. Apart from a handful exceptions, it nests all attributes into a data object.
This means users of the gem currently don't have a way to provide an id to prevent duplicate events.
Proposed fix
Add an (optional) id parameter to create_event and all methods that reference it. Pass it as a top-level key to the API.
This will be a backwards-compatible change, as current implementations won't currently provide an id directly into the create_event calls. Notably, any id that might be included in the attributes hash continue to work as before.
def track(customer_id, event_name, attributes = {}) needs to be updated too. This is a bit trickier, because it uses positional arguments. I think adding a fourth, optional argument does the trick: def track(customer_id, event_name, attributes = {}, id = nil)
Optionally, the following code can be used to validate the correctness of the id:
def valid_ulid?(ulid)
!!(ulid =~ /\A[0123456789ABCDEFGHJKMNPQRSTVWXYZabcdefghjkmnpqrstvwxyz]{26}\z/)
end