Don't fear the furry. Embrace your inner 6ft anthropomorphic wolf thing, its not going to kill you. (well not unless you get heat stroke, furries die in hot convention centres people. )
I'm going to have to spoil some of it to point out that part of what he's done is reinventing the idea of delay-line memory, although he makes no mention of this: https://en.wikipedia.org/wiki/Delay-line_memory
...of course if that's all there were to it it wouldn't be interesting, but I won't reveal what the rest is as per your suggestions. :)
my dear child, the fun is not the destination, the fun is the slow decent into madness to get there. For other people: don't read the summary, read the whole thing. its a work of art.
Find someone who reads this and goes "i want to learn what all those words meant." The explain could be done amusingly too, i think.
dunno if the effort would be worth it; but I'm thinking of people like me who read th eBOFH stories and decided they needed to learn more, to understand them properly. "First hit free, kids!"
I'm not part of this subculture, but I honesty enjoy this type of idonsyncratic presentation which always was, and hopefully always will be part of hacker culture.
The content is not only relevant and hilarious, but I'd much rather personal blogs like this keep being updated instead of seeing the the sterile Medium or LinkedIn Pulse versions, usually written to impress future employers.
Zany visuals, doing things with your friends just because you can and writing up detailed accounts of it to share with everyone is the quintessential hacker culture. If Hackers' Cyberdelia was set in the 2020s, no doubt Mara would fit in.
Author here. Thank you for liking this. One of the most amusing things is that doing this zany visuals/detailed writeups/unabashed character in my writing actually makes me more impressive to future employers than any sterile LinkedIn posts ever will. I estimate that at this point if I wanted to get hired I could literally post a banger like this, add a banner to it halfway in that says "by the way, I'm looking for gainful employment, if you want someone doing DevRel that writes like this and gives talks like [link], please get in contact" and I could probably get a job in a week or two.
I want to keep hacker culture alive by not accepting the gentrification of it. Hacker culture is queer, neurodiverse, furry, weaboo, and more. As a philosopher of the arts, that is the kind of culture I want to create more of. Not platitudes on LinkedIn. I want to create the kind of culture that celebrates art for the sake of art.
I’m sorry to hear that you felt offended by the cartoon shark in the article about programming. I understand that you may have different preferences and expectations for the content you consume. However, I hope you can also respect my creative choices and freedom of expression. I am not obligated to cater to your personal tastes or opinions, especially when I am providing my content to the world for free. I appreciate your feedback, but I also ask you to be more considerate and respectful of other readers who may enjoy my work. Thank you.
I would ask you to perform self-reflection to ascertain as to why the cartoon shark discomforts you. You may want to sit with that discomfort to understand why you feel that way so you can hopefully move past that and towards a more peaceful future.
There are a number of logical fallacies being presented in your assertions, however I don't feel like I need to spend the time to pick them apart.
sneak wanted OP to be less openly queer in their personal blog for their own comfort, due to their own inability to imagine that the subculture OP is part of is more than their own narrow definition of it.
I guess the disrespect is clearer when one has grown up with its many forms, but assuming your request for more context comes out of a sincere desire to increase your understanding, I hope this helped.
> assuming your request for more context comes out of a sincere desire to increase your understanding, I hope this helped.
I appreciate the benefit of the doubt -- I was trying to approach it with the assumption that there's probably some perspective that I wasn't aware of.
> sneak wanted OP to be less openly queer in their personal blog for their own comfort
I can see how it may be interpreted that way. To me it read more like "hey, great content, presentation of it wasn't for me" in a way to convey feedback in the event the author wanted to better capture their attention. I didn't get the sense that there was an expectation that the author change their writing style to accommodate their preferences.
re-reading this, I don't think I appreciated that it was really in defense of the readers rather than the content
> I also ask you to be more considerate and respectful of other readers who may enjoy my work
I'm surmising that the real problem statement is:
> I'm sure there are non-sexual furries but the subculture is primarily a sexual one (same as with BDSM)
which I can appreciate as a generalization, I suppose I wouldn't have personally considered furries as under the queer umbrella, but I'm certainly no voice of authority on the matter. I suppose there's also the possibility that 'furries' was a dog whistle for 'queer', and being less charitable to sneak, I could better understand finding disrespect in the post.
So queer the fandom got booted out of the anime cons it spawned out of for being so. Unchained from the narrow views of the anime community, our power only grew.
> sneak wanted OP to be less openly queer in their personal blog for their own comfort, due to their own inability to imagine that the subculture OP is part of is more than their own narrow definition of it.
This is entirely false.
soft_dev_person, what I do want is for you to constrain your assertions about me to facts, and refrain from inaccurate or baseless speculation. It does neither you nor I any favors.
I understand that is what you want, but you cannot reserve yourself from being interpreted when posting on a public forum.
The language you chose to use and the details you chose to focus on is what triggered the response. If your point was that the cartoons was distracting, you could have made that clear in a less disrespectful way (or let the content speak for itself), or perhaps consider if it was worth contributing to the discussion.
Again, you double down on one definition of this particular subculture in another reply. It is reminiscent of how others have tried to define what certain subcultures related to sexual orientation (some now more mainstream) entail, while not being part of them, and I hope you understand how this can be problematic. I appreciate that this may not have been your intention.
Only if you make it. Relax. What someone is wearing or what innocent pictures they put alongside their presentation does not necessarily have to concern you at all. Just ignore it and focus on the actual subject matter.
The only thing worse would be this “on the blockchain.”
On second thought it seems likely that some charlatan has already years ago raised a couple of millions in an ICO for such a project. “We’re making the entire Internet web3-compatible!”
Yes, it's actually somewhat of a decent (if cursed) message queue for many usecases too. Not to mention the debuggability (you already know how to use an email client).
As long as you keep it internal-only, get a reliable server that doesn't do any anti-spam shit (AKA, nothing from MS or any other large company), doesn't use some unreliable proprietary database (again no MS), and have a reliable journaled disk, your only important failure mode will be losing disks. That's an easy failure mode to deal with.
I love email, and to me it is a very important part of our infrastructure, but it is quite cursed as an arbitrary transport. The semantics are very complex, and any transported data will generally need to be encoded as base64, which is very inefficient.
You also need to add misbehaving clients on your list of things not to use with a message-queue, just opening the queue's folder on Outlook to inspect it may be enough to completely corrupt it (Outlook will happily reorder, even rewrite, header fields of incoming messages, replicate messages to infinity, or who knows what else).
I'd be worried to have a message queue that is compatible with such a cursed ecosystem and transport protocol.
I co-founded a webmail provider in '99, and when we needed a message queue reaching for our heavily customized Qmail setup was a relatively natural choice. I've mentioned it here before. Provides all the routing and retries we needed, and made debugging trivial (e-mail from our desktop clients to the queues worked; cc:'ing a real mailbox with copies worked; checking out queues with POP3 worked...)
I always thought using e-mail in this would be good for systems that occasionally need a human in the loop. Normally one service processes and mails results to the next, occasionally something is forwarded to a human, who can make some decision, edit the mail, then forward it along back into the automated path.
Before there was REST and other http based standards ebXML was a hotness and tools like bizspark etc. You could see the logical progression through:
I fill in the order form and post it. They mail back an invoice.
I fax the order form, they fax back an invoice.
My computer sends the order form in a structured way over email.
My computer sends the order form in a structured way over http.
And that's why many large telcos and banks still use ebXML in their B2B transactions. It's fundamentally the same business process and logic it's always been, with glacially slow improvement in performance over time.
One of my customers used email (a gmail account, no less) as a message queue between their front end site and the back-office processor. This worked quite well for close to a decade I think.
It basically evolved from when applications from their original customer facing site were emailed and manually entered into the back-office system by a human. They were looking to automate this with a minimum of changes to too many of the moving parts at once, so I reformatted the sent email to contain an XML payload so the new back-office automation could read and process it (and in a pinch, a human could still review any problem applications) using Java's mail APIs.
Things evolved, the front-end web site got replaced with a Wordpress site, but the email message queue kept working for a long time. In the last year or so it was getting more and more onerous though. Reconciling information between the front-end and the mail box showed not all emails were being delivered, and authentication to gmail was becoming more and more of a burdensome moving target.
I just recently replaced the whole thing with an API call made from the back-office to the Wordpress site to access the stored data. (The original site didn't store, just emailed, which was why this was not an option historically.)
Also, you can actually make it cost competitive if the object you store is the last n milliseconds of packets instead of one packet each. So, instead of incurring two API calls per packet, you incur two API calls per minimum buffering time. If S3 is zero-rated for any ingress/egress then you get “infinite” bandwidth for 4.22$ * 3 (for the active case) = 12.66$ a day if you are willing to accept 500 ms minimum latency, or ~600$ a day at a more reasonable 10 ms. If you are saturating even just a 1 Gb link for a whole day that is ~10,000 GB which would be ~700$ via the blessed channel, so you could very well come out ahead.
You could do even better if you out-of-band signal the readiness so you do not need to poll while idle. Then you only incur a cost while actively transmitting so as long as you average 1 Gb/s on the channel you should be coming out even or ahead with minimal latency impact.
This isn't theoretical; many companies do PostgreSQL async 1:N physical replication, by using e.g. https://pgbackrest.org/ to have the primary push WAL segment files (a.k.a. "the last n milliseconds of packets" in the write-ahead log) as objects to S3. All the read-replicas then independently discover the new objects in S3 as they become available; fetch them; and replay them.
> You could do even better if you out-of-band signal the readiness so you do not need to poll while idle.
S3 and its clones have "object lifecycle notifications", where you can be informed by a push-based mechanism whenever a new object is put into the bucket.
But — what do you have to do, to get these notifications?
Subscribe to a real message queue, that S3 puts these notifications into.
Not really, but you can use Patroni for that, which automatically promote one of your replica to master, it can also create the replica from WAL archive in S3 using wal-g/pgbackrest.
This is astoundingly well-written and informative. It's the sort of thing I come here for. It's also engaging and charming in a way rarely seen in tech writing.
I like that they started out by talking about $0.07/G cost and went through the whole exercise before pointing out what immediately came to mind for me when they started pushing bytes in and out of S3.
> <Cadey> Hello! Thank you for visiting my website. You seem to be using an ad-blocker. I understand why you do this, but I'd really appreciate if it you would turn it off for my website. These ads help pay for running the website and are done by Ethical Ads. I do not receive detailed analytics on the ads and from what I understand neither does Ethical Ads. If you don't want to disable your ad blocker, please consider donating [snip] or sending some extra cash to [snip] or [snip]. It helps fund the website's hosting bills and pay for the expensive technical editor that I use for my longer articles. Thanks and be well!
I once used a MySQL database as a replacement for a message queue. This was the easiest solution to implement since all the servers were already connected to the database anyways. A server would write a new row to the table and all the servers would remember the last row they had already seen. Occasionally the table is cleared. I'm sure there are some race conditions in the system but its only purpose is to send Discord notifications when someone breaks a highscore in a video game, so its not really critical. It's still working that way today.
> We decided to store Centrifuge data inside Amazon’s RDS instances running on MySQL. RDS gives us managed datastores, and MySQL provides us with the ability to re-order our jobs.
I am doing the same with SQL Server. The messages table is more of a bus than a queue in our case (columns like ReplyToId, etc). Using it for RPC communication between cloud bits. Much cheaper than Azure Service Bus and friends.
I don’t know the OPs answer, but I’d hazard to guess because ssmb is a completely neglected feature with very little in the way of community or UI. In theory it would be great, but MS basically never invested in it after its release and now it’s just a random, “who knows when we’ll drop support for this” sql server feature.
This is actually pretty common, and usually a "good enough" solution. You can also add things like scheduling (add a run_at column), at least once execution (mark a row when it is being processed, delete it only when successful), topics, etc with minor modifications to your table.
If you want something that works "well enough" I'd say it's a reasonable choice.
Yeah, I'm using it as a transactional outbox to ensure at least once delivery to SNS.
Can't really think of a better way to ensure that a message is always sent if the DB transactions succeeds and is never sent if the DB transaction fails
You can get so far by ensuring at least once and making everything idempotent (will get you as close to "exactly once" as you can). With a database, the most common pattern is: insert the row for the job, when a worker starts working on it, mark it as in progress so it doesn't get started again, if the task fails, or after some reasonable time-out period, another worker can pick up the task again, ultimately the row for the task is only ever deleted when a worker successfully completes it.
The code is in there for Postgres, MS SQL and MySQL (which all support SKIP LOCKED) though at some point I abandoned all but Postgres.
If I was to write another message queue then I wouldn’t use a database, I’d use the file system based around Linux file moves, which are atomic. What I really want is a message queue that is fast and requires zero config, file based message queues are both…. better than a database.
Interesting. What makes you want to switch to the file system? I wrote one for a project[0] a while back (for MongoDB) and it didn't seem like the database introduced too much complexity. I didn't write the implementation from scratch, but the couple hundred lines of code were easy to reason about.
I found almost all message queues to be horribly complex to configure, debug and run. Even database queues require a lot of config, relative to using the file system.
I did actually write a file system based message queue in Rust and it instantly maxed out the disk at about 30,000 messages a second. It did about 7 million messages a second when run as a purely RAM message queue but that didn’t use file system at all.
It depends what you’re doing of course… running a bank on a file system queue wouldn’t make sense.
A fast message queue should be a tiny executable that you run and you’re in business in seconds, no faffing around with even a minute of config.
> I did actually write a file system based message queue in Rust and it instantly maxed out the disk at about 30,000 messages a second. It did about 7 million messages a second when run as a purely RAM message queue but that didn’t use file system at all.
Did you try an in-memory filesystem through tmpfs?
Database config should be two connection strings, 1 for the admin user that creates the tables and anther for the queue user. Everything else should be stored in the database itself. Each queue should be in its own set of tables. Large blobs may or may not be referenced to an external file.
Shouldn't a message send be worst case a CAS. It really seems like all the work around garbage collection would have some use for in-memory high speed queues.
Are you familiar with the LMAX Disruptor? Is is a Java based cross thread messaging library used for day trading applications.
I really feel like file systems aren't used for enough things. File systems come with so much useful metadata.
I've experimented with using the file system for storing configuration data where each config value is a single file. Nested structures just use directories. The name of the file is the field name. The file extension is a hint about the data type contained within (.txt is obvious, but I also liked .bool). Parsing data is trivial. I don't need any special viewing or editing tools, just a file manager and text editor. You can see when a specific config value was changed by checking the file update time. You don't have to load the whole configuration just to access one field. And you could conceivably TAR up the whole thing if you wanted to transmit it somewhere.
I use it to configure little sub-projects in my personal website. I really like it, but I shudder to think of the complaining I'd hear from other developers if I ever used it in a work project, just because it's not whatever they've ever seen before and would require a moment of two of thinking on their behalf to get over ingrained habits.
It's a single byte file. You read the entire file contents and if it's not zero, it's true. The existence of the file tells you whether or not to use a default value. An INI file would have to be fully parsed before we know whether it contains a value for that config value.
You read the entire file contents, trim leading and trailing whitespace and toLower for good measure if you want, then validate against your list of installed themes. Done. No goofy JSON or YAML parser in site.
And what reinvention is there? If you're just using a system that already exists, you're not reinventing anything.
A company I used to work for extensively used this method. It's incredibly useful to be able to read a config or state value from any language and even bash scripts quickly.
However, and this is a big drawback, once you have too many config files and you start reading and writing from different processes, you get into bottleneck situations quickly.
I haven't used this system extensively yet. But I don't really see how that situation gets improved by having a single-file configuration system.
First of all, if you have multiple processes trying to read/write the same config, that's kind of suspect, and if file I/O is a bottleneck for your config system, that's a different suspicious situation. Why are your processes writing to the config so... often?
But regardless, I can't see how those problems get immediately better by storing that config in a single file. If anything, having it split across multiple files would improve the situation, as different processes that might only be concerned with different sections of the config won't need to wait on file locks from process unrelated to their concerns.
I realize it may have sounded like I was suggesting the approach. Quite the contrary: I would never do that again or suggest it. I was merely pointing out that it was quite useful at times :-) We had lots of problems similar to what you were describing. Luckily that's all in the past now.
This was tried and called Elektra I think around Y2K. Don’t believe the idea was even new then, but there was also research into tiny file performance at the time, resulting in things like reiserfs. I think it packed tiny files into the directory itself resulting in blistering speed.
Anyway it’s an elegant idea. Silly to have dozens of config file formats when the fs already has everything it needs. We have xattr too.
The flaw on the OS level is that it is hard to get everyone to change. For new apps not a problem, and any performance concerns are no longer an issue for config.
Oh man, reiserfs. Seeing that name reminds me that the original developer, Hans Reiser, is currently spending time in prison for murdering his wife. She was the interpreter during his first meeting with a Russian "mail-order bride".
The paradigm is also used by /proc and /sys, so I guess other developers won't get confused. However I never tried to tar -x into /proc to start the same set of processes on another node, or as an alternative to /etc/sysctl.conf :)
I actually did this once (over SMB on Windows, though) - and unintentionally crippled our corporate SAN with all of its polling and locking activity. I had a cluster of 20 workers which would poll every five seconds for messages, and I believe we had an EMC VNX storage appliance. I never did figure out why that was enough to bring the whole thing to its knees, but IT was very quick to track the problem back to me.
Since you seem to be from citusdata: I used cstore_fdw 2 - 3 years back and at least when paired with TPC-H it was horrendously broken for both small (10 gig) and large (100 gig) datasets. It has been integrated into some other product by the time being, I hope you managed to improve it.
I briefly worked for a major corporation 15 years ago that did this with SQL Server to create distributed worker processes to handle all the AI-generated used car listings and photo recolorings [0] for almost all of the used car lots in the country.
[0] Why take hundreds of photos of Honda Civics in red, green, blue, and black when you already have a dozen in white?
Why even take the dozen in white when they have a model you can render in any manner? Most car commercials do not have real cars in them. Maybe the shots of a car actually in motion, but most of the static shots are 3D models placed onto backgrounds. I don't know why, but I was surprised by this when I worked in a post house that did a lot of car commercials. One of the roles for a coworker was to get flown around to locations to take the images for the background plates using photogrammetry. "Can't fly an Alexa through the back glass to zoom in on the dash now can we" was one comment.
I’ve run into all sorts of database locking issues and concurrency issues when using a database as a queue. I saw that mistake made a long time ago and I would never do it myself.
Database engines are getting features like SELECT FOR UPDATE SKIP LOCKED, so what were once serious blockers on this idea may no longer be as much of a problem.
No? Unless there's some edge case with that statement I don't know about. That statement is basically tailor made for queues so you can select jobs that aren't currently being worked on by other workers.
Inasmuch as you trust your db's locking correctness it eliminates the concurrency issues. You can very naively have n workers pulling jobs from a queue not stepping on each-other.
It’s not necessary, but it is a lot less fiddly: you automatically look at only the tasks that someone else isn’t currently working on, and because the lock is held by the database connection you get automatic retries if your worker crashes and drops the connection. You could figure out all of the interactions needed to make this work yourself, but if the database already has support built in you may as well use it (and there’s a straightforward path to migrate if you need more sophistication later).
This has been a thing since before databases were relational. 4G languages (Progress, etc.) were especially nice for their ability to wrap a queue table around a series of reversible transactions, if you coded things right .. meaning a lot of modules written for app infrastructure were based on an 'inbox table' methodology ..
I've built a hybrid task queue/process supervisor on top of SQL. Classical task queues like Celery didn't exactly fit our use case: a single process could run for hours or days, but in case of a node failing, it must be resurrected elsewhere as soon as possible (within seconds). I didn't have the time to re-architect everything for Kubernetes, or rewrite half the product in Erlang; so I built that weird thing. It's been super stable, running mission critical code, and making us money - for several years now.
It’s not so out of the ordinary. A few libraries in Rails create message queues in Postgres using advisory locks and listen/notify.
Hell, if it’s not an RDBMS then it’ll be Redis (at a much greater expense for a managed instance). I’ve seen that setup in the Ruby world far more often than using a dedicated message queue.
I implemented a message queue in MySQL too and it worked pretty well. Incoming messages would be written to the table and the workers would poll the database each cron period and process whatever rows were in the queue. To avoid race conditions, the workers would lock the records they were working on and then delete them as soon as the work was complete. It was simple but it worked just fine for my purposes
If you don't want to publish events from uncommitted transactions you'll have to first store them in a local table and then move them to the queue after the commit. But if all consumers have direct access to the database anyway...
As a junior dev I used folder pairs (to_process and processed) as a way to move messages between loosely coupled systems with file system watchers picking up new files in the to_process folder. Very light weight, got the job done, and was told it was in production for over a decade (even after better best practices came into use).
Literally spooling message-filled tape onto a tape reel! I never even thought about that.
On the topic of message queues, I wonder if anyone ever designed a mechanical, asynchronous hardware IPC mechanism based on tape. Imagine: an endless-loop tape that stretches between a "sender" tape-drive on one machine, and a "receiver" tape-drive on another machine; with each tape drive locally tensioning the tape as it passes through, but letting it hang slack outside the drive; with two tape-width buffer boxes in between the two drives, for taking up the slack; and where each tape-drive has a strain gauge on its input-end capstan.
With this design, you'd never need to seek the tape (backward, at least) — the receive head would just read the tape forward at whatever speed it could until it ran out of slack in the tape (i.e. blocked on read); and the send head would write the tape forward at whatever speed it could until it ran out of slack (i.e. blocked on write.) The tape itself would be a literal, physical ring buffer.
Western Union built a store-and-forward message switching system in pretty much exactly the way you describe (but with paper tape rather than magnetic): https://en.wikipedia.org/wiki/Plan_55-A
Analog audio delay/echo machines work like this. They could have multiple read heads and you could move them relative to each other and adjust the speed of the tape to get various cool effects.
So having "discovered" this approach as a young .NET dev retroactively gives me a smug smile that I came up with such a battle-tested pattern. Then again, it's also quite an obvious and simple pattern which is why it was used in the first place, I'm sure.
Sometimes a filesystem-based queue like that is all you really need. Recently I used S3 API compatible storage for something similar, as introducing AMQP or pubsub would have been immensely overkill for this low volume component.
This is a very sensible design for small-scale queueing systems. A few implementation notes I’ve learned along the way:
- You’ll want writers to create a temp file and then rename it into place; otherwise your reader might pick up a file that’s only half-written. (POSIX rename() is atomic within a filesystem.)
- It’s also helpful to have an `in_process` folder, and a cronjob to send alerts if a task sits in that place too long. That way you can quickly catch crashes and other failures.
- You can have multiple readers; they cooperate by rename()ing the input file into in_process/ before they start working on it, and ignoring ENOENT (which indicates some other process got to it first).
- This pattern is great for loosely-coupled systems. In my case I was importing orders into a system that ran very slowly; once a reliable import queue was available new use cases kept presenting themselves, and it was very easy to add them; since the API was just “write a file in the correct format”, individual scripts could be written in whatever way was easiest for the particular task at hand. (It helped that the input format hadn’t changed in a couple decades; if it had needed changing a lot you’d want a more structured system. But this is the same as any distributed systems interface design.)
With respect to how to move things into folders, the simplest advice is to tell people to just read the Maildir spec. And read Qmail as well. While Qmail is dated as a mailsystem, as a description of how to compose a decoupled system that reliably processes filesystem based queues, it contains lots of little nuggets.
3 years ago, I extensively used the all-company's shared filesystem to pass information between 2 independent Jenkins instances (One on Windows for jobs that worked best under a Windows machine and one on Redhat which was considered as the "main" instance); and between the Jenkins and target application servers (Windows and Redhat) which all had the company's filesystem mounted. It took time to perfect, but worked wonderfully once I adopted the rename-in-place technique as described by parent.
I wonder if the system is still in place. Last time I checked the Jenkins folder was occupying 270 GB (!) of the 10 TB shared FS, most likely because FS block size was 1 MB.
At my old company, we had a system where we had a limited number of physical machines that multiple testers would need to remote into. We didn't want to disallow two people logging in simultaneously because sometimes that was necessary, and if someone stayed logged in then wen to lunch, where was no way to kick them off to get access without waling to the server closet, pulling up the machine on the KVM, and kicking them that way.
I wrote some VBScript that wrote a locking folder into a sub-folder in a network folder, then launched VNC targeting the proper VM. When VNC was closed, the script would complete and delete the locking folder. That let us know what was available and when. I always thought it was hacky, but at ~60 lines it's incredibly simple and has never really failed.
> In Linux, you can create a TUN/TAP device to let applications control how network or datagram links work. In essence, it lets you create a file descriptor that you can read packets from and write packets to. As long as you get the packets to their intended destination somehow and get any other packets that come back to the same file descriptor, the implementation isn't relevant. This is how OpenVPN, ZeroTier, FreeLAN, Tinc, Hamachi, WireGuard and Tailscale work: they read packets from the kernel, encrypt them, send them to the destination, decrypt incoming packets, and then write them back into the kernel.
This is one of those articles where the journey is far more interesting than the destination.
(Edit: this comment made more sense when it was replying to a different complaint about the article; the parent comment seems to have been edited in the interim.)
So the premise of the problem is the need to egress traffic to the internet from a private VPC, without using an expensive NAT gateway. The solution is to do NAT manually by having an EC2 instance in a public VPC, and tunneling traffic from the private VPC through that instance.
The meat of the article is how to create that tunnel using S3 for data transfer instead of using a more traditional VPN service.
> The bytes are stored in the cloud, which is slightly slower to read from than it would be to read data out of the heap.
Given latency and bandwidth differences, that's like saying that it's slightly slower to transport water by driving standard, 1-gallon jugs between the US east and west coasts than it is to transport it a few miles using a tanker truck.
261 comments
[ 3.0 ms ] story [ 306 ms ] threadSomeone submit it as "IPv8" immediately.
IPv4?
But seriously, I appreciate that the blog was written using IPv6, not some other old and deprecated legacy tech.
https://floccinaucinihilipilificationa.tumblr.com/post/96040...
The Cardio rate control library is cool, https://pkg.go.dev/within.website/x/cardio this library would be a great problem for using a neural net to model a PID loop.
https://www.semanticscholar.org/paper/A-Design-of-FPGA-Based...
https://www.semanticscholar.org/paper/Self-Tuning-Neural-Net...
https://youtube.com/watch?v=JcJSW7Rprio
It's better to go in unspoiled so I won't reveal any details.
...of course if that's all there were to it it wouldn't be interesting, but I won't reveal what the rest is as per your suggestions. :)
Not that it ain't perfect like it is.
dunno if the effort would be worth it; but I'm thinking of people like me who read th eBOFH stories and decided they needed to learn more, to understand them properly. "First hit free, kids!"
The content is not only relevant and hilarious, but I'd much rather personal blogs like this keep being updated instead of seeing the the sterile Medium or LinkedIn Pulse versions, usually written to impress future employers.
Zany visuals, doing things with your friends just because you can and writing up detailed accounts of it to share with everyone is the quintessential hacker culture. If Hackers' Cyberdelia was set in the 2020s, no doubt Mara would fit in.
I want to keep hacker culture alive by not accepting the gentrification of it. Hacker culture is queer, neurodiverse, furry, weaboo, and more. As a philosopher of the arts, that is the kind of culture I want to create more of. Not platitudes on LinkedIn. I want to create the kind of culture that celebrates art for the sake of art.
I may be "cringe", but I am free.
I would ask you to perform self-reflection to ascertain as to why the cartoon shark discomforts you. You may want to sit with that discomfort to understand why you feel that way so you can hopefully move past that and towards a more peaceful future.
There are a number of logical fallacies being presented in your assertions, however I don't feel like I need to spend the time to pick them apart.
Be well,
I don't believe OP asserted anything to the contrary, could you highlight where you inferred that?
> I appreciate your feedback, but I also ask you to be more considerate and respectful of other readers who may enjoy my work.
It would be helpful if you would be willing to expand on how you found the OPs statements disrespectful or inconsiderate.
I guess the disrespect is clearer when one has grown up with its many forms, but assuming your request for more context comes out of a sincere desire to increase your understanding, I hope this helped.
I appreciate the benefit of the doubt -- I was trying to approach it with the assumption that there's probably some perspective that I wasn't aware of.
> sneak wanted OP to be less openly queer in their personal blog for their own comfort
I can see how it may be interpreted that way. To me it read more like "hey, great content, presentation of it wasn't for me" in a way to convey feedback in the event the author wanted to better capture their attention. I didn't get the sense that there was an expectation that the author change their writing style to accommodate their preferences.
re-reading this, I don't think I appreciated that it was really in defense of the readers rather than the content
> I also ask you to be more considerate and respectful of other readers who may enjoy my work
I'm surmising that the real problem statement is:
> I'm sure there are non-sexual furries but the subculture is primarily a sexual one (same as with BDSM)
which I can appreciate as a generalization, I suppose I wouldn't have personally considered furries as under the queer umbrella, but I'm certainly no voice of authority on the matter. I suppose there's also the possibility that 'furries' was a dog whistle for 'queer', and being less charitable to sneak, I could better understand finding disrespect in the post.
The furry subculture is deeply queer, both conceptually and in terms of its members. But "queer" doesn't mean "sexual".
Essential viewing: https://www.youtube.com/watch?v=iv0QaTW3kEY
This is entirely false.
soft_dev_person, what I do want is for you to constrain your assertions about me to facts, and refrain from inaccurate or baseless speculation. It does neither you nor I any favors.
The language you chose to use and the details you chose to focus on is what triggered the response. If your point was that the cartoons was distracting, you could have made that clear in a less disrespectful way (or let the content speak for itself), or perhaps consider if it was worth contributing to the discussion.
Again, you double down on one definition of this particular subculture in another reply. It is reminiscent of how others have tried to define what certain subcultures related to sexual orientation (some now more mainstream) entail, while not being part of them, and I hope you understand how this can be problematic. I appreciate that this may not have been your intention.
> It overshadows the content
Only if you make it. Relax. What someone is wearing or what innocent pictures they put alongside their presentation does not necessarily have to concern you at all. Just ignore it and focus on the actual subject matter.
Words to live by, words to die for.
Please keep posting bangers!
On second thought it seems likely that some charlatan has already years ago raised a couple of millions in an ICO for such a project. “We’re making the entire Internet web3-compatible!”
https://ieeexplore.ieee.org/document/8632560
How can something be reduced over 100% What is it that they actually mean here?
It's a perfectly apt message queue, just a bit heavyweight. But if it's "light enough", it comes "for free" with many OSes.
As long as you keep it internal-only, get a reliable server that doesn't do any anti-spam shit (AKA, nothing from MS or any other large company), doesn't use some unreliable proprietary database (again no MS), and have a reliable journaled disk, your only important failure mode will be losing disks. That's an easy failure mode to deal with.
You also need to add misbehaving clients on your list of things not to use with a message-queue, just opening the queue's folder on Outlook to inspect it may be enough to completely corrupt it (Outlook will happily reorder, even rewrite, header fields of incoming messages, replicate messages to infinity, or who knows what else).
I'd be worried to have a message queue that is compatible with such a cursed ecosystem and transport protocol.
It was so old that the 1u case started to droop in the middle. (it was an sparc something or other with real SCSI ultra 320 drives in them)
I fill in the order form and post it. They mail back an invoice.
I fax the order form, they fax back an invoice.
My computer sends the order form in a structured way over email.
My computer sends the order form in a structured way over http.
And that's why many large telcos and banks still use ebXML in their B2B transactions. It's fundamentally the same business process and logic it's always been, with glacially slow improvement in performance over time.
It basically evolved from when applications from their original customer facing site were emailed and manually entered into the back-office system by a human. They were looking to automate this with a minimum of changes to too many of the moving parts at once, so I reformatted the sent email to contain an XML payload so the new back-office automation could read and process it (and in a pinch, a human could still review any problem applications) using Java's mail APIs.
Things evolved, the front-end web site got replaced with a Wordpress site, but the email message queue kept working for a long time. In the last year or so it was getting more and more onerous though. Reconciling information between the front-end and the mail box showed not all emails were being delivered, and authentication to gmail was becoming more and more of a burdensome moving target.
I just recently replaced the whole thing with an API call made from the back-office to the Wordpress site to access the stored data. (The original site didn't store, just emailed, which was why this was not an option historically.)
Also, you can actually make it cost competitive if the object you store is the last n milliseconds of packets instead of one packet each. So, instead of incurring two API calls per packet, you incur two API calls per minimum buffering time. If S3 is zero-rated for any ingress/egress then you get “infinite” bandwidth for 4.22$ * 3 (for the active case) = 12.66$ a day if you are willing to accept 500 ms minimum latency, or ~600$ a day at a more reasonable 10 ms. If you are saturating even just a 1 Gb link for a whole day that is ~10,000 GB which would be ~700$ via the blessed channel, so you could very well come out ahead.
You could do even better if you out-of-band signal the readiness so you do not need to poll while idle. Then you only incur a cost while actively transmitting so as long as you average 1 Gb/s on the channel you should be coming out even or ahead with minimal latency impact.
> You could do even better if you out-of-band signal the readiness so you do not need to poll while idle.
S3 and its clones have "object lifecycle notifications", where you can be informed by a push-based mechanism whenever a new object is put into the bucket.
But — what do you have to do, to get these notifications?
Subscribe to a real message queue, that S3 puts these notifications into.
So using it here would be somewhat cheating ;)
I like that they started out by talking about $0.07/G cost and went through the whole exercise before pointing out what immediately came to mind for me when they started pushing bytes in and out of S3.
ok, what the good parts of the internet used to be like.
I also love that its highlights an AWS dark pattern. more, more I say.
> <Cadey> Hello! Thank you for visiting my website. You seem to be using an ad-blocker. I understand why you do this, but I'd really appreciate if it you would turn it off for my website. These ads help pay for running the website and are done by Ethical Ads. I do not receive detailed analytics on the ads and from what I understand neither does Ethical Ads. If you don't want to disable your ad blocker, please consider donating [snip] or sending some extra cash to [snip] or [snip]. It helps fund the website's hosting bills and pay for the expensive technical editor that I use for my longer articles. Thanks and be well!
Interesting. Thanks for sharing
https://learn.microsoft.com/en-us/azure/azure-sql/database/f...
If you want something that works "well enough" I'd say it's a reasonable choice.
Can't really think of a better way to ensure that a message is always sent if the DB transactions succeeds and is never sent if the DB transaction fails
Great talk on it from Citus Con 2022:
Queues in PostgreSQL | Citus Con: An Event for Postgres 2022 -- https://www.youtube.com/watch?v=WIRy1Ws47ic&list=PLlrxD0Htie...)
Citus is a horizontal scale out extension for postgres -- imagine the power of those two things together!
JK you don't have to imagine:
https://www.citusdata.com/blog/2018/01/24/citus-and-pg-partm...
https://github.com/starqueue/starqueue
The code is in there for Postgres, MS SQL and MySQL (which all support SKIP LOCKED) though at some point I abandoned all but Postgres.
If I was to write another message queue then I wouldn’t use a database, I’d use the file system based around Linux file moves, which are atomic. What I really want is a message queue that is fast and requires zero config, file based message queues are both…. better than a database.
[0] https://github.com/gchq/Bailo/tree/main/lib/p-mongo-queue
I found almost all message queues to be horribly complex to configure, debug and run. Even database queues require a lot of config, relative to using the file system.
I did actually write a file system based message queue in Rust and it instantly maxed out the disk at about 30,000 messages a second. It did about 7 million messages a second when run as a purely RAM message queue but that didn’t use file system at all.
It depends what you’re doing of course… running a bank on a file system queue wouldn’t make sense.
A fast message queue should be a tiny executable that you run and you’re in business in seconds, no faffing around with even a minute of config.
I just hate configuration in general.
Did you try an in-memory filesystem through tmpfs?
Bank transfers are done by a text file sent over FTP (file transfer protocol; circa 1971)
https://orientalbank.com/assets/Pdfs/ach/ACH_ORIGINATION_AGR...
Shouldn't a message send be worst case a CAS. It really seems like all the work around garbage collection would have some use for in-memory high speed queues.
Are you familiar with the LMAX Disruptor? Is is a Java based cross thread messaging library used for day trading applications.
https://lmax-exchange.github.io/disruptor/
I've experimented with using the file system for storing configuration data where each config value is a single file. Nested structures just use directories. The name of the file is the field name. The file extension is a hint about the data type contained within (.txt is obvious, but I also liked .bool). Parsing data is trivial. I don't need any special viewing or editing tools, just a file manager and text editor. You can see when a specific config value was changed by checking the file update time. You don't have to load the whole configuration just to access one field. And you could conceivably TAR up the whole thing if you wanted to transmit it somewhere.
I use it to configure little sub-projects in my personal website. I really like it, but I shudder to think of the complaining I'd hear from other developers if I ever used it in a work project, just because it's not whatever they've ever seen before and would require a moment of two of thinking on their behalf to get over ingrained habits.
Not a bad idea at all, but perhaps re-inventing a very old wheel?
And what reinvention is there? If you're just using a system that already exists, you're not reinventing anything.
However, and this is a big drawback, once you have too many config files and you start reading and writing from different processes, you get into bottleneck situations quickly.
First of all, if you have multiple processes trying to read/write the same config, that's kind of suspect, and if file I/O is a bottleneck for your config system, that's a different suspicious situation. Why are your processes writing to the config so... often?
But regardless, I can't see how those problems get immediately better by storing that config in a single file. If anything, having it split across multiple files would improve the situation, as different processes that might only be concerned with different sections of the config won't need to wait on file locks from process unrelated to their concerns.
Anyway it’s an elegant idea. Silly to have dozens of config file formats when the fs already has everything it needs. We have xattr too.
The flaw on the OS level is that it is hard to get everyone to change. For new apps not a problem, and any performance concerns are no longer an issue for config.
https://en.wikipedia.org/wiki/Hans_Reiser
If you want to reach people who can actually help, you probably want to check this link:
https://github.com/citusdata/cstore_fdw/issues
[0] Why take hundreds of photos of Honda Civics in red, green, blue, and black when you already have a dozen in white?
Inasmuch as you trust your db's locking correctness it eliminates the concurrency issues. You can very naively have n workers pulling jobs from a queue not stepping on each-other.
https://github.com/procrastinate-org/procrastinate
https://github.com/bensheldon/good_job
Hell, if it’s not an RDBMS then it’ll be Redis (at a much greater expense for a managed instance). I’ve seen that setup in the Ruby world far more often than using a dedicated message queue.
On the topic of message queues, I wonder if anyone ever designed a mechanical, asynchronous hardware IPC mechanism based on tape. Imagine: an endless-loop tape that stretches between a "sender" tape-drive on one machine, and a "receiver" tape-drive on another machine; with each tape drive locally tensioning the tape as it passes through, but letting it hang slack outside the drive; with two tape-width buffer boxes in between the two drives, for taking up the slack; and where each tape-drive has a strain gauge on its input-end capstan.
With this design, you'd never need to seek the tape (backward, at least) — the receive head would just read the tape forward at whatever speed it could until it ran out of slack in the tape (i.e. blocked on read); and the send head would write the tape forward at whatever speed it could until it ran out of slack (i.e. blocked on write.) The tape itself would be a literal, physical ring buffer.
- You’ll want writers to create a temp file and then rename it into place; otherwise your reader might pick up a file that’s only half-written. (POSIX rename() is atomic within a filesystem.)
- It’s also helpful to have an `in_process` folder, and a cronjob to send alerts if a task sits in that place too long. That way you can quickly catch crashes and other failures.
- You can have multiple readers; they cooperate by rename()ing the input file into in_process/ before they start working on it, and ignoring ENOENT (which indicates some other process got to it first).
- This pattern is great for loosely-coupled systems. In my case I was importing orders into a system that ran very slowly; once a reliable import queue was available new use cases kept presenting themselves, and it was very easy to add them; since the API was just “write a file in the correct format”, individual scripts could be written in whatever way was easiest for the particular task at hand. (It helped that the input format hadn’t changed in a couple decades; if it had needed changing a lot you’d want a more structured system. But this is the same as any distributed systems interface design.)
I wonder if the system is still in place. Last time I checked the Jenkins folder was occupying 270 GB (!) of the 10 TB shared FS, most likely because FS block size was 1 MB.
I wrote some VBScript that wrote a locking folder into a sub-folder in a network folder, then launched VNC targeting the proper VM. When VNC was closed, the script would complete and delete the locking folder. That let us know what was available and when. I always thought it was hacky, but at ~60 lines it's incredibly simple and has never really failed.
> In Linux, you can create a TUN/TAP device to let applications control how network or datagram links work. In essence, it lets you create a file descriptor that you can read packets from and write packets to. As long as you get the packets to their intended destination somehow and get any other packets that come back to the same file descriptor, the implementation isn't relevant. This is how OpenVPN, ZeroTier, FreeLAN, Tinc, Hamachi, WireGuard and Tailscale work: they read packets from the kernel, encrypt them, send them to the destination, decrypt incoming packets, and then write them back into the kernel.
(Edit: this comment made more sense when it was replying to a different complaint about the article; the parent comment seems to have been edited in the interim.)
Read (egress) packets from the TUN/TAP device.
Serialize them, assign sequence numbers, and upload them to S3.
On the recieve side, poll for newer objects (packets) in S3.
Write them to your TUN/TAP device.
---
Here, the TUN device is a router using S3 as gateway.
The meat of the article is how to create that tunnel using S3 for data transfer instead of using a more traditional VPN service.
Given latency and bandwidth differences, that's like saying that it's slightly slower to transport water by driving standard, 1-gallon jugs between the US east and west coasts than it is to transport it a few miles using a tanker truck.