The Valley of Webhooks
Posted by weli 1 day ago
Comments
Comment by toomim 1 day ago
Both drafts request a subscription with a GET plus a header:
Scroll Request:
GET /scroll/feed/customers
Prefer: stream
Braid Request:
GET /customers
Subscribe:
In both systems, the GET leaves its response open to stream events. SCROLL responds with application/x-ndjson. Braid subscriptions are a 209 Multiresponse, with content-type application/http-history. This lets them support more than just JSON. You can send updates to the state of CSV, or PNGs, XML, HTML, plain text, or any media type.The author noted that it's hard to get adoption. Well, the reason that Webhooks are so common is that they are bog-standard HTTP. For this to get adopted, we need to put it into bog-standard HTTP. So we need to go to the IETF, and and extend HTTP in a general way to support state synchronization. It should just work for any existing HTTP media type (not just JSON), and any resource/URL (not just special /scroll/* URLs), and any way of marking timestamps (not just the ordered strings proposed in SCROLL).
Then we can bake this stuff into HTTP, and thus into all our bog-standard libraries, utilities, and code, and you won't have to reimplement the same sync-logic-over-webhooks again, and again, and again.
Reach out if you're interested!
Comment by Joeri 1 day ago
https://semiceu.github.io/LinkedDataEventStreams/releases/1....
Comment by bobbiechen 1 day ago
And why formalize on HTTP rather than on a similar protocol over websockets?
Comment by anamexis 1 day ago
Comment by weli 1 day ago
Just one correction. My spec doesn't force /scroll/ URL's, just proposes it as a convention.
Comment by dzonga 1 day ago
hell this is without the proposal for a new protocol - just a 'GET' stream or paginated one like the author said.
whereas with web hooks - a consumer has to do all the work - as the article above outlined.
Comment by weli 17 hours ago
Comment by RyoSaeba89 13 hours ago
Comment by angrysponge 1 day ago
Comment by alt227 1 day ago
On create a user or invoice for example sometimes it will return an error, yet it actually created the entity. This means you have to check manually after creating everything to know if its created properly.
Then you have the issue that sometimes quickbooks takes a while to update, and locks the company file while it does some background magic. This means you cannot immediately do the existence check, and also sometimes the check errors or times out which essentially means you need to keep checking forever until you can properly reconcile your db against theirs. But with hundreds/thousands of transactions per minute this state is never reached. You perpetually live in a state of trying to catch up but never managing it.
When I brought it up with Quickbooks dev support their response was literally "Its your job to make sure things are created properly in our system".
How did we get to this place where we started putting up with systems that cannot ever be trusted?
Comment by hyperhello 1 day ago
Comment by lelanthran 1 day ago
Well... yeah. I mean it's pretty obvious, no?
Here's some things that could go wrong regardless of what care the software tries to provide:
- The transaction completed on the backend cluster but the app instance died before if could create the response and after it committed the transaction.
- The transaction completed, the app instance transmitted a response, but the load-balancer/reverse-proxy in-between died before it could relay that response.
- Everything went well, but the ISP dropped some packets before it could get to you.
- Everything completed and the ISP stayed up, but on your end the response was flagged as malicious, or never made it through your load-balancer.
So, yeah. in general when you make an API request and get an error you have to check if the state was changed anyway, and if you aren't doing that you're doing it wrong anyway and cannot blame the system on the other side for returning errors.
Comment by alt227 23 hours ago
Some Apis are designed to always fail safe and send the correct response, or at least accept multiple messages without creating duplicates, so you can just keep firing the same message until you get the correct response. Not doing that is just lazy design.
Comment by tux3 1 day ago
Of course none of that applies in this case, since it's about Quickbooks. If the quickbooks api says the sky is blue, you should double check just to make sure.
Comment by pjmlp 21 hours ago
Instead they deep dive into distributed systems, without ever learning about them and all the issues that can arise.
There is a reason many CS degrees have two semesters full of distributed systems content, between networking approaches, architecture design and algorithms to make everything robust.
Comment by tlonny 1 day ago
Thus I think webhooks still have a place - but as a simple "poke" that can be sent to the client to tell them something has changed - supplementing a default low frequency polling interval.
This gives us the best of both worlds:
1. No need to bother de-duping/retrying pokes - if you miss a webhook you will shortly recover anyway when you next poll. 2. No need for any local-specific tunnelling/tooling - the local app will work just fine with the default poll interval. 3. No need to keep a connection live for each client. 4. All the good stuff OP mentioned in his blog post.
Comment by AgentME 1 day ago
Comment by evolve-maz 1 day ago
On the flip side, it helps to have endpoints which have a query param linking to some sort of resource update time stamp. That way you can query to only get those items changed since last poll.
Comment by throwaway7783 1 day ago
Webhooks are fine, but a pollable API is a must have. The amount of hacks I had to do at work to workaround shitty APIs gives me nightmares.
Comment by bytesandbots 1 day ago
Problems listed are signatures, dedup, buffering, bootstrap, cron. Everything other than signatures and bootstrap, can be solved by having a counter in every webhook payload. It will increment each time. When you receive a webhook and the counter does not match, the consumer can fetch the missing data from the events API.
I agree with the author that providers simply saying "at least once delivery" is insufficient. they should have solutions that does not require an architecture diagram.
Bootstrap is better served with a bulk events API so you don't make one call per request. It can have an after/cursor pagination. Solutions that work for our internal Kafka might not be suited to work across services, over the internet.
Comment by oasisbob 1 day ago
An open connection is just a bit of state on either end. The C10K problem has been solved for ages.
Anyone remember consuming Twitter hoses back in the day? Those were also long-lived persistent connections for efficiency reasons.
Comment by weli 1 day ago
Comment by shreygupta 1 day ago
Tried to talk about this on X until the CEO of WorkOS wanted to bring it in private, then proceeded not to help at all. https://x.com/grinich/status/1913035839866835297?s=20
Comment by tasn 1 day ago
These weaknesses are why we[1] added FIFO endpoints, Polling Endpoints, and what we call "Svix Stream" as ways to do ordered state synchronization (each with its own tradeoffs). This lets people consume the events in the way that best fits their use-case. We are working on more things to make the state sync even easier. I'd love to hear about more challenges people are facing with webhooks, as we want to make these things better.
OP: I'd love to hear more about your thoughts there, and will send you an email in a moment.
P.S, if you're unfamiliar, please check out Standard Webhooks[2]. It's a spec we created to help with signature verification that has been adopted by OpenAI, Anthropic, Google, and many others. We are chipping at one webhook challenge at a time. :)
1: I'm the founder of Svix (mentioned in the post), we do webhooks infrastructure as a service.
Comment by NortySpock 5 hours ago
So you have to
(a) repeatedly query incremental date ranges, with some overlap (b) deal with late arriving rows
(c) deal with occasional bugs where a bug in a sproc caused the timestamp not to update
(d) query each day for all primary keys and remove rows that had been deleted (but only if you have newer data, otherwise you delete old values but don't have the updates)
(e) Sweat about if this goes wrong on a large table, how can you rapidly determine what state is out of sync? (Idea: how do I "hash" this in a way that hints at where the problem is?)
(f) Deduplicate, as mentioned
Martin Kleppmann's "Designing Data-Intensive Applications" book has some detailed discussions of some of the challenges...
Comment by zrail 1 day ago
Comment by weli 1 day ago
Comment by seandoe 1 day ago
> Nobody serves this today. That’s the catch, and it’s also the point.
and I was left wondering what was missing.
Comment by zffr 1 day ago
With SCROLL, consumers are responsible for choosing when to ask a provider for updates. Without a mechanism for knowing when data has changed, consumers will be forced to be pessimistic and poll providers for new data on some cadence.
I see two issues with the proposal: (1) SCROLL will lead to an increase in unnecessary network traffic for both the consumer and provider, and (2) because a consumer cannot know when data has changed, the lag between a consumer's local model and the provider's data model will be larger when with Webhooks.
Comment by lxgr 1 day ago
Comment by Multicomp 1 day ago
1. Long Poll the cursor to pull down the latest events
2. Trigger a long-poll even if in exponential backoff because they shot you a webhook saying 'eTag changed!'
Comment by inigyou 1 day ago
Comment by marklar423 15 hours ago
The solution my team eventually settled on to the dedup, buffering, and race problems was:
* When a webhook came in, store a single copy of the payload (usually json) in some temporary storage and enqueue the id.
* Any subsequent updates (while the id was enqueued) overwrote that payload and skipped the queue.
So, we were able to ensure we only updated the object once and with the latest state (since the webhook payload always held the entire object state).We didn't have a great solution for the bootstrap problem though.
I do like the SCROLL proposal, but I wonder about the cost of keeping around log-structured data forever - every log structured DB I know about does compactions for this reason.
Comment by weli 12 hours ago
Comment by ksymph 1 day ago
They go on about how we've settled in the trough, but the whole local optimum problem is about settling in an early peak, and being unwilling to cross a trough to get to a higher peak. The workarounds would be propping up the first peak, not evidence that we've settled in the trough.
Either way, the metaphor feels kinda forced IMO.
Comment by zie 1 day ago
* Database sync of log events. * "Real" time updates.
Webhooks can already mostly handle the "real-time" event portion. Of course there are problems. as the article expounds on, but a lot of those won't magically get solved with other solutions either. Distributed real-time communication is hard. Webhooks are good enough for this purpose.
For the database of log events, personally I'd rather just have a SQLite DB I can yank whenever. Don't give me CSV or JSON or whatever I have to parse and manage, just give me a SQLite DB ready to go. I'd love you for it. I'll just take a whole fresh copy with everything thanks. Maybe you limit it to to the last X events, say 90 days or 365 days or whatever, depending on sizing of events, but just send it all every time I fetch and I'm happy enough. If I need to generate a delta to keep some other DB in sync, well that's my problem. Just give every row a stable identifier.
Comment by bobtheborg 1 day ago
Comment by abrookewood 1 day ago
Comment by mrkeen 9 hours ago
Comment by Terr_ 1 day ago
One complication in this approach involves access-windows: What if my system is only supposed to be seeing stuff that happened during two separate weeks in the year, because those are the spans when it was subscribed or authorized?
So the data-host would need to maintain a concept of "connection history" for other services, and also use that to filter/modify its real event stream, inserting artificial "initial state" roll-ups of events that happened in dark periods.
Comment by zbentley 1 day ago
If that is a real requirement, it seems like it'd be easier to meet by giving customers a realtime-stream/log API whose history starts when they were most recently granted access, and providing them older historical events via a separate API of the classic "ask for a report and we'll get back to you within a day or two with an S3 presigned URL" variety, then synthesizing that huge historical report in batch code that's aware of the subtleties of the customer's visibility windows.
Comment by Terr_ 1 day ago
1. I have events in a Calendar service.
2. I want to authorize Reminder service to see upcoming events, so that it can send reminders to attendees in a way the Calendar service does not directly support, e.g. SMS/WhatsApp.
3. With the necessary credentials/SSO, the Reminder service subscribes to Calendar and Calendar periodically POSTSs webhook updates. Reminder needs to recognize when an event is cancelled or rescheduled, so that can alter its reminders.
Do I want to give Reminder potential access to all events ever, or just ones active across the usage period? Meanwhile, the Reminder guys probably don't want to step through the whole Calendar-wide event stream to reconstruct which events haven't finally happened yet.
Comment by gnat 23 hours ago
Comment by thingification 1 day ago
(I'm not serious about 1954 in particular, I am about hoping somebody here knows the CS literature better than me)
Comment by rawgabbit 1 day ago
When things change, you don’t immediately update the balance. Instead it is written to a transaction journal aka a log. The thing is this log is the source of truth. State or the balance is derived from the log.
You don’t send a continuous stream of logs. Instead it is batched and sent asynchronously. It is also applied asynchronously. It also records if the batch was successful or not.
If you have multiple systems sending their logs to a central server. No problem. The central server orders them all before applying the batches.
Every so often. The books are “closed”. Meaning the central server won’t accept any more journal entries for things that happened older than X dates.
Comment by zrail 1 day ago
It's always surprising to me how much of the real world runs on CSV and EDI files sent back and forth over SFTP.
Comment by qlkzy 1 day ago
Webhooks aren't at-least-once, nor at-most-once, nor are they guaranteed in-order. Some people build systems to make them more reliable, but if you really care about the data you need to think of a webhook delivery as best-effort, a bit like UDP.
That's before you get into all the extra complexities around these systems being owned by different people. For example, either or both system might have to roll back their database. Or either side might have a long-term bug in how they process webhooks, and now you have months of broken data.
My view is that the only reasonable thing is to start with the process that gets things back into sync if everything is broken. That almost certainly involves a poll or query of at least the upstream side, and maybe both sides.
I find that if you put a decent bit of engineering effort into that "disaster recovery" synchronisation, it can often act as the main or only synchronisation process for quite a lot of systems.
Stepping up from that, it's often useful to introduce webhooks as notifications only; that is, to provide a signal that some or all of the data is stale. You have to do a bit of consolidation, but this approach is usually enough to get completely reasonable latency for the kind of applications the author is describing.
Only if that wasn't enough for speed/scale reasons would I reach for a truly "push-driven" fast path. But you always have to be able to disaster recovery assuming the stream is wildly out of sync.
Some bits of the author's idea seem reasonable: certainly, I would love for there to be a standard protocol to request new data since some cursor or since some timestamp, ideally with some webhook notifications to give hints on when to poll.
The problem I have with the author's idea is that it is very strongly event-based, but the desired outcome isn't event-based. The desired outcome is almost always "the state over here looks like the state over there". Relying too strongly events ends up at the same kind of problem another level down: the "disaster recovery" script ends up wanting to compare the states anyway to figure out whether the events are broken.
Going fully event-sourced can work (although, I think, less often than advertised), but it really relies on everyone collectively agreeing on the same event stream being the source of truth. Once you start doing work across multiple organisations then that coordination is relatively rare.
What really surprises me is the variation in maturity on this topic. There seem to be people at all experience levels who are both doing this well and doing it badly. I have worked with people with decades of experience whose whole design just collapses if you ask "but what if X?" for some really banal values of X like "we have an outage for more than five minutes" or "we have to restore the DB to yesterday" or "someone, one time, accidentally merges a bug into master".
As an aside, I do find the obvious LLM-ness of the blog post and the proposal a bit disheartening. These are problems that require diligence and precision of thought. LLMs may be able to achieve those things, but that level of quality just isn't expressible in "Claudish".
Comment by SpaceNugget 1 day ago
Comment by jallmann 1 day ago
Another benefit is that you get to exercise those disaster recovery mechanisms regularly as part of the normal functioning of the system, rather than a specialized path that is only rarely exercised (and thus may be broken when you need it the most).
Comment by weli 1 day ago
Comment by MGriisser 1 day ago
"It’s a jigsaw puzzle where the manufacturer had the original picture, cut it up, mailed me the pieces one at a time, lost a few in the post, mailed some twice, and printed nothing on the box."
"and that’s the entire problem: nothing announces a gap."
"None of this is any provider’s bug. Their webhooks work exactly as documented. The problem is what a webhook is: a notification, “something happened, here’s a POST about it.”"
Almost this entire section is clearly written by an LLM
Comment by thingification 1 day ago
I didn't get that reading this (I didn't read the whole piece but I had read the parts you quote before reading your comment).
Often the LLM-beloved constructions are good usage in the right contexts.
Comment by qlkzy 1 day ago
But I wrote my commment after reading the article then the spec (https://welidev.github.io/scroll/), and so the spec was "top of mind".
The spec is just awash in LLM-isms. The cadence and rhetorical style are very Claudish. The visual style is basically "Claude's artifact plugin" (it may not be exactly that but it is an incredibly distinct signature). So the experience of reading the spec is very much an "AI slop" experience.
The reason I object to this is that the way these LLMs write is really well-tuned to gloss over small but critical details. And "small but critical details" are sort of the whole field of distributed systems.
This seems to be most true for Anthropic models (I am assuming there is some cultural defect in the way they give feedback), but it seems to be pretty universal, unless you give them some really strong stylistic anchor to a different style.
(As an aside, I sometimes wonder if this is part of the reason that LLMs seem from the outside to be succeeding disproportionately at mathematics: mathematics papers and mathematical notation may be a strong enough cultural force to override Anthropic's lack of taste and unlock the true power of the model).
I'm not saying there might not have been plenty of human guidance, but either way I don't think there's quite enough substance to this (based on everything I wrote in my comment) for this to feel like "a solution" either way.
Comment by nvme0n1p1 1 day ago
Comment by cobbzilla 1 day ago
The article presents a good framing and is well-written, but doesn’t really propose anything new.
Comment by cadamsdotcom 1 day ago
Comment by stymaar 1 day ago
Nah, it's almost pure slop with just the em-dashes edited away.
Comment by lubujackson 1 day ago
Comment by mrkeen 9 hours ago
All your problems start when you try to modify your current state representation in response to hearing the USER_ADDED or USER_BLOCKED events. Just don't. Leave them as events. Any time you have a new stupid edge case (double send, out-of-order, add-then-delete-then-add), this becomes one new unit test, where you can soberly decide what it means, and update your read path to understand it.
If you bake the nonsense into the current db state every time a new event arrives, your first step in any debug or reasoning scenario is to unbake it: what events led to this mess? If you don't throw away the events, your debugging is done for you.
Comment by nektro 1 day ago
Comment by jmaw 15 hours ago
Comment by sandeepkd 1 day ago
> 1. Trigger a side effect: send the receipt, start the build, ping the channel. > 2. Keep a copy of the provider’s data correct:
On high level
1. System can either be PUSH or PULL, webhooks are essentially push and towards the end the OP is exploring the possibility with PULL. The caveat is that OP already iterated the PUSH mechanisms thrice and is aware of all the hardships and is somehow hoping that PULL would solve them. Unfortunately the grass is same on other side too.
a) The availability of the server can always be questionable in PULL mechanisms and its a lot of load on servers to support this kind of data at scale in bulk to multiple customers. You are essentially getting into database table scans. Its becomes a lot more costly with NOSQL databases.
b) The customer would end up making way too many calls to server even if data is not available or there would be additional latency when data was updated and when it was queried. This is one of the reasons why servers prefer to push instead of pull if they can find a listener available on other side.
c) CRLs (Certificate revocation lists) are good example which are available for PULL, same for all clients and yet rarely anyone does it correctly or does it at all even though its in security domain. In fact they are simple files on webservers in most of the implementations.
2. The primary use case for Webhook is for triggering the side effect and allowing the customers to choose if they want to subscribe for that event. A customer subscribing for everything even if its non-actionable should just treat it as logging data.3. Logging data can and always have gaps, it should never be treated as source of truth. I might question the need for deduplication, usually there is a unique identifier and almost all databases support insert ignore kind of clause. Logging the event data just provides you with better availability and latency, the source of truth is still with the provider if a next step needs to happen.
4. If user cancelled the subscription in stripe and the event never arrived then its a system design issue or system availability issue on the client side. The complete data checksum or bulk imports at night are attempt to fix the problem in a hammerhead way . I understand it exists in lot of places, however it defeats the whole purpose.
Comment by Elucalidavah 1 day ago
If all events need to arrive, then the problem is not "notification" (which would be solved by webhooks) but "database replication": subscribe to new events, fetch the full snapshot, fetch the updates in range, have the monotonic value to establish the "range" in the first place. Reach the eventual consistency.
The proposed SCROLL handles half of these, which limits its use-cases.
Comment by foresterre 1 day ago
But there is no way (for a merchant) to get the latest 'true' state as held by Adyen. So you better hope your data is exactly in sync with the notifications you got from the webhook (which it never exactly is, because there are so so many points of failures, and unlike what this author says, the docs aren't thát well presented to hold the same model as the PSP does. It is often close enough though, but you are constantly gardening your implementation, because the model also changes on their end with little information in the changelogs).
The "latest state" data exists though! If you open the customer portal it is presented to you without problem.
Comment by WorldMaker 1 day ago
Comment by pphysch 1 day ago
Pull-oriented models are much easier to reason about and should be preferred where possible (cybernetically they are a closed loop, vs. push models which could literally just be a barrage of UDP packets). But they do have a little bit of overhead which makes them the wrong tool for some cases, like live-streamed entertainment or massive telemetry flows which value performance (latency, throughput) over missing a few packets.
Comment by ninju 1 day ago
How does the provider know what event the cursor you provided refers to?
Sounds like external state that needs to be managed ("cursor" -> timestamp)
Comment by weli 1 day ago
Comment by cyberax 1 day ago
Write your code to work as a "reconciler" that checks the state of the remote system and reconciles it with the local view of that system. Run reconciliation for the full state periodically using a scheduler, and then treat webhooks as a hint to run the reconciler immediately.
This way, you will have a robust system that can survive logical bugs and outages because you don't store the synchronization state per se.
In the case of Stripe, for example, have a process that polls every open checkout session every couple of minutes. A webhook then just triggers the run earlier. If you're worried about DDoS, have an exponential backoff for the poll period.
Theoretically polling doesn't scale, but in practice it works just fine.
Comment by delusional 1 day ago
The key, and only thing that matters, is that the cursor rides in your database, and is therefore transactionally consistent with the event. That's the whole magic trick.
We've done event streams like this at the bank I work at for years.
Comment by russellbeattie 1 day ago
Documenting unexpected or intermittent behavior: The easiest bug fixes of all.
Comment by stymaar 1 day ago
Comment by hungryhobbit 1 day ago
Comment by lobofta 1 day ago
Comment by zbentley 1 day ago
That aside, what I don't understand (especially having worked on the side of the webhook sender, which is itself really tricky to get correct/performant/cheap) is why more companies which broadcast webhooks don't, say, provide direct access to Kafka topics, S3 buckets with ordered data objects landing, SQS queues, or any of the alternatives to those things.
"But it's irresponsible to expose an internal-use-only datastore directly to clients" goes one objection. But plenty of log-store systems have the notion of sharing a subpart of the log with a less-than-trusted external peer, so while exposing Kafka directly might be asking for the same kind of trouble as exposing your customer's SQL database for authenticated connection over the open internet (e.g. "we said you could issue reads, not that you could open/close TCP connections a million times a second! You just took out our message broker!"), exposing, say, an S3 bucket or Kinesis stream is much less risky because those systems have put some thought towards semi-trusted sharing.
"But everyone is used to getting HTTP webhooks and doesn't have the expertise to connect to something else"--that'd be true if, say, reading from a websocket or Postgres NOTIFY stream or Kafka topic or S3-change-notification stream were advanced techniques, but libraries around those things are so good nowadays that even the most web-tech-only low-skill developer can probably integrate with them with minimal hassle. Maybe it's just that a lot of shops literally only know how to run their code in a webserver, and have never deployed any other kind of application service/cronjob/queue worker? That seems unlikely to me, but I might be surprised.
"If we do something weird our competition will beat us on ease-of-use" goes another objection. But is it that hard given the libraries available? And can't you hedge back on the ease-of-use sell with "our data is fresher and more provably ordered and correct"?
I'm glad that SCROLL exists as a possible solution here. I'm just puzzled why more people haven't been using existing technologies to achieve this property.
Do most webhook senders literally not have a log store? Are they just firing webhooks in the middle of business event handlers and giving up synchronously if they can't be delievered?
Because if that's not the case (and I don't think it's the case), then it seems like the SCROLL API is ... basically just the Kafka consumer API. Or Kinesis. Or SQS. And so on.
Comment by weli 1 day ago
I'm pretty sure you've hit the nail on the head. Especially now with LLM's you'd be surprised of how many people are running full on production apps that are coded solely by an agent, deployed with a mix of random providers (supabase + fly.io + whatever) and have no clue about what Kafka is. They are never going to ask for it because... they don't know they can, and why they should. They ask an agent "connect to stripe" and the agent codes your typical webhook ingestion mechanism, never proposes advocating for an event polling loop. Whenever there is a bug they will tell the agent to fix it and the agent will just write a webhook deduplication mechanism and that's it. You'd be surprised how little supposedly technical people care about the current state of technologies.
PS: Thanks for the feedback on the writing.
Comment by tasn 1 day ago
Comment by zbentley 1 day ago
Do you see receive-side customers as prepared to outright reject paying for vendors that only offer non-webhook event streams if there's a webhook-ful competitor available? Or is that preference more of the "well, it's easier to add a webhook route to our existing webapp than it is to run a stream consumer/cron/whatever, but neither of those two is cost- or effort-preventative" situation, where customers don't consider event delivery systems to be the main differentiating factor?
Comment by tasn 1 day ago
Though the data I do have: how many people adopt these advanced endpoints in practice (as we offer these), and it's less than webhooks.
Comment by zbentley 1 day ago
Comment by sicromoft 1 day ago
Comment by emmanueltsakpo 6 hours ago
Comment by aurumflux20 1 day ago
Comment by kzmttkc 1 day ago
Comment by ZenithBar 1 day ago
Comment by __MatrixMan__ 1 day ago
Comment by zbentley 1 day ago
If I offer my customers a source of ordered records, the "trust" in that system is the fact that they pay me to make sure records are ordered. If I sell a fast or slow log database, approximately zero customers in the world care to verify ordering cryptographically.
Or by "blockchain" do you just mean .... records with sequential IDs? Because sequential, guaranteed IDs surface gappiness/idempotency a lot easier than Markov chains over cryptographic primitives.
That also doesn't address the other core problems in the article: the replication (or data retrieval/polling) protocol is a lot more complex than a blockchain's "I can verify and replicate the entire chain state from the beginning of time to you" single behavior. People want more specificity than that.
Comment by __MatrixMan__ 1 day ago
> I do not trust the copy I built, and I have no way to know when it’s wrong, so I will re-derive it from scratch every night, forever.
Then guaranteed sequentiality means that they only have to verify each new block rather than fetch the whole thing every night.
Without it, you have this ever growing probability, which resets to 0 each night, that you unknowingly hold an invalid state. You might've acted on that state and so now when the nightly cleanup runs you have add code to go back out the consequences and instead apply the prosequences.
The complexity you think you're avoiding by not having a consensus protocol you're instead embracing as a data cleanup job, except instead of the same code everywhere, each reader has their own separate implementation.
That all goes away if you just don't process inbound data until you're sure nothing else is going to come along and invalidate it.
Sequential ID's work when there is only one writer and their implementation can be trusted but sometimes we get different events which both say they're number 12 and then we have to go call upstream and learn that so-and-so was on vacation and it won't happen again we promise. It takes days to resolve during which the potential of propagating bad state based on the lack of resolution continues to rise.
Ideally you can just avoid coordination delays entirely by keeping things monotonic and leaning on the CALM theorem but when that's not in the cards it's way better to put that delay on the writer's side, which is what blockchains do. Waiting for the consensus protocol to spit out a block before assuming that a write landed saves so many headaches on the reader side.
Comment by Xirdus 1 day ago
Comment by Terr_ 1 day ago
Especially since in most of the cases where it's not-totally-insane to use, the right solution is still the classic distributed database which already existed. In those, the ledger is kept among a predefined/controlled node-membership... as opposed to a bloated mass of workarounds and limitations to make it barely survive being ungovernable.
I've seen some boosters pivot to saying "private blockchain is good", but that's contradictory buzzword nonsense. It's like selling a blog as "single-user Twitter" or advertising a regular car as "user-controlled autonomous vehicle."
Comment by __MatrixMan__ 1 day ago
The craziness comes in when you'll accept blocks from anybody willing to burn enough electricity to do so, or gamble enough tokens to do so, or whatever other artificial scarcity game people like to play. But if you're only planning to consume data from the eight other companies you do business with then there's no reason to bother with any of that, you can just hard code their public keys into your consensus protocol and you've sidestepped the nonsense.
Comment by Xirdus 14 hours ago
Comment by __MatrixMan__ 1 day ago
> I do not trust the copy I built, and I have no way to know when it’s wrong, so I will re-derive it from scratch every night, forever.
Then your life would probably be better if you just had to consume block-at-a-time and not the whole dataset every night. Better to be persistently five minutes behind, then to go all day not knowing whether you're wrong, with a brief moment of certainty each night.
Your nightly reconciliation job just ends up being an inside out version of the consensus protocol that you failed to enforce up front (which may be a necessary evil if you have no influence over the people who publish your data, but let's not let those people off the hook for failing to support incremental verification of sync).
Comment by Xirdus 14 hours ago
> Then your life would probably be better if you just had to consume block-at-a-time and not the whole dataset every night.
Yes, exactly, that's the whole point of the article, the data should be an ordered stream, not asynchronous events. As long as it's an ordered stream, the author's life is peachy. Blockchain gives you an ordered stream, yes. But so does SCROLL. And if you choose SCROLL, you don't have to deal with the plethora of blockchain-specific problems.
Whenever you have a choice between SCROLL and a blockchain, you should always pick SCROLL and never a blockchain. Only if SCROLL won't work for your use case - for example, you actually need a consensus mechanism - you should consider a blockchain.
And no, blindly copying another database and overwriting every discrepancy with their version is NOT a consensus protocol! It's not meant to build a consensus! It's meant to copy data from authoritative source! There's no consensus to be had!