Current section

Files

Jump to
posthog lib posthog.ex
Raw

lib/posthog.ex

defmodule Posthog do
@moduledoc """
A comprehensive Elixir client for PostHog's analytics and feature flag APIs.
This module provides a high-level interface to PostHog's APIs, allowing you to:
- Track user events and actions
- Manage and evaluate feature flags
- Handle multivariate testing
- Process events in batch
- Work with user, group, and person properties
## Configuration
Add your PostHog configuration to your application config:
config :posthog,
api_url: "https://us.i.posthog.com", # Or your self-hosted instance
api_key: "phc_your_project_api_key"
Optional configuration:
config :posthog,
json_library: Jason, # Default JSON parser (optional)
enabled_capture: true # Whether to enable PostHog tracking (optional, defaults to true)
# Set to false in development/test environments to disable tracking
### Disabling PostHog
You can disable PostHog tracking by setting `enabled: false` in your configuration.
This is particularly useful in development or test environments where you don't want
to send actual events to PostHog.
When `enabled_capture` is set to `false`:
- All `Posthog.capture/3` and `Posthog.batch/2` calls will succeed silently
- PostHog will still communicate with the server for Feature Flags
This is useful for:
- Development and test environments where you don't want to pollute your PostHog instance
- Situations where you need to temporarily disable tracking
Example configuration for development:
# config/dev.exs
config :posthog,
enabled_capture: false # Disable tracking in development
Example configuration for test:
# config/test.exs
config :posthog,
enabled_capture: false # Disable tracking in test environment
## Event Tracking
Events can be tracked with various levels of detail:
# Basic event
Posthog.capture("page_view", distinct_id: "user_123")
# Event with properties
Posthog.capture("purchase", %{
distinct_id: "user_123",
product_id: "prod_123",
price: 99.99
})
# Event with custom timestamp
Posthog.capture("signup", "user_123", %{}, timestamp: DateTime.utc_now())
# Event with custom headers (e.g., for IP forwarding)
Posthog.capture("login", "user_123", %{}, headers: [{"x-forwarded-for", "127.0.0.1"}])
## Feature Flags
PostHog feature flags can be used for feature management and A/B testing:
# Get all feature flags for a user
{:ok, flags} = Posthog.feature_flags("user_123")
# Check specific feature flag
{:ok, flag} = Posthog.feature_flag("new-dashboard", "user_123")
# Quick boolean check
if Posthog.feature_flag_enabled?("new-feature", "user_123") do
# Show new feature
end
# Feature flags with group/person properties
Posthog.feature_flags("user_123",
groups: %{company: "company_123"},
group_properties: %{company: %{industry: "tech"}},
person_properties: %{email: "user@example.com"}
)
## Batch Processing
Multiple events can be sent in a single request for better performance:
events = [
{"page_view", [distinct_id: "user_123"], nil},
{"button_click", [distinct_id: "user_123", button: "signup"], nil}
]
Posthog.batch(events)
Each event in the batch is a tuple of `{event_name, properties, timestamp}`.
"""
@doc """
Captures an event in PostHog.
## Parameters
* `event` - The name of the event (string or atom)
* `params` - Required parameters including `:distinct_id` and optional properties
* `opts` - Optional parameters that can be either a timestamp or a keyword list of options
## Options
* `:headers` - Additional HTTP headers for the request
* `:groups` - Group properties for the event
* `:group_properties` - Additional properties for groups
* `:person_properties` - Properties for the person
* `:timestamp` - Custom timestamp for the event
## Examples
# Basic event
Posthog.capture("page_view", "user_123")
# Event with properties
Posthog.capture("purchase", "user_123", %{
product_id: "prod_123",
price: 99.99
})
# Event with timestamp
Posthog.capture("signup", "user_123", %{}, timestamp: DateTime.utc_now())
# Event with custom headers
Posthog.capture("login", "user_123", %{}, headers: [{"x-forwarded-for", "127.0.0.1"}])
"""
alias Posthog.{Client, FeatureFlag}
@spec capture(Client.event(), Client.distinct_id(), Client.properties(), Client.opts()) ::
Client.result()
defdelegate capture(event, distinct_id, properties \\ %{}, opts \\ []), to: Client
@doc """
Sends multiple events to PostHog in a single request.
## Parameters
* `events` - List of event tuples in the format `{event_name, distinct_id, properties}`
* `opts` - Optional parameters for the batch request
## Examples
events = [
{"page_view", "user_123", %{}},
{"button_click", "user_123", %{button: "signup"}}
]
Posthog.batch(events)
"""
@spec batch(list(tuple()), keyword()) :: Client.result()
defdelegate batch(events, opts \\ []), to: Client
@doc """
Retrieves all feature flags for a given distinct ID.
## Parameters
* `distinct_id` - The unique identifier for the user
* `opts` - Optional parameters for the feature flag request
## Options
* `:groups` - Group properties for feature flag evaluation
* `:group_properties` - Additional properties for groups
* `:person_properties` - Properties for the person
## Examples
# Basic feature flags request
{:ok, flags} = Posthog.feature_flags("user_123")
# With group properties
{:ok, flags} = Posthog.feature_flags("user_123",
groups: %{company: "company_123"},
group_properties: %{company: %{industry: "tech"}}
)
"""
@spec feature_flags(binary(), keyword()) :: Client.result()
defdelegate feature_flags(distinct_id, opts \\ []), to: Client
@doc """
Retrieves information about a specific feature flag for a given distinct ID.
## Parameters
* `flag` - The name of the feature flag
* `distinct_id` - The unique identifier for the user
* `opts` - Optional parameters for the feature flag request
## Examples
# Boolean feature flag
{:ok, flag} = Posthog.feature_flag("new-dashboard", "user_123")
# Returns: %Posthog.FeatureFlag{name: "new-dashboard", payload: true, enabled: true}
# Multivariate feature flag
{:ok, flag} = Posthog.feature_flag("pricing-test", "user_123")
# Returns: %Posthog.FeatureFlag{
# name: "pricing-test",
# payload: %{"price" => 99, "period" => "monthly"},
# enabled: "variant-a"
# }
"""
@spec feature_flag(binary(), binary(), Client.feature_flag_opts()) :: Client.result()
defdelegate feature_flag(flag, distinct_id, opts \\ []), to: Client
@doc """
Checks if a feature flag is enabled for a given distinct ID.
This is a convenience function that returns a boolean instead of a result tuple.
For multivariate flags, returns true if the flag has any value set.
## Parameters
* `flag` - The name of the feature flag
* `distinct_id` - The unique identifier for the user
* `opts` - Optional parameters for the feature flag request
## Examples
if Posthog.feature_flag_enabled?("new-dashboard", "user_123") do
# Show new dashboard
end
"""
@spec feature_flag_enabled?(binary(), binary(), keyword()) :: boolean()
def feature_flag_enabled?(flag, distinct_id, opts \\ []) do
flag
|> feature_flag(distinct_id, opts)
|> case do
{:ok, %FeatureFlag{enabled: false}} -> false
{:ok, %FeatureFlag{}} -> true
_ -> false
end
end
end