Use posthog-rails gem alongside posthog-ruby for automatic exception capture and ActiveJob instrumentation
Run rails generate posthog:install to create the initializer, or manually create config/initializers/posthog.rb
Configure auto_capture_exceptions: true to automatically track unhandled exceptions in controllers
Configure report_rescued_exceptions: true to also capture exceptions that Rails rescues (e.g. with rescue_from)
Configure auto_instrument_active_job: true to track background job failures with job class, queue, and arguments
Use PostHog.capture() and PostHog.identify() class-level methods (NOT instance methods) — the posthog-rails gem manages the client lifecycle via PostHog.init
Do NOT manually create PostHog::Client instances in Rails — use PostHog.init in the initializer and PostHog.capture/identify everywhere else
capture_exception takes POSITIONAL args: PostHog.capture_exception(exception, distinct_id, additional_properties) — do NOT use keyword args
Define posthog_distinct_id on the User model for automatic user association in error reports — posthog-rails auto-detects by trying: posthog_distinct_id, distinct_id, id, pk, uuid (in order)
For ActiveJob user association, use the class-level DSL posthog_distinct_id ->(user) { user.email } or pass user_id: in a hash argument
Store API key in Rails credentials or environment variables, never hardcode
For frontend tracking alongside posthog-rails, add the posthog-js snippet to the layout template — posthog-js handles pageviews, session replay, and client-side errors while posthog-ruby handles backend events, server errors, feature flags, and background jobs
posthog-ruby is the Ruby SDK gem name (add gem 'posthog-ruby' to Gemfile) but require it with require 'posthog' (NOT require 'posthog-ruby')
Use PostHog::Client.new(api_key: key, host: host) for instance-based initialization in scripts and CLIs
In CLIs and scripts: MUST call client.shutdown before exit or all events are lost
Use begin/rescue/ensure with shutdown in the ensure block for proper cleanup
capture and identify take a single hash argument: client.capture(distinct_id: ‘user_123’, event: ‘my_event’, properties: { key: ‘value’ })
capture_exception takes POSITIONAL args (not keyword): client.capture_exception(exception, distinct_id, additional_properties) — do NOT use distinct_id: keyword syntax
Install this repository
$ npx skills add PostHog/skills
» /plugin marketplace add PostHog/skills
Skills install per repository, not per chapter — the CLI has no documented per-skill form, so we do not print one.
MIT — the text of every chapter is reproduced unmodified, frontmatter included, under the upstream licence.
Discovery
200 chapters found by walking the repository tree for SKILL.md, not by matching a directory convention. 5 distinct layouts observed: skills/omnibus/*/SKILL.md, skills/posthog/all/skills/*/SKILL.md, skills/posthog/error-tracking/skills/*/SKILL.md, skills/posthog/feature-flags/skills/*/SKILL.md, skills/posthog/integration/skills/*/SKILL.md.
Issue colours
Resolved from the awesome-design-md registry — hue 38°, chroma 0.190. Two accent tones are generated per issue and each is proven against its own ground before it ships: a single accent that passes AA on both light and dark paper is arithmetically impossible.
Typefaces
Display: IBM Plex Sans Variable is not a face we ship; the reader's own choice is used.
Body: IBM Plex Sans Variable is not a face we ship; the reader's own choice is used.
Mono: Source Code Pro is not a face we ship; the reader's own choice is used.
We never load a typeface at request time from a third-party origin, so a brand face we do not already self-host is substituted rather than fetched.
Heading repairs
1 repair applied to this chapter so the document has one h1 and no skipped levels:
Shifted “4 headings” from h1 to h2 so the chapter title is the only h1.
Spec compliance
40 editorial notes across 40 of 200 chapters. They are printed in the margin of each chapter rather than as errors here.
Images inside a chapter come from the upstream repository. Where the author gave no alternative text we mark the image decorative rather than inventing a description — a plausible caption we made up is worse than none for the reader who depends on it.
Marketplace
A plugin manifest is published at .claude-plugin/marketplace.json by PostHog, declaring 5 plugins. It is read for editorial metadata only — never as the skill index, which is always the repository tree.
Signal
Install counts come from skills.sh. They measure downloads, not quality, and an unranked repository is not an unread one.
Agent surfaces
The whole issue is available as one markdown document at /PostHog/skills.md, and each chapter at its own .md URL.
Publication
Set by Skills Docs from the source repository. Body text is Literata at the reader’s chosen size and measure; code is Geist Mono. Nothing on this page was written by us except this paragraph.