nothing goes wrong
without you knowing.
a window onto everything your applications are doing: errors, logs, journeys and uptime, the moment they do it. it watches, and it never changes anything.
for the team of three who need on-call, not the procurement department of a company that can buy four monitoring products and a pager seat for everybody.
first error in about two minutes sentry-compatible python · javascript · dart zero-dependency sdks sms & whatsapp read-only, always
one night, reconstructed
told in clocks. the gaps between them are the part that costs money.
checkout · 1,284 requests · every one healthy
quiet is information too.
NullPointerException · checkout.charge():88
you were asleep. the eye was not.
paged: inbox, webhook, phone
3 identical crashes, one incident, one message.
you opened the dashboard already knowing
frames, request, breadcrumbs, session. where you left them.
and this one is real
that story is a reconstruction. this is not: the page you are reading reports itself to cyclopes, so everything below was measured by the product it is selling, a few minutes ago at most.
- 98.9%
- uptime across 72587 real checks in 30 days, floored, never rounded up
- 73ms
- the most recent check of this instance, from outside it
- 1d
- since cyclopes last had to wake anyone here. the goal is for this number to keep climbing
no dashboard screenshot, because a screenshot is a drawing. this is the instance you are talking to, describing itself.
what you get
the whole night,
not just the exception.
the stack trace is the easy part. who it hit, how many, what they were doing, whether it is still going, and who to wake: that is the night.
elsewhere that is four subscriptions: error tracking, product analytics, uptime, and a pager. three of them bill per person, so knowing what broke costs more every time you hire.
here it is one product, priced per organisation. twenty-five people on Team is $19, not $19 each.
journeys
the ones who left without telling you, drawn as a map.
errors count exceptions. journeys count people: the map draws itself from real sessions, names the step they gave up on, and replays one of them screen by screen. no error tracker does this.
issues
the crash, and the ten seconds before it.
grouped by fingerprint, counted, and kept with the frames, the local variables, the breadcrumbs and the session that led there. a resolved issue that comes back says so instead of quietly reopening.
logs & terminal
every project in one live stream, every stored line searchable.
tailed live over a websocket, with a severity rail down the margin you read like a seismograph. filter by level, then page back to the first line that went wrong.
monitors
the outages that never reach your code at all.
websites, servers, mailboxes and cron heartbeats. a job that stops running pages you for the events that never arrived, which no error tracker can see because nothing errored. tls expiry too: it is always the certificate.
incidents & on-call
a rotation, a ladder, and a record of who knew what.
rotations computed from the clock, never stored, so a missed handover cannot page last week's person. the timeline records who was told, where, and when they answered: the document you want when somebody asks why nobody moved for forty minutes.
sms & whatsapp
a pager that already lives in their pocket.
email is read tomorrow. sms and whatsapp are read now: no app, no seat, nothing to stay logged into. the whatsapp page carries ack, snooze and resolve as buttons, so 3am is one tap on a lock screen. no data on the handset? reply ack and a six-character code.
switching costs one line
already on sentry? keep the sdk. change the dsn.
cyclopes speaks sentry's ingest protocol, /store/ and /envelope/, so an unmodified sentry-sdk reports here. no code change, no re-instrumentation, no migration weekend.
run both for a week: nothing here is exclusive, and two dashboards on one incident beats any demo. transactions and attachments are accepted, then dropped. we do not store what we cannot show you.
spend that cannot run away
a crash loop should not arrive as an invoice.
paging real handsets costs real money. so routing here is priced before it fires, capped in three places, and built to refuse rather than ask forgiveness.
- one incident per issue
- a thousand identical crashes are one thing wrong. paged once.
- free stays free
- email, in-app, push and signed webhooks, at any volume. only sms and whatsapp draw a credit.
- three ceilings
- per incident, per project, per month. the tightest wins and names itself.
- quiet, never blind
- at the ceiling the alert still arrives, by email, with the reason recorded.
- undelivered is refunded
- the carrier says it never landed, the credit comes back on its own.
- the price before you commit
- every rule is replayed against your last 30 days: this would have paged you 4 times. noisy rules die as drafts.
the same night, from their side
nobody files a ticket.
they just leave.
03:12 has a second half: the people who were partway through paying when it broke. errors count exceptions. journeys count the ones who quietly gave up, and name the step they gave up on.
flow map · checkout · last 7 days
- completion
- 0%
- the blocker
- payment_added
- time to complete
- 1m 48s
796 of the 1,284 sessions that reached the cart
70% of unfinished sessions never got this far
median · 4m 12s at the 90th
session a41f·9c2, one of the 488
- 00:00 screen Cart
- 00:12 track add_to_cart
- 00:31 screen Checkout
- 01:04 track card_submitted
- 01:04 error NullPointerException · checkout.charge():88
- 01:39 exit gone. no ticket, no email, no idea, until now
488 abandoned carts, one null pointer.
flow map · send money · last 7 days
- completion
- 0%
- the blocker
- otp_verified
- time to complete
- 2m 34s
1,712 of the 2,940 transfers that were started
81% of abandoned transfers died waiting for a code
median · 9m 51s at the 90th
session 7b03·1de, one of the 1,228
- 00:00 screen SendMoney
- 00:22 track recipient_selected
- 00:40 track amount_entered
- 00:41 track otp_requested
- 00:56 error GatewayTimeout · sms/otp.dispatch():212
- 03:18 exit waited three minutes for a code that never came
1,228 transfers abandoned. the money never moved.
flow map · onboarding · last 30 days
- activation
- 0%
- the blocker
- workspace_created
- time to activate
- 6m 02s
291 of 812 signups sent their first event
64% of dormant signups never got a workspace
median · 2d 4h at the 90th
session c9e4·77a, one of the 521
- 00:00 screen Signup
- 00:48 track email_verified
- 01:03 screen CreateWorkspace
- 01:20 track workspace_submitted
- 01:20 error IntegrityError · workspaces.slugify():44
- 01:52 exit signed up, never activated, never replied to onboarding
521 signups you already paid to acquire.
flow map · place order · last 7 days
- completion
- 0%
- the blocker
- address_confirmed
- time to order
- 3m 11s
2,433 of the 4,105 sessions that opened a restaurant
74% of dropped baskets never confirmed an address
median · 8m 40s at the 90th
session 2fa8·05b, one of the 1,672
- 00:00 screen Restaurant
- 00:35 track item_added
- 01:12 screen AddressPicker
- 01:14 error PlatformException · location/permission denied
- 01:14 log map tiles failed to load, falling back to list
- 02:06 exit full basket, no address, gone
1,672 full baskets, one permission your SDK never handled.
- where they actually go. the map is drawn from events you already send. there is no funnel to configure first.
- whether they finish. define what done means and cyclopes measures it, then names the required step the unfinished sessions never reached.
- what this one did. replayed event by event, with the errors and logs that landed on each step.
that is the whole instrumentation. three calls, batched in the background, dropped on the floor if cyclopes is unreachable. the map, the completion rate and the replay are all built from them:
cyclopes.identify({"id": user.id})
cyclopes.screen("Checkout")
cyclopes.track("card_submitted", {"amount": 4471})
matching is unordered, on purpose. real people wander off, come back through search, apply a coupon and then pay. insisting on a fixed sequence would mark most genuine completions as failures. what counts is that everything meaning done happened, inside the window you set.
when it has to wake someone
a ladder, not a firehose
one incident per issue, carrying an ack link short enough to survive an sms. unanswered, it climbs.
push to whoever is on call
the rotation is computed from the clock, so a missed handover cannot page last week's person.
still unanswered · sms and whatsapp
every rung names its own channel and its own people.
everyone, and the signed webhook
capped per incident: a crash loop cannot become a thousand messages and a bill.
acknowledged, and the climb stops
set an ack timeout and it resumes: whoever acked at 3am and fell back asleep stopped the pager, not the problem.
what can page you
- new issue
- a resolved issue coming back
- level at or above
- event threshold
- rate spike
- affected users
- monitor down
- monitor recovered
- cron heartbeat missed
- tls certificate expiring
on any of
- sms
- push
- hmac-signed webhook
- in-app
and it fits in your pocket
the same eye, on your desk and on your phone
pair the app with an activation code and the stream follows you: a live feed on the phone, a desktop panel that dilates with the event rate and turns red before anyone files a ticket.
it runs a receiver of its own too, so an sdk can point straight at it with no server at all.
the wire
grab the dsn from your project's settings and point an sdk at it. every sdk reports uncaught errors on its own, and none of them will break or block your app when cyclopes is unreachable. signing up to a first error takes about two minutes: make a project, copy the dsn, restart, throw something.
$ pip install cyclopes
import cyclopes
cyclopes.init(dsn="https://key@cyclopes.dev/ingest/1", environment="production")
# unhandled exceptions now report themselves
cyclopes.logger.info("charge.settled", order=4471)
$ npm install @cyclopes/sdk
import * as cyclopes from "@cyclopes/sdk";
cyclopes.init({ dsn: "https://key@cyclopes.dev/ingest/1", environment: "production" });
// window.onerror and unhandledRejection are wired for you
cyclopes.logger.info("charge.settled", { order: 4471 });
$ dart pub add cyclopes
import 'package:cyclopes/cyclopes.dart';
await Cyclopes.init(dsn: 'https://key@cyclopes.dev/ingest/1');
// flutter errors and zone errors are caught for you
Cyclopes.logger.info('charge.settled', attrs: {'order': 4471});
before you decide
the four questions we get by email
- what if cyclopes goes down?
- your app does not notice. the sdk buffers, gives up quietly, and never blocks a request or raises into your code.
- how long do you keep my data?
- errors for 90 days, logs for 30, activity for 90. then it is pruned: data we did not need is still a breach.
- what if i run out of credit?
- the alert arrives by email instead, and the timeline says why. nothing is dropped.
- can i leave?
- delete the account from the dashboard, on a timer you can cancel during. no retention clause, nobody to email for permission.
what it costs
every plan watches everything.
paying decides who gets woken.
issues, logs, the terminal, monitors and journeys are on every tier, free included. what you pay for is who gets woken, how loudly, and how far back the history stays open. never per person: twenty-five people on Team is $19, not $19 each.
Free
$0forever
- email, webhook, push and in-app alerts
- 1 journey, 7 days of history
- 10 seats
- no escalation ladder
Hobby
USD 2/mo
- 40 sms or whatsapp alerts a month
- 2 journeys, 14 days of history
- 10 seats
- 1 escalation ladder
Solo
USD 5/mo
- 100 sms or whatsapp alerts a month
- 3 journeys, 30 days of history
- 10 seats
- 1 escalation ladder
Pair most pick this
USD 11/mo
- 220 sms or whatsapp alerts a month
- 6 journeys, 60 days of history
- 15 seats
- 3 escalation ladders
- on-call rotations
- sms and whatsapp held in reserve
Team
USD 19/mo
- 400 sms or whatsapp alerts a month
- 10 journeys, 90 days of history
- 25 seats
- 5 escalation ladders
- on-call rotations
- sms and whatsapp held in reserve
Business
USD 39/mo
- 900 sms or whatsapp alerts a month
- unlimited journeys, full history
- unlimited seats
- unlimited escalation ladders
- on-call rotations
- sms and whatsapp held in reserve
out of alerts before the month is? buy alerts, not a bigger plan: top-ups need no plan and never expire. every tier is prepaid, so nothing auto-charges and a period that lapses drops you to free rather than into arrears.
it watches, and it never
changes anything.
read-only by design. cyclopes stores what your app tells it and shows it back to you. it never runs your code, never rewrites a request, and never gets between you and your users.
built in zimbabwe, for teams who page real phones on real networks. the pager was the first thing we made work, not the last.
cyclopes sign in docs support privacy terms delete your account pricing