I just would like to give my opinion on some of your points, which I don't agree with:
> Looking at the documentation directly, what they advise you to do is kind of the worst idea they could come up with: https://stripe.com/docs/webhooks/signatures – you need custom logic[2] to verify that their MAC ("signature" they call it incorrectly) is valid and you need to configure a different secret for each of your endpoints
It certainly help that I use their official SDK, but it's one line of code to add the signature validation. Also, I'm not sure why you would want to create a lot of endpoints to listen to these webhook. I simply have one, and the Stripe SDK helps me in determine the event type, its deserialization, etc.
> Payment process information is such a vital business concern that "let's try to call them and if that fails... well we tried" is broken on principal alone
That's not how it works. The webhooks keep retrying with exponential backoff until they succeed. You can also manually retrigger them for individual events.
> The obvious approach is to have an event list which you as customer long-poll or just poll every few seconds if your framework doesn't support async well
Nothing is preventing you to do that. In fact, in my codebase I do polling to the Stripe API as a fallback to check if payment is successful in case there are issues with webhooks. But it's nice to have the webhook telling you immediately if a payment fails/succeed, in order to give feedback to the user fast about the status of his payment (and not wait the next long polling iteration)
Not everything on Stripe is perfect, but I do find it really pleasant to work with in general
While what you say is correct, it doesn't apply to the problem Troy Hunt faced. What he needs is DDOS protection on his API. The request authentication Stripe provides is too complicated to be checked by the web application firewall.
The (edit:) pragmatic approach is to
a) not use webhooks or
b) let Stripe connect to you via HTTPS (to prevent replay attacks and leakage of the secret URI), give Stripe a secret URI, whitelist the secret URI in the WAF and verify the payload MAC via the official SDK.
> in order to give feedback to the user fast about the status of his payment (and not wait the next long polling iteration)
Nitpick: The long poll / Server Sent Event should respond immediately once there is new data available, so it should not be slower than the webhook.
> b) let Stripe connect to you via HTTPS (to prevent replay attacks and leakage of the secret URI), give Stripe a secret URI, whitelist the secret URI in the WAF and verify the payload MAC via the official SDK.
IMHO the long term best architecture would be HTTPS client certificates / mutual TLS auth- you would just whitelist that only clients signed/approved by Stripe can connect to that Stripe-callback endpoint.
Maybe but the feasibility takes a huge dive, because you now need the application to terminate tls (or additional configuration for the route wherever TLS is terminated), plus a flow to rotate certificate.
Azure App Service provides an integrated optional auth wall for the apps deployed, without adding extra code. It may be a bit overkill to deploy a static site on the App Service, but it's supported. See here: https://learn.microsoft.com/en-us/azure/app-service/overview...
Here are the signs that I had during my burnout:
- Hoping to get sick to get a few days without having to cope with work
- Trouble sleeping
- Not being able to enjoy my holiday / weekend due to the thought of having to go back to work with an increased backlog
- Enhanced imposter syndrome
- Work productivity drop
- Complete lack of purpose in the daily work
All of the above built up very slowly and I didn't realize until things got overwhelming. The good news for me was that all of the above disappeared almost instantly when I switched jobs.
I've spent the last year working on an e-commerce project that esclusively uses websocket for real-time updates and communication. There are some great benefits to it, but websockets also introduce a lot of technical challenges that may not be obvious when you start. Things that come to mind are:
- Persistent connections make horizontal scaling more difficult
- Web Application Firewall don't usually support payload scanning for threats over websocket messages (eg. Cloudflare)
- If you need to integrate with third parties, you may end up needing a standard REST API anyway, since it's a lot less common to integrate via websockets (especially server-side). You then end up with two APIs. Also, websockets have less standard tooling for automatic documentation purposes such as Swagger/OpenAPI
- It's harder to load test the system, difficult to estimate the breaking point of the infrastructure via websockets
- HTTP Status Codes provide a standard error mechanism to HTTP server calls, while with websockets it's entirely up to you (which can be a good and bad thing)
- You need to manage explicitly situations where the connection drops and what to do when it recovers, as you may have lost some data in the meantime
- You give up a lot of standard mature tooling for caching and rate limiting
The need to support third parties is exactly why we ended up embarking on a phased deprecation of our websocket implementation.
As it turned out barely anybody wanted to learn how to open a websocket connection and relearn all the oddities of a bespoke websocket connection (error handling, etc.) whereas with REST all these things are just more or less standardized.
Using the Actor Model provided by Akka and an event sourced architecture does not fit very well with the request-response model of HTTP. Commands are usually issued in a fire-and-forget pattern, with resulting events being pushed to the client in a completely asynchronous way.
By using websockets via SignalR, we can better accomodate this pattern on the client code as well. On top of being a better fit with our backend architecture, it also provides some benefits in the frontend such as:
- Limited availability items disappear as soon as they actually are not available anymore, without the client having to refresh
- We can integrate more easily with payment gateways where payment confirmation usually arrives via a server side webhook. We can then easily push the "payment succeeeded" event to the client as soon as we receive it, without polling.
- Even the backoffice benefits from real-time, as all backoffice users are guaranteed that when they look up a customer/orders/products, they are looking at the most up-to-date information, even if somebody else edits the same record at the same time, or the record is updated by external APIs/scheduled job.
- We can provide easily real-time dashboboards that are listening to the feed of events being persisted
I can confirm that this happens in Italian as well. I've never visited the site before and my search placeholders in the top bar are just full of weird NSFW terms.
Weirdly, it only happens to the desktop site, if I access it via mobile I get mostly normal suggestions.
I don't know java, but that's not the message I got from the comment.
It looks like with java, 3 VMs with 2 cores are better than 6 VMs with 1 core, which may be forgotten when configuring equivalent kubernetes services.
> like stackoverflow.com, that punish people who don't accept all cookies by prompting on every visit
Well, not sure if that's fair. Until you accept at least the "strictly necessary" cookies, it makes sense that you get prompted the consent at every visit, since no cookies are saved.
it doesn't. there's no law against cookies, there's a law against tracking. you can perfectly well store the cookie banner consent choice in a cookie.
EDIT: the reality is that it should actually be a "can we track you?" consent box. sites using the word "cookie" instead of "tracking" in the consent banner/popup are using technobabble to confuse you into just clicking "ok". users are not supposed to understand what it means.
it hurts me deeply that even programmers, who do understand what cookies are, have seen these misleading cookie banners so often that they think that's what GDPR prescribes. it's not, it's a lie.
> it doesn't. there's no law against cookies, there's a law against tracking. you can perfectly well store the cookie banner consent choice in a cookie...they think that's what GDPR prescribes. it's not, it's a lie.
This is just wrong.
The Cookie Law (ePrivacy Directive of 2002 and 2009) is distinct from the GDPR. It really is a law against unconsented cookies: not just "tracking" ones but also anything that stores the user's preference: anything not "strictly necessary for the delivery of a service requested by the user".
That said, websites could certainly do a bit better here and give users a clear option of "I request a service delivered without the use of cookies, apart from the one necessary to remember this request".
This is just FUD. Storing the cookie consent in a cookie is obviously "strictly necessary" if that's all you do with the cookie. Strictly necessary cookies do not, themselves, require consent.
You're saying that without obtaining consent, you can't store the cookie consent preference which is a ridiculous catch 22 explicitly rejected by the first link you shared (which states that the consent choice must be stored)
I've now worked for about six months on a Akka.NET codebase.
I find it a very elegant high-performance framework that gives you a lot of flexibility in how you want to solve a wide range problems.
This being said, I've been burned already several times by the complexity and its raw power. The codebase tends to become verbose and difficult to navigate (everything being an ActorRef). Debugging is difficult and coding is challenging for junior engineers, as you said. I found it very unforgiving to mistakes, and it's easy to shoot yourself in the foot if you use the abstractions without knowing very well what's going on under the hood. Edge cases can be very tricky to manage.
I'm still very conflicted about it. One one side the services powered by Akka are quite stable and performant, but I'm not sure the complexity justifies the means.
> The Task Parallel Library (TPL) provides dataflow components to help increase the robustness of concurrency-enabled applications. These dataflow components are collectively referred to as the TPL Dataflow Library. This dataflow model promotes actor-based programming by providing in-process message passing for coarse-grained dataflow and pipelining tasks. The dataflow components build on the types and scheduling infrastructure of the TPL and integrate with the C#, Visual Basic, and F# language support for asynchronous programming.
I'm glad to hear that somebody's using it in the wild. It was rejected at my place of work in favour of a BPMN-driven process engine. The thinking was that it's too difficult otherwise for business-people to understand the process.
> Looking at the documentation directly, what they advise you to do is kind of the worst idea they could come up with: https://stripe.com/docs/webhooks/signatures – you need custom logic[2] to verify that their MAC ("signature" they call it incorrectly) is valid and you need to configure a different secret for each of your endpoints
It certainly help that I use their official SDK, but it's one line of code to add the signature validation. Also, I'm not sure why you would want to create a lot of endpoints to listen to these webhook. I simply have one, and the Stripe SDK helps me in determine the event type, its deserialization, etc.
> Payment process information is such a vital business concern that "let's try to call them and if that fails... well we tried" is broken on principal alone
That's not how it works. The webhooks keep retrying with exponential backoff until they succeed. You can also manually retrigger them for individual events.
> The obvious approach is to have an event list which you as customer long-poll or just poll every few seconds if your framework doesn't support async well
Nothing is preventing you to do that. In fact, in my codebase I do polling to the Stripe API as a fallback to check if payment is successful in case there are issues with webhooks. But it's nice to have the webhook telling you immediately if a payment fails/succeed, in order to give feedback to the user fast about the status of his payment (and not wait the next long polling iteration)
Not everything on Stripe is perfect, but I do find it really pleasant to work with in general