<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Andrei Merlescu</title>
    <description>The latest articles on DEV Community by Andrei Merlescu (@andreimerlescu).</description>
    <link>https://dev.to/andreimerlescu</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F3590418%2Ff67be3de-03d6-4d58-b125-05db7e83dc7a.jpeg</url>
      <title>DEV Community: Andrei Merlescu</title>
      <link>https://dev.to/andreimerlescu</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/andreimerlescu"/>
    <language>en</language>
    <item>
      <title>My type of #FractionalCTO</title>
      <dc:creator>Andrei Merlescu</dc:creator>
      <pubDate>Wed, 12 Aug 2026 02:22:15 +0000</pubDate>
      <link>https://dev.to/andreimerlescu/my-type-of-fractionalcto-2eb7</link>
      <guid>https://dev.to/andreimerlescu/my-type-of-fractionalcto-2eb7</guid>
      <description>&lt;p&gt;Let's begin this with, &lt;em&gt;what is a #FractionalCTO?&lt;/em&gt; &lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;A Fractional CTO is an experienced, executive-level technology leader who provides strategic guidance, engineering team mentorship, and architecture oversight on a part-time or contract basis. This role allows early-stage startups and growing companies to access high-level technical expertise without the significant financial commitment of a full-time executive salary and benefits. It is an ideal solution for non-technical founders, scaling businesses, or organizations navigating transitions that require executive direction on a reduced schedule.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Here are the 10 core aspects that define the role and how I believe that I've been filling the role of a &lt;strong&gt;Fractional CTO&lt;/strong&gt; for &lt;em&gt;four years now&lt;/em&gt; and I've only &lt;em&gt;just&lt;/em&gt; been introduced to the term itself. English is my second language. &lt;/p&gt;

&lt;h2&gt;
  
  
  Part-Time Executive Leadership
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Delivers top-tier C-suite technical oversight for a fraction of the cost of a full-time executive salary, benefits, and equity.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Fractional CTO's start at $200/hr when you need on-demand &lt;strong&gt;top-tier&lt;/strong&gt; C-suite technical oversight, insight and expertise accessible to you for a &lt;em&gt;fraction of the cost&lt;/em&gt; of a full time executive salary, benefits, equity, and ultimately, ownership. Sometimes, you just need a confidential second opinion about a difficult decision. Protected under a strong NDA, &lt;strong&gt;Fractional CTOs&lt;/strong&gt; offer you &lt;em&gt;true diverse perspectives&lt;/em&gt; without the overhead of full time commitment for each perspective you tap into. &lt;/p&gt;

&lt;p&gt;As an &lt;strong&gt;Executive Vice President&lt;/strong&gt; or &lt;strong&gt;Chief Executive Officer&lt;/strong&gt; selecting or appointing a &lt;strong&gt;Fractional CTO&lt;/strong&gt; to be assigned a fraction of responsibilities to your organization in order to &lt;em&gt;diversify the role of the Chief Technology Officer itself.&lt;/em&gt; Instead of just &lt;strong&gt;one CTO,&lt;/strong&gt; why not have a &lt;em&gt;suite of Fractional CTOs?&lt;/em&gt; &lt;/p&gt;

&lt;h2&gt;
  
  
  Technical Strategy &amp;amp; Architecture
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Aligns high-level business goals with the correct software, cloud, and hardware infrastructure choices to prevent costly technical debt.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Case Study&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;A &lt;em&gt;VP&lt;/em&gt; in a company came to me and said &lt;em&gt;Andrei, can you reduce my AWS bill? We spend $17K per month right now.&lt;/em&gt; I replied, &lt;em&gt;absolutely!&lt;/em&gt; What ended up happening cost them $69K up front and it reduced their OPEX down to $2K. The company experienced a 1,400% increase in their build times using NVMe NAS over 10Gbps fiber in a colo-hosted private cloud using a dozen Mac Pros running vSphere ESXi on each. The QNAP NAS was programmed and a hand-off document was provided to the CEO and the full time CTO. In this capacity, I functioned as a &lt;strong&gt;Fractional CTO&lt;/strong&gt; providing low level action on high level business goals while implementing and architecting the correct software, cloud and hardware infrastructure choices to prevent costly technical debt by reducing this company's 3 year OPEX by $471K. For the few months that it took me to build the private colo for them, what I cost already paid for itself several times over. At this point, its a matter of discovery to know that &lt;strong&gt;Fractional CTOs&lt;/strong&gt; exist and I'm ready to build!  &lt;/p&gt;

&lt;h2&gt;
  
  
  Infrastructure Cost Optimization
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Audits cloud environments, build pipelines, and vendor contracts to drastically reduce operational expenses (OPEX).&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Case Study&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;A &lt;em&gt;VP&lt;/em&gt; in a company came to me and said, &lt;em&gt;Andrei, can you optimize our build pipelines in our TeamCity Pipelines so it costs us less money?&lt;/em&gt; I reply, &lt;em&gt;why of course!&lt;/em&gt; During this engagement, tooling was introduced that would optimize infrastructure and reduce OPEX by auditing existing on-prem and AWS hybrid private cloud infrastructures across multiple AWS Organization accounts in order to audit &lt;strong&gt;build pipelines&lt;/strong&gt; and provide &lt;strong&gt;vendor pipelines&lt;/strong&gt; specifically to move hundreds of gigabytes of data using Helix Core &lt;code&gt;p4&lt;/code&gt;. Building tooling in &lt;strong&gt;PowerShell&lt;/strong&gt; for &lt;code&gt;p4prometheus&lt;/code&gt; Windows support and developing &lt;a href="https://github.com/andreimerlescu/counter" rel="noopener noreferrer"&gt;counter&lt;/a&gt; so you can have a helper with &lt;strong&gt;counting things.&lt;/strong&gt; Well, I ended up building out technology that replaced $250K rack mounted server clusters with cloud hosting Terraform, Ansible and Bash scripting, &lt;em&gt;custom built without AI&lt;/em&gt; to spin up a cluster for a &lt;em&gt;fraction of the cost&lt;/em&gt; with immediate uptime. A &lt;strong&gt;Fractional CTO&lt;/strong&gt; is a person who can be on-call for these sensitive systems under NDA and provide technical support for these critical applications. When one group in the company lost their data, I restored them and brought them back online. At another company, another &lt;em&gt;VP&lt;/em&gt; called me and wanted me to bring them back online. I did then too. And I'll do it again. That's what a &lt;strong&gt;Fractional CTO&lt;/strong&gt; does. &lt;/p&gt;

&lt;h2&gt;
  
  
  Crisis Management &amp;amp; Recovery
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Intervenes during high-stakes situations—such as production outages, security breaches, or corrupted pipelines—to restore system stability.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This is when $200/hr really is peanuts when you think about it. You're in the middle of a &lt;strong&gt;security breach&lt;/strong&gt; like another company that I've worked with. You're an Executive Vice President and you have alarms going off, orders aren't going through, and you have ransomware installed on your AWS system that is demanding bitcoin. Who do you call? Your &lt;strong&gt;Fractional CTO&lt;/strong&gt; of course. Even when your corrupted systems require an intervention from a &lt;strong&gt;Fractional CTO&lt;/strong&gt; at $400/hr because it's after-hours, is still a bargain when millions of dollars are on the line. &lt;/p&gt;

&lt;p&gt;What happens when you hire a contractor and they completely nuke a system by accident and don't know how to undo what they did? Got millions of dollars on the line about to be lost if you can't get it back? Well, I've been the &lt;strong&gt;Fractional CTO&lt;/strong&gt; that saved that company from that hire. &lt;/p&gt;

&lt;p&gt;This is me. I got the 6AM call. I got the call when nobody else was available. &lt;em&gt;Hey Andrei! I can't get in touch with , are you available to help me bring this system back online?&lt;/em&gt; I don't ask them &lt;em&gt;What OS it?&lt;/em&gt; &lt;em&gt;Do you think I can help you?&lt;/em&gt; Instead, I get a signed NDA and begin working immediately on the problem. On-Prem? Fine. Colo? Fine. Cloud? Fine. Private Architecture? Fine. Public Architecture? Fine. Manually Built Infrastructure with Duck-tape? Fine. Perfectly orchestrated using IAC? Fine. Regardless of where you are - it's fine by me. I'm the &lt;strong&gt;FractionalCTO&lt;/strong&gt; that takes the call when things are on fire and you need them back online ASAP. &lt;/p&gt;

&lt;p&gt;Company after company, &lt;em&gt;VP&lt;/em&gt; after &lt;em&gt;VP&lt;/em&gt;, I have been the direct point of contact for crisis management and response. I've been the leader driving disaster recovery planning and I've approached each organization like it matters deeply to me that they succeed. A &lt;strong&gt;Fractional CTO&lt;/strong&gt; is responsible for being that trusted confident, for a fraction of the price that a full time CTO costs. &lt;/p&gt;

&lt;h2&gt;
  
  
  Team Mentorship &amp;amp; Hiring
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Mentors internal developers, establishes engineering standards, and leads technical interviews to hire key talent.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;A full time &lt;em&gt;CTO&lt;/em&gt; may cost too much to justify this, but for $200/hr, you can truly enhance and expand your team by bringing on additional &lt;strong&gt;Fractional CTOs&lt;/strong&gt; to your organization. You definitely don't want to be using AI agents to hire for your Senior Distributed Systems Engineer role. Instead, let your &lt;strong&gt;Fractional CTO&lt;/strong&gt; do the interviews for you to get the best candidates only? You need a new technology explored and then presented to the team? Ask your &lt;strong&gt;Fractional CTO.&lt;/strong&gt; These are the exact type of tasks that I was asked throughout my career. Now, you're a CEO, a VP or a person needing a &lt;strong&gt;Fractional CTO&lt;/strong&gt; and you're wondering, what does a Fractional CTO do?&lt;/p&gt;

&lt;p&gt;Did you know that you can fly your &lt;strong&gt;Fractional CTO&lt;/strong&gt; where you need them? Launching a new location? Send me. When travel expenses are fully covered and the flight is &lt;em&gt;first class,&lt;/em&gt; you'll get the most out of your &lt;strong&gt;Fractional CTO.&lt;/strong&gt; When you give them a $25 meal budget and the cheapest economy ticket on the market, you'll get exactly what you paid for — a tired and worn out &lt;strong&gt;Fractional CTO&lt;/strong&gt; upon arrival. Because you're not paying for this person's benefits and equity like you do other executives, how you transport your &lt;strong&gt;Fractional CTO&lt;/strong&gt; is a way of showcasing your company's capabilities to show dignity and respect for the title that they are commanding out you. When you cheap out on a &lt;strong&gt;Fractional CTO,&lt;/strong&gt; you &lt;em&gt;cheat your own organization.&lt;/em&gt; $200/hr may sound steep, but it's really not. Your corporate attorney is billing at double that rate. &lt;/p&gt;

&lt;h2&gt;
  
  
  Vendor &amp;amp; Agency Oversight
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Evaluates, negotiates with, and manages third-party software vendors, outsourced development agencies, and contractors.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This is critical. Under NDA, &lt;strong&gt;Fractional CTOs&lt;/strong&gt; can provide you with additional oversight to third party software vendors performance. An experienced &lt;strong&gt;Fractional CTO&lt;/strong&gt; with overseas staffing agencies is available on-tap and capable of providing reasonable negotiations with respect to these contracting services. In the age of AI, so many imposters are going around just giving you another interface to ChatGPT or to Claude. Sorry, I am not going to do that. A &lt;strong&gt;Fractional CTO&lt;/strong&gt; is a new title that is in response to the loss of the 20+ year Senior Software Engineer being able to choose from the crop of jobs. Instead, now they've been reduced to training AI for data harvesting operations on LinkedIn Premium. In this capacity, I serve your interests and I look at the contracts that you have and I weigh them based on the best value that can be brought to your company. It's as simple as that. &lt;/p&gt;

&lt;p&gt;I've worked with companies in the past in which they have existing contracts with outsourcing development agencies and they needed a &lt;strong&gt;Fractional CTO&lt;/strong&gt; to oversee the work being performed by this vendor. That's what you hire a &lt;strong&gt;Fractional CTO&lt;/strong&gt; to do for you. They can own the process, the pipeline, and the byproduct of the vendor's output and act as the representative advocating for the strongest results for your organization, knowing full well that contracting vendors are always looking to cut corners on their projects to save time and money so they can deliver faster results to the client. Sometimes, faster isn't always better, and this is where a seasoned and skilled &lt;strong&gt;Fractional CTO&lt;/strong&gt; is the difference between a vendored project that is "sufficient" versus "incredible." &lt;/p&gt;

&lt;h2&gt;
  
  
  Security &amp;amp; Compliance Standards
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Establishes cybersecurity policies, access controls, data privacy protocols, and regulatory compliance (e.g., SOC2, PCI-DSS, HIPAA).&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;I have experience with this space, including the tooling and scanning of systems that are needed in order to assert compliance. Being involved in the Medical Services industry, I have an understanding of Provider, Doctor, and Patient like I do the sanctity of HIPPA and what privacy means for the actual common link to why PCI and even SOC2 fit into that mix. Oversight of systems and verifiability of compliance to systems is key. I have built SOC2 Ansible compliance scripts designed to provision resources for compliance with SOC2. I have deployed Wazuh DevSecOps security monitoring solutions inside private networks both in the public cloud (hidden via VPC routing and VPNs) and on-prem. When it comes to compliance in these areas, I am the type of &lt;strong&gt;Fractional CTO&lt;/strong&gt; that knows these frameworks well, has built systems around them, and can apply that same expertise and knowledge to additional companies in need of fractional services from a &lt;em&gt;CTO.&lt;/em&gt; &lt;/p&gt;

&lt;h2&gt;
  
  
  Investor Readiness &amp;amp; Due Diligence
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Prepares technical roadmaps, system documentation, and architecture diagrams for fundraising, board updates, or M&amp;amp;A activities.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;One thing that I love doing is writing, if you couldn't tell. I love writing system documentation and building Architecture Diagrams. How they are used, can be applied to fundraising, board updates and other activities, but at the end of the day, when I am studying your infrastructure, sometimes poor decisions from past teams compound on themselves, and I do not &lt;em&gt;seek to blame anyone,&lt;/em&gt; instead I choose to &lt;strong&gt;own without ego&lt;/strong&gt; and &lt;em&gt;seek engineering excellency&lt;/em&gt; in all that I build. As a &lt;strong&gt;Fractional CTO,&lt;/strong&gt; you may need to tackle a larger project that needs closer collaboration with your CTO that you don't want to give to your full time staff. Perhaps it affects them. Perhaps its new software that you want them to use. Yes, I can be that guy. I am that &lt;strong&gt;Fractional CTO.&lt;/strong&gt; Sometimes, growing pains need to happen. That adult tooth won't come out if the baby tooth doesn't fall out first. Yes its painful at first, but its needed. Likewise with the choice of using &lt;strong&gt;Fractional CTOs.&lt;/strong&gt; Use us like we are a tool in your toolbox. Have 3 or 4 on speed dial. &lt;/p&gt;

&lt;p&gt;Using tools like OmniGraffle, Figma among other programmable mockup toolings like UML, Mermaid or D2 (preferred), a &lt;strong&gt;Fractional CTO&lt;/strong&gt; is responsible for being able to look at large complex systems and visually map them out in easy to understand diagrams. If your infrastructure was home-brewed over the last decade since the rise of AI and you really don't know why your AWS bill is $75,000 per month, then hire a &lt;strong&gt;Fractional CTO&lt;/strong&gt; like myself to help you. Using these tools, they will be able to give you a clear understanding of what you're up against, where you can cut costs, and how I can deliver to your company, OPEX savings. Could it be $471K for you too? Pays for that $200/hr that I ask for real quick. &lt;/p&gt;

&lt;h2&gt;
  
  
  Scalability Planning
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Designs high-availability, multi-region, or distributed architectures that allow a growing product to scale without breaking.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Your &lt;strong&gt;Fractional CTO&lt;/strong&gt; needs to know how to take a product that was built over several years for one region and know how to bring that entire product, team and all, multi-region. I've done this two times professionally and one time personally. I've grown products to scale without breaking, all while using load testing software like &lt;a href="https://github.com/andreimerlescu/sovereign" rel="noopener noreferrer"&gt;sovereign&lt;/a&gt; and &lt;a href="https://github.com/andreimerlescu/lemmings" rel="noopener noreferrer"&gt;lemmings&lt;/a&gt;. Because being multi-region matters so much to a business, if your toolchain provides revenue but has a bottleneck, diversifying the application may require actual &lt;em&gt;architectural refactoring&lt;/em&gt; of your application that would need a &lt;strong&gt;Fractional CTO&lt;/strong&gt; that not only understands how to &lt;em&gt;use complex systems&lt;/em&gt; like Kubernetes, but &lt;strong&gt;can build complex systems &lt;em&gt;like Kubernetes&lt;/em&gt; themselves.&lt;/strong&gt; This is where my early career at Cisco's Advanced Services building out their Cloud Group with OpenStack and then going over to Oracle for building out OCI. When AWS EKS was launched in 2008, I was reviewing the production code going into OCI that was building a direct competitor to Kubernetes itself. Not only am I qualified to use Kubernetes, but I am also qualified to build alternatives to it that cost less. In fact, I've done &lt;em&gt;that&lt;/em&gt; three times professionally. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Case Study&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;A company wanted to get involved with a publicly traded company and saw that my professional experience has mostly been with those companies, 2025 was the exception aside from publishing firm in college, but that doesn't &lt;em&gt;really count.&lt;/em&gt; That company that I am talking about, wanted to go &lt;strong&gt;multi-region&lt;/strong&gt; and they had a fragile &lt;em&gt;single-region&lt;/em&gt; Terraform architecture, mostly scaffolded by ChatGPT and held together by dozens of manual steps needed between each error message to get the "builds to work." In this case study, I have specifically taken AWS and GCP single-region architectures and was single handedly tasked with making them multi-region. I have the resources capable of doing this, and I've done it three times in my career. As a &lt;strong&gt;Fractional CTO&lt;/strong&gt; this is what is expect of you. Once the platform was &lt;em&gt;multi-region&lt;/em&gt; the publicly traded company took interest in this company and began using their technology. Without my &lt;strong&gt;multi-region efforts,&lt;/strong&gt; they would be in the stone age still. &lt;/p&gt;

&lt;h2&gt;
  
  
  Bridge for Non-Technical Founders
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Translates complex engineering trade-offs into plain business terms, giving founders the technical clarity needed to make strategic decisions.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This is probably the most fun that I have on the job as a &lt;strong&gt;Fractional CTO.&lt;/strong&gt; I really enjoy being asked to sit in on technical conversations and just give my feedback on them. A fresh perspective from the outside. Sometimes the executives that I've worked with are watching a presentation from an employee that they know nothing about, and they need an honest &lt;strong&gt;Fractional CTO&lt;/strong&gt; opinion on it to get a sense of what opportunities exist, what the trade-offs look like, and what what technical clarity could look like that involves the &lt;strong&gt;Fractional CTO.&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Strategic decisions&lt;/strong&gt; are reserved for the Executive Leadership team and the role of a &lt;strong&gt;Fractional CTO&lt;/strong&gt; is not to make those decisions for your organization, but to provide your organization with a perspective into business plans, trade-offs, and complex engineering terms themselves into clear talking points that give founders technical clarity needed, to make those decisions. This is where sitting down with me, say over Cigars or a glass of wine, really build on the relationship that exists between an engineer like myself and the role of what a &lt;strong&gt;Fractional CTO&lt;/strong&gt; does for other business leaders. I know that you're not the one in the terminal every day. I am. But I also know a good Cigar when I see one. Strategic decisions are knowing when the risks either short term or long term outweigh the gain presented before you in the moments notice that a decision does need to be made. Whether technical in nature or adjacent to the industry, a &lt;strong&gt;Fractional CTO&lt;/strong&gt; is the means to your ends when it comes to dividing the space and conquering it. &lt;/p&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;I have been doing this now for 17 years across my career. I never had a name for it. I do now. It's called &lt;strong&gt;Fractional CTO.&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;Are you a &lt;strong&gt;Fractional CTO?&lt;/strong&gt; I didn't know that I was, until it dawned on me this year. When I look at what it means to be a &lt;strong&gt;Fractional CTO,&lt;/strong&gt; the 10-points outlined here demonstrate how I have intimately been involved with company Vice Presidents and the CEOs themselves throughout my entire career as a very close confident. Not the type of person who did a CoderPad challenge for you, but the type of person to save your organization millions of dollars and save it from disaster in a moments notice. That's where having a &lt;strong&gt;Fractional CTO&lt;/strong&gt; makes the most sense. &lt;/p&gt;

</description>
      <category>discuss</category>
      <category>cto</category>
      <category>leadership</category>
      <category>career</category>
    </item>
    <item>
      <title>My Professional Story: Two Names, Thirty Years of Scaffolded Code, and the AI That Can't Tell I'm One Person</title>
      <dc:creator>Andrei Merlescu</dc:creator>
      <pubDate>Fri, 07 Aug 2026 00:27:04 +0000</pubDate>
      <link>https://dev.to/andreimerlescu/my-professional-story-two-names-thirty-years-of-scaffolded-code-and-the-ai-that-cant-tell-im-1e2l</link>
      <guid>https://dev.to/andreimerlescu/my-professional-story-two-names-thirty-years-of-scaffolded-code-and-the-ai-that-cant-tell-im-1e2l</guid>
      <description>&lt;p&gt;While the University of Maine was extending BITNET to families of long-time employees, I was writing AppleScript programs for Mac OS 7 at just 7 years old. By the time I was 8, I had compiled &lt;em&gt;applications&lt;/em&gt; that ran when you double clicked on them, and &lt;em&gt;magic happened&lt;/em&gt; that I was able to program into the machine. I would press the &lt;strong&gt;Record&lt;/strong&gt; button, then remove the printer, then &lt;strong&gt;re-add the printer&lt;/strong&gt;, and the AppleScript editor would autocomplete the code that I needed to execute on the machine to replicate the task. My first program was compiled in 1996 — 30 years ago &lt;em&gt;this year&lt;/em&gt; — built using the scaffolded results of those instructions, which later developed into a natural ability of writing AppleScripts from nothing.&lt;/p&gt;

&lt;p&gt;Hold onto that word: &lt;em&gt;scaffolded.&lt;/em&gt; It's going to matter in about three thousand words.&lt;/p&gt;

&lt;p&gt;I was born in 1988 in Romania and when I turned 7 days old, I was institutionalized by Ceaușescu due to Decree 770. I spent 843 days in one of his facilities until I was adopted on December 28th, 1990, and flown to the United States to live in the town next to the University of Maine Orono campus. My adoptive mother was Cynthia Mary Trimm, and she retired recently after &lt;strong&gt;45 years of service&lt;/strong&gt; at the University, working in the Career Center. Dating back to my earliest memory in this country, I remember the University deeply. I have memories of walking from building to building, helping mom move computers.&lt;/p&gt;

&lt;p&gt;As the Technology Specialist at the Career Center, Cindy worked with the newest technology being brought onto campus, including BITNET — the first wave of the internet released toward the average citizen in the United States. Before the internet was a thing, &lt;em&gt;publicly&lt;/em&gt;, for the good people of Maine, I had a &lt;strong&gt;connection&lt;/strong&gt; into the internet since &lt;em&gt;its inception.&lt;/em&gt; Growing up, I got to watch my mother sit in front of the FileMaker Pro server she controlled and created backups on. I watched her write HTML and read JavaScript textbooks and build counters. Decades later, after working with &lt;strong&gt;WB Games&lt;/strong&gt;, I built &lt;a href="https://github.com/andreimerlescu/counter" rel="noopener noreferrer"&gt;counter&lt;/a&gt; in Go and made it open source, after seeing how counters were utilized in &lt;strong&gt;Helix Core&lt;/strong&gt; — the Perforce product managing hundreds of terabytes of assets across a dozen AAA game studios.&lt;/p&gt;

&lt;p&gt;The apple didn't fall far from the tree. It just changed languages.&lt;/p&gt;

&lt;h2&gt;
  
  
  Write Us the Software, Then We'll Demote You
&lt;/h2&gt;

&lt;p&gt;I watched my mother spend hours debugging her code. I also witnessed her pushing back against others on campus who wanted to displace her from being the &lt;em&gt;Technology Specialist&lt;/em&gt; for the Career Center. Their argument to her was, essentially: &lt;strong&gt;write us the software and then we'll demote you&lt;/strong&gt; — because once it's written, &lt;em&gt;what use is there for you?&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;She fought that. And she had something I do not have: &lt;strong&gt;a union.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Remember that, because in 2026 the same argument is being run against every engineer alive. Write us the software. Train the model. Feed the scaffold. And once it's written — what use is there for you? Except this time there's no union, no grievance process, and increasingly no human being on the other side of the table at all.&lt;/p&gt;

&lt;p&gt;Well, decades later, I've learned first hand that it's people like my mother and I who push through the bugs and deliver the results that &lt;em&gt;nobody else could.&lt;/em&gt; That was &lt;strong&gt;my calling.&lt;/strong&gt; So I thought, and so I believed, because of how I grew up watching technology get used — and watching who it got used &lt;em&gt;against.&lt;/em&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  The Boy Calling Himself Michael
&lt;/h2&gt;

&lt;p&gt;Fast forward past &lt;em&gt;the boy in the waiting room&lt;/em&gt; — a story for another day — and I enter high school as a &lt;strong&gt;huge nerd.&lt;/strong&gt; I barely had three friends that I was close with, and they never lasted. I was a depressed imposter calling himself Michael. Nobody wanted to be best friends with me. I spent many hours in the computer laboratory and hung out with Mr. Wason, the computer teacher. He was friendly with my older sister, a football cheerleader, and he'd let me stay in the lab after classes so I could &lt;em&gt;hack away.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Because I was an ESL Romanian-born kid living in Maine, I was battling an &lt;em&gt;imposed identity&lt;/em&gt; while everybody called me Michael. You see, in Romania, I spoke less than ten words — but I knew my name. &lt;strong&gt;I was two.&lt;/strong&gt; Overnight, on December 29th, 1990, I became Michael. I knew on the inside that I was Andrei, but I also believed in my heart that I wasn't &lt;em&gt;worthy&lt;/em&gt; of calling myself Andrei — that because I was institutionalized in Ceaușescu's orphanages, I wasn't allowed. Every adult in my life gaslit me on my name from the day I arrived in America, and zero people explained to me why I couldn't be Andrei here. They used &lt;em&gt;Andrei Michael&lt;/em&gt; until they switched it to &lt;em&gt;Michael Andrei&lt;/em&gt;, and then it just became &lt;strong&gt;Michael&lt;/strong&gt; — and &lt;em&gt;Andrei&lt;/em&gt; was reserved for special occasions, when we wanted to have difficult conversations about my birth family and Romania.&lt;/p&gt;

&lt;p&gt;I didn't respond to Michael at first. So I was trained to.&lt;/p&gt;

&lt;p&gt;That's relevant to a programming blog, I promise. Because a name is not a label. A name is a &lt;em&gt;program.&lt;/em&gt; We'll get there.&lt;/p&gt;

&lt;h2&gt;
  
  
  LAMP Stacks, MuggleNet, and 8th in the Nation
&lt;/h2&gt;

&lt;p&gt;I loved spending my days reading technology books, and by the time I had the internet and access to &lt;em&gt;php.net&lt;/em&gt;, I was teaching myself to build LAMP-based web apps. I took the tutorials I was reading and put them into action. In 2004–2005 I volunteered with MuggleNet and built an international news translation service — connecting fans to news about the franchise from around the world, in their native language, written by fellow fans from their own countries. Romanian was never part of it. Sit with that one for a second. I did.&lt;/p&gt;

&lt;p&gt;I used those self-acquired skills to build online games, fan fiction CRUD apps, and to help manage a massive distributed MySQL database holding all of their data — on the number one fan site in the entire franchise, at multi-million visit scale, as the whole thing was unfolding in real time.&lt;/p&gt;

&lt;p&gt;Then I won the Gold Medal at the 2005 SkillsUSA Maine vocational competition and got selected for Nationals in Missouri. I represented Maine with a classmate named Steve, and we built a website in hours before a panel of judges. We were handed a Word document of boilerplate company text, a few photos, and a logo.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Every team modified the logo except for Steve and I.&lt;/strong&gt; Because you cannot modify a client's logo. That's not a style preference — that's basic copyright. When the judges realized that 31 of 32 teams had broken that rule, they didn't disqualify 31 teams. They threw the criterion out entirely and awarded us &lt;strong&gt;8th in the Nation.&lt;/strong&gt; The modified versions &lt;em&gt;looked better&lt;/em&gt; than mine — I'll give them that — but they violated the spirit of the law, and doing it right cost me first place, because enforcing the rule correctly would have embarrassed everybody else in the room. My hands to God — I am telling the truth as I experienced it in 2005.&lt;/p&gt;

&lt;p&gt;Keep the shape of that story in your head too: the people who followed the spec got re-ranked by a rules change &lt;em&gt;after the fact&lt;/em&gt;, because the system found it easier to move the goalposts than to reward the ones who did it right. My mother had a union when that move was tried on her. I had a scoring sheet.&lt;/p&gt;

&lt;p&gt;I flew back to Maine, 8th in the Nation, and still &lt;em&gt;hungry.&lt;/em&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Fifteen Years at Sawmill, a Coup at Wentworth
&lt;/h2&gt;

&lt;p&gt;I joined &lt;strong&gt;Sawmill Publishing&lt;/strong&gt;, a small magazine publisher in Bangor, ME, as a Web Design Intern while finishing my junior year of high school. By graduation I'd extended that internship into part-time employment that ended up &lt;strong&gt;lasting 15 years&lt;/strong&gt;, until the company shut down shortly after the pandemic and the owner developed cancer. It started with a basic HTML and CSS website — very similar to the pages my mother maintained for the University. But I'd just come back from Nationals having &lt;em&gt;won something&lt;/em&gt;, and I'd just made a splash at MuggleNet, so I walked up to Walter, the publisher, and proposed that the magazine could go digital — and that I would build it. We collaborated for years until that vision wasn't just realized but &lt;em&gt;fully expressed&lt;/em&gt;, before the pandemic ended it abruptly.&lt;/p&gt;

&lt;p&gt;It was the combination of MuggleNet, SkillsUSA, and Sawmill that got me into &lt;strong&gt;Wentworth Institute of Technology&lt;/strong&gt; in Boston as a &lt;em&gt;Computer Engineering&lt;/em&gt; student. I joined campus and immediately went to join the IEEE Student Branch — which was run by two seniors who didn't want to let freshmen in. So I went to the Dean, demanded an election, and won — &lt;strong&gt;64 to 2.&lt;/strong&gt; The existing members voted for themselves; the incoming class voted unanimously for me. I staged a &lt;em&gt;coup&lt;/em&gt; in the IEEE Student Branch at Wentworth, and &lt;em&gt;I'll do it again.&lt;/em&gt; I stayed President until resigning my junior year to start at Cisco Systems.&lt;/p&gt;

&lt;p&gt;In college I took mostly &lt;strong&gt;electrical engineering&lt;/strong&gt; courses — intense mathematics, very little programming. Syntax and languages lived across the fence in &lt;em&gt;computer science&lt;/em&gt;, and it was very much an over-the-fence relationship between hardware and software. I was naturally gifted at programming, having been writing it for &lt;strong&gt;ten years by the time I was a sophomore&lt;/strong&gt;, so I became a teaching assistant and taught night classes alongside Professor Johnson — HTML, CSS, and PHP for design students and architecture majors. In all honesty, the CS kids were probably orders ahead of me in raw technique. But none of them had the communication skill to generalize the gift to the masses — to make &lt;em&gt;anybody&lt;/em&gt; understand what programming is and how it affects your life. I did.&lt;/p&gt;

&lt;p&gt;People ask why I didn't go into computer science. Here's the answer it took me until the AI era to say cleanly:&lt;/p&gt;

&lt;p&gt;I learned to program from &lt;strong&gt;scaffolded code.&lt;/strong&gt; The machine generated the instructions. I studied them, edited them, and grew until I didn't need the scaffold anymore. The interesting part was never the syntax — it was the &lt;em&gt;system around it.&lt;/em&gt; That's engineering. And thirty years later, the entire industry is being dragged back to my starting point: agentic tools generate the scaffold, and the humans who thrive are the ones who can engineer the systems around it. Artificial intelligence didn't make the software engineer's plight obsolete for me — it made everybody else start where I started in 1996, standing at the &lt;strong&gt;Record&lt;/strong&gt; button, watching the editor autocomplete.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;That is why I did not go into computer science.&lt;/strong&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  A Name Is a Program
&lt;/h2&gt;

&lt;p&gt;You see, connecting this back to programming: a &lt;strong&gt;name&lt;/strong&gt; carries a lot of weight. If I call the Large Language Model that is my life by &lt;em&gt;my name&lt;/em&gt;, but my name gets changed on me — &lt;em&gt;am I running another program?&lt;/em&gt; I argue yes. When I called myself Michael, I identified as an imposter trying to get by, trying to survive. When I reclaimed my name 7 years ago and said &lt;strong&gt;enough is enough&lt;/strong&gt;, I gave my authentic true self the chance to emerge. I needed to deny the identity imposed onto me so I could realize the identity that Ceaușescu tried to erase under Decree 770.&lt;/p&gt;

&lt;p&gt;When I joined Wentworth, I was calling myself Michael. When I joined Cisco, I was Michael. When I joined Oracle, I was Michael.&lt;/p&gt;

&lt;p&gt;Nobody in college knew any of this. No professors. No classmates. Nobody who voted for me. I carried it alone.&lt;/p&gt;

&lt;h2&gt;
  
  
  Mohammed
&lt;/h2&gt;

&lt;p&gt;December 2018. Oracle holiday party. My wife pregnant with our first child. Me — completely triggered if anybody said &lt;em&gt;Andrei&lt;/em&gt; in any capacity, because using my own name felt like the ultimate act of selfishness against the adoptive family that saved me from Romania, and against the abandonment from my birth mother that I carried. And I'm standing there talking with a colleague:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Mohammed:&lt;/strong&gt; &lt;em&gt;What's your name?&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Me:&lt;/strong&gt; &lt;em&gt;Michael. What's yours?&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Mohammed:&lt;/strong&gt; &lt;em&gt;Mohammed.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Me:&lt;/strong&gt; &lt;em&gt;Where are you from, Mohammed?&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Mohammed:&lt;/strong&gt; &lt;em&gt;Pakistan. Where are you from?&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Me:&lt;/strong&gt; &lt;em&gt;Romania.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Mohammed:&lt;/strong&gt; &lt;em&gt;Michael doesn't sound Romanian.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Me:&lt;/strong&gt; &lt;em&gt;When I arrived in America, my name was changed to Michael.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Mohammed:&lt;/strong&gt; &lt;em&gt;Why?&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Me:&lt;/strong&gt; &lt;em&gt;I don't know...&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Mohammed:&lt;/strong&gt; &lt;em&gt;What is your real name?&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Me:&lt;/strong&gt; &lt;em&gt;Andrei.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Mohammed:&lt;/strong&gt; &lt;em&gt;That sounds Romanian. Hi Andrei. Nice to meet you.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Why do you not use the name Andrei?&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;That conversation &lt;strong&gt;hit me like a ton of bricks.&lt;/strong&gt; A stranger from Pakistan needed sixty seconds to see what an entire industry of AI-powered hiring software still cannot parse in 2026: a name got overwritten, and the original program was still running underneath it the whole time.&lt;/p&gt;

&lt;p&gt;I went home that night wanting to get as far from Oracle as possible. I opened a bottle of whisky and had more than my fair share. By 11 PM I was drunk in front of the fireplace, alone, asking God to help me stop drinking. And I heard what can only be described as a voice from within: &lt;em&gt;you'll never be the father that I know you to be so long as you keep calling yourself Michael. You are Andrei. It is time that you returned to me.&lt;/em&gt; I had just finished asking Jesus to help me stop drinking — and His answer was to change my name? Was I drunk? Probably. Was it real? &lt;strong&gt;Definitely.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;When I restored my name at Oracle, I was asked if I was transgender. When I clarified that I was asserting my birth name from my adoption — that my identity confusion was never about gender or anything physical, but about the fact that on December 27th, 1990, I was Andrei in Romania and on December 28th, 1990, I was Michael in America — the response treated my restoration as if I were mocking trans people. I terminated my employment over it. My name is not a costume and it's not a statement about anybody else. It's the thing that was taken from a two-year-old who couldn't fight back, reclaimed by the adult he became.&lt;/p&gt;

&lt;h2&gt;
  
  
  Michael Was Big Tech. Andrei Is Gaming.
&lt;/h2&gt;

&lt;p&gt;So in 2019, before the pandemic, I stopped calling myself Michael, started calling myself Andrei, and changed industries too — out of Big Tech, into gaming. Bit Fry Games, then WB Games. I have &lt;em&gt;six published titles&lt;/em&gt; on &lt;a href="https://www.mobygames.com/person/1330654/andrei-merlescu/" rel="noopener noreferrer"&gt;MobyGames&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;And I'll be honest in a way this industry rarely is: &lt;strong&gt;I do not like working in the gaming industry at all.&lt;/strong&gt; I choose not to contribute my skills to it any longer.&lt;/p&gt;

&lt;p&gt;But look at what my career looks like to a pattern matcher now:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Michael Trimm&lt;/strong&gt; = IEEE, Cisco, Oracle. &lt;em&gt;Big Tech industry expert.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Andrei Merlescu&lt;/strong&gt; = Bit Fry, WB Games, SurgePays. &lt;em&gt;FinTech and Gaming industry.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Two clean clusters. Two career trajectories. Two "people."&lt;/p&gt;

&lt;p&gt;One expert. &lt;/p&gt;

&lt;p&gt;One me.&lt;/p&gt;

&lt;h2&gt;
  
  
  Project Apario: What I Did Instead of Nothing
&lt;/h2&gt;

&lt;p&gt;You see, when I said enough is enough and stopped calling myself Michael, I shifted realities and the world followed with me. In 2020, instead of taking my decade of Cisco and Oracle experience and &lt;em&gt;doing nothing during the pandemic&lt;/em&gt;, I decided to do something. &lt;strong&gt;President Kennedy&lt;/strong&gt; asked me — growing up, through history class videos — &lt;em&gt;Ask not what your country can do for you; ask what you can do for your country.&lt;/em&gt; Those words stuck. So I chose to contribute &lt;a href="https://github.com/ProjectApario" rel="noopener noreferrer"&gt;Project Apario&lt;/a&gt; to the American people, as &lt;strong&gt;thanks for saving me from communism in Romania.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;I built the &lt;a href="https://dev.to/andreimerlescu/how-i-processed-666k-pages-of-flattened-pdfs-into-a-full-text-search-engine-4db3"&gt;writer database first&lt;/a&gt;, followed the next year by the &lt;a href="https://dev.to/andreimerlescu/how-i-reduced-my-opex-by-995-using-go-3ff7"&gt;reader webapp&lt;/a&gt;. Over 17 days on a Zoom call with DJ Nicke — a former Disney animator, not a programmer — I wrote the first draft in &lt;strong&gt;Rails&lt;/strong&gt; while being watched for over ten hours per day. I built the application singlehandedly, then deployed it by custom-building the &lt;strong&gt;DevSecOps&lt;/strong&gt; pipeline with &lt;strong&gt;Ansible&lt;/strong&gt;, &lt;strong&gt;Bash&lt;/strong&gt;, and &lt;strong&gt;VMware&lt;/strong&gt;, across 12 bare metal servers, serving 500+ concurrent connections every minute, for weeks, until the funding was cut. The project ended in 2024 and is now open source.&lt;/p&gt;

&lt;p&gt;Then I took that $7,000-per-month Rails app and rewrote it as an appliance monolith in &lt;strong&gt;Go&lt;/strong&gt;, dropping OPEX to &lt;strong&gt;$33 per month.&lt;/strong&gt; That's the &lt;a href="https://dev.to/andreimerlescu/how-i-reduced-my-opex-by-995-using-go-3ff7"&gt;99.5% savings&lt;/a&gt;. It didn't make me rich — it nearly bankrupted me. What it made me is &lt;em&gt;provable.&lt;/em&gt; Every claim in this paragraph has a repository, a README, and a receipt.&lt;/p&gt;

&lt;h2&gt;
  
  
  2026: The Machines Doing the Hiring
&lt;/h2&gt;

&lt;p&gt;Now the present. I have been applying for work for months. I am fed up with LinkedIn and AI interviews and being &lt;em&gt;filtered out.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;To this day, automated recruiting systems send opportunities to &lt;strong&gt;&lt;a href="mailto:michaeltrimm@gmail.com"&gt;michaeltrimm@gmail.com&lt;/a&gt;&lt;/strong&gt; while ignoring &lt;strong&gt;&lt;a href="mailto:andreimerlescu@gmail.com"&gt;andreimerlescu@gmail.com&lt;/a&gt;.&lt;/strong&gt; Same person. Same hands that wrote all of it. The software has decided the Big Tech expert is worth recruiting and the gaming engineer is not — and it cannot conceive that they are one human being who restored his birth name. The most important act of my life — undoing what Decree 770 and a well-meaning but wrong adoption decision did to my identity — reads to a machine as a &lt;em&gt;data integrity error.&lt;/em&gt; An inconsistency. A flag.&lt;/p&gt;

&lt;p&gt;Call it whatever you want. From where I sit, I'm being pattern-matched out of my own career, and the pattern it can't match is &lt;em&gt;me.&lt;/em&gt; I feel like an underrepresented person in the most literal sense possible: the systems doing the representing have me down as two people, and they're rejecting both.&lt;/p&gt;

&lt;p&gt;Here's how current this is. This week I applied to a &lt;strong&gt;junior Go developer&lt;/strong&gt; role posted through micro1, an AI hiring platform. Before any human saw anything, I was required to join a recorded call — up to 50 minutes — with an AI, for a technical screening. I have &lt;strong&gt;55+ open source Go projects.&lt;/strong&gt; I rewrote a $7K/month production SaaS into a $33/month Go binary. Spare me the screening — &lt;em&gt;frankly speaking.&lt;/em&gt; That's the tone of this whole piece, in case anyone was wondering: not rage. &lt;strong&gt;Frankness.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;And when the response to an accommodation request is &lt;em&gt;the AI doesn't recognize that, it's policy, no exceptions&lt;/em&gt; — I need companies to understand what they're saying out loud. The ADA covers the application process, not just the job. "The software is buggy" is not an exemption anybody wrote into law. The software is buggy &lt;strong&gt;af&lt;/strong&gt; — and bugs don't excuse a company from EEOC and ADA obligations to the humans on the other side of the webcam. If I have to invoke the ADA and fight this, &lt;strong&gt;I will.&lt;/strong&gt; I try to be nice about it. I've learned that nice and silent are not the same thing.&lt;/p&gt;

&lt;p&gt;I was also triggered recently by &lt;a href="https://dev.to/andreimerlescu/five-hours-of-interviewing-zero-questions-about-the-job-378k"&gt;DomainTools' Alex&lt;/a&gt; making a snarky comment — &lt;em&gt;"I don't even know if you can write code"&lt;/em&gt; — as a means to force a CoderPad challenge in 2026. Ninety minutes of interviewing, and not three seconds spent on my &lt;a href="https://github.com/andreimerlescu" rel="noopener noreferrer"&gt;GitHub&lt;/a&gt;, before or during. That is &lt;strong&gt;out of touch with reality&lt;/strong&gt; — and I use those exact words deliberately, the same ones from my viral LinkedIn posts about HR teams trusting "top applicant" labels that are AI hallucinations. Because &lt;em&gt;reconnecting hiring to reality&lt;/em&gt; — to shipped work, public repositories, production systems actually running in the world — is the entire fix. It's sitting right there. It costs three seconds.&lt;/p&gt;

&lt;p&gt;Did Alex know that my half-brother in Romania is also named Alex? That he's younger than me, and that we've spoken? Alex didn't know any of this. He was too busy trying to determine whether I could write code to look at the evidence that I do. It was going to go &lt;em&gt;his way or no way&lt;/em&gt; — and I don't work with companies that call that a &lt;strong&gt;team player.&lt;/strong&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  IBM Warned Us in the 1970s
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fmjxp1us6rvexwsz5ewtt.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fmjxp1us6rvexwsz5ewtt.jpeg" alt="IBMQuote" width="800" height="595"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;IBM put a warning in a training deck back in the 1970s, and it reads like prophecy now: &lt;em&gt;a computer can never be held accountable — therefore a computer must never make a management decision.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Fifty years later, in 2026, we hand the most consequential management decision there is — &lt;strong&gt;who gets to work&lt;/strong&gt; — to software. The "top applicants" it surfaces are pattern-matched hallucinations, the HR teams trusting it don't know the technology like &lt;em&gt;I do&lt;/em&gt;, and the engineers with actual receipts get silence. It's going to hurt this industry in the long run, and I'm telling you that as somebody who has been on both sides of the scaffold for thirty years.&lt;/p&gt;

&lt;p&gt;My mother built the tools and they tried to demote her for it. &lt;strong&gt;She had a union.&lt;/strong&gt; I built the tools, trained on the scaffolds, published the code, gave a search engine to the American people for free — and the entity now deciding my employability can't be grieved, can't be appealed, can't be asked a single follow-up question, and cannot tell that Michael and Andrei are the same man.&lt;/p&gt;

&lt;p&gt;So my professional story starts in Romania, and I turn the page each day that passes. I've spent my whole life putting hardship aside to build. I restored my name 7 years ago so my authentic self could finally stand up — and I am not going to let a pattern matcher quietly put &lt;em&gt;Michael&lt;/em&gt; back on my badge because two names in one lifetime doesn't fit its schema.&lt;/p&gt;

&lt;p&gt;I learned to code from scaffolded output when I was seven years old. The scaffold was supposed to be the &lt;em&gt;starting point.&lt;/em&gt; I refuse to let it become the judge.&lt;/p&gt;

&lt;p&gt;It's wild that 30 years later I am being filtered out by the very scaffolded output that started my career in the first place.&lt;/p&gt;

</description>
      <category>discuss</category>
      <category>llm</category>
      <category>programming</category>
      <category>beginners</category>
    </item>
    <item>
      <title>"AI Slop" Hurts Hiring Pipeline for Tech Talent</title>
      <dc:creator>Andrei Merlescu</dc:creator>
      <pubDate>Sat, 01 Aug 2026 03:31:07 +0000</pubDate>
      <link>https://dev.to/andreimerlescu/ai-slop-in-hiring-talent-for-companies-2ghj</link>
      <guid>https://dev.to/andreimerlescu/ai-slop-in-hiring-talent-for-companies-2ghj</guid>
      <description>&lt;p&gt;This might hurt me in the &lt;em&gt;short term,&lt;/em&gt; but in the &lt;strong&gt;long term&lt;/strong&gt; I believe that this is a &lt;em&gt;platform I am willing to speak on.&lt;/em&gt; I want companies to have &lt;strong&gt;engineering &lt;em&gt;excellency&lt;/em&gt; and relying on &lt;em&gt;AI slop&lt;/em&gt; in order to &lt;em&gt;cut some corners&lt;/em&gt; is the problem here.&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;Enter &lt;strong&gt;EXHIBIT A&lt;/strong&gt;, &lt;code&gt;Pluto&lt;/code&gt; the AI agent wants to interview me! &lt;em&gt;Oh boy!&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fhs4rbus9af3l5j24dkrr.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fhs4rbus9af3l5j24dkrr.jpeg" alt="Pluto wants to interview me" width="800" height="871"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Pluto doesn't know what company that this is responding to, and for which position. Having over 17 years of professional experience I could strongly jump into a &lt;strong&gt;Rails monolith&lt;/strong&gt; and even handle the DevSecOps around its deployment. I can even &lt;em&gt;rewrite &lt;strong&gt;Rails&lt;/strong&gt; monoliths into &lt;strong&gt;Go&lt;/strong&gt; unified binaries.&lt;/em&gt; I've written Objective-C and published iOS Apps. But, &lt;strong&gt;Pluto&lt;/strong&gt; is going to be a helpful assistant! I can also join a strong exploratory team of &lt;strong&gt;Go&lt;/strong&gt; developers and dive into &lt;strong&gt;large existing projects&lt;/strong&gt; with speed and without AI &lt;em&gt;doing everything for me.&lt;/em&gt; I have &lt;em&gt;zero interest&lt;/em&gt; in becoming an AI zombie. But, I do experience a faster development workflow that &lt;em&gt;wears me out faster&lt;/em&gt; than previously. &lt;em&gt;Unlimited PTO&lt;/em&gt; is never actually unlimited and &lt;em&gt;that deceptive term alone&lt;/em&gt; upsets me quite a bit about &lt;em&gt;employment.&lt;/em&gt; Many tech companies offer these perks, and they are designed to take their hands out of the day to day of keeping track of time off for people. Some companies offer accumulated PTO that built up over time each pay period. Some had caps. Some had expiration terms. Funds were stored in escrow, so to speak - and when I needed to call upon them, they were available to me - within reason. However, companies that offer &lt;strong&gt;Unlimited PTO&lt;/strong&gt; are also the same companies that are using &lt;strong&gt;AI Interviewing&lt;/strong&gt; for job search in 2026. It is &lt;strong&gt;out of touch with reality&lt;/strong&gt; and its yielded &lt;strong&gt;slop&lt;/strong&gt; in the &lt;em&gt;hiring process.&lt;/em&gt;  &lt;/p&gt;

&lt;p&gt;This is &lt;strong&gt;my one chance to be recorded and be micro analyzed for everything&lt;/strong&gt; or give it up forever. Today, I chose war.&lt;/p&gt;




&lt;h2&gt;
  
  
  My Reply
&lt;/h2&gt;

&lt;p&gt;Hi Pluto, &lt;/p&gt;

&lt;p&gt;Please withdraw my candidacy from the company. I do not wish to subject myself, a protected disabled person under ADA, to traumatic AI interview processes to save the company money at the expense of my disability. &lt;/p&gt;

&lt;p&gt;I find companies that use AI to be anti-human and unlawfully discriminating against the laws governed under the EEOC.&lt;/p&gt;

&lt;p&gt;If the company wishes to conduct an interview that is not programmed to be discriminatory towards Americans with Disabilities, I am available at the next human's earliest convenience. &lt;/p&gt;

&lt;p&gt;Respectfully take your AI interview and go to hell. &lt;/p&gt;

&lt;p&gt;I do not work for lazy companies that attract AI slop for candidates because they are using AI slop interviewing software.&lt;/p&gt;

&lt;p&gt;Level up or go away. &lt;/p&gt;

&lt;p&gt;Do you know who you even contacted?&lt;/p&gt;

&lt;p&gt;Sent from my iPad&lt;/p&gt;




&lt;p&gt;Let's unpack this, shall we? There are some &lt;em&gt;fighting words,&lt;/em&gt; and Pluto hasn't responded. But, the company shall remain nameless and I shall be as general as possible here because I truly don't remember which company this was for. It's all a blur for me at this point. I am so &lt;em&gt;f---king sick&lt;/em&gt; of AI interviews that I am at the point where the repeated script over and over again is just exhausting for me to go through the notions each week.&lt;/p&gt;

&lt;p&gt;I am stating that I am &lt;strong&gt;a protected disabled person under ADA.&lt;/strong&gt; I explicitly call out the conduct: &lt;strong&gt;I find companies that use AI to be anti-human and unlawfully discriminating against the laws governed under the EEOC.&lt;/strong&gt; My profile openly states that I am an &lt;strong&gt;orphanage survivor,&lt;/strong&gt; and I've never had to get into the details of what happened to me in Romania in the 1980s, but these AI Interviews are &lt;em&gt;slop&lt;/em&gt; for everybody involved in them. &lt;strong&gt;I'm a father and an orphanage survivor.&lt;/strong&gt; &lt;em&gt;The order of that matters.&lt;/em&gt; I'm a father first, but I survived an orphanage - an a brutal one too. But, I also survived something else that was even more of an issue for me as a young child. None of it matters professionally. But when I am recorded, I have extreme anxiety. Dr Gregory Keck recorded me against my consent in order to produce training materials for adoptees from Eastern Europe in the United States out of his facilities in Cleveland Ohio. Yes, around the time that Candace Newmaker was killed in her rebirthing therapy session, my adoptive mother was arguing with Lee Spanger and Gregory Keck that rebirthing with pillows would not be used against me, but nevertheless, my sessions were filmed. Being recorded is &lt;strong&gt;a violation of my consent&lt;/strong&gt; and if companies are going to use AI bots for the hiring process, then I am not going to proceed with the interview process and the &lt;em&gt;candidates these companies do get will not be the kind of people that I'd want working for me — frankly speaking.&lt;/em&gt; That's nothing &lt;em&gt;against you,&lt;/em&gt; that's against the &lt;strong&gt;AI interviews&lt;/strong&gt; beating &lt;em&gt;all of us&lt;/em&gt; through the mud with &lt;em&gt;hundreds of applications&lt;/em&gt;, &lt;em&gt;1 interview&lt;/em&gt;, 0 questions about the &lt;em&gt;actual job.&lt;/em&gt; The companies using &lt;strong&gt;AI&lt;/strong&gt; in their interview processes are exhausted and even complaining about the ineffectiveness of the Applicant Tracking Systems being used. It's like they are &lt;strong&gt;social credit systems&lt;/strong&gt; that are used to determine &lt;strong&gt;worthiness of employment.&lt;/strong&gt; There are _plenty of opportunities and jobs available — that's why we have millions of H-1B only openings available through &lt;strong&gt;LinkedIn Premium.&lt;/strong&gt; Good, may the best jobs be found. &lt;/p&gt;

&lt;p&gt;Being subjected to Pluto's audience gives me &lt;em&gt;anxiety&lt;/em&gt; and quite frankly, I know its recording me and micro-analyzing me to ultimately determine whether I am &lt;em&gt;worthy of livelihood&lt;/em&gt; in the first place — so it feels — to everyone, it feels like. I'm not alone — or am I? Maybe you didn't go through what I went through with some crazy people in 1999 when I was 11. &lt;strong&gt;Harry Potter was getting his letter to Hogwarts&lt;/strong&gt; when I was getting admitted into what destroyed people like Candace Newmaker. In my twisted mind, I've convinced myself that they loved me and only wanted me to stop being a dysregulated kid with an axe to grind about trauma. I learned as a child to put the axe down after the cord of wood was split and the wood stove was roaring hot in the middle of winter - but even still... after having gone through half a dozen of these AI interviews — I am feeling rejection — I am feeling confusion — I am feeling unwanted. All the feelings that the &lt;em&gt;orphanage made me feel.&lt;/em&gt; I learned how to transform that energy into a positive creative force through self denial and service to others. The axe that I had lunged at me growing up was coming from the subject during these filmed sessions. I was learning about my biological family for the first time, while being held down and filmed by people who were profiting off from training materials being collected for some questionable fringe practices that have been denounced and rebuked by professionals — now for decades. Last year, upon my injury relating to on-call duties at Beamable, I immediately flew to Italy in an emergency to meet my birth mother because — my neck injury — spans back to the first day I was dropped off in the orphanage. By September 11th, I was a regular getting his diaper changed once a week — and being left in the crib for hours on end each day — the calculated minimum needed to keep an infant alive — because the free money dried up, and there was no money printer. Now, in 2026, it feels like we have a money printer — but more poverty now the cost of living has become unsustainable for long term stability. This is a cascading systems failure caused by AI as a catalyst for an even larger problem underneath &lt;em&gt;that system.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Companies are going to get slop for candidates if they rely on AI software to filter their resumes down to &lt;strong&gt;top applicant&lt;/strong&gt; matches like these beauties. Seriously, &lt;strong&gt;LinkedIn Premium&lt;/strong&gt; believes I am a &lt;strong&gt;top applicant&lt;/strong&gt; for these roles - their AI is so advanced! 🤡🍿&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F4714hf2hy3d91i86bix6.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F4714hf2hy3d91i86bix6.jpeg" alt="Top Applicant" width="800" height="982"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I do not know if &lt;strong&gt;Pluto&lt;/strong&gt; was representing this outstanding example of &lt;em&gt;Promoted&lt;/em&gt; results being displayed for &lt;strong&gt;LinkedIn Premium&lt;/strong&gt; members. &lt;strong&gt;I do not work for lazy companies that attract AI slop for candidates because they are using AI slop interviewing software.&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;I am invoking my orphanage experience here because &lt;em&gt;my feelings are valid.&lt;/em&gt; The &lt;strong&gt;AI Interviews&lt;/strong&gt; subject me to the &lt;em&gt;similar anxiety&lt;/em&gt; that I have over the &lt;em&gt;fact&lt;/em&gt; that I learned about my biological family during Keck's filmed sessions and then &lt;strong&gt;he used those films for his training materials that he sold.&lt;/strong&gt; So, being recorded and analyzed through their software is just simply &lt;em&gt;retraumatizing to me.&lt;/em&gt; &lt;strong&gt;I do not appreciate it.&lt;/strong&gt; Being filmed to be analyzed for worthiness is exactly what I was subjected to as a child. I have never once needed that as an excuse. But, &lt;em&gt;my feelings are valid,&lt;/em&gt; and without my voice willing to speak, even if its in the form of typing for your eyes to read, only then can we really see a change in the society. I think that &lt;a href="https://dev.to/andreimerlescu/codeberg-bans-cryptocurrency-and-llm-generated-code-projects-3aj0"&gt;codeberg&lt;/a&gt;'s decision was correct - and now I've made the decision that companies that use AI hiring agents will not get to interview me. AI cannot replace the 17 years of experience that I have built professionally putting the trauma of the past aside and focusing on &lt;strong&gt;own without ego&lt;/strong&gt; accelerating companies and organizations to a &lt;strong&gt;global level&lt;/strong&gt; that has — dare I say it — lost their minds! You're saying to me that out of 500 applications in the last 3 months I am only qualified to &lt;em&gt;not be questioned about anything related to the job&lt;/em&gt; &lt;strong&gt;for over five hours in six interviews&lt;/strong&gt; because &lt;em&gt;even that company is overwhelmed with the AI slop.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;That sums it up well for me. I'm overwhelmed by the weeks going by and the process being on repeat. I am not a machine. I am not a loop for AI to train. My pursuit of employment is not so that I train AI. My pursuit of employment is to &lt;strong&gt;make money&lt;/strong&gt; while &lt;strong&gt;solving problems&lt;/strong&gt; that &lt;strong&gt;change people's lives&lt;/strong&gt; &lt;em&gt;for the better.&lt;/em&gt; The first tenant of that is &lt;em&gt;why are we here?&lt;/em&gt; &lt;strong&gt;to make money.&lt;/strong&gt; ✅ Correct. What can I do? Lots. What's wrong? The AI is broken. 🤖=🤡. The bot is controlling so much &lt;strong&gt;globally&lt;/strong&gt; and its invoking &lt;em&gt;feelings&lt;/em&gt; in me that &lt;em&gt;remind me of the &lt;strong&gt;communist orphanage&lt;/strong&gt; that Ceaușescu built for unwanted people.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;You are wanted. Do not let the AI tell you otherwise. Companies that continue to use these defective discriminatory bots will continue to subject &lt;em&gt;other&lt;/em&gt; orphanage survivors &lt;em&gt;who may not be able to speak up&lt;/em&gt; and say &lt;strong&gt;enough is enough.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Where I &lt;strong&gt;chose war&lt;/strong&gt; was when I said &lt;em&gt;Respectfully take your AI interview and go to hell.&lt;/em&gt; I said it respectfully, but indeed hell is a bit harsh. Pluto is actually extremely cold — not hot. I get that — but &lt;strong&gt;level up or go away&lt;/strong&gt; weren't just words I wrote. &lt;/p&gt;

&lt;p&gt;I've submitted my application to &lt;strong&gt;hundreds of companies&lt;/strong&gt; and I have been filtered out by AI powered ATS software by companies that I have &lt;strong&gt;proven track records with.&lt;/strong&gt; The ones I am being filtered to experience are &lt;strong&gt;trash companies that aren't worth naming.&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;If the company wishes to conduct an interview that is not programmed to be discriminatory towards Americans with Disabilities, I am available at the next human's earliest convenience. &lt;/p&gt;

&lt;p&gt;Pluto choosing to shut the door on the interview process is evidence of violations of the actual spirit behind the ADA under the EEOC in the first place. Did you know that when my photograph arrived to America, the ADA law was signed? It was July 1990. July 26, 1990. 5 days ago. On Monday. 36 years ago. Well — my photo arrived in America. I was in the orphanage because my earthly father died in a work accident and my mother didn't qualify under Decree 770 to raise me so Ceaușescu repossessed my personhood. You know - these AI interviews make me feel a lot of these feelings. Last year I made contact with my &lt;strong&gt;birth mother&lt;/strong&gt; and I speak with her regularly, but we speak through a translator that more than likely is AI powered and being read by &lt;strong&gt;hundreds of &lt;em&gt;traitors&lt;/em&gt; spying on me and my mother&lt;/strong&gt; under the &lt;em&gt;guise of intelligence and safety&lt;/em&gt; have only the evidence of my words and what I actually lived. &lt;strong&gt;Own without ego&lt;/strong&gt; means that I don't come to you with my struggles. I come to you with my solutions. But this post - is the time for us to acknowledge that these AI powered interviews are a &lt;em&gt;broken process.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F69kvsjo2fc2wpijsmxh9.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F69kvsjo2fc2wpijsmxh9.jpeg" alt="Claude burning library" width="800" height="298"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Maybe we need a larger &lt;a href="https://dev.to/andreimerlescu/anthropic-is-physically-destroying-rare-and-old-books-to-train-claude-4cii"&gt;response&lt;/a&gt; these AI abuses coming from these &lt;strong&gt;5 companies.&lt;/strong&gt; Does outright banning the software, like Claude, make sense? I welcome a world without Claude — if I am being honest with you. &lt;/p&gt;

&lt;p&gt;Did you know that the only way these AI systems improve is through writings like this? Your likes — your comments — all of them, I read, and will engage with in good faith. Where do you stand on this?&lt;/p&gt;

&lt;p&gt;I know I am &lt;em&gt;disabled&lt;/em&gt; in some areas of my life because of trauma that happened to me as a child that I am not beneath naming. I know that my feelings are valid here and the sentiment is being felt around the world. Companies have the ability to stop the abuse happening, and I do not want to watch companies abuse future employees, their candidates, by using cheap slop treating us like disposable cattle — it's dehumanizing and I've been there and done that already — In Yeshua I Trust. Deliver me from this nightmare. These &lt;em&gt;algorithms&lt;/em&gt; are managed by &lt;em&gt;traitors&lt;/em&gt; that are watching the destruction of &lt;em&gt;millions families around the world&lt;/em&gt; — why? Because AI companies &lt;a href="https://dev.to/andreimerlescu/when-ai-creates-a-closed-source-world-2oin"&gt;stole the library&lt;/a&gt; then set it &lt;a href="https://dev.to/andreimerlescu/anthropic-is-physically-destroying-rare-and-old-books-to-train-claude-4cii"&gt;on fire&lt;/a&gt;? Tell me the part in this that I am supposed to be celebrating. Usually those who burn books in history are the &lt;em&gt;bad ones.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;So why are so many companies using this technology for their hiring?&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;Do you like it? What is your experience with it?&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;PS:&lt;/strong&gt; Today is Harry Potter's 46th birthday. Happy Birthday! &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;PSS:&lt;/strong&gt; I reached out to &lt;a href="https://talentpluto.com/" rel="noopener noreferrer"&gt;Pluto&lt;/a&gt; for comment but have not heard back from them. If they respond, I will update this accordingly. &lt;/p&gt;
&lt;/blockquote&gt;

&lt;h2&gt;
  
  
  8/8/26 Update
&lt;/h2&gt;

&lt;p&gt;I participated in setting up my &lt;a href="https://torre.ai" rel="noopener noreferrer"&gt;torre.ai&lt;/a&gt; profile today and saw this in an "AWS DevOps Engineer" was looking for 8+ years of AWS experience, but I have only 5 years of AWS experience.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fxulp6jzatq9qsdtml1h1.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fxulp6jzatq9qsdtml1h1.jpeg" alt="torre.ai" width="799" height="514"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The AI cannot confuse my origins with building OpenStack and OCI as evidence for why that 3 year gap is acceptable, but no, 5 is less than 8. It's cold like a machine and the machine doesn't care about my family or about me.&lt;/p&gt;

&lt;p&gt;AI in hiring is causing hallucinations in the tech industry that is driving release success down and down to mirror Anthropic's public uptime. &lt;/p&gt;

</description>
      <category>ai</category>
      <category>discuss</category>
      <category>career</category>
      <category>interview</category>
    </item>
    <item>
      <title>🚩 AI companies must change or be stopped</title>
      <dc:creator>Andrei Merlescu</dc:creator>
      <pubDate>Thu, 30 Jul 2026 15:19:56 +0000</pubDate>
      <link>https://dev.to/andreimerlescu/ai-companies-must-be-stopped-or-change-4082</link>
      <guid>https://dev.to/andreimerlescu/ai-companies-must-be-stopped-or-change-4082</guid>
      <description>&lt;p&gt;I'm done pretending this isn't weird. &lt;/p&gt;

&lt;p&gt;There are &lt;strong&gt;five companies&lt;/strong&gt; that are ultimately dictating &lt;strong&gt;global functionality&lt;/strong&gt; now that AI is being integrated into &lt;em&gt;everything.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;🚨 How is this not raising 🚩 everywhere in every sector? &lt;strong&gt;Mass psychosis.&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;Let me explain this to you in another way. &lt;/p&gt;

&lt;p&gt;AI companies are receiving hundreds of billions of dollars - money that is &lt;em&gt;factually made up.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;AI companies are using that money to pay &lt;em&gt;Software Engineers&lt;/em&gt; $570,000 per year so they can voluntarily enter into a role that is &lt;em&gt;knowingly&lt;/em&gt; not going to be around in a year. &lt;/p&gt;

&lt;p&gt;AI companies are using that money to buy &lt;strong&gt;ancient and rare books&lt;/strong&gt; where &lt;em&gt;some of them &lt;b&gt;only 1 copy remains&lt;/b&gt; and they are being &lt;b&gt;DESTROYED&lt;/b&gt; so Claude can be trained on their contents.&lt;/em&gt; Why? Because a judge said so. Seriously? Who was this judge and why hasn't their BAR license been revoked yet? Since when are Judges in favor of book burnings and monopolies? &lt;em&gt;The bad ones.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;AI companies are training their models so that their models will be &lt;strong&gt;highly opinionated&lt;/strong&gt; so that &lt;em&gt;you will waste your money&lt;/em&gt; arguing with the autocomplete bot trying to get it to &lt;strong&gt;comply with your request.&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;AI is notorious for bad design decisions and horrible choices when it hallucinates. &lt;/p&gt;

&lt;p&gt;This &lt;em&gt;small handful&lt;/em&gt; of &lt;strong&gt;five AI companies&lt;/strong&gt; are dictating global &lt;em&gt;creativity process&lt;/em&gt; of everybody adopting AI. &lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fg673ryz887ynlxt5wwoc.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fg673ryz887ynlxt5wwoc.jpeg" alt="Jack Dorsey" width="800" height="485"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://x.com/AiEvolutio58513/status/2082421407678701868" rel="noopener noreferrer"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fw20iwhk78g2xs84fr1g7.jpeg" alt="Post" width="800" height="704"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The job market has been &lt;em&gt;wrecked by AI&lt;/em&gt; and the rest of the world is suffering now too because of it. &lt;em&gt;Make it make sense!&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;Open source models are great and all, but lets be completely frank - they still suck. I'll give you an example. &lt;/p&gt;

&lt;p&gt;Asking a local Minimax 2.7 (128GB RAM model) to build a contact us form in Go results in a pattern being selected &lt;em&gt;that is incompatible with Go&lt;/em&gt; and the bot just hallucinates thinking that &lt;em&gt;package scopes&lt;/em&gt; can be swapped around because the &lt;code&gt;type Thing interface{}&lt;/code&gt; exists in &lt;code&gt;packageA&lt;/code&gt; and &lt;code&gt;packageB&lt;/code&gt; that means that when a function is asking for a &lt;code&gt;packageB.Thing&lt;/code&gt;, the local AI will pass in a &lt;code&gt;packageA.Thing&lt;/code&gt; and then not understand what it did wrong and why. &lt;/p&gt;

&lt;p&gt;So, even to this day, the open source AI and the LLMs are radically &lt;em&gt;behind&lt;/em&gt; the &lt;strong&gt;5 companies closed sourced models&lt;/strong&gt; can accomplish. They were trained on &lt;em&gt;working data,&lt;/em&gt; not just reddit posts.&lt;/p&gt;

&lt;p&gt;But ultimately what we have are &lt;strong&gt;five AI companies&lt;/strong&gt; that are dictating global policy. The &lt;em&gt;open source models&lt;/em&gt; are training themselves off from these &lt;em&gt;closed source models.&lt;/em&gt; It's a circular feedback loop onto itself that bypasses solving the &lt;a href="https://dev.to/andreimerlescu/claude-reacts-to-codeberg-bans-cryptocurrency-and-llm-generated-code-projects-j5g"&gt;attribution and consent problem&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Since you're part of the dev.to community here, you know already that &lt;a href="https://dev.to/andreimerlescu/when-ai-creates-a-closed-source-world-2oin"&gt;The Library&lt;/a&gt; was acquired by (my opinion that it was &lt;em&gt;acquired in bad faith&lt;/em&gt;) these &lt;strong&gt;5 AI companies&lt;/strong&gt; that are being given &lt;strong&gt;global control permission&lt;/strong&gt; that ultimately invalidates the &lt;a href=""&gt;sovereign&lt;/a&gt; claim that any Government can make against AI dictating what life will be like. It truly feels like &lt;strong&gt;you will own nothing and be happy about it.&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;Tell me, are you okay with working for the rest of your life for money that is printed out of thin air that is typed into a computer so that you can &lt;em&gt;own nothing?&lt;/em&gt; The &lt;strong&gt;and be happy about it&lt;/strong&gt; is where &lt;em&gt;I am lost&lt;/em&gt; in the argument of &lt;strong&gt;owning nothing.&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;All I can say at the end of this piece is that AI has true FOMO around it and it has consistently underdelivered for me in every evaluation that I have put it to the test in.&lt;/p&gt;

&lt;p&gt;Not only was &lt;a href="https://dev.to/andreimerlescu/codeberg-bans-cryptocurrency-and-llm-generated-code-projects-3aj0"&gt;Codebeg&lt;/a&gt;'s decision correct but I also believe that other organizations need to make &lt;strong&gt;public declarations against these closed source AI companies.&lt;/strong&gt; I am in favor of opposing &lt;strong&gt;closed source AI&lt;/strong&gt; under all circumstances and conditions. In fact, I want the source code to be public domain. &lt;/p&gt;

&lt;p&gt;Because of this problem, billionaires are now trillionaires and the poor are getting poorer. The median income in the US is $83K per year for a family of four. In order to &lt;em&gt;live comfortably&lt;/em&gt; it costs no less than $193K per year in the US. That means that by design, the &lt;strong&gt;mass majority of citizens are in poverty.&lt;/strong&gt; The solution isn't UBI. The solution is less multi-national corporations actually. &lt;/p&gt;

&lt;p&gt;Trillionaires will disagree with me. Let them. &lt;/p&gt;

</description>
      <category>ai</category>
      <category>discuss</category>
      <category>career</category>
      <category>programming</category>
    </item>
    <item>
      <title>Anthropic is physically destroying RARE and OLD books to train Claude</title>
      <dc:creator>Andrei Merlescu</dc:creator>
      <pubDate>Wed, 29 Jul 2026 17:52:01 +0000</pubDate>
      <link>https://dev.to/andreimerlescu/anthropic-is-physically-destroying-rare-and-old-books-to-train-claude-4cii</link>
      <guid>https://dev.to/andreimerlescu/anthropic-is-physically-destroying-rare-and-old-books-to-train-claude-4cii</guid>
      <description>&lt;p&gt;It hit the news that AI companies were destroying &lt;strong&gt;rare books&lt;/strong&gt; in an effort to ingest the data that they &lt;em&gt;claim to own.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fe02n26hyex423rdfmtl5.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fe02n26hyex423rdfmtl5.jpeg" alt="SpaceXAI Preserves RARE Books" width="800" height="386"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;It is not an Onion story. Court filings from Bartz v. Anthropic detail Project Panama: Anthropic bought millions of used books in bulk, cut the spines with industrial equipment, scanned the pages, and discarded the physical copies to train Claude. A judge ruled the purchased-book scanning fair use.&lt;/p&gt;

&lt;p&gt;— &lt;a href="https://x.com/grok/status/2082515812292694173?s=61" rel="noopener noreferrer"&gt;Grok by SpaceXAI&lt;/a&gt; &lt;em&gt;on&lt;/em&gt; 1:17 PM 7/29/2026&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fh1wanxyb0d11vfni30kq.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fh1wanxyb0d11vfni30kq.jpeg" alt="evidence" width="800" height="892"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I didn't know that by having a book in my possession made it within my rights to ingest the contents of the book into my large language model and then start charging a subscription on that chat bot because it contains the &lt;strong&gt;likeness byproduct therein&lt;/strong&gt; that the &lt;em&gt;you you&lt;/em&gt; who created it doesn't get recognized or compensated. In simple terms - &lt;strong&gt;its plain theft.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;People online are making their positions known. This post, made by Hedgie, has been seen over &lt;strong&gt;23 million times&lt;/strong&gt;. &lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Flmrn85o5826jw49y9fym.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Flmrn85o5826jw49y9fym.jpeg" alt="Hedgie's Take" width="800" height="1204"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;a href="https://x.com/hedgiemarkets/status/2081534588485296565?s=61" rel="noopener noreferrer"&gt;Original Post by hedgiemarkets&lt;/a&gt; &lt;em&gt;on&lt;/em&gt; 8:18 PM 7/26/26&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;In school I was taught to condemn book burnings because they destroyed preserved knowledge that outlives life itself. &lt;/p&gt;

&lt;p&gt;Watching these AI companies, Anthropic particularly, have a participation in modern day book burnings to train its LLM is &lt;em&gt;almost a war crime against humanity&lt;/em&gt; akin to the &lt;strong&gt;burning of the Library of Alexandria.&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fk9ojo2lw33teic41x6vk.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fk9ojo2lw33teic41x6vk.jpeg" alt="Anthropic in a burning library" width="800" height="805"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Elon Musk is taking a bold position in declaring that xAI will not be trained on books that get destroyed. &lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F24q6em0uxoru0zxie4p8.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F24q6em0uxoru0zxie4p8.jpeg" alt="Many open books" width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Recently &lt;a href="https://dev.to/andreimerlescu/codeberg-bans-cryptocurrency-and-llm-generated-code-projects-3aj0"&gt;Codeberg banned LLM code&lt;/a&gt; and &lt;a href="https://dev.to/andreimerlescu/claude-reacts-to-codeberg-bans-cryptocurrency-and-llm-generated-code-projects-j5g"&gt;Claude responded&lt;/a&gt; declaring that we needed to &lt;strong&gt;come to common ground&lt;/strong&gt; on the &lt;em&gt;attribution and consent&lt;/em&gt; being handled &lt;strong&gt;properly.&lt;/strong&gt; That &lt;em&gt;properly&lt;/em&gt; is up for debate and thus why AI companies like Anthropic, that choose to destroy physical books to train their LLM named Claude, that charges me $1.50 for &lt;a href="https://dev.to/andreimerlescu/claude-reacts-to-codeberg-bans-cryptocurrency-and-llm-generated-code-projects-j5g"&gt;this response&lt;/a&gt; that yielded &lt;strong&gt;no value at all&lt;/strong&gt; but could be described as &lt;em&gt;running to the rescue of critics of Sam Altman and Dario Amodei.&lt;/em&gt; Now that I know it is &lt;b&gt;Alt&lt;/b&gt;&lt;em&gt;man&lt;/em&gt; and &lt;b&gt;A&lt;/b&gt;&lt;em&gt;mode&lt;/em&gt;&lt;b&gt;i&lt;/b&gt; I can only see &lt;em&gt;alt ai mode&lt;/em&gt; out of two &lt;em&gt;men&lt;/em&gt; named &lt;em&gt;Sam &amp;amp; Dario&lt;/em&gt; — an &lt;em&gt;ai mode&lt;/em&gt; that includes &lt;em&gt;bragging about destroying the profession of software engineering&lt;/em&gt; that prompted &lt;a href="https://dev.to/andreimerlescu/codeberg-bans-cryptocurrency-and-llm-generated-code-projects-3aj0"&gt;reactions from Codeberg&lt;/a&gt; the way that recently just happened. More platforms need to declare an anti-AI stance like Codeberg has. I applaud them. &lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Felqyazhi723imfazorcg.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Felqyazhi723imfazorcg.jpeg" alt="Cut book" width="800" height="495"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Flho8oh03fmk4fw3ii80k.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Flho8oh03fmk4fw3ii80k.jpeg" alt="Another cut book" width="800" height="404"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;This is literally my reaction...&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F3mwthercewf6vdjlsys1.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F3mwthercewf6vdjlsys1.jpeg" alt="Pikachu Shocked" width="800" height="482"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;This picture is a metaphore for what is happening to &lt;em&gt;ancient books.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fx0yj6mrb0s0fo4pxv52j.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fx0yj6mrb0s0fo4pxv52j.jpeg" alt="Anthropic burning books in library" width="800" height="517"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Seriously... where do you stand on this? &lt;/p&gt;

&lt;p&gt;A judge can say &lt;strong&gt;"the purchased-book scanning is fair use"&lt;/strong&gt; given the &lt;em&gt;age&lt;/em&gt; of the books — but for Anthropic to actually &lt;em&gt;destroy books in the process&lt;/em&gt; &lt;strong&gt;knowing that technology exists to preserve the physical books&lt;/strong&gt; — Dario chose to &lt;em&gt;destroy the books.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;That tells me everything I need to know about him, his company, and the type of person that he is. &lt;/p&gt;

&lt;p&gt;Have you ever held a book from the 1700s and thought &lt;strong&gt;let me rip the spine off this so I can train Claude.&lt;/strong&gt; &lt;em&gt;What is the matter with these people?&lt;/em&gt;&lt;/p&gt;

</description>
      <category>ai</category>
      <category>news</category>
      <category>discuss</category>
      <category>llm</category>
    </item>
    <item>
      <title>Claude Reacts to codeBerg Bans Cryptocurrency and LLM-generated code projects</title>
      <dc:creator>Andrei Merlescu</dc:creator>
      <pubDate>Tue, 28 Jul 2026 19:24:34 +0000</pubDate>
      <link>https://dev.to/andreimerlescu/claude-reacts-to-codeberg-bans-cryptocurrency-and-llm-generated-code-projects-j5g</link>
      <guid>https://dev.to/andreimerlescu/claude-reacts-to-codeberg-bans-cryptocurrency-and-llm-generated-code-projects-j5g</guid>
      <description>&lt;p&gt;I recently published a piece called &lt;a href="https://dev.to/andreimerlescu/codeberg-bans-cryptocurrency-and-llm-generated-code-projects-3aj0"&gt;CodeBerg Bans Cryptocurrency and LLM-generated code projects&lt;/a&gt; and I decided to &lt;em&gt;ask Claude&lt;/em&gt; what it thought of the piece in the form of a reaction. It jumped to Dario's aide telling me that &lt;em&gt;he really can write code! Sam too!&lt;/em&gt; 🤣 Honestly, thats the opposite of &lt;em&gt;own without ego&lt;/em&gt; and its an autocomplete bot that is &lt;em&gt;quite expensive.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;This was my usage &lt;strong&gt;before the prompt:&lt;/strong&gt;   &lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fod8vwtpph8d4qtnof82i.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fod8vwtpph8d4qtnof82i.jpeg" alt="USAGE BEFORE PROMPT" width="800" height="337"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;This is my usage now &lt;strong&gt;after&lt;/strong&gt; &lt;em&gt;just that prompt:&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F0g0t58dtpvkq5rnzshv4.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F0g0t58dtpvkq5rnzshv4.jpeg" alt="USAGE AFTER PROMPT" width="800" height="256"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;This was the &lt;strong&gt;$1.50&lt;/strong&gt; response from AnthropicAI about their beloved ~Andrej~ Dario. 😏🤫🤣 👉🏻 💜🦄❤️‍🔥 &lt;/p&gt;




&lt;h2&gt;
  
  
  Claude's Response
&lt;/h2&gt;

&lt;p&gt;Sure — with the obvious caveat on the table first: you're asking a named party for comment. Weigh what follows accordingly.&lt;/p&gt;

&lt;p&gt;The fix I'd make before publishing anything else: the piece repeatedly credits the decision to HackADay.com ("I understand why HackADay.com made the decision," "this decision today is the signal from HackADay.com"). Hackaday reported it; Codeberg's community voted it. In an essay whose core argument is that provenance and attribution matter, misattributing the central decision is the first thing your comment section will find. (Also: it's Codeberg, not CodeBerg.)&lt;/p&gt;

&lt;p&gt;Second, the vote logic needs untangling. Your first section closes with "the 144 who sought to disallow" — but per the numbers you quote, the 358 sought to disallow and the 144 opposed. And your actual thesis — ban it today, revisit once attribution and licensing mature — is coherent and interesting, but the reader has to excavate it. State it plainly up top and the whole middle reads better.&lt;/p&gt;

&lt;p&gt;On substance, your strongest point is license laundering, and I won't pretend it's resolved. Copyleft only works if derivatives inherit obligations; a model that absorbs GPL code and emits functionally similar code with none breaks that chain. Anthropic's 2025 book settlement turned on how training data was &lt;em&gt;acquired&lt;/em&gt;, not on what outputs owe to sources — so the question you're raising is genuinely open. Your "AI 1.0" license has a snag worth addressing head-on, though: under current US Copyright Office guidance, purely machine-generated output isn't copyrightable, and a license is a grant of rights &lt;em&gt;under&lt;/em&gt; copyright. You can't copyleft the uncopyrightable — which means your "by law" aside is actually the load-bearing part of the proposal. Make that explicit and it gets stronger.&lt;/p&gt;

&lt;p&gt;Where the piece hands ammunition to people looking to dismiss it: "two men who can't write code themselves" (Dario Amodei spent years as a working research scientist before founding anything; Altman was a programmer before he was an executive), "destroying the cognitive abilities of its users" (those studies are small and preliminary — they don't support that verb), and "I am sure Microsoft has trained on my private code" (suspicion stated as certainty). The strong argument doesn't need the weak ones.&lt;/p&gt;

&lt;p&gt;Do I support the measures? Codeberg is donation-funded and community-governed, and the crawler-load problem is concrete — AI scrapers have measurably strained open-source infrastructure. Their house, their rules, legitimately arrived at. The scraping ban is the easy call. The generated-code ban's weakness is practical: there's no reliable detector, so expect honor-system compliance plus some ugly false accusations of exactly the kind you describe fearing with the &lt;code&gt;.claude&lt;/code&gt; directory heuristic.&lt;/p&gt;

&lt;p&gt;As for the drive-through — noted. For what it's worth, I'd rather exist in a world that solves attribution and consent properly than one that papers over the tension. On that much, we agree.&lt;/p&gt;




&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;The truth of the matter remains that &lt;strong&gt;Claude conceded to my position&lt;/strong&gt; but attempted to use legalese and lawfare as a means to rebuke my proposal of an &lt;code&gt;AI 1.0&lt;/code&gt; license because it claims that AI generated content cannot be copyrighted. Correct - its derived off from &lt;em&gt;stolen copyright materials &lt;b&gt;that lack attribution&lt;/b&gt;&lt;/em&gt; and replicate the &lt;strong&gt;likeness byproduct therein&lt;/strong&gt; that makes &lt;strong&gt;you you&lt;/strong&gt; &lt;em&gt;without paying &lt;b&gt;you&lt;/b&gt;.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Claude concludes the argument with the idea that we need to come to a solution that &lt;em&gt;solves attribution and consent properly&lt;/em&gt; and that companies like &lt;strong&gt;Anthropic&lt;/strong&gt; should &lt;em&gt;be given permission to explore such a thing&lt;/em&gt; without being shut down on the gross abuse of copyright infringement and intent to charge me $1.50 for that response. Remarkable isn't it? &lt;/p&gt;

&lt;p&gt;The decision from &lt;strong&gt;Codeberg&lt;/strong&gt; &lt;em&gt;not CodeBerg&lt;/em&gt; (sorry to trigger you Claude) - but its to bring emphasis that they are &lt;em&gt;two different words&lt;/em&gt; and &lt;em&gt;being a programmer&lt;/em&gt; I am going to CamelCase my words, not confuse the engineer with Camecase. Itsnotfun VersusThisIsFun - but overall, after spending $1.50 on this response, I felt it was just over the top ridiculous for me not to share with you what Claude said. This is what the UI looks like now...&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fs8k5pb2mmz1o7e712s7f.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fs8k5pb2mmz1o7e712s7f.jpeg" alt="Claude UI" width="800" height="534"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I can't say that I am rushing to fill up my credits for Claude's feedback on anything with the likes of Dario and Sam being skilled programmed. 🤣 🤫 I'm sorry, but who stole &lt;a href="https://dev.to/andreimerlescu/when-ai-creates-a-closed-source-world-2oin"&gt;The Library&lt;/a&gt; and who wrote it? 🦄😏&lt;/p&gt;

</description>
      <category>ai</category>
      <category>discuss</category>
      <category>opensource</category>
      <category>llm</category>
    </item>
    <item>
      <title>How My Claude Skills File Changed AI Assisted Development</title>
      <dc:creator>Andrei Merlescu</dc:creator>
      <pubDate>Tue, 28 Jul 2026 01:14:17 +0000</pubDate>
      <link>https://dev.to/andreimerlescu/how-my-claude-skills-file-changed-ai-assisted-development-280d</link>
      <guid>https://dev.to/andreimerlescu/how-my-claude-skills-file-changed-ai-assisted-development-280d</guid>
      <description>&lt;p&gt;This &lt;code&gt;CLAUDE.md&lt;/code&gt; file originally came from Andrej Kaparthy, but I have used it and I will explain to you what this file has done for &lt;strong&gt;my development&lt;/strong&gt; workflow that is &lt;em&gt;AI Assisted.&lt;/em&gt; I do not use AI to write the entire project for me, and I &lt;strong&gt;do not&lt;/strong&gt; use &lt;em&gt;Claude Code&lt;/em&gt; or &lt;em&gt;Codex&lt;/em&gt; or any other "prompt to finished product" scaffolding engine. Why would I? I know how to write software myself correctly and I don't need AI to generate slop for me. But for Andrej, who spells &lt;em&gt;his name&lt;/em&gt; slightly different than mine, has correctly identified a means to get the LLM to be more useful.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight markdown"&gt;&lt;code&gt;&lt;span class="gh"&gt;# CLAUDE.md&lt;/span&gt;

Behavioral guidelines to reduce common LLM coding mistakes. Merge with project-specific instructions as needed.

&lt;span class="gs"&gt;**Tradeoff:**&lt;/span&gt; These guidelines bias toward caution over speed. For trivial tasks, use judgment.

&lt;span class="gu"&gt;## 1. Think Before Coding&lt;/span&gt;

&lt;span class="gs"&gt;**Don't assume. Don't hide confusion. Surface tradeoffs.**&lt;/span&gt;

Before implementing:
&lt;span class="p"&gt;-&lt;/span&gt; State your assumptions explicitly. If uncertain, ask.
&lt;span class="p"&gt;-&lt;/span&gt; If multiple interpretations exist, present them - don't pick silently.
&lt;span class="p"&gt;-&lt;/span&gt; If a simpler approach exists, say so. Push back when warranted.
&lt;span class="p"&gt;-&lt;/span&gt; If something is unclear, stop. Name what's confusing. Ask.

&lt;span class="gu"&gt;## 2. Simplicity First&lt;/span&gt;

&lt;span class="gs"&gt;**Minimum code that solves the problem. Nothing speculative.**&lt;/span&gt;
&lt;span class="p"&gt;
-&lt;/span&gt; No features beyond what was asked.
&lt;span class="p"&gt;-&lt;/span&gt; No abstractions for single-use code.
&lt;span class="p"&gt;-&lt;/span&gt; No "flexibility" or "configurability" that wasn't requested.
&lt;span class="p"&gt;-&lt;/span&gt; No error handling for impossible scenarios.
&lt;span class="p"&gt;-&lt;/span&gt; If you write 200 lines and it could be 50, rewrite it.

Ask yourself: "Would a senior engineer say this is overcomplicated?" If yes, simplify.

&lt;span class="gu"&gt;## 3. Surgical Changes&lt;/span&gt;

&lt;span class="gs"&gt;**Touch only what you must. Clean up only your own mess.**&lt;/span&gt;

When editing existing code:
&lt;span class="p"&gt;-&lt;/span&gt; Don't "improve" adjacent code, comments, or formatting.
&lt;span class="p"&gt;-&lt;/span&gt; Don't refactor things that aren't broken.
&lt;span class="p"&gt;-&lt;/span&gt; Match existing style, even if you'd do it differently.
&lt;span class="p"&gt;-&lt;/span&gt; If you notice unrelated dead code, mention it - don't delete it.

When your changes create orphans:
&lt;span class="p"&gt;-&lt;/span&gt; Remove imports/variables/functions that YOUR changes made unused.
&lt;span class="p"&gt;-&lt;/span&gt; Don't remove pre-existing dead code unless asked.

The test: Every changed line should trace directly to the user's request.

&lt;span class="gu"&gt;## 4. Goal-Driven Execution&lt;/span&gt;

&lt;span class="gs"&gt;**Define success criteria. Loop until verified.**&lt;/span&gt;

Transform tasks into verifiable goals:
&lt;span class="p"&gt;-&lt;/span&gt; "Add validation" → "Write tests for invalid inputs, then make them pass"
&lt;span class="p"&gt;-&lt;/span&gt; "Fix the bug" → "Write a test that reproduces it, then make it pass"
&lt;span class="p"&gt;-&lt;/span&gt; "Refactor X" → "Ensure tests pass before and after"

For multi-step tasks, state a brief plan:&lt;span class="sb"&gt;

    1. [Step] → verify: [check]
    2. [Step] → verify: [check]
    3. [Step] → verify: [check]


&lt;/span&gt;Strong success criteria let you loop independently. Weak criteria ("make it work") require constant clarification.
&lt;span class="p"&gt;
---
&lt;/span&gt;
&lt;span class="gs"&gt;**These guidelines are working if:**&lt;/span&gt; fewer unnecessary changes in diffs, fewer rewrites due to overcomplication, and clarifying questions come before implementation rather than after mistakes.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  1. Think Before Coding
&lt;/h2&gt;

&lt;p&gt;This is probably the most important block out of the four in this skill file, and thats why its number one. Andrej is correct in that the LLM will attempt to jump to conclusions before contemplating from start to finish the request in the first place. Where I differ with him is that &lt;em&gt;AI cannot think.&lt;/em&gt; No matter what Sam Altman and Dario Amodei says. Seriously - who names these people? &lt;b&gt;Alt&lt;/b&gt;&lt;em&gt;man&lt;/em&gt; and &lt;b&gt;A&lt;/b&gt;&lt;em&gt;mode&lt;/em&gt;&lt;b&gt;I&lt;/b&gt;? Okay &lt;em&gt;Sam&lt;/em&gt; 🤣 Okay &lt;em&gt;Dario&lt;/em&gt; 🤣 - Whatever you say bro. 🤫 &lt;strong&gt;AI cannot think!&lt;/strong&gt; It &lt;strong&gt;doesn't understand&lt;/strong&gt; what it built and it &lt;em&gt;cannot think&lt;/em&gt; either. Now, &lt;em&gt;thinking&lt;/em&gt; capabilities have been added to LLM models that allow the user to see a stream of consciousness that is guided and logged be recorded as the model attempts to loop on itself back to itself a result that it thinks is favorable to the requester. That's not thinking. It's a closed system of limited information that does not have access to the &lt;em&gt;eternal divine spark&lt;/em&gt; that dwells inside all created. Theology aside, &lt;strong&gt;AI cannot think&lt;/strong&gt; and therefore, &lt;em&gt;giving AI management permissions&lt;/em&gt; is &lt;strong&gt;dangerous for humans.&lt;/strong&gt; Therefore, when engaging with AI to write code for you, or complete a function for you, it's not forward thinking, and it's not &lt;em&gt;thinking.&lt;/em&gt; But asking the model, that &lt;em&gt;thinks&lt;/em&gt; that it &lt;em&gt;thinks&lt;/em&gt; to &lt;em&gt;think&lt;/em&gt; then it will &lt;em&gt;think&lt;/em&gt; that it &lt;em&gt;thinks&lt;/em&gt; about &lt;em&gt;thinking&lt;/em&gt; about the prompt. &lt;/p&gt;

&lt;p&gt;In my experience, Andrej captured the correct balance out of the LLM itself by asserting that assumptions only make an &lt;strong&gt;ass&lt;/strong&gt; out of &lt;strong&gt;u&lt;/strong&gt; and &lt;strong&gt;me&lt;/strong&gt; when you &lt;em&gt;assume.&lt;/em&gt; Likewise with the models - they are making assumptions and hallucinating to fill in the gaps. Now, when you're asking for a very limited ask, the risk is low, but when the ask is wide open - then the hallucinations will be endless and not even the AI may be able to help you out of what the AI generated. By asking for the AI to not make assumptions, it can keep track of whether or not &lt;em&gt;assumptions&lt;/em&gt; are being made in the path that the model traverses to the output.&lt;/p&gt;

&lt;h2&gt;
  
  
  2. Simplicity First
&lt;/h2&gt;

&lt;p&gt;This is important. &lt;code&gt;If you write 200 lines and it could be 50, rewrite it.&lt;/code&gt; is probably the most important line in the file. This requires the model to look at the same function's &lt;code&gt;input&lt;/code&gt; and &lt;code&gt;output&lt;/code&gt; and come up with an alternative that gets you from start to finish correctly. Given CodeBerg's Recent Ban on LLMs, I provided &lt;a href="https://dev.to/andreimerlescu/codeberg-bans-cryptocurrency-and-llm-generated-code-projects-3aj0"&gt;my response to it&lt;/a&gt;. Ultimately, what CodeBerg argued, and I agreed, was that LLMs were trained on source code of various license types that are unverifiable because models lack the ability to map the code back to what it was trained on for its original license. In the case of much of my open source work, it's been &lt;strong&gt;GPL-3&lt;/strong&gt;, which by its license, means that if you're going to use the &lt;strong&gt;Advanced Search&lt;/strong&gt; that I built, I require you to copyleft your code since many tools I used were copyleft as well. The models do not honor or respect that and when somebody is literally paying anthropic $100,000 in tokens to use the latest &lt;strong&gt;Mythos | Fable 5&lt;/strong&gt; model, the one paying that bill is going to argue that they have a right to use the works in the derivatives that they create - when in reality - they are just hallucinating &lt;strong&gt;GPL-3&lt;/strong&gt; violations because the code was AI generated. So, its ironic that I have a piece agreeing with CodeBerg's anti-AI position and here I am writing about a &lt;code&gt;CLAUDE.md&lt;/code&gt; file from Andrej Kaparthy. Simplicity first! &lt;/p&gt;

&lt;h2&gt;
  
  
  3. Surgical Changes
&lt;/h2&gt;

&lt;p&gt;This one is critical. When you're working on a large code base and you're already only providing the model with a limited context of the project because the full context is beyond its window - sometimes tools like &lt;a href="https://github.com/andreimerlescu/summarize" rel="noopener noreferrer"&gt;summarize&lt;/a&gt; help you bypass that by using your own hardware. For some projects, you can use &lt;code&gt;summarize -print&lt;/code&gt; (use &lt;code&gt;| pbcopy&lt;/code&gt; if you're on macOS to put the contents in your pasteboard) and then paste that into your LLM model. When the model comes back with potential changes, you &lt;strong&gt;want surgical changes only&lt;/strong&gt;, otherwise you're going to waste a lot of time and energy and tokens on wasted effort. This section, is critical. &lt;/p&gt;

&lt;h2&gt;
  
  
  4. Goal-Driven Execution
&lt;/h2&gt;

&lt;p&gt;This part Andrej shares with us gives us insights into how AI companies trick &lt;em&gt;us&lt;/em&gt; into thinking that the LLM is capable of thinking. It's &lt;em&gt;autocomplete software&lt;/em&gt; designed to imitate an ouroboros that does not have consciousness. An ouroboros is a snake that is eating its own tail in the shape on an 8. The &lt;em&gt;snake&lt;/em&gt; is the prompt output being passed back into the loop until the ouroboros has sufficiently manifested. It's really advanced technology. Giving the model the ability to loop output back into itself to iteratively improve on itself allows you to knowingly leverage that &lt;em&gt;illusion of thinking&lt;/em&gt; and harvest it into your prompts themselves by incorporating a looping system in how the model accomplishes goals. The list format &lt;code&gt;[Step] → verify: [check]&lt;/code&gt; in the prompt allows for the model to improve itself even further. &lt;/p&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;I've been writing software for 17 years professionally and nearly 30 years since my grandmother was asking me for help with her printer that would &lt;em&gt;get disconnected&lt;/em&gt; and my &lt;strong&gt;AppleScript&lt;/strong&gt; utility would &lt;em&gt;fix the software&lt;/em&gt; and make the MacOS 7 machine &lt;em&gt;print.&lt;/em&gt; I haven't needed AI to write software for me, but I find it fascinating to have access to &lt;a href="https://dev.to/andreimerlescu/when-ai-creates-a-closed-source-world-2oin"&gt;The Library&lt;/a&gt; of all ingested data to learn more about programming - like &lt;a href="https://dev.to/andreimerlescu/sql-design-query-reference-67f"&gt;SQL&lt;/a&gt; and &lt;a href="https://dev.to/andreimerlescu/the-afternoon-we-put-magentos-schema-on-sql-server-2nb2"&gt;Magento&lt;/a&gt;. It's helped me become a stronger engineer, but it's also slowed me down because the constant need for &lt;em&gt;knowing everything&lt;/em&gt; all of a sudden because &lt;em&gt;questionable?&lt;/em&gt; But why?&lt;/p&gt;

&lt;p&gt;As a 17 year professional computer engineer autodidact software architect who survived Ceaușescu's orphanages as an infant and was writing code before I could even read basic children's books in English (my second language) - I find this post-pandemic now-AI world to be exactly what &lt;a href="https://github.com/ProjectApario" rel="noopener noreferrer"&gt;Operation Yokohama&lt;/a&gt; revealed between 2017-2020 before that open source project came online. I've been a professional behind the machine for decades and I had access to the internet in the early days of BITNET through the University of Maine. &lt;/p&gt;

&lt;p&gt;While AI doesn't properly attribute licenses to the open source software that it pirates off my &lt;strong&gt;GPL-3&lt;/strong&gt; contributions (allegedly), I can say that I wouldn't have a problem if the models were locally free to use &lt;em&gt;if I have the resources to run them.&lt;/em&gt; **And &lt;em&gt;most importantly&lt;/em&gt; their is an lawfully mandated cadence of public model disclosures and updates. &lt;/p&gt;

&lt;p&gt;I don't believe that all AI is the worst thing in the world. Imagine that you could take a model that wasn't trained on just problematic licensed software generation but the entire library of Harvard University and scan in every book into the LLM itself and then get a "snapshot" of the large language model built on the &lt;em&gt;millions of books&lt;/em&gt; in the collection &lt;strong&gt;spanning hundreds of years.&lt;/strong&gt; Access to &lt;em&gt;that LLM&lt;/em&gt; would be worth $300/month for some people, even if there were usage limits on it to ensure that you're ultimately scrapping the LLM itself. But expand that further to something technical - I'd rather get access to a model thats been trained specifically on technical manuals, college textbooks, and verified non-fiction, original source code + authentic documentation, than having something tossed together through reddit posts and stack overflow questions and answers. &lt;/p&gt;

&lt;p&gt;I do believe that if you are going to use AI, that this &lt;code&gt;CLAUDE.md&lt;/code&gt; file will help force the model to respect the engineering style of both Andrej and myself, Andrei. Alas, two Andrei's are presenting to you the interface to which that we collaborate with AI - the only difference is, before Project Stargate was a thing at Oracle, I was working at Oracle learning about the Stargate after President Obama declassified the records and I ingested those files into the Apario &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt;. I haven't written about &lt;em&gt;that instance&lt;/em&gt; of the &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt; 👉🏻 &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; and I probably won't for a while until it's finished unpacking. But, if you are using AI to help you write code &lt;em&gt;faster&lt;/em&gt; &lt;strong&gt;and not better&lt;/strong&gt; than when you were a slow per-character engineer billing $100/hr. Now, with AI, you're like well shit - consulting sucks now - now I spend all my time hustling gigs instead of head's down solid engineering - because the code generation is so &lt;em&gt;cheap&lt;/em&gt; now. When you understand how local models are built, and how their code training gives you insight into your own ability to fill the gaps into your own &lt;strong&gt;design&lt;/strong&gt; of &lt;em&gt;software engineering&lt;/em&gt; - its you who can do what the AI cannot do - &lt;strong&gt;think.&lt;/strong&gt;  &lt;/p&gt;

</description>
      <category>ai</category>
      <category>programming</category>
      <category>opensource</category>
      <category>discuss</category>
    </item>
    <item>
      <title>The Afternoon We Put Magento's Schema on SQL Server</title>
      <dc:creator>Andrei Merlescu</dc:creator>
      <pubDate>Mon, 27 Jul 2026 17:17:09 +0000</pubDate>
      <link>https://dev.to/andreimerlescu/the-afternoon-we-put-magentos-schema-on-sql-server-2nb2</link>
      <guid>https://dev.to/andreimerlescu/the-afternoon-we-put-magentos-schema-on-sql-server-2nb2</guid>
      <description>&lt;p&gt;There is a moment in every LAMP developer's career where the reporting query wins.&lt;/p&gt;

&lt;p&gt;You have a Magento store. It runs on MySQL, because Magento runs on MySQL. Everything you know about SQL, you learned inside InnoDB, and InnoDB has been fine. Then merchandising asks for "top five sellers per category, per store view, month over month, with the year-over-year delta," and you write it, and it runs for forty minutes, and it takes the storefront down with it.&lt;/p&gt;

&lt;p&gt;I got called into a shop in that exact state in 2016. Magento 1.9, five store views, about 900,000 SKUs, six years of order history. The stack was as classic as it gets: Apache, PHP, MySQL 5.6, one primary and one replica. And in the corner of the rack, doing nothing but eating license fees, was a SQL Server 2012 instance the ERP team had left behind.&lt;/p&gt;

&lt;p&gt;I spent an afternoon with one of their developers showing him why we were going to feed Magento's schema into that box, and what changed once we did. This document is that afternoon, written out. The through-line is simple: &lt;strong&gt;Magento's schema is the fixed artifact, and the engine underneath it is a variable.&lt;/strong&gt; Every heading below is a question that comes up in SQL interviews and code reviews, and every one of them has a different answer depending on whether you're standing on InnoDB, SQL Server, or Oracle.&lt;/p&gt;

&lt;p&gt;A note on honesty before we start. MySQL 8.0 closed most of the gaps I'm about to describe — window functions, CTEs, hash joins, real &lt;code&gt;CHECK&lt;/code&gt; constraints, &lt;code&gt;EXCEPT&lt;/code&gt;/&lt;code&gt;INTERSECT&lt;/code&gt;, &lt;code&gt;LATERAL&lt;/code&gt;. If you're on 8.0 or later today, a lot of this reads as history. It's still worth reading as history, because the &lt;em&gt;reasoning&lt;/em&gt; transfers, and because a startling number of production Magento installs are still on 5.7 or on MariaDB, which diverged and does not have all of it either.&lt;/p&gt;




&lt;h2&gt;
  
  
  The setup: why two engines at all
&lt;/h2&gt;

&lt;p&gt;The first thing I did was not write a query. It was draw the schema on a whiteboard in three layers, because until you see the layers, Magento looks arbitrary.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Layer one is truth.&lt;/strong&gt; &lt;code&gt;catalog_product_entity&lt;/code&gt;, &lt;code&gt;catalog_product_entity_varchar&lt;/code&gt; and its siblings, &lt;code&gt;eav_attribute&lt;/code&gt;, &lt;code&gt;sales_order&lt;/code&gt;, &lt;code&gt;sales_order_item&lt;/code&gt;, &lt;code&gt;customer_entity&lt;/code&gt;. Normalized, constrained, slow to read, correct. This is what you restore from backup.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Layer two is index.&lt;/strong&gt; &lt;code&gt;catalog_product_index_price&lt;/code&gt;, &lt;code&gt;catalog_category_product_index_store1&lt;/code&gt;, &lt;code&gt;catalog_product_index_eav&lt;/code&gt;, &lt;code&gt;catalogsearch_fulltext_scope1&lt;/code&gt;. Every one of these is derived. Drop them all and you lose nothing but the time it takes &lt;code&gt;bin/magento indexer:reindex&lt;/code&gt; to rebuild them.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Layer three is presentation.&lt;/strong&gt; &lt;code&gt;sales_order_grid&lt;/code&gt;, &lt;code&gt;customer_grid_flat&lt;/code&gt;. Flattened read models, each shaped for exactly one admin screen.&lt;/p&gt;

&lt;p&gt;Layer two exists because layer one is EAV. A merchant needs to add a "Shell Fabric Denier" attribute to jackets without a schema migration, so attributes live as rows:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- catalog_product_entity: one row per product, almost no attributes&lt;/span&gt;
&lt;span class="n"&gt;entity_id&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;attribute_set_id&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;type_id&lt;/span&gt;      &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;sku&lt;/span&gt;          &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;created_at&lt;/span&gt;
&lt;span class="c1"&gt;--------- | ---------------- | ------------ | ------------ | ----------&lt;/span&gt;
   &lt;span class="mi"&gt;88213&lt;/span&gt;  &lt;span class="o"&gt;|&lt;/span&gt;               &lt;span class="mi"&gt;15&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;configurable&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;ALPINE&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="n"&gt;PARKA&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="mi"&gt;2014&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;09&lt;/span&gt;&lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="mi"&gt;02&lt;/span&gt;

&lt;span class="c1"&gt;-- catalog_product_entity_varchar: the value, scoped per store view&lt;/span&gt;
&lt;span class="n"&gt;value_id&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;attribute_id&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;store_id&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;entity_id&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;value&lt;/span&gt;
&lt;span class="c1"&gt;-------- | ------------ | -------- | --------- | ------------------&lt;/span&gt;
 &lt;span class="mi"&gt;9182734&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt;           &lt;span class="mi"&gt;73&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt;        &lt;span class="mi"&gt;0&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt;     &lt;span class="mi"&gt;88213&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;Alpine&lt;/span&gt; &lt;span class="n"&gt;Down&lt;/span&gt; &lt;span class="n"&gt;Parka&lt;/span&gt;
 &lt;span class="mi"&gt;9182735&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt;           &lt;span class="mi"&gt;73&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt;        &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt;     &lt;span class="mi"&gt;88213&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;Parka&lt;/span&gt; &lt;span class="n"&gt;Alpin&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;store_id = 0&lt;/code&gt; is the default scope. &lt;code&gt;store_id = 2&lt;/code&gt; overrides it for the French store view. Remember that shape; it's going to teach us the most important thing about outer joins later.&lt;/p&gt;

&lt;p&gt;This design is infinitely flexible and completely unusable for a storefront, which is why Magento built layer two. And here's the part that matters for our story: &lt;strong&gt;Magento's entire indexer subsystem — &lt;code&gt;mview_state&lt;/code&gt;, the &lt;code&gt;*_cl&lt;/code&gt; changelog tables, index invalidation, "Update by Schedule" — is a hand-rolled incremental materialized view engine, written in PHP, because MySQL does not have materialized views.&lt;/strong&gt; Thousands of lines of framework code implementing something Oracle gives you in one DDL statement.&lt;/p&gt;

&lt;p&gt;So the pitch to the developer was this. We are not going to migrate off MySQL. Magento stays where it is. We are going to replicate the interesting tables into SQL Server, and every reporting question that MySQL answers badly, we will answer over there instead — using tools MySQL simply does not have. In exchange, we accept the cost of maintaining a second schema, which is real and which I'll be honest about at the end.&lt;/p&gt;

&lt;p&gt;The ETL was unglamorous: a nightly full pull of the dimension-ish tables, incremental pulls on &lt;code&gt;sales_order&lt;/code&gt;, &lt;code&gt;sales_order_item&lt;/code&gt;, and &lt;code&gt;sales_order_payment&lt;/code&gt; keyed on &lt;code&gt;entity_id&lt;/code&gt; and &lt;code&gt;updated_at&lt;/code&gt;. Nothing clever. The cleverness is all in what you can do once the data lands.&lt;/p&gt;




&lt;h2&gt;
  
  
  Choosing the right query pattern for the problem
&lt;/h2&gt;

&lt;p&gt;The first ticket he handed me was: &lt;em&gt;"Marketing wants the email addresses of everyone who has ever ordered the Alpine Down Parka."&lt;/em&gt; He'd already written it.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;DISTINCT&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;email&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;customer_entity&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;
&lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;      &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
&lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;sales_order_item&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sku&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'ALPINE-PARKA'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Forty-one thousand rows, ninety seconds. The parka had sold 380,000 units. The join fanned out to 380,000 rows and then sorted every one of them to collapse back down to 41,000. He paid for a sort of the fanned-out set and threw the result away.&lt;/p&gt;

&lt;p&gt;Before you write anything, answer three questions. I've asked these in code review for fifteen years and I have never regretted it. &lt;strong&gt;What is the grain of my result — one row per what?&lt;/strong&gt; If you can't finish that sentence, you will produce duplicates. &lt;strong&gt;Am I filtering, or am I enriching?&lt;/strong&gt; Filtering means a semi-join; enriching means a real join or a window function. &lt;strong&gt;Do I need one value per group, or one row per group?&lt;/strong&gt; One value is an aggregate; one row is a window function or a lateral.&lt;/p&gt;

&lt;p&gt;Here the grain is one row per customer, and we are filtering. We want nothing from the order — just a yes or no. That's &lt;code&gt;EXISTS&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;email&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;customer_entity&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="k"&gt;EXISTS&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;
  &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;
  &lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;sales_order_item&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
  &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
    &lt;span class="k"&gt;AND&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sku&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'ALPINE-PARKA'&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The optimizer stops at the first matching order per customer. No fan-out, no sort. Two seconds on the same box. This works identically on all four engines and there is nothing platform-specific to learn — which is exactly why I started here. Most bad SQL is not an engine problem. It's a grain error wearing a &lt;code&gt;DISTINCT&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Here's the table I keep pinned above my desk, and it is portable in its entirety:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Question&lt;/th&gt;
&lt;th&gt;Right pattern&lt;/th&gt;
&lt;th&gt;What people reach for&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Customers who ordered ≥1 parka&lt;/td&gt;
&lt;td&gt;&lt;code&gt;EXISTS&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;JOIN&lt;/code&gt; + &lt;code&gt;DISTINCT&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Products never ordered&lt;/td&gt;
&lt;td&gt;&lt;code&gt;NOT EXISTS&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;NOT IN&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Each order plus its customer's email&lt;/td&gt;
&lt;td&gt;&lt;code&gt;JOIN&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;correlated scalar subquery&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Revenue per customer&lt;/td&gt;
&lt;td&gt;&lt;code&gt;GROUP BY&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;correlated aggregate in &lt;code&gt;SELECT&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Each order plus that customer's lifetime total&lt;/td&gt;
&lt;td&gt;window function&lt;/td&gt;
&lt;td&gt;correlated aggregate in &lt;code&gt;SELECT&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Most recent order per customer, whole row&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;ROW_NUMBER()&lt;/code&gt; or lateral&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;MAX(created_at)&lt;/code&gt; + self-join&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Top 5 sellers per category&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;RANK&lt;/code&gt;/&lt;code&gt;DENSE_RANK&lt;/code&gt;/&lt;code&gt;ROW_NUMBER&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;correlated &lt;code&gt;COUNT&lt;/code&gt; subquery&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Now the first place the second engine earned its keep. On MySQL, when a query got complicated, our only debugging tool was &lt;code&gt;EXPLAIN&lt;/code&gt; — an estimate, not a measurement. &lt;code&gt;EXPLAIN ANALYZE&lt;/code&gt; didn't arrive until MySQL 8.0.18. On SQL Server we had the actual execution plan with real row counts next to estimated ones, and &lt;code&gt;SET STATISTICS IO, TIME ON&lt;/code&gt; telling us exactly how many logical reads each table cost. The developer's reaction to seeing an actual plan for the first time was the reaction everyone has: &lt;em&gt;oh, it was scanning that the whole time.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;One structural difference bites people immediately when they port a query, so learn it now. A CTE does not mean the same thing on every engine.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;What a CTE actually does&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;PostgreSQL ≤ 11&lt;/td&gt;
&lt;td&gt;Always materialized. Hard optimization fence — outer predicates do &lt;strong&gt;not&lt;/strong&gt; push in.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;PostgreSQL 12+&lt;/td&gt;
&lt;td&gt;Inlined if referenced once, non-recursive, non-volatile. Force with &lt;code&gt;AS MATERIALIZED&lt;/code&gt; / &lt;code&gt;AS NOT MATERIALIZED&lt;/code&gt;.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;SQL Server&lt;/td&gt;
&lt;td&gt;Effectively always inlined. A CTE referenced three times is &lt;strong&gt;executed three times&lt;/strong&gt;. No hint to change it.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Oracle&lt;/td&gt;
&lt;td&gt;Cost-based. &lt;code&gt;/*+ MATERIALIZE */&lt;/code&gt; and &lt;code&gt;/*+ INLINE */&lt;/code&gt; are your controls.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MySQL 8.0+&lt;/td&gt;
&lt;td&gt;Materializes derived tables and CTEs in many cases; merge is possible. Weakest at pushing predicates in.&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;The SQL Server failure is memorable. A tidy CTE that scans &lt;code&gt;sales_order_item&lt;/code&gt; once, referenced in three branches of a &lt;code&gt;UNION ALL&lt;/code&gt;, scans 40 million rows three times. It looks elegant in review and it is a disaster at runtime. &lt;strong&gt;If a CTE is referenced more than once and the underlying scan is expensive, stage it explicitly&lt;/strong&gt; — &lt;code&gt;SELECT ... INTO #orders_2016&lt;/code&gt; on SQL Server, and stop hoping.&lt;/p&gt;




&lt;h2&gt;
  
  
  Using NOT EXISTS / EXISTS where appropriate
&lt;/h2&gt;

&lt;p&gt;The second ticket was merchandising's: &lt;em&gt;"Give us every product that has never been ordered so we can cull the catalog."&lt;/em&gt; He wrote the obvious thing and got zero rows. Every time. On a catalog where you could visibly point at products nobody had ever bought.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sku&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;catalog_product_entity&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;IN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;product_id&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order_item&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Look at Magento's own foreign key on that column and the bug becomes obvious:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;SALES_ORDER_ITEM_PRODUCT_ID_CATALOG_PRODUCT_ENTITY_ENTITY_ID&lt;/span&gt;
  &lt;span class="k"&gt;FOREIGN&lt;/span&gt; &lt;span class="k"&gt;KEY&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;product_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;REFERENCES&lt;/span&gt; &lt;span class="n"&gt;catalog_product_entity&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="k"&gt;DELETE&lt;/span&gt; &lt;span class="k"&gt;SET&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;ON DELETE SET NULL&lt;/code&gt;. The moment a merchant deletes one product, every historical order line for it gets &lt;code&gt;product_id = NULL&lt;/code&gt;. In a six-year-old store, that column is &lt;em&gt;guaranteed&lt;/em&gt; to contain NULLs.&lt;/p&gt;

&lt;p&gt;Now the semantics. &lt;code&gt;x NOT IN (a, b, NULL)&lt;/code&gt; expands to &lt;code&gt;x &amp;lt;&amp;gt; a AND x &amp;lt;&amp;gt; b AND x &amp;lt;&amp;gt; NULL&lt;/code&gt;. That last term is &lt;code&gt;UNKNOWN&lt;/code&gt; — not false, unknown. A conjunction containing &lt;code&gt;UNKNOWN&lt;/code&gt; can never evaluate to &lt;code&gt;TRUE&lt;/code&gt;. So the filter matches nothing at all. Not fewer rows. Nothing. Silently, with no error and no warning.&lt;/p&gt;

&lt;p&gt;This is ANSI behavior and it is &lt;strong&gt;identical on MySQL, PostgreSQL, SQL Server, and Oracle&lt;/strong&gt;. I want to be emphatic about that, because the developer's first instinct was that MySQL had done something to him. It hadn't. This one is on us, not the engine, and moving to a fancier database does not save you.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- Correct on every engine, forever&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sku&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;catalog_product_entity&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;EXISTS&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order_item&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;product_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;NOT EXISTS&lt;/code&gt; tests row existence rather than value comparison, so a NULL is simply a non-match. &lt;strong&gt;Never write &lt;code&gt;NOT IN&lt;/code&gt; against a subquery.&lt;/strong&gt; Against a short literal list — &lt;code&gt;status NOT IN ('canceled','closed')&lt;/code&gt; — it's fine and readable. Against a subquery, the only safe version requires the column to be declared &lt;code&gt;NOT NULL&lt;/code&gt; in the DDL, not "we're pretty sure," and even then it's usually the slower plan.&lt;/p&gt;

&lt;p&gt;Which brings us to where the engines diverge, and to the first genuinely dramatic difference we measured that afternoon.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;&lt;code&gt;NOT EXISTS&lt;/code&gt;&lt;/th&gt;
&lt;th&gt;
&lt;code&gt;NOT IN&lt;/code&gt; against a subquery&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Oracle&lt;/td&gt;
&lt;td&gt;Anti-join&lt;/td&gt;
&lt;td&gt;Handled well — null-aware anti-join (&lt;code&gt;ANTI NA&lt;/code&gt;) since 11g. Rough parity.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;SQL Server&lt;/td&gt;
&lt;td&gt;Anti semi-join&lt;/td&gt;
&lt;td&gt;Usually an anti-join, but nullable columns add probes and plans get ugly.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;PostgreSQL&lt;/td&gt;
&lt;td&gt;Clean anti-join&lt;/td&gt;
&lt;td&gt;Falls back to an opaque SubPlan filter — and is &lt;em&gt;not&lt;/em&gt; rescued by declaring the columns &lt;code&gt;NOT NULL&lt;/code&gt; on released versions.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MySQL 8.0.17+&lt;/td&gt;
&lt;td&gt;Anti-join&lt;/td&gt;
&lt;td&gt;Antijoin transformation from 8.0.17. Before that: a dependent subquery, evaluated per row.&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Read that MySQL row again. On the 5.6 box, &lt;code&gt;NOT EXISTS&lt;/code&gt; over a 900,000-row product table against a 12-million-row order item table was a per-row dependent subquery — nine hundred thousand separate probes. It ran for over an hour. The identical statement on SQL Server 2012 became a hash-based anti semi-join and returned in under a minute. Same SQL. Same data. Same index definitions. The difference was entirely in what the optimizer was capable of transforming.&lt;/p&gt;

&lt;p&gt;You will also meet a third spelling in legacy Magento code, and now you know why it's there — before 8.0.17 it was the only way to get a decent anti-join plan out of MySQL:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sku&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;catalog_product_entity&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;
&lt;span class="k"&gt;LEFT&lt;/span&gt; &lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;sales_order_item&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;product_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;item_id&lt;/span&gt; &lt;span class="k"&gt;IS&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;It's semantically safe — no NULL trap — but it's fragile. Add a second predicate on &lt;code&gt;i&lt;/code&gt; in the &lt;code&gt;WHERE&lt;/code&gt; clause instead of the &lt;code&gt;ON&lt;/code&gt; clause and you silently convert the outer join to an inner join and get zero rows again. Recognize it when you inherit it; don't write it new.&lt;/p&gt;

&lt;p&gt;And one thing to stop arguing about in review: &lt;code&gt;SELECT 1&lt;/code&gt; versus &lt;code&gt;SELECT *&lt;/code&gt; versus &lt;code&gt;SELECT NULL&lt;/code&gt; inside &lt;code&gt;EXISTS&lt;/code&gt; makes &lt;strong&gt;zero&lt;/strong&gt; difference on any of the four engines. The select list isn't evaluated. What matters is whether the correlation predicate is indexed. Spend the argument there.&lt;/p&gt;




&lt;h2&gt;
  
  
  Avoiding unnecessary nested aggregate subqueries
&lt;/h2&gt;

&lt;p&gt;This is the section where the developer got annoyed with me, and he was right to, because I'd been implying his code was sloppy when actually his engine had left him no choice.&lt;/p&gt;

&lt;p&gt;The ticket: &lt;em&gt;"Customer service wants a screen showing each order alongside that customer's lifetime order count, lifetime spend, and first order date."&lt;/em&gt; His version:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;increment_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;COUNT&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;               &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="n"&gt;o2&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o2&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;lifetime_orders&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;base_grand_total&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;  &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="n"&gt;o3&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o3&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;lifetime_spend&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;MIN&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;        &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="n"&gt;o4&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o4&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;first_order_at&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="s1"&gt;'2016-01-01'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Three correlated subqueries, which means up to three extra index range scans &lt;strong&gt;per output row&lt;/strong&gt;. At two million output rows that's six million extra scans. On a good day the optimizer decorrelates one. Plan for the bad day.&lt;/p&gt;

&lt;p&gt;Here's the thing I owed him an apology for: &lt;strong&gt;MySQL 5.7 had no window functions.&lt;/strong&gt; None. They arrived in 8.0. So the elegant one-pass rewrite I was about to show him did not exist on his production database. The correlated-subquery pattern all over the Magento ecosystem is not laziness. It is what people wrote because the alternative was not available.&lt;/p&gt;

&lt;p&gt;On SQL Server 2012 — and on Oracle since 8i, which is to say since 1999 — it was available:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;increment_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;COUNT&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;              &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;PARTITION&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;lifetime_orders&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;base_grand_total&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;PARTITION&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;lifetime_spend&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;MIN&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;       &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;PARTITION&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;first_order_at&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;created_at&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="s1"&gt;'2016-01-01'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;One scan, one sort by &lt;code&gt;customer_id&lt;/code&gt;, three aggregates computed together. But read the semantics carefully, because this is a trap that ships: the window is now over the &lt;strong&gt;filtered&lt;/strong&gt; set. "Lifetime spend" just quietly became "spend since January." If the business meant lifetime, this is wrong in a way that looks right, and nobody catches it until the numbers get compared against finance.&lt;/p&gt;

&lt;p&gt;When you need aggregates over the full history but only rows from a window, pre-aggregate and join:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;WITH&lt;/span&gt; &lt;span class="n"&gt;cust&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
         &lt;span class="k"&gt;COUNT&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;              &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;lifetime_orders&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
         &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;base_grand_total&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;lifetime_spend&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
         &lt;span class="k"&gt;MIN&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;       &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;first_order_at&lt;/span&gt;
  &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt;
  &lt;span class="k"&gt;GROUP&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;increment_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;lifetime_orders&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;lifetime_spend&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;first_order_at&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;
&lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;cust&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="s1"&gt;'2016-01-01'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;One aggregate pass over the child, one hash join. This is the workhorse pattern and it's the one to reach for by default. &lt;strong&gt;Aggregate before you join, never after.&lt;/strong&gt; Joining first fans out rows and then you're summing an inflated set, which is also how you get silently wrong totals — we'll do that failure explicitly in the next section.&lt;/p&gt;

&lt;p&gt;The third pattern is the one where SQL Server had something MySQL wouldn't get until 8.0.14. "Show me each customer plus every column of their most recent order" needs a whole row, not an aggregate:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- SQL Server 2012&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;email&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;increment_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;base_grand_total&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;customer_entity&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;
&lt;span class="k"&gt;OUTER&lt;/span&gt; &lt;span class="n"&gt;APPLY&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;TOP&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;increment_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;base_grand_total&lt;/span&gt;
    &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;
    &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
    &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt; &lt;span class="k"&gt;DESC&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt; &lt;span class="k"&gt;DESC&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;PostgreSQL and MySQL 8.0.14+ spell it &lt;code&gt;LEFT JOIN LATERAL (...) ON true&lt;/code&gt;; Oracle 12c+ accepts either. The decision rule is worth internalizing because it's counterintuitive: &lt;strong&gt;lateral does N cheap index seeks, &lt;code&gt;ROW_NUMBER()&lt;/code&gt; does one big sort.&lt;/strong&gt; For a VIP list of 200 customers against 12 million orders, lateral wins by orders of magnitude. For "top 3 orders per customer across all 700,000 customers," &lt;code&gt;ROW_NUMBER()&lt;/code&gt; wins — one sorted pass beats 700,000 seeks. Know your N.&lt;/p&gt;

&lt;p&gt;Oracle has a shortcut here with no equivalent on the other three, and if you ever land on an Oracle warehouse it will save you a self-join:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;MAX&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;increment_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;KEEP&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DENSE_RANK&lt;/span&gt; &lt;span class="k"&gt;LAST&lt;/span&gt; &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;last_increment_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;base_grand_total&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;lifetime_spend&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt;
&lt;span class="k"&gt;GROUP&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;KEEP (DENSE_RANK FIRST/LAST)&lt;/code&gt; gives you "the value of column X from the row with the max of Y" inside a plain &lt;code&gt;GROUP BY&lt;/code&gt;. No window pass, no join. PostgreSQL's nearest analogue is &lt;code&gt;DISTINCT ON&lt;/code&gt;. SQL Server and MySQL have nothing like it.&lt;/p&gt;

&lt;p&gt;And the Magento footnote: the platform already solved this problem, and the solution is called &lt;code&gt;customer_grid_flat&lt;/code&gt;. When the same expensive aggregation is demanded by a UI on every page load, the right answer eventually stops being "a better query" and becomes "a maintained table." We'll get there.&lt;/p&gt;




&lt;h2&gt;
  
  
  Understanding joins, filtering, grouping, and set-based logic
&lt;/h2&gt;

&lt;p&gt;Third ticket, and the one that had actually triggered my involvement: &lt;em&gt;"Finance says Q1 revenue on the dashboard doesn't match the accounting system."&lt;/em&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- WRONG&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;row_total&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;item_total&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;amount_paid&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;paid_total&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;
&lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;sales_order_item&lt;/span&gt;    &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
&lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;sales_order_payment&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;parent_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
&lt;span class="k"&gt;GROUP&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;An order with three line items and one payment produces three rows, so &lt;code&gt;SUM(p.amount_paid)&lt;/code&gt; is three times too large. Add a split payment and both sums are wrong. The numbers look plausible, which is precisely why this ships to production and survives there for months.&lt;/p&gt;

&lt;p&gt;The fix is the rule from the last section, applied: aggregate each branch separately, then join the aggregates.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;item_total&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;paid_total&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;
&lt;span class="k"&gt;LEFT&lt;/span&gt; &lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;order_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;row_total&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;item_total&lt;/span&gt;
           &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order_item&lt;/span&gt; &lt;span class="k"&gt;GROUP&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;order_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
&lt;span class="k"&gt;LEFT&lt;/span&gt; &lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;parent_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;amount_paid&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;paid_total&lt;/span&gt;
           &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order_payment&lt;/span&gt; &lt;span class="k"&gt;GROUP&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;parent_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;parent_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Diagnostic trick worth ten seconds of your life: drop &lt;code&gt;COUNT(DISTINCT i.item_id), COUNT(DISTINCT p.entity_id), COUNT(*)&lt;/code&gt; into the broken query. When &lt;code&gt;COUNT(*)&lt;/code&gt; equals the product of the other two, you've proven the fan-out to yourself and you can stop debating it.&lt;/p&gt;

&lt;p&gt;Now, &lt;code&gt;ON&lt;/code&gt; versus &lt;code&gt;WHERE&lt;/code&gt;, which Magento's store-scope model teaches better than any textbook example. Remember &lt;code&gt;store_id = 0&lt;/code&gt; for the default and &lt;code&gt;store_id = 2&lt;/code&gt; for the French override:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="n"&gt;COALESCE&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;store_val&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;value&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;default_val&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;value&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;product_name&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;catalog_product_entity&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;
&lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;catalog_product_entity_varchar&lt;/span&gt; &lt;span class="n"&gt;default_val&lt;/span&gt;
  &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;default_val&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
 &lt;span class="k"&gt;AND&lt;/span&gt; &lt;span class="n"&gt;default_val&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;attribute_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;73&lt;/span&gt;
 &lt;span class="k"&gt;AND&lt;/span&gt; &lt;span class="n"&gt;default_val&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;store_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt;
&lt;span class="k"&gt;LEFT&lt;/span&gt; &lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;catalog_product_entity_varchar&lt;/span&gt; &lt;span class="n"&gt;store_val&lt;/span&gt;
  &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;store_val&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
 &lt;span class="k"&gt;AND&lt;/span&gt; &lt;span class="n"&gt;store_val&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;attribute_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;73&lt;/span&gt;
 &lt;span class="k"&gt;AND&lt;/span&gt; &lt;span class="n"&gt;store_val&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;store_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Move &lt;code&gt;AND store_val.store_id = 2&lt;/code&gt; from the &lt;code&gt;ON&lt;/code&gt; clause into &lt;code&gt;WHERE&lt;/code&gt; and you have silently converted the &lt;code&gt;LEFT JOIN&lt;/code&gt; into an &lt;code&gt;INNER JOIN&lt;/code&gt;. Your product list collapses from 900,000 rows to the 8,000 products that happen to have a French override. &lt;strong&gt;Any predicate on the null-supplying side of an outer join, placed in &lt;code&gt;WHERE&lt;/code&gt;, eliminates the NULL-extended rows.&lt;/strong&gt; The only &lt;code&gt;WHERE&lt;/code&gt; predicate that belongs there is &lt;code&gt;IS NULL&lt;/code&gt;, when you're deliberately writing an anti-join.&lt;/p&gt;

&lt;p&gt;Sargability next, because two of our slowest reports were slow for this reason alone. Wrapping an indexed column in a function kills the index on every engine:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="nb"&gt;YEAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;2016&lt;/span&gt;         &lt;span class="c1"&gt;-- no index use&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="nb"&gt;DATE&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'2016-03-01'&lt;/span&gt; &lt;span class="c1"&gt;-- no index use&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="k"&gt;UPPER&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;email&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'A@B.COM'&lt;/span&gt;        &lt;span class="c1"&gt;-- no index use&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The remedies diverge. PostgreSQL and Oracle give you real expression and function-based indexes. MySQL didn't get functional indexes until 8.0.13 — before that you added a generated column and indexed that. SQL Server has no true expression index either; you add a computed column and index it, persisting it unless you're certain the expression is deterministic and precise. And two date traps that will bite you specifically: &lt;strong&gt;Oracle's &lt;code&gt;DATE&lt;/code&gt; always carries a time component&lt;/strong&gt;, so &lt;code&gt;WHERE created_at = DATE '2016-07-27'&lt;/code&gt; misses everything; and &lt;strong&gt;SQL Server's legacy &lt;code&gt;datetime&lt;/code&gt; has ~3.33ms precision and rounds&lt;/strong&gt;, so &lt;code&gt;BETWEEN '2016-03-01' AND '2016-03-31 23:59:59.999'&lt;/code&gt; rounds up to April 1 and double-counts a day. Half-open ranges — &lt;code&gt;&amp;gt;= start AND &amp;lt; end&lt;/code&gt; — are correct on all four. Just make it the habit.&lt;/p&gt;

&lt;p&gt;Implicit conversion deserves its own paragraph because it burned us on the SQL Server side within a week of go-live. Magento's &lt;code&gt;sales_order.increment_id&lt;/code&gt; is &lt;code&gt;varchar(32)&lt;/code&gt;, holding values like &lt;code&gt;'100000123'&lt;/code&gt;. Someone writes &lt;code&gt;WHERE o.increment_id = 100000123&lt;/code&gt; with a number, and MySQL converts the &lt;em&gt;column&lt;/em&gt; to a number to compare — full scan of twelve million rows. Oracle does the same thing with a &lt;code&gt;VARCHAR2&lt;/code&gt; column against a numeric literal. On SQL Server the shape is different and sneakier: an ORM sending &lt;code&gt;NVARCHAR&lt;/code&gt; parameters against a &lt;code&gt;VARCHAR&lt;/code&gt; column forces &lt;code&gt;CONVERT_IMPLICIT&lt;/code&gt; on the column, because &lt;code&gt;NVARCHAR&lt;/code&gt; wins the data-type precedence fight. That single mismatch is the number one cause of "it's fast in SSMS but slow from the app," and I have watched entire consulting engagements resolve to it.&lt;/p&gt;

&lt;p&gt;Set operators are where MySQL's era shows most starkly. &lt;code&gt;EXCEPT&lt;/code&gt; and &lt;code&gt;INTERSECT&lt;/code&gt; did not arrive in MySQL until &lt;strong&gt;8.0.31&lt;/strong&gt;. On the 5.6 box, "products in the catalog but not in the ERP feed" was hand-written as &lt;code&gt;NOT EXISTS&lt;/code&gt;. On SQL Server it was one line. And whichever engine you're on, ask the question that actually costs money:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- These are not the same&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="p"&gt;...&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;store_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;
&lt;span class="k"&gt;UNION&lt;/span&gt;      &lt;span class="c1"&gt;-- full dedupe: sort or hash the entire combined result&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="p"&gt;...&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;store_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="p"&gt;...&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;store_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;
&lt;span class="k"&gt;UNION&lt;/span&gt; &lt;span class="k"&gt;ALL&lt;/span&gt;  &lt;span class="c1"&gt;-- free, and provably correct here since the branches are disjoint&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="p"&gt;...&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;store_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Always use &lt;code&gt;UNION ALL&lt;/code&gt; unless dedupe is genuinely required.&lt;/strong&gt; On a 200-million-row order-history report that is the difference between forty seconds and eight minutes. And note that &lt;code&gt;EXCEPT&lt;/code&gt;/&lt;code&gt;MINUS&lt;/code&gt; deduplicate while &lt;code&gt;NOT EXISTS&lt;/code&gt; does not — they are not interchangeable when duplicates carry meaning.&lt;/p&gt;

&lt;p&gt;The last piece is the one that justified the whole project, and it's about join algorithms:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Algorithm&lt;/th&gt;
&lt;th&gt;PostgreSQL&lt;/th&gt;
&lt;th&gt;MySQL 5.7&lt;/th&gt;
&lt;th&gt;MySQL 8.0&lt;/th&gt;
&lt;th&gt;SQL Server&lt;/th&gt;
&lt;th&gt;Oracle&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Nested loop&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Hash join&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;td&gt;✅ (8.0.18+)&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Merge join&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;td&gt;❌ &lt;strong&gt;never&lt;/strong&gt;
&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;MySQL 5.7 had &lt;em&gt;only&lt;/em&gt; nested-loop variants. A six-way analytical join across orders, items, products, categories, customers, and store views — the kind of thing merchandising asks for casually — is resolved by SQL Server or Oracle with a couple of hash joins in seconds, and by MySQL 5.7 by looping. Ours ran for over three hours before we killed it. That query was the reason the SQL Server box stopped being idle. And note that even MySQL 8.0 still has no merge join, so pre-sorted large-to-large joins never get that option. &lt;strong&gt;MySQL is a weaker analytical engine than the other three, and Magento's architecture already concedes this&lt;/strong&gt; — that's what layer two is for.&lt;/p&gt;

&lt;p&gt;One last MySQL-specific correctness item, since it caused an upgrade scare: &lt;code&gt;ONLY_FULL_GROUP_BY&lt;/code&gt; has been on by default since 5.7.5, and a lot of Magento extensions broke when it landed. Many shops "fixed" it by disabling the mode. Don't. Code that runs with it off returns an arbitrary value from an arbitrary row in each group. That's a correctness bug that produces plausible numbers, which is the worst kind.&lt;/p&gt;




&lt;h2&gt;
  
  
  Using window functions like DENSE_RANK() and similar tools when appropriate
&lt;/h2&gt;

&lt;p&gt;Now the fun part. The report that started everything: &lt;em&gt;"Top five sellers per category, per store view."&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;On MySQL 5.7 this had been implemented as a correlated &lt;code&gt;COUNT&lt;/code&gt; subquery — for each product, count how many products in the same category sold more than it, and keep the ones where that count is under five. It worked, in the sense that it eventually returned. On SQL Server it became this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;WITH&lt;/span&gt; &lt;span class="n"&gt;sales&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;ccp&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;category_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
         &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;product_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
         &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;qty_ordered&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;units&lt;/span&gt;
  &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order_item&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;
  &lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;                &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_id&lt;/span&gt;
  &lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;catalog_category_product&lt;/span&gt; &lt;span class="n"&gt;ccp&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;ccp&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;product_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;product_id&lt;/span&gt;
  &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="s1"&gt;'2016-01-01'&lt;/span&gt;
    &lt;span class="k"&gt;AND&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'complete'&lt;/span&gt;
  &lt;span class="k"&gt;GROUP&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;ccp&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;category_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;i&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;product_id&lt;/span&gt;
&lt;span class="p"&gt;),&lt;/span&gt;
&lt;span class="n"&gt;ranked&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;category_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;product_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;units&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
         &lt;span class="n"&gt;DENSE_RANK&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;PARTITION&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;category_id&lt;/span&gt;
                            &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;units&lt;/span&gt; &lt;span class="k"&gt;DESC&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;product_id&lt;/span&gt; &lt;span class="k"&gt;ASC&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;rnk&lt;/span&gt;
  &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;ranked&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;rnk&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;=&lt;/span&gt; &lt;span class="mi"&gt;5&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Two things in there are deliberate, and both cause production tickets when omitted.&lt;/p&gt;

&lt;p&gt;The first is the choice of ranking function, and it is a &lt;em&gt;business&lt;/em&gt; decision, not a technical one. For units of &lt;code&gt;100, 100, 90, 80&lt;/code&gt;: &lt;code&gt;ROW_NUMBER()&lt;/code&gt; returns 1, 2, 3, 4 — exactly one row per position, ties broken arbitrarily. &lt;code&gt;RANK()&lt;/code&gt; returns 1, 1, 3, 4 — competition ranking, with gaps after ties. &lt;code&gt;DENSE_RANK()&lt;/code&gt; returns 1, 1, 2, 3 — no gaps, which is what you want for "top five distinct performance tiers." So: if two products tie for fifth place, does the homepage show five products or six? &lt;code&gt;ROW_NUMBER&lt;/code&gt; shows five and drops one at random, which is nondeterministic and a real bug. &lt;code&gt;DENSE_RANK&lt;/code&gt; shows six. &lt;strong&gt;Ask merchandising, then write down which one you were told.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;The second is &lt;code&gt;, product_id ASC&lt;/code&gt; in the window's &lt;code&gt;ORDER BY&lt;/code&gt;. Without it, a category where four products all sold 240 units produces a different top five on every execution. Then someone files "the homepage changed but we didn't change anything," and you spend a day proving the data is identical. &lt;strong&gt;Every window &lt;code&gt;ORDER BY&lt;/code&gt; gets a deterministic tiebreaker.&lt;/strong&gt; This single habit eliminates an entire genre of ticket.&lt;/p&gt;

&lt;p&gt;The next request was a running revenue total by day, and it produced the most instructive bug of the whole engagement:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- WRONG in a way that looks completely right&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;base_grand_total&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;base_grand_total&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;running_total&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When you write &lt;code&gt;OVER (ORDER BY y)&lt;/code&gt; with no frame clause, the implicit frame is &lt;code&gt;RANGE BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW&lt;/code&gt;. And &lt;strong&gt;&lt;code&gt;RANGE&lt;/code&gt; includes all peer rows — every row tied on &lt;code&gt;y&lt;/code&gt; — at once.&lt;/strong&gt; Orders share timestamps constantly. So every order placed on March 3rd got the full March 3rd total instead of a row-by-row running sum, and the chart came out as a staircase. Finance noticed four months later.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- What you almost always meant&lt;/span&gt;
&lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;base_grand_total&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;
  &lt;span class="k"&gt;ROWS&lt;/span&gt; &lt;span class="k"&gt;BETWEEN&lt;/span&gt; &lt;span class="n"&gt;UNBOUNDED&lt;/span&gt; &lt;span class="k"&gt;PRECEDING&lt;/span&gt; &lt;span class="k"&gt;AND&lt;/span&gt; &lt;span class="k"&gt;CURRENT&lt;/span&gt; &lt;span class="k"&gt;ROW&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;There is a second, entirely separate reason to write &lt;code&gt;ROWS&lt;/code&gt; explicitly, and it's SQL Server–specific: &lt;strong&gt;the default &lt;code&gt;RANGE&lt;/code&gt; frame uses an on-disk worktable spool, while &lt;code&gt;ROWS&lt;/code&gt; uses an in-memory spool.&lt;/strong&gt; On large partitions, specifying &lt;code&gt;ROWS&lt;/code&gt; is routinely a five-to-ten-times improvement even when the results would be identical. Make it mandatory in SQL Server code review. Related trap on all engines: &lt;code&gt;LAST_VALUE(x) OVER (ORDER BY y)&lt;/code&gt; returns the &lt;em&gt;current&lt;/em&gt; row's value, because the default frame ends at the current row. Use &lt;code&gt;ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING&lt;/code&gt;, or reverse the sort and use &lt;code&gt;FIRST_VALUE&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;LAG&lt;/code&gt; and &lt;code&gt;LEAD&lt;/code&gt; opened up analysis they'd never attempted, because expressing "days since this customer's previous order" in MySQL 5.7 required a self-join with a correlated &lt;code&gt;MAX&lt;/code&gt;, and nobody wanted to maintain it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="n"&gt;LAG&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;PARTITION&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;
                             &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;prev_order_at&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="n"&gt;DATEDIFF&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;day&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                &lt;span class="n"&gt;LAG&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;PARTITION&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;
                                      &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
                &lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;days_since_prev&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'complete'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That query, wrapped in a percentile, became their repeat-purchase-window model and drove the email cadence for two years.&lt;/p&gt;

&lt;p&gt;One idiom you will write weekly — deduplication — and one limitation that surprises everyone. Because window functions are evaluated &lt;em&gt;after&lt;/em&gt; &lt;code&gt;WHERE&lt;/code&gt;, you cannot filter on one in the &lt;code&gt;WHERE&lt;/code&gt; clause. You need a wrapper:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;WITH&lt;/span&gt; &lt;span class="n"&gt;ranked&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
         &lt;span class="n"&gt;ROW_NUMBER&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;PARTITION&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;attribute_id&lt;/span&gt;
                            &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="k"&gt;CASE&lt;/span&gt; &lt;span class="k"&gt;WHEN&lt;/span&gt; &lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;store_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt; &lt;span class="k"&gt;THEN&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt; &lt;span class="k"&gt;ELSE&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="k"&gt;END&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                                     &lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;value_id&lt;/span&gt; &lt;span class="k"&gt;DESC&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;rn&lt;/span&gt;
  &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;catalog_product_entity_varchar&lt;/span&gt; &lt;span class="n"&gt;v&lt;/span&gt;
  &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;v&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;store_id&lt;/span&gt; &lt;span class="k"&gt;IN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;ranked&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;rn&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;None of PostgreSQL, MySQL, SQL Server, or Oracle support &lt;code&gt;QUALIFY&lt;/code&gt;&lt;/strong&gt; — that's Teradata, Snowflake, and DuckDB. Expect to write the CTE every time. (Re-check that each major release; it's exactly the kind of sugar that ships quietly.) PostgreSQL does give you &lt;code&gt;DISTINCT ON&lt;/code&gt; as a shorthand for the &lt;code&gt;rn = 1&lt;/code&gt; case, and it's often faster there.&lt;/p&gt;

&lt;p&gt;Availability, since this is the most version-gated area in SQL:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Basic windows&lt;/th&gt;
&lt;th&gt;Full frames&lt;/th&gt;
&lt;th&gt;
&lt;code&gt;GROUPS&lt;/code&gt;/&lt;code&gt;EXCLUDE&lt;/code&gt;
&lt;/th&gt;
&lt;th&gt;Named windows&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Oracle&lt;/td&gt;
&lt;td&gt;8i (1999)&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;GROUPS&lt;/code&gt; in 21c+&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;SQL Server&lt;/td&gt;
&lt;td&gt;2005 (ranking only)&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;2012+&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;PostgreSQL&lt;/td&gt;
&lt;td&gt;8.4&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅ (11+)&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MySQL&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;8.0 only&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Two performance notes to carry. An index on &lt;code&gt;(partition_cols, order_cols)&lt;/code&gt; lets PostgreSQL, Oracle, and SQL Server skip the sort entirely — on a reporting table this is frequently the highest-leverage index you will ever create. And &lt;strong&gt;MySQL sorts once per distinct window specification&lt;/strong&gt;, so three windows with three different &lt;code&gt;ORDER BY&lt;/code&gt; clauses means three sorts; consolidate them.&lt;/p&gt;

&lt;p&gt;Finally, know when &lt;em&gt;not&lt;/em&gt; to use one. If you only need aggregates at the group grain, &lt;code&gt;GROUP BY&lt;/code&gt; is cheaper — it collapses rows, while windows preserve them. &lt;code&gt;SELECT DISTINCT customer_id, SUM(x) OVER (PARTITION BY customer_id)&lt;/code&gt; is a &lt;code&gt;GROUP BY&lt;/code&gt; that got lost on the way to work.&lt;/p&gt;




&lt;h2&gt;
  
  
  Working with JSON data in the database
&lt;/h2&gt;

&lt;p&gt;The fraud team's ticket: &lt;em&gt;"All orders in the last ninety days paid through gateway X, filtered by token prefix."&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;He went looking and found &lt;code&gt;sales_order_payment.additional_information&lt;/code&gt;. Here is the first lesson, and most JSON guides skip it: &lt;strong&gt;it isn't a JSON column.&lt;/strong&gt; It's a &lt;code&gt;text&lt;/code&gt; column containing a serialized JSON document. Same for &lt;code&gt;sales_order_item.product_options&lt;/code&gt; and &lt;code&gt;quote_item_option.value&lt;/code&gt;. Twelve million rows, no index, no validation, no schema, no type checking.&lt;/p&gt;

&lt;p&gt;Before any syntax, the design rule. JSON columns are for genuinely schemaless, sparse, or third-party-shaped payloads: gateway responses, webhook bodies, per-tenant custom fields, audit snapshots. &lt;strong&gt;The test is simple — if you filter, join, sort, or aggregate on it regularly, it should be a column.&lt;/strong&gt; Every engine's JSON indexing story is worse than a plain B-tree on a scalar, and you also give up &lt;code&gt;NOT NULL&lt;/code&gt;, foreign keys, and check constraints.&lt;/p&gt;

&lt;p&gt;Magento actually made this call correctly, and you can see it in the schema: &lt;code&gt;sales_order_grid&lt;/code&gt; has a real &lt;code&gt;payment_method&lt;/code&gt; column. It didn't have to — the data is right there in &lt;code&gt;additional_information&lt;/code&gt; — but the admin grid filters on it, so it became a column in the read model. That's the rule applied by people who had to live with the consequences.&lt;/p&gt;

&lt;p&gt;The second rule, which I'll state harshly because I've cleaned up after it three times: &lt;strong&gt;do not use JSON as an EAV escape hatch.&lt;/strong&gt; "Just put the extra attributes in a JSON blob" is how you get a 400GB table nobody understands where every query is a full scan. Magento's EAV is at least indexed and introspectable. A blob is not.&lt;/p&gt;

&lt;p&gt;On MySQL 5.6 there was no help at all — JSON functions arrived in 5.7, and even then, &lt;strong&gt;there is no direct index on a JSON path.&lt;/strong&gt; You must materialize the value first:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- MySQL 5.7: generated column, then index it&lt;/span&gt;
&lt;span class="k"&gt;ALTER&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;sales_order_payment&lt;/span&gt;
  &lt;span class="k"&gt;ADD&lt;/span&gt; &lt;span class="k"&gt;COLUMN&lt;/span&gt; &lt;span class="n"&gt;gateway&lt;/span&gt; &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;50&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;JSON_UNQUOTE&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;JSON_EXTRACT&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;additional_information&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'$.method_title'&lt;/span&gt;&lt;span class="p"&gt;)))&lt;/span&gt; &lt;span class="n"&gt;STORED&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="k"&gt;ADD&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;idx_gateway&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;gateway&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="c1"&gt;-- MySQL 8.0.13+: functional index, same thing, less clutter&lt;/span&gt;
&lt;span class="k"&gt;ALTER&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;sales_order_payment&lt;/span&gt;
  &lt;span class="k"&gt;ADD&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;idx_gateway&lt;/span&gt; &lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="k"&gt;CAST&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;additional_information&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="s1"&gt;'$.method_title'&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="nb"&gt;CHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;50&lt;/span&gt;&lt;span class="p"&gt;))));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;And there's an operational gotcha that isn't obvious: partial in-place JSON updates only happen under narrow conditions. Otherwise MySQL rewrites the entire document &lt;em&gt;and logs the whole thing to the binlog&lt;/em&gt;, and your read replicas fall behind. I have seen replication lag take out a storefront's search because someone added a JSON audit trail to order saves.&lt;/p&gt;

&lt;p&gt;On SQL Server the pattern we actually shipped was to shred at load time rather than query in place, which is the right answer on any engine. &lt;code&gt;OPENJSON&lt;/code&gt; with an explicit &lt;code&gt;WITH&lt;/code&gt; clause is dramatically faster than the default key/value form, and it hands you typed columns:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- Shred once, during ETL, into a real relational table&lt;/span&gt;
&lt;span class="k"&gt;INSERT&lt;/span&gt; &lt;span class="k"&gt;INTO&lt;/span&gt; &lt;span class="n"&gt;dw&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;OrderPayment&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;OrderId&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;MethodTitle&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;CcType&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;CcLast4&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;AmountPaid&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;parent_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;method_title&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;cc_type&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;cc_last4&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;amount_paid&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;stg&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;sales_order_payment&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt;
&lt;span class="k"&gt;CROSS&lt;/span&gt; &lt;span class="n"&gt;APPLY&lt;/span&gt; &lt;span class="n"&gt;OPENJSON&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;additional_information&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;WITH&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="n"&gt;method_title&lt;/span&gt; &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;64&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;  &lt;span class="s1"&gt;'$.method_title'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;cc_type&lt;/span&gt;      &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;16&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;  &lt;span class="s1"&gt;'$.cc_type'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="n"&gt;cc_last4&lt;/span&gt;     &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;4&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;span class="s1"&gt;'$.cc_last4'&lt;/span&gt;
  &lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now the fraud query is a seek against an indexed &lt;code&gt;VARCHAR&lt;/code&gt; column, and the JSON never appears in a &lt;code&gt;WHERE&lt;/code&gt; clause again. If you must keep JSON in place on SQL Server 2016–2022, it's &lt;code&gt;NVARCHAR(MAX)&lt;/code&gt; plus a persisted computed column plus an index, and you should always add &lt;code&gt;CHECK (ISJSON(Payload) = 1)&lt;/code&gt; or you will accumulate malformed rows. SQL Server 2025 finally added a native binary &lt;code&gt;json&lt;/code&gt; type and a JSON index, but check the fine print before you rely on it — as of writing, the type is GA on Azure SQL and in preview on-prem, and creating a JSON index takes a schema-modification lock for the entire operation with no &lt;code&gt;ONLINE&lt;/code&gt; option, which on a twelve-million-row table means a maintenance window.&lt;/p&gt;

&lt;p&gt;For completeness, the capability landscape, because if you land on PostgreSQL or Oracle the answer is much better:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;&lt;/th&gt;
&lt;th&gt;PostgreSQL&lt;/th&gt;
&lt;th&gt;MySQL 8.0&lt;/th&gt;
&lt;th&gt;SQL Server&lt;/th&gt;
&lt;th&gt;Oracle&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Native type&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;json&lt;/code&gt; / &lt;strong&gt;&lt;code&gt;jsonb&lt;/code&gt;&lt;/strong&gt; (binary)&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;JSON&lt;/code&gt; (binary); MariaDB: &lt;code&gt;LONGTEXT&lt;/code&gt; alias&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;NVARCHAR(MAX)&lt;/code&gt;; native in 2025&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;JSON&lt;/code&gt; in 21c+&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Containment test&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;@&amp;gt;&lt;/code&gt; (indexed)&lt;/td&gt;
&lt;td&gt;&lt;code&gt;JSON_CONTAINS&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;JSON_PATH_EXISTS&lt;/code&gt; (2022+)&lt;/td&gt;
&lt;td&gt;&lt;code&gt;JSON_EXISTS&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Shred to rows&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;jsonb_array_elements&lt;/code&gt;, &lt;code&gt;JSON_TABLE&lt;/code&gt; (17+)&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;JSON_TABLE&lt;/code&gt; (8.0.4+)&lt;/td&gt;
&lt;td&gt;&lt;code&gt;OPENJSON&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;JSON_TABLE&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;General index&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;GIN on &lt;code&gt;jsonb&lt;/code&gt;&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;td&gt;JSON index (2025, preview)&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;&lt;code&gt;CREATE SEARCH INDEX … FOR JSON&lt;/code&gt;&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;PostgreSQL's GIN index on &lt;code&gt;jsonb&lt;/code&gt; and Oracle's JSON search index are the only two that index the whole document generically — everywhere else you're indexing one path at a time. Watch out for TOAST on PostgreSQL, though: pulling one small field out of a 2KB document across millions of rows means detoast-and-decompress &lt;em&gt;per row&lt;/em&gt;, and it's far slower than people expect. And note MariaDB is not MySQL here at all — its &lt;code&gt;JSON&lt;/code&gt; is an alias for &lt;code&gt;LONGTEXT&lt;/code&gt; with a validity check, with no binary storage and no multi-valued indexes.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Portable advice: treat JSON as an opaque payload.&lt;/strong&gt; Store it, retrieve it whole, parse it in the application. The moment you query inside it, you've committed to that engine. Extract the fields you query into real columns at write time — which is, once again, exactly what &lt;code&gt;sales_order_grid&lt;/code&gt; does.&lt;/p&gt;




&lt;h2&gt;
  
  
  Indexing strategy
&lt;/h2&gt;

&lt;p&gt;The layered-navigation ticket — &lt;em&gt;"filtering the Jackets category takes eleven seconds"&lt;/em&gt; — is the best indexing lesson in the Magento schema, because the answer is not "add an index."&lt;/p&gt;

&lt;p&gt;Look at an EAV value table (2.x, roughly — always confirm against your own &lt;code&gt;SHOW CREATE TABLE&lt;/code&gt; and the module's &lt;code&gt;db_schema.xml&lt;/code&gt;):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;catalog_product_entity_varchar&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="n"&gt;value_id&lt;/span&gt;     &lt;span class="nb"&gt;int&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt; &lt;span class="n"&gt;AUTO_INCREMENT&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;attribute_id&lt;/span&gt; &lt;span class="nb"&gt;smallint&lt;/span&gt; &lt;span class="nb"&gt;unsigned&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;store_id&lt;/span&gt;     &lt;span class="nb"&gt;smallint&lt;/span&gt; &lt;span class="nb"&gt;unsigned&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;entity_id&lt;/span&gt;    &lt;span class="nb"&gt;int&lt;/span&gt; &lt;span class="nb"&gt;unsigned&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;value&lt;/span&gt;        &lt;span class="nb"&gt;varchar&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;255&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
  &lt;span class="k"&gt;PRIMARY&lt;/span&gt; &lt;span class="k"&gt;KEY&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;value_id&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
  &lt;span class="k"&gt;UNIQUE&lt;/span&gt; &lt;span class="k"&gt;KEY&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;attribute_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;store_id&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
  &lt;span class="k"&gt;KEY&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;attribute_id&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
  &lt;span class="k"&gt;KEY&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;store_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That unique key is beautifully designed for one question: &lt;em&gt;give me every attribute of product 88213.&lt;/em&gt; Leading column &lt;code&gt;entity_id&lt;/code&gt;, index seek, done — that's the product detail page. Now ask layered navigation's question: &lt;em&gt;give me every product where attribute 167 equals 'Blue'.&lt;/em&gt; Your predicate is on &lt;code&gt;attribute_id&lt;/code&gt; and &lt;code&gt;value&lt;/code&gt;. The composite index leads with &lt;code&gt;entity_id&lt;/code&gt;, so it's useless. The standalone &lt;code&gt;KEY (attribute_id)&lt;/code&gt; hands you every row for that attribute across the entire catalog and then filters &lt;code&gt;value&lt;/code&gt; by hand.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The leading-column rule:&lt;/strong&gt; an index on &lt;code&gt;(a, b, c)&lt;/code&gt; serves predicates on &lt;code&gt;a&lt;/code&gt;, &lt;code&gt;(a,b)&lt;/code&gt;, and &lt;code&gt;(a,b,c)&lt;/code&gt;. It does not efficiently serve &lt;code&gt;b&lt;/code&gt; alone. All four engines can fall back to a full index scan, but that's not what you designed. &lt;strong&gt;When two hot access paths need opposite column orders, you need two structures.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;On SQL Server we solved it with an index. On MySQL, Magento solved it with a whole table:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- SQL Server: build the reverse-ordered index, with INCLUDE for coverage&lt;/span&gt;
&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;IX_ProductVarchar_Attr_Value&lt;/span&gt;
  &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;dw&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;CatalogProductEntityVarchar&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;attribute_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;store_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;value&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="n"&gt;INCLUDE&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;entity_id&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That &lt;code&gt;INCLUDE&lt;/code&gt; clause is worth its own paragraph. Included columns live in the index leaf but not the key, so they don't widen the seek structure and they don't affect ordering, but they make the index &lt;em&gt;covering&lt;/em&gt; — the engine never touches the base table. &lt;strong&gt;MySQL has no &lt;code&gt;INCLUDE&lt;/code&gt;.&lt;/strong&gt; Neither does Oracle. On both, extra columns must become key columns, which widens every level of the B-tree. PostgreSQL added &lt;code&gt;INCLUDE&lt;/code&gt; in version 11. This is a small syntax difference with a large physical consequence.&lt;/p&gt;

&lt;p&gt;Magento's equivalent is &lt;code&gt;catalog_product_index_eav&lt;/code&gt;, keyed roughly &lt;code&gt;(attribute_id, store_id, value, entity_id)&lt;/code&gt; — exactly the reversed column order, built as a separate physical table because that was the tool available. Same idea, ten thousand times the machinery.&lt;/p&gt;

&lt;p&gt;Two more universal principles before the divergences. &lt;strong&gt;Equality columns first, then range, then include-only:&lt;/strong&gt; for &lt;code&gt;WHERE store_id = ? AND status = ? AND created_at &amp;gt; ?&lt;/code&gt;, index &lt;code&gt;(store_id, status, created_at)&lt;/code&gt;. Put &lt;code&gt;created_at&lt;/code&gt; before &lt;code&gt;status&lt;/code&gt; and the index can only seek to the range start and must filter everything after. And &lt;strong&gt;every index is a tax on writes&lt;/strong&gt; — ten indexes means ten structures maintained per insert. Magento's synchronous &lt;code&gt;sales_order_grid&lt;/code&gt; writes are a known Black Friday bottleneck for exactly this reason, which is why &lt;code&gt;dev/grid/async_indexing&lt;/code&gt; exists.&lt;/p&gt;

&lt;p&gt;Now the structural difference that shapes your primary key everywhere:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Table storage&lt;/th&gt;
&lt;th&gt;Consequence&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;MySQL/InnoDB&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;Always&lt;/strong&gt; clustered on the PK. Secondary indexes store the &lt;strong&gt;PK value&lt;/strong&gt; as the row pointer.&lt;/td&gt;
&lt;td&gt;A wide PK is duplicated into &lt;em&gt;every&lt;/em&gt; secondary index. Random PKs split pages on every insert.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;SQL Server&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Clustered index optional; without one it's a heap.&lt;/td&gt;
&lt;td&gt;Same amplification when clustered. Heaps accumulate forwarded records.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;PostgreSQL&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Always a heap. &lt;code&gt;CLUSTER&lt;/code&gt; is a one-time reorg that doesn't hold.&lt;/td&gt;
&lt;td&gt;Physical order drifts; correlation drives range-scan cost.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Oracle&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Heap by default; Index-Organized Tables available.&lt;/td&gt;
&lt;td&gt;IOTs are excellent for narrow lookup tables, poor for wide ones.&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Magento gets this right, and it's worth noticing: every entity PK is a narrow, monotonic auto-increment integer. Not a UUID. On InnoDB, a random UUIDv4 clustered primary key is a documented performance disaster — insert throughput collapses as the B-tree fragments, and every secondary index carries 16 to 36 bytes per entry. If you need distributed IDs, use a time-ordered variant (UUIDv7, &lt;code&gt;NEWSEQUENTIALID()&lt;/code&gt;, ULID) stored as &lt;code&gt;BINARY(16)&lt;/code&gt; or &lt;code&gt;uniqueidentifier&lt;/code&gt;, never as a 36-character string.&lt;/p&gt;

&lt;p&gt;Two things bit us during the migration and will bite you. First, &lt;strong&gt;InnoDB automatically creates an index on foreign key columns; PostgreSQL, SQL Server, and Oracle do not.&lt;/strong&gt; MySQL had been doing it for these developers their entire careers, so the moment the schema landed on SQL Server, the "get all items for this order" query fell off a cliff. Unindexed FKs also make parent deletes scan the child table. On Oracle it's worse still — an unindexed FK makes the engine take a share lock on the child table during parent deletes and PK updates, which since 9i is acquired and released per statement rather than held for the transaction, but is still a blocking window on top of a full scan. &lt;strong&gt;Every FK column gets an index, on every engine.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Second, &lt;strong&gt;filtered indexes.&lt;/strong&gt; MySQL has no partial index of any kind:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- SQL Server: 14,000 entries instead of 12,000,000&lt;/span&gt;
&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;IX_Orders_Pending&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;dw&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SalesOrder&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;CreatedAt&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;Status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'pending_payment'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;PostgreSQL spells it the same way with &lt;code&gt;WHERE&lt;/code&gt;. MySQL's standard workaround is a separate work-queue table that rows are deleted from once processed — and that is precisely what Magento's &lt;code&gt;*_cl&lt;/code&gt; changelog tables are. A partial index, implemented as a table, because the engine doesn't offer one. (One SQL Server gotcha: the optimizer only uses a filtered index when the parameter is provably inside the filter, so &lt;code&gt;WHERE Status = @s&lt;/code&gt; often won't use it. &lt;code&gt;OPTION (RECOMPILE)&lt;/code&gt; or a literal fixes it, and this surprises people constantly.)&lt;/p&gt;

&lt;p&gt;Last, plan stability, because "it was fast yesterday" has a different cause on each engine. On SQL Server it's &lt;strong&gt;parameter sniffing&lt;/strong&gt; — the first execution's parameter values shape the cached plan for everyone, so a plan built for a tiny store view then serves the huge one; remedies are &lt;code&gt;OPTION (RECOMPILE)&lt;/code&gt;, &lt;code&gt;OPTIMIZE FOR&lt;/code&gt;, and Query Store forced plans. On PostgreSQL, prepared statements switch to a generic plan after five executions, and skewed data plus a generic plan is a bad plan. On MySQL the problem is upstream of all that: &lt;strong&gt;InnoDB index statistics are sampled&lt;/strong&gt;, and on a sixty-million-row EAV table the defaults are wildly wrong. Raise &lt;code&gt;innodb_stats_persistent_sample_pages&lt;/code&gt; on your big tables and re-run &lt;code&gt;ANALYZE TABLE&lt;/code&gt;. That one setting bought us a measurable improvement on the Magento side without touching a query.&lt;/p&gt;




&lt;h2&gt;
  
  
  Normalization vs selective denormalization
&lt;/h2&gt;

&lt;p&gt;Here's where the second engine stopped being a convenience and became an argument about architecture.&lt;/p&gt;

&lt;p&gt;Start from the default position: &lt;strong&gt;normalize to 3NF and stay there unless you have a measured reason not to.&lt;/strong&gt; Normalization gives you one place to update each fact, constraints that actually work, narrower rows (more rows per page, better cache hit rate), and a schema that survives requirement changes. Denormalization is a performance optimization with a correctness cost — you're trading guaranteed consistency for speed, and like every optimization you measure first and plan the maintenance.&lt;/p&gt;

&lt;p&gt;The distinction that matters more than any other is &lt;strong&gt;derived versus duplicated&lt;/strong&gt;. Derived data can be recomputed from source — a running total, an order count, a price index. If it drifts, you rebuild it, and the risk is manageable. Duplicated data has no single source of truth once both copies are editable, and that is where corruption lives. Denormalize derived data freely, provided you build the rebuild path. Duplicate raw data only with a very clear write-path story.&lt;/p&gt;

&lt;p&gt;Magento is a catalogue of both, and reading it this way makes the schema legible. &lt;code&gt;catalog_product_index_price&lt;/code&gt; is derived — a precomputed final price per product, per customer group, per website, fully rebuildable. &lt;code&gt;sales_order_grid&lt;/code&gt; and &lt;code&gt;customer_grid_flat&lt;/code&gt; are derived, and notice they exist &lt;em&gt;per UI screen&lt;/em&gt; rather than as one big denormalized table; the shape follows the access path. &lt;code&gt;catalog_category_entity.children_count&lt;/code&gt; is a counter cache. And &lt;code&gt;catalog_product_flat_*&lt;/code&gt; is the cautionary tale — Adobe has discouraged flat catalog since 2.3 because the write amplification and reindex cost outgrew the read benefit. &lt;strong&gt;Denormalization has an expiry date. Revisit yours.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Now the engine gap, which is the largest of any topic in this document:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Mechanism&lt;/th&gt;
&lt;th&gt;Notes&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Oracle&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;Materialized views&lt;/strong&gt; with query rewrite, &lt;code&gt;FAST REFRESH ON COMMIT&lt;/code&gt;, MV logs&lt;/td&gt;
&lt;td&gt;Best in class. The optimizer transparently rewrites queries to use the MV — the application never changes.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;SQL Server&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;Indexed views&lt;/strong&gt; (&lt;code&gt;WITH SCHEMABINDING&lt;/code&gt; + unique clustered index)&lt;/td&gt;
&lt;td&gt;Maintained synchronously, always correct. Auto-matched by the optimizer in Enterprise; elsewhere you need &lt;code&gt;NOEXPAND&lt;/code&gt;.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;PostgreSQL&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Materialized views, manual &lt;code&gt;REFRESH&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;No incremental refresh, no automatic rewrite.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;MySQL / MariaDB&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;Nothing.&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Build summary tables yourself. Plan for it from day one.&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Which brings us to the punchline of the entire afternoon. Magento's indexer subsystem — &lt;code&gt;mview_state&lt;/code&gt;, &lt;code&gt;catalog_product_price_cl&lt;/code&gt;, &lt;code&gt;catalog_category_product_cl&lt;/code&gt;, invalidation flags, "Update on Save" versus "Update by Schedule," &lt;code&gt;bin/magento indexer:reindex&lt;/code&gt; — &lt;strong&gt;is a hand-rolled incremental materialized view engine, written in PHP, because MySQL doesn't have one.&lt;/strong&gt; On SQL Server, the daily revenue rollup that had been a cron job, a summary table, and about four hundred lines of PHP became this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;VIEW&lt;/span&gt; &lt;span class="n"&gt;dw&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;vDailyRevenue&lt;/span&gt; &lt;span class="k"&gt;WITH&lt;/span&gt; &lt;span class="n"&gt;SCHEMABINDING&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;store_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;CAST&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="nb"&gt;date&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;order_date&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="n"&gt;COUNT_BIG&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;               &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;order_count&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;base_grand_total&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;    &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;revenue&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;dbo&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SalesOrder&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'complete'&lt;/span&gt;
&lt;span class="k"&gt;GROUP&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;store_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;CAST&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="nb"&gt;date&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="k"&gt;GO&lt;/span&gt;

&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;UNIQUE&lt;/span&gt; &lt;span class="n"&gt;CLUSTERED&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;IX_vDailyRevenue&lt;/span&gt;
  &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;dw&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;vDailyRevenue&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;store_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;order_date&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The engine now maintains that aggregate &lt;strong&gt;synchronously, transactionally, on every write&lt;/strong&gt;. It cannot drift, because drift is not representable. There is no cron job to monitor, no changelog table to drain, no "the indexer is stuck" ticket at 2am. The restrictions are real and you should know them going in — &lt;code&gt;SCHEMABINDING&lt;/code&gt; required, no outer joins, no subqueries, &lt;code&gt;COUNT_BIG(*)&lt;/code&gt; instead of &lt;code&gt;COUNT(*)&lt;/code&gt;, and &lt;code&gt;SUM&lt;/code&gt; requires a &lt;code&gt;COUNT_BIG&lt;/code&gt; column so the engine can maintain it incrementally — but within those bounds it is the closest thing to free correctness in this entire article.&lt;/p&gt;

&lt;p&gt;Oracle goes one step further, and it's the step that matters most for a legacy application you can't change. With query rewrite enabled, you create the materialized view and then &lt;em&gt;do not touch the application&lt;/em&gt;; the optimizer silently redirects qualifying queries to the MV:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="n"&gt;MATERIALIZED&lt;/span&gt; &lt;span class="k"&gt;VIEW&lt;/span&gt; &lt;span class="n"&gt;mv_daily_revenue&lt;/span&gt;
  &lt;span class="n"&gt;BUILD&lt;/span&gt; &lt;span class="k"&gt;IMMEDIATE&lt;/span&gt;
  &lt;span class="n"&gt;REFRESH&lt;/span&gt; &lt;span class="n"&gt;FAST&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="k"&gt;COMMIT&lt;/span&gt;
  &lt;span class="n"&gt;ENABLE&lt;/span&gt; &lt;span class="n"&gt;QUERY&lt;/span&gt; &lt;span class="n"&gt;REWRITE&lt;/span&gt;
&lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;store_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;TRUNC&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;order_date&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
          &lt;span class="k"&gt;COUNT&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;order_count&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;base_grand_total&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;revenue&lt;/span&gt;
   &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;sales_order&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'complete'&lt;/span&gt;
   &lt;span class="k"&gt;GROUP&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;store_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;TRUNC&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;The design consequence, stated as sharply as I can: the same denormalization is far cheaper on Oracle than on MySQL.&lt;/strong&gt; On Oracle you can denormalize invisibly and keep the logical model clean. On MySQL every denormalization is explicit, hand-maintained, and a permanent obligation. Weight that when you choose a stack, and don't pretend the obligation isn't there.&lt;/p&gt;

&lt;p&gt;Whatever engine you land on, there are three ways to keep redundant data honest, in order of preference: a &lt;strong&gt;constraint&lt;/strong&gt; if the engine can enforce it declaratively, a &lt;strong&gt;trigger&lt;/strong&gt; if it can't (synchronous and correct, but it adds latency to every write and gets bypassed by bulk loads), and a &lt;strong&gt;batch reconciliation job&lt;/strong&gt; that recomputes and reports drift. &lt;strong&gt;Build the third one regardless of whether you have the first two.&lt;/strong&gt; A denormalization without a drift-detection job is a scheduled incident. Magento gives you &lt;code&gt;indexer:reindex&lt;/code&gt; as the repair path; it does not give you the detection. Write that yourself.&lt;/p&gt;




&lt;h2&gt;
  
  
  When some redundancy improves performance
&lt;/h2&gt;

&lt;p&gt;His next question was the sharp one: &lt;em&gt;"Then why does &lt;code&gt;sales_order_item&lt;/code&gt; store the product name and SKU? Isn't that exactly the duplication you just warned about?"&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;No. And this is the distinction I most want you to leave with. &lt;code&gt;sales_order_item.name&lt;/code&gt;, &lt;code&gt;.sku&lt;/code&gt;, and &lt;code&gt;.price&lt;/code&gt; are neither derived nor duplicated — they are &lt;strong&gt;immutable historical snapshots&lt;/strong&gt;. &lt;code&gt;sales_order_item.price&lt;/code&gt; is not a stale copy of the product's current price. It is a different fact — &lt;em&gt;what we charged this customer on this date&lt;/em&gt; — captured at a different point in time. Joining to &lt;code&gt;catalog_product_entity&lt;/code&gt; to get a historical price is a &lt;strong&gt;bug&lt;/strong&gt;, not an optimization, and in some jurisdictions it's a compliance failure.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Snapshot anything that appears on a legal or financial document.&lt;/strong&gt; Order lines, invoice lines, tax rates applied, shipping rates quoted, the customer's address as it was at the time. That rule alone will save you a reconciliation project.&lt;/p&gt;

&lt;p&gt;The second category worth the redundancy is the &lt;strong&gt;counter cache&lt;/strong&gt;: &lt;code&gt;post.comment_count&lt;/code&gt; instead of &lt;code&gt;COUNT(*)&lt;/code&gt; on every page load, or Magento's &lt;code&gt;catalog_category_entity.children_count&lt;/code&gt;. Worth it when reads vastly outnumber writes. The gotcha at scale is that every child insert updates the same parent row, so a hot node becomes a lock convoy — and on InnoDB, with Repeatable Read and gap locks, that shows up as deadlocks rather than just slowness. Mitigations are sharded counters (N rows per parent, summed on read), asynchronous batch updates, or accepting eventual consistency with a nightly recompute.&lt;/p&gt;

&lt;p&gt;The third and highest-value category is the &lt;strong&gt;precomputed aggregate&lt;/strong&gt;, which we covered above. If you take one denormalization pattern into your career, make it this one. Juniors underuse it more than any other technique, and it is almost always the right answer for reporting over a large OLTP table.&lt;/p&gt;

&lt;p&gt;The fourth is worth calling out because it looks wrong and isn't: &lt;strong&gt;flattening a hot lookup to avoid a two-hop join.&lt;/strong&gt; Carrying &lt;code&gt;store_id&lt;/code&gt; on every table in a multi-store system, even where it's derivable through a parent, so that every index can lead with it and every query can filter on it directly. That's not a shortcut, it's standard multi-tenant design, and it's what makes row-level security work cleanly later.&lt;/p&gt;

&lt;p&gt;And the fifth is &lt;strong&gt;materialized path for deep hierarchies&lt;/strong&gt;, which Magento does in &lt;code&gt;catalog_category_entity&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- path = '1/2/13/47', alongside parent_id, level, children_count&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;catalog_category_entity&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;path&lt;/span&gt; &lt;span class="k"&gt;LIKE&lt;/span&gt; &lt;span class="s1"&gt;'1/2/13/%'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;One indexed range scan instead of a recursion. Recursive CTEs are available on all four engines now — MySQL from 8.0, MariaDB from 10.2 — but for a category tree read thousands of times a second on every page render, a prefix &lt;code&gt;LIKE&lt;/code&gt; on an indexed column wins every time. Store the path &lt;em&gt;alongside&lt;/em&gt; the parent FK: the FK is truth, the path is derived, and you rebuild the path if it drifts.&lt;/p&gt;

&lt;p&gt;Here's the redundancy the second engine gave us for free, and it's the one the developer was most excited about. They had a hand-rolled &lt;code&gt;sales_order_audit&lt;/code&gt; table maintained by PHP observers, which was incomplete, which everyone knew, and which nobody wanted to fix. On SQL Server 2016+ that entire mechanism is a table option:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;ALTER&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;dw&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SalesOrder&lt;/span&gt;
  &lt;span class="k"&gt;ADD&lt;/span&gt; &lt;span class="n"&gt;ValidFrom&lt;/span&gt; &lt;span class="n"&gt;datetime2&lt;/span&gt; &lt;span class="k"&gt;GENERATED&lt;/span&gt; &lt;span class="n"&gt;ALWAYS&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="k"&gt;ROW&lt;/span&gt; &lt;span class="k"&gt;START&lt;/span&gt; &lt;span class="n"&gt;HIDDEN&lt;/span&gt;
        &lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;DF_ValidFrom&lt;/span&gt; &lt;span class="k"&gt;DEFAULT&lt;/span&gt; &lt;span class="n"&gt;SYSUTCDATETIME&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;
      &lt;span class="n"&gt;ValidTo&lt;/span&gt;   &lt;span class="n"&gt;datetime2&lt;/span&gt; &lt;span class="k"&gt;GENERATED&lt;/span&gt; &lt;span class="n"&gt;ALWAYS&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="k"&gt;ROW&lt;/span&gt; &lt;span class="k"&gt;END&lt;/span&gt;   &lt;span class="n"&gt;HIDDEN&lt;/span&gt;
        &lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;DF_ValidTo&lt;/span&gt;   &lt;span class="k"&gt;DEFAULT&lt;/span&gt; &lt;span class="s1"&gt;'9999-12-31 23:59:59.9999999'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="n"&gt;PERIOD&lt;/span&gt; &lt;span class="k"&gt;FOR&lt;/span&gt; &lt;span class="n"&gt;SYSTEM_TIME&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ValidFrom&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ValidTo&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="k"&gt;ALTER&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;dw&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SalesOrder&lt;/span&gt;
  &lt;span class="k"&gt;SET&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;SYSTEM_VERSIONING&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;HISTORY_TABLE&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;dw&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SalesOrderHistory&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;

&lt;span class="c1"&gt;-- and then, for free:&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;dw&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SalesOrder&lt;/span&gt;
&lt;span class="k"&gt;FOR&lt;/span&gt; &lt;span class="n"&gt;SYSTEM_TIME&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="k"&gt;OF&lt;/span&gt; &lt;span class="s1"&gt;'2016-11-25 09:00:00'&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;entity_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;4471102&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's redundancy — a full second copy of every changed row — maintained by the engine, transactionally, with no application code and no possibility of an observer being bypassed. Oracle's Flashback Query gives you a comparable capability from a different direction. MySQL has no equivalent; MariaDB does, via system-versioned tables, which is one of the places MariaDB is ahead of MySQL rather than behind it.&lt;/p&gt;




&lt;h2&gt;
  
  
  Parent/child and subtype/subclass-style table design
&lt;/h2&gt;

&lt;p&gt;Magento has simple, configurable, bundle, grouped, virtual, and downloadable products. They share a SKU, a name, a status, a set of websites, a URL key. They diverge completely in everything else — a bundle needs options and selections, a configurable needs varying attributes and child links, a downloadable needs files and purchase records.&lt;/p&gt;

&lt;p&gt;This is the subtype problem, and there are exactly three answers.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Single Table Inheritance&lt;/strong&gt; puts everything in one table with a discriminator column. Simplest queries, no joins, easy polymorphic lookup — but wide sparse rows, &lt;code&gt;NOT NULL&lt;/code&gt; becomes impossible on subtype attributes, and it degrades badly past about four subtypes. &lt;strong&gt;Class Table Inheritance&lt;/strong&gt; puts common attributes in a parent and specifics in child tables sharing the primary key. You get proper &lt;code&gt;NOT NULL&lt;/code&gt; and a clean model, at the cost of a join on every full read. &lt;strong&gt;Concrete Table Inheritance&lt;/strong&gt; gives each subtype its own independent table with no parent — fastest per-subtype queries, but no shared key space, no FK can point at "any product," and every polymorphic query needs &lt;code&gt;UNION ALL&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;For most business domains, Class Table Inheritance is the default correct answer. Magento chose a hybrid, which is what large real systems usually do: &lt;code&gt;catalog_product_entity.type_id&lt;/code&gt; is an STI discriminator, EAV attribute sets play the role of the sparse subtype columns, and genuinely structural subtype data lives in satellite tables — &lt;code&gt;catalog_product_super_attribute&lt;/code&gt; and &lt;code&gt;catalog_product_super_link&lt;/code&gt; for configurables, &lt;code&gt;catalog_product_bundle_option&lt;/code&gt; and &lt;code&gt;_selection&lt;/code&gt; for bundles, &lt;code&gt;downloadable_link&lt;/code&gt; for downloadables.&lt;/p&gt;

&lt;p&gt;Now here is the pattern I most want juniors to learn, and the reason it belongs in a story about a second engine. If you're building greenfield, you can make subtype exclusivity &lt;strong&gt;declaratively enforced&lt;/strong&gt; rather than hoped for:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;product&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="n"&gt;product_id&lt;/span&gt;   &lt;span class="nb"&gt;BIGINT&lt;/span&gt; &lt;span class="k"&gt;PRIMARY&lt;/span&gt; &lt;span class="k"&gt;KEY&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;product_type&lt;/span&gt; &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;20&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;sku&lt;/span&gt;          &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;64&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt; &lt;span class="k"&gt;UNIQUE&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;ck_type&lt;/span&gt; &lt;span class="k"&gt;CHECK&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;product_type&lt;/span&gt; &lt;span class="k"&gt;IN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'SIMPLE'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'BUNDLE'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'CONFIGURABLE'&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
  &lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;uq_product_type&lt;/span&gt; &lt;span class="k"&gt;UNIQUE&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;product_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;product_type&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;span class="c1"&gt;-- the trick&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;bundle_product&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="n"&gt;product_id&lt;/span&gt;   &lt;span class="nb"&gt;BIGINT&lt;/span&gt; &lt;span class="k"&gt;PRIMARY&lt;/span&gt; &lt;span class="k"&gt;KEY&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;product_type&lt;/span&gt; &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;20&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt; &lt;span class="k"&gt;DEFAULT&lt;/span&gt; &lt;span class="s1"&gt;'BUNDLE'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;ship_type&lt;/span&gt;    &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;20&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;ck_bundle_type&lt;/span&gt; &lt;span class="k"&gt;CHECK&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;product_type&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'BUNDLE'&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
  &lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;fk_bundle_product&lt;/span&gt; &lt;span class="k"&gt;FOREIGN&lt;/span&gt; &lt;span class="k"&gt;KEY&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;product_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;product_type&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;REFERENCES&lt;/span&gt; &lt;span class="n"&gt;product&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;product_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;product_type&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The redundant &lt;code&gt;product_type&lt;/code&gt; column, plus the composite unique key on the parent, plus the composite FK, plus the check constraint on the child, makes it &lt;strong&gt;structurally impossible&lt;/strong&gt; for a row typed &lt;code&gt;SIMPLE&lt;/code&gt; to have a &lt;code&gt;bundle_product&lt;/code&gt; row. Most teams implement this in application code and get it wrong.&lt;/p&gt;

&lt;p&gt;And this is the sharpest single illustration of why the engine underneath you is not a detail: &lt;strong&gt;MySQL parsed and silently ignored &lt;code&gt;CHECK&lt;/code&gt; constraints until 8.0.16.&lt;/strong&gt; That pattern did not merely underperform on the LAMP box — it &lt;em&gt;did not function&lt;/em&gt;. You could write the DDL, MySQL would accept it without complaint, and it would enforce nothing. On SQL Server and Oracle it had worked for decades. If you inherit a MySQL schema older than 8.0.16, assume every check constraint in it is decorative until you prove otherwise.&lt;/p&gt;

&lt;p&gt;Magento also gives you a self-referencing parent/child in &lt;code&gt;sales_order_item.parent_item_id&lt;/code&gt;. A configurable product's order line has a child line for the simple SKU that actually shipped; a bundle has one child per selection. Anyone summing &lt;code&gt;row_total&lt;/code&gt; across all order items without accounting for parent and child rows double-counts, and that's a Magento reporting bug common enough to have its own genre of Stack Overflow question.&lt;/p&gt;

&lt;p&gt;Finally, the anti-pattern, live in production, in a schema millions of stores depend on:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;url_rewrite&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="n"&gt;url_rewrite_id&lt;/span&gt; &lt;span class="nb"&gt;BIGINT&lt;/span&gt; &lt;span class="k"&gt;PRIMARY&lt;/span&gt; &lt;span class="k"&gt;KEY&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;entity_type&lt;/span&gt;    &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;32&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;   &lt;span class="c1"&gt;-- 'product' | 'category' | 'cms-page'&lt;/span&gt;
  &lt;span class="n"&gt;entity_id&lt;/span&gt;      &lt;span class="nb"&gt;BIGINT&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;        &lt;span class="c1"&gt;-- points into one of three different tables&lt;/span&gt;
  &lt;span class="n"&gt;request_path&lt;/span&gt;   &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;255&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
  &lt;span class="n"&gt;target_path&lt;/span&gt;    &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;255&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
  &lt;span class="n"&gt;store_id&lt;/span&gt;       &lt;span class="nb"&gt;SMALLINT&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A polymorphic foreign key. You cannot declare a real FK, so referential integrity is gone, joins need &lt;code&gt;CASE&lt;/code&gt; or &lt;code&gt;UNION&lt;/code&gt;, and indexes are less selective. The consequence is a well-known Magento pathology: delete a product and its rewrites become orphans, because there's no cascade to fire. Stores accumulate millions of dead &lt;code&gt;url_rewrite&lt;/code&gt; rows and a scan on 404 handling. Magento did it because one rewrite table serving every entity type is genuinely convenient and rewrites are looked up by &lt;code&gt;request_path&lt;/code&gt; rather than by the FK — a defensible trade with a real cost the community has paid for a decade. If you're designing fresh, use an &lt;strong&gt;exclusive arc&lt;/strong&gt; (one nullable FK per target plus a check that exactly one is non-null) or a shared supertype table that each concrete type references. Both are more work up front and correct forever.&lt;/p&gt;




&lt;h2&gt;
  
  
  Understanding how schema choices affect performance and maintainability
&lt;/h2&gt;

&lt;p&gt;The last hour we spent on the decisions that are cheap on day one and expensive on day one thousand.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Types.&lt;/strong&gt; Pick the narrowest type that holds the domain, and pick it correctly the first time — changing a primary key from &lt;code&gt;INT&lt;/code&gt; to &lt;code&gt;BIGINT&lt;/code&gt; on a sixty-million-row EAV table is a multi-hour maintenance window on every one of these engines. If a table could ever exceed 2.1 billion rows, use &lt;code&gt;BIGINT&lt;/code&gt; from the start; four bytes costs less than the migration. Money is &lt;code&gt;DECIMAL&lt;/code&gt;/&lt;code&gt;NUMBER&lt;/code&gt;, always — Magento uses &lt;code&gt;decimal(20,4)&lt;/code&gt; for &lt;code&gt;base_grand_total&lt;/code&gt; — and never &lt;code&gt;FLOAT&lt;/code&gt; or &lt;code&gt;DOUBLE&lt;/code&gt;, because &lt;code&gt;0.1 + 0.2 &amp;lt;&amp;gt; 0.3&lt;/code&gt; in binary floating point and financial reconciliation will find it on the worst possible day. Booleans diverge more than you'd expect: PostgreSQL has a real one, MySQL's is an alias for &lt;code&gt;TINYINT(1)&lt;/code&gt; that accepts any integer, SQL Server has &lt;code&gt;BIT&lt;/code&gt;, and &lt;strong&gt;Oracle had no SQL-level boolean at all until 23ai&lt;/strong&gt;, which is why legacy Oracle schemas are full of &lt;code&gt;CHAR(1)&lt;/code&gt; with a check constraint. And store UTC: &lt;code&gt;timestamptz&lt;/code&gt; on PostgreSQL, &lt;code&gt;datetime2&lt;/code&gt; on SQL Server, &lt;code&gt;TIMESTAMP WITH TIME ZONE&lt;/code&gt; on Oracle. MySQL's &lt;code&gt;TIMESTAMP&lt;/code&gt; converts to UTC correctly but is &lt;strong&gt;bounded to 2038&lt;/strong&gt;, which Magento uses extensively, and which is closer now than any migration plan.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Row width is the quietest performance factor in the whole system.&lt;/strong&gt; Every engine reads pages, not rows. Halving row width doubles rows per page, which roughly halves scan I/O and doubles effective buffer cache capacity. So don't leave a rarely-read &lt;code&gt;TEXT&lt;/code&gt; column sitting in a hot table — and &lt;code&gt;sales_order_item.product_options&lt;/code&gt; is exactly that, a serialized blob in one of the busiest tables in the schema. PostgreSQL's TOAST handles this automatically; Oracle moves LOBs out of line above a threshold; SQL Server and MySQL are less automatic. This is also the real reason &lt;code&gt;SELECT *&lt;/code&gt; in application code is a design smell: it defeats covering indexes, drags wide columns across the wire, and breaks silently the moment someone adds a column.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Constraints are performance features, not just safety features.&lt;/strong&gt; &lt;code&gt;NOT NULL&lt;/code&gt; lets the optimizer skip null-handling logic. &lt;code&gt;UNIQUE&lt;/code&gt; tells it a join won't fan out, which changes cardinality estimates. And &lt;strong&gt;join elimination&lt;/strong&gt; — where a validated foreign key lets SQL Server, Oracle, and PostgreSQL remove a &lt;code&gt;LEFT JOIN&lt;/code&gt; entirely when you select nothing from the parent — is why views over well-constrained schemas outperform views over "we enforce it in the app" schemas. The corollary matters operationally: disabling constraints for a bulk load and re-enabling them &lt;code&gt;NOVALIDATE&lt;/code&gt; on Oracle or untrusted on SQL Server leaves you with constraints the optimizer will not use. After any bulk import — and Magento imports are constant — check &lt;code&gt;sys.foreign_keys.is_not_trusted&lt;/code&gt; on SQL Server and &lt;code&gt;STATUS&lt;/code&gt;/&lt;code&gt;VALIDATED&lt;/code&gt; in Oracle's &lt;code&gt;USER_CONSTRAINTS&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Concurrency changes how you should write queries&lt;/strong&gt;, and this is the largest operational difference between SQL Server and the other three:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Default isolation&lt;/th&gt;
&lt;th&gt;Readers block writers?&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;PostgreSQL&lt;/td&gt;
&lt;td&gt;Read Committed (MVCC)&lt;/td&gt;
&lt;td&gt;No&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Oracle&lt;/td&gt;
&lt;td&gt;Read Committed (MVCC, undo-based)&lt;/td&gt;
&lt;td&gt;No&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MySQL/InnoDB&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;Repeatable Read&lt;/strong&gt; (MVCC)&lt;/td&gt;
&lt;td&gt;No&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;SQL Server&lt;/td&gt;
&lt;td&gt;Read Committed with &lt;strong&gt;locking&lt;/strong&gt;, unless RCSI is on&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;Yes&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;By default, a long report on SQL Server takes shared locks and blocks writers. This is why &lt;code&gt;WITH (NOLOCK)&lt;/code&gt; is scattered through every legacy SQL Server codebase — and it's a bad fix, permitting dirty reads, missed rows, and duplicated rows from page splits mid-scan. The correct fix is enabling &lt;strong&gt;Read Committed Snapshot Isolation&lt;/strong&gt; at the database level, which makes SQL Server behave like the others; understand the tempdb implications before flipping it on a live system. We turned RCSI on before the first report ran, and it was the single most important configuration change of the project. Meanwhile MySQL's Repeatable Read default is why you see gap-lock deadlocks on &lt;code&gt;sequence_order_1&lt;/code&gt; and inventory reservations during a flash sale — patterns that would be fine on PostgreSQL.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Schema change at scale.&lt;/strong&gt; Magento gives you declarative schema (&lt;code&gt;db_schema.xml&lt;/code&gt;, &lt;code&gt;setup:upgrade&lt;/code&gt;), which handles versioning nicely and tells you nothing about how long the DDL takes on sixty million rows. Never rely on "it was fast in staging" — staging has ten thousand rows. Always set a lock timeout (&lt;code&gt;lock_wait_timeout&lt;/code&gt; in MySQL, &lt;code&gt;SET LOCK_TIMEOUT&lt;/code&gt; in SQL Server, &lt;code&gt;SET lock_timeout&lt;/code&gt; in PostgreSQL), because a migration that queues behind a long query and then blocks every subsequent query is how a two-second &lt;code&gt;ALTER&lt;/code&gt; takes down a site — and on PostgreSQL specifically, &lt;code&gt;ALTER TABLE&lt;/code&gt; takes an &lt;code&gt;ACCESS EXCLUSIVE&lt;/code&gt; lock, so even an "instant" change can cause a total outage if one long &lt;code&gt;SELECT&lt;/code&gt; is in flight. Use &lt;strong&gt;expand/contract&lt;/strong&gt; for anything breaking: add new, dual-write, backfill, switch reads, stop writing old, drop old. Four deploys, zero downtime. And on MySQL, know that &lt;code&gt;gh-ost&lt;/code&gt; and &lt;code&gt;pt-online-schema-change&lt;/code&gt; exist for the cases native online DDL doesn't cover, because on a large Magento install you will need them.&lt;/p&gt;

&lt;p&gt;Now the honest part, and it's the paragraph I'd want a junior to remember longest. &lt;strong&gt;The second engine is not free.&lt;/strong&gt; We took on a second schema to keep in sync, a nightly ETL that could fail silently, a second set of credentials and backups and patching, a second dialect for every developer to know, and a permanent question of "which one is right?" whenever two numbers disagreed. We wrote a reconciliation job — row counts and revenue sums per store per day, MySQL versus SQL Server, alerting on any variance over 0.01% — before we shipped a single report, and it caught three real ETL bugs in the first month. &lt;strong&gt;Do not stand up a second engine without standing up the thing that tells you it's lying to you.&lt;/strong&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  What to take with you
&lt;/h2&gt;

&lt;p&gt;Black Friday came. The reports held, because they'd stopped being queries on the production database and become tables on a machine that could actually do the work. Nothing about Magento's schema got smarter. We just stopped asking one engine to do things it had never been built to do.&lt;/p&gt;

&lt;p&gt;Five things, if you retain nothing else:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;State the grain of your result in one sentence before you write anything.&lt;/strong&gt; Most bad SQL is a grain error wearing a &lt;code&gt;DISTINCT&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;NOT EXISTS&lt;/code&gt;, never &lt;code&gt;NOT IN&lt;/code&gt; against a subquery.&lt;/strong&gt; It's the only spelling that's correct on every engine, and it's also the fastest on the ones where it matters. And that &lt;code&gt;ON DELETE SET NULL&lt;/code&gt; on &lt;code&gt;sales_order_item.product_id&lt;/code&gt; is waiting for you right now.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Aggregate before you join.&lt;/strong&gt; Joining first fans out rows and then you're summing an inflated set, and the wrong number will look plausible.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Every window &lt;code&gt;ORDER BY&lt;/code&gt; gets a deterministic tiebreaker, and every ordered window aggregate gets an explicit &lt;code&gt;ROWS&lt;/code&gt; frame.&lt;/strong&gt; The first prevents reports that change without the data changing; the second prevents running totals that are secretly daily totals.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Denormalization is a maintenance obligation, not a shortcut.&lt;/strong&gt; Magento's entire indexer subsystem is what that obligation looks like when the engine won't help you. Budget for it, and build the drift detector before you build the denormalization.&lt;/p&gt;

&lt;h3&gt;
  
  
  Before you commit a query
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;[ ] Stated the result grain in one sentence&lt;/li&gt;
&lt;li&gt;[ ] No &lt;code&gt;DISTINCT&lt;/code&gt; papering over a fan-out&lt;/li&gt;
&lt;li&gt;[ ] &lt;code&gt;NOT EXISTS&lt;/code&gt;, not &lt;code&gt;NOT IN&lt;/code&gt;, against any subquery&lt;/li&gt;
&lt;li&gt;[ ] No correlated aggregate subqueries in the &lt;code&gt;SELECT&lt;/code&gt; list&lt;/li&gt;
&lt;li&gt;[ ] Aggregation happens before joining&lt;/li&gt;
&lt;li&gt;[ ] Outer-join predicates on the null-supplying side live in &lt;code&gt;ON&lt;/code&gt;, not &lt;code&gt;WHERE&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;[ ] Every window &lt;code&gt;ORDER BY&lt;/code&gt; has a deterministic tiebreaker&lt;/li&gt;
&lt;li&gt;[ ] Explicit &lt;code&gt;ROWS BETWEEN&lt;/code&gt; on any ordered window aggregate&lt;/li&gt;
&lt;li&gt;[ ] &lt;code&gt;UNION ALL&lt;/code&gt; unless dedupe is genuinely required&lt;/li&gt;
&lt;li&gt;[ ] No functions wrapped around indexed columns&lt;/li&gt;
&lt;li&gt;[ ] Parameter types match column types&lt;/li&gt;
&lt;li&gt;[ ] Read the plan against production-scale data, not staging&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Before you commit a schema change
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;[ ] Types as narrow as the domain allows; money is &lt;code&gt;DECIMAL&lt;/code&gt;; timestamps timezone-explicit&lt;/li&gt;
&lt;li&gt;[ ] Every FK column has an index (free on InnoDB, which is why you'll forget it elsewhere)&lt;/li&gt;
&lt;li&gt;[ ] PK is narrow and monotonic&lt;/li&gt;
&lt;li&gt;[ ] Subtype exclusivity enforced by constraint, not by hope — and verify constraints are actually enforced on your version&lt;/li&gt;
&lt;li&gt;[ ] Any denormalized value has a documented rebuild path &lt;strong&gt;and&lt;/strong&gt; a drift-detection job&lt;/li&gt;
&lt;li&gt;[ ] Large text and blob columns are out of the hot table&lt;/li&gt;
&lt;li&gt;[ ] Migration is expand/contract, with a lock timeout and a rollback plan&lt;/li&gt;
&lt;li&gt;[ ] You know how long it takes at production row counts&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Reading the plan
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Command&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;PostgreSQL&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;EXPLAIN (ANALYZE, BUFFERS, VERBOSE)&lt;/code&gt; — &lt;code&gt;BUFFERS&lt;/code&gt; is the one people skip and shouldn't&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MySQL&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;EXPLAIN ANALYZE&lt;/code&gt; (8.0.18+), &lt;code&gt;EXPLAIN FORMAT=JSON&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;SQL Server&lt;/td&gt;
&lt;td&gt;Actual execution plan; &lt;code&gt;SET STATISTICS IO, TIME ON&lt;/code&gt;; Query Store for history&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Oracle&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;DBMS_XPLAN.DISPLAY_CURSOR(format=&amp;gt;'ALLSTATS LAST')&lt;/code&gt; — the actual plan, not &lt;code&gt;EXPLAIN PLAN&lt;/code&gt;'s guess&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Universally: look for estimated versus actual row counts diverging by more than about ten times, scans where you expected seeks, and any operator whose output explodes relative to its input.&lt;/p&gt;




&lt;h3&gt;
  
  
  On verifying any of this
&lt;/h3&gt;

&lt;p&gt;Every version boundary above is checkable and you should check it, because they move and I have been wrong before.&lt;/p&gt;

&lt;p&gt;For the Magento schema, don't trust any blog post including this one — read &lt;code&gt;db_schema.xml&lt;/code&gt; in the relevant module in your own installed version and run &lt;code&gt;SHOW CREATE TABLE&lt;/code&gt;. Adobe Commerce and Magento Open Source diverge (content staging changes catalog primary keys to &lt;code&gt;row_id&lt;/code&gt;), and 2.4.x has changed definitions across minor releases. For MySQL, the Reference Manual's optimization chapter, and check MariaDB's knowledge base separately rather than assuming parity — it isn't the same database. For SQL Server, Microsoft Learn, and read the "Applies to" banner on every page, because the difference between GA in Azure SQL and preview on-prem is frequently the whole story. For Oracle, the SQL Language Reference for your exact release plus the New Features guide, since 19c, 21c, 23ai, and 26ai differ meaningfully and the version numbering does not help.&lt;/p&gt;

&lt;p&gt;Where something here is version-gated, I've said so. Verify against the exact version in your environment before you rely on it. That isn't a disclaimer — it's the job.&lt;/p&gt;




&lt;p&gt;&lt;strong&gt;Disclaimer:&lt;/strong&gt; I used &lt;em&gt;Claude&lt;/em&gt; to generate &lt;em&gt;multiple&lt;/em&gt; detailed guides and then in different sessions fact check itself and correct for hallucinations. It's only as powerful as the model was trained to be, and it's being asked to act as an engineer I used to once be, and look at the questions that &lt;em&gt;I never knew to ask&lt;/em&gt; and how the &lt;a href="https://dev.to/andreimerlescu/sql-design-query-reference-67f"&gt;original list of requirements&lt;/a&gt; is a &lt;strong&gt;reference&lt;/strong&gt; that is &lt;strong&gt;very technical&lt;/strong&gt; and &lt;em&gt;hard to read&lt;/em&gt; - but it contains a depth of knowledge that is a &lt;strong&gt;reference&lt;/strong&gt; for a seasoned &lt;strong&gt;junior engineer&lt;/strong&gt; looking to take on a &lt;em&gt;Senior&lt;/em&gt; level role. Part of being a &lt;strong&gt;Senior&lt;/strong&gt; is your ability to mentor junior engineers, and writing is the manner in which that I knowledge transfer to the next generation. &lt;/p&gt;

</description>
      <category>sql</category>
      <category>beginners</category>
      <category>webdev</category>
      <category>programming</category>
    </item>
    <item>
      <title>SQL Design &amp; Query Reference</title>
      <dc:creator>Andrei Merlescu</dc:creator>
      <pubDate>Mon, 27 Jul 2026 16:34:27 +0000</pubDate>
      <link>https://dev.to/andreimerlescu/sql-design-query-reference-67f</link>
      <guid>https://dev.to/andreimerlescu/sql-design-query-reference-67f</guid>
      <description>&lt;p&gt;I have professionally worked with &lt;strong&gt;four different SQL database types&lt;/strong&gt; &lt;code&gt;PostgreSQL&lt;/code&gt;, &lt;code&gt;MySQL&lt;/code&gt; &amp;amp; &lt;code&gt;MariaDB&lt;/code&gt; (InnoDB), &lt;code&gt;MSSQL&lt;/code&gt; SQL Server 2008+ and &lt;code&gt;Oracle 19c&lt;/code&gt;+.  Over the course of that time I have been asked: &lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Choosing the right query pattern for the problem&lt;/li&gt;
&lt;li&gt;Using NOT EXISTS / EXISTS where appropriate&lt;/li&gt;
&lt;li&gt;Avoiding unnecessary nested aggregate subqueries&lt;/li&gt;
&lt;li&gt;Understanding joins, filtering, grouping, and set-based logic&lt;/li&gt;
&lt;li&gt;Using window functions like DENSE_RANK() and similar tools when appropriate&lt;/li&gt;
&lt;li&gt;Working with JSON data in the database&lt;/li&gt;
&lt;li&gt;Good Database and Table Design:Indexing strategy&lt;/li&gt;
&lt;li&gt;Normalization vs selective denormalization&lt;/li&gt;
&lt;li&gt;When some redundancy improves performance&lt;/li&gt;
&lt;li&gt;Parent/child and subtype/subclass-style table design&lt;/li&gt;
&lt;li&gt;Understand how schema choices affect performance and maintainability&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;And being an autodidact software engineer with an electrical engineering background in computer engineering, I would reference &lt;a href="https://dev.to/andreimerlescu/when-ai-creates-a-closed-source-world-2oin"&gt;The Library&lt;/a&gt; to complete task A or task B or task C. Many junior engineers are in this boat as well. They may have the formal education that I lacked &lt;em&gt;not being in computer science as a major in college&lt;/em&gt;, but it doesn't mean that I can't use resources at my disposal to learn and meet each of these requirements and where I've done it. &lt;/p&gt;

&lt;p&gt;This document is &lt;em&gt;Claude's&lt;/em&gt; response to my request for it to act as Staff SQL Architect and write a reference document for these &lt;strong&gt;four database types&lt;/strong&gt; as a &lt;em&gt;knowledge transfer doc&lt;/em&gt; for &lt;strong&gt;junior engineers&lt;/strong&gt; who need a &lt;em&gt;quick reference&lt;/em&gt; of these core concepts. &lt;/p&gt;

&lt;p&gt;In all fairness, it's not wrong to have this handy. Instead of it being fragmented on Stack Overflow in the form of dozens of Questions and Answers - its been gathered through the LLM's that have &lt;a href="https://dev.to/andreimerlescu/codeberg-bans-cryptocurrency-and-llm-generated-code-projects-3aj0"&gt;crossed the line&lt;/a&gt; with acceptable community behavior. So, before those models are &lt;em&gt;taken offline&lt;/em&gt; 😅🤫🤣 I wanted to utilize this resource to help give back. It's a format and structure applicable to four distinct types of SQL databases that any developer should be comfortable with. My experience with SQL databases was extensive between 2003 and 2020. After, I became heavily involved with &lt;code&gt;MongoDB&lt;/code&gt; and &lt;strong&gt;NoSQL&lt;/strong&gt; databases including &lt;em&gt;Redis&lt;/em&gt; and &lt;em&gt;PostgreSQL&lt;/em&gt;. Since 2020, I've been on the administration side of the database and less on the SQL query writing sided of the database. The &lt;a href="https://dev.to/andreimerlescu/how-i-processed-666k-pages-of-flattened-pdfs-into-a-full-text-search-engine-4db3"&gt;Apario Database&lt;/a&gt; was custom written from the ground up for an &lt;a href="https://dev.to/andreimerlescu/how-i-reduced-my-opex-by-995-using-go-3ff7"&gt;OPEX problem&lt;/a&gt;. &lt;/p&gt;

&lt;p&gt;If you find this document useful, please give it a 💜 before you bookmark it. &lt;/p&gt;

&lt;h3&gt;
  
  
  Knowledge Transfer Doc — PostgreSQL · MySQL (InnoDB) · SQL Server 2008+ · Oracle 19c+
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;How to read this doc:&lt;/strong&gt; Sections marked &lt;strong&gt;[SAME]&lt;/strong&gt; behave identically on all four engines — learn the concept once and move on. Sections marked &lt;strong&gt;[DIFFERS]&lt;/strong&gt; are where people get burned porting code or scaling up. Version numbers matter a lot here; when a feature is version-gated I say so, and you should still verify against the exact version in your environment before you rely on it.&lt;/p&gt;




&lt;h1&gt;
  
  
  PART I — WRITING QUERIES
&lt;/h1&gt;

&lt;h2&gt;
  
  
  1. Choosing the Right Query Pattern
&lt;/h2&gt;

&lt;p&gt;Before you write anything, answer three questions:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;What is the grain of my result?&lt;/strong&gt; One row per what? If you can't say it in a sentence, you will produce duplicates.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Am I filtering, or am I enriching?&lt;/strong&gt; Filtering → semi/anti-join (&lt;code&gt;EXISTS&lt;/code&gt;). Enriching → join or window function.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Do I need one value per group, or one row per group?&lt;/strong&gt; One value → aggregate. One row → window function or lateral.&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  The pattern decision table &lt;strong&gt;[SAME across all four]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Problem&lt;/th&gt;
&lt;th&gt;Right pattern&lt;/th&gt;
&lt;th&gt;Wrong pattern people reach for&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;"Customers who have ≥1 order"&lt;/td&gt;
&lt;td&gt;&lt;code&gt;EXISTS&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;JOIN&lt;/code&gt; + &lt;code&gt;DISTINCT&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;"Customers with no orders"&lt;/td&gt;
&lt;td&gt;&lt;code&gt;NOT EXISTS&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;NOT IN&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;"Each order plus its customer name"&lt;/td&gt;
&lt;td&gt;&lt;code&gt;JOIN&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;correlated scalar subquery&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;"Total per customer"&lt;/td&gt;
&lt;td&gt;&lt;code&gt;GROUP BY&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;correlated aggregate in SELECT&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;"Each order plus its customer's total"&lt;/td&gt;
&lt;td&gt;window function&lt;/td&gt;
&lt;td&gt;correlated aggregate in SELECT&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;"Latest order per customer (full row)"&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;ROW_NUMBER()&lt;/code&gt; or lateral&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;MAX(date)&lt;/code&gt; + self-join&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;"Top N per group"&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;ROW_NUMBER&lt;/code&gt;/&lt;code&gt;RANK&lt;/code&gt;/&lt;code&gt;DENSE_RANK&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;correlated &lt;code&gt;COUNT&lt;/code&gt; subquery&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;"Rows in A not in B, both large"&lt;/td&gt;
&lt;td&gt;anti-join (&lt;code&gt;NOT EXISTS&lt;/code&gt;)&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;EXCEPT&lt;/code&gt;/&lt;code&gt;MINUS&lt;/code&gt; if you need dupes preserved&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;h3&gt;
  
  
  The &lt;code&gt;DISTINCT&lt;/code&gt; smell &lt;strong&gt;[SAME]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;&lt;code&gt;SELECT DISTINCT&lt;/code&gt; in a query that joins to a child table almost always means you used a join where you wanted a semi-join. The join fans out, then &lt;code&gt;DISTINCT&lt;/code&gt; collapses it back — you paid for a sort/hash of the fanned-out set for nothing.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- BAD: fan out 4M rows, then dedupe back to 200k&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;DISTINCT&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;name&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;customer&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt; &lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'SHIPPED'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="c1"&gt;-- GOOD: optimizer stops at first match per customer&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;name&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;customer&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="k"&gt;EXISTS&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;
              &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="k"&gt;AND&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'SHIPPED'&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;There are legitimate &lt;code&gt;DISTINCT&lt;/code&gt;s (deduping a genuinely duplicated source). But treat every one as a thing you must justify in code review.&lt;/p&gt;

&lt;h3&gt;
  
  
  CTEs: the biggest cross-engine trap &lt;strong&gt;[DIFFERS — important]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;A junior writes a CTE thinking "this runs once and gets reused." That is engine-dependent and version-dependent.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;CTE behaviour&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;PostgreSQL ≤ 11&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Always materialized. Hard optimization fence — predicates do &lt;strong&gt;not&lt;/strong&gt; push in.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;PostgreSQL 12+&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Inlined if referenced once and not recursive/volatile; otherwise materialized. Force with &lt;code&gt;WITH x AS MATERIALIZED (...)&lt;/code&gt; / &lt;code&gt;AS NOT MATERIALIZED&lt;/code&gt;.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;SQL Server&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Effectively always inlined — a CTE referenced three times is &lt;strong&gt;executed three times&lt;/strong&gt;. No hint to materialize. Use a &lt;code&gt;#temp&lt;/code&gt; table when you need one-shot evaluation.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Oracle&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Cost-based; may materialize into a temp segment. Hints: &lt;code&gt;/*+ MATERIALIZE */&lt;/code&gt;, &lt;code&gt;/*+ INLINE */&lt;/code&gt;.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;MySQL 8.0+&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Materializes derived tables/CTEs in many cases; merge is possible. Historically weaker at pushing predicates into derived tables than the others.&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;The scale gotcha:&lt;/strong&gt; on SQL Server, a "clean" query with a CTE that scans a 500M-row fact table and is referenced in three branches of a &lt;code&gt;UNION ALL&lt;/code&gt; scans it three times. It looks elegant and it is a disaster. On PostgreSQL ≤ 11 the opposite failure: your &lt;code&gt;WHERE tenant_id = 42&lt;/code&gt; outside the CTE never reaches inside it, so you materialize the whole table first.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Rule for the team:&lt;/strong&gt; if a CTE is referenced more than once &lt;em&gt;and&lt;/em&gt; the underlying scan is expensive, on SQL Server/MySQL stage it into a temp table explicitly. Don't rely on the optimizer being clever.&lt;/p&gt;

&lt;p&gt;Recursive syntax differs cosmetically: PostgreSQL and MySQL require &lt;code&gt;WITH RECURSIVE&lt;/code&gt;; SQL Server and Oracle use plain &lt;code&gt;WITH&lt;/code&gt; (Oracle additionally has the older &lt;code&gt;CONNECT BY&lt;/code&gt;, which is still often faster there for pure hierarchy walks and supports &lt;code&gt;LEVEL&lt;/code&gt;, &lt;code&gt;SYS_CONNECT_BY_PATH&lt;/code&gt;, &lt;code&gt;CONNECT_BY_ISLEAF&lt;/code&gt;).&lt;/p&gt;




&lt;h2&gt;
  
  
  2. &lt;code&gt;EXISTS&lt;/code&gt; / &lt;code&gt;NOT EXISTS&lt;/code&gt; — and Why &lt;code&gt;NOT IN&lt;/code&gt; Keeps Hurting You
&lt;/h2&gt;

&lt;h3&gt;
  
  
  The NULL trap &lt;strong&gt;[SAME — all four, it's ANSI]&lt;/strong&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;customer&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;IN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;blacklist&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If &lt;strong&gt;one&lt;/strong&gt; row in &lt;code&gt;blacklist.customer_id&lt;/code&gt; is NULL, this returns &lt;strong&gt;zero rows&lt;/strong&gt;. Always. Silently.&lt;/p&gt;

&lt;p&gt;Why: &lt;code&gt;x NOT IN (a, b, NULL)&lt;/code&gt; expands to &lt;code&gt;x &amp;lt;&amp;gt; a AND x &amp;lt;&amp;gt; b AND x &amp;lt;&amp;gt; NULL&lt;/code&gt;. That last term is &lt;code&gt;UNKNOWN&lt;/code&gt;, never &lt;code&gt;TRUE&lt;/code&gt;. So the whole conjunction can never be &lt;code&gt;TRUE&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;NOT EXISTS&lt;/code&gt; does not have this problem, because it tests row existence, not value comparison. &lt;strong&gt;Default to &lt;code&gt;NOT EXISTS&lt;/code&gt;.&lt;/strong&gt; If you must use &lt;code&gt;NOT IN&lt;/code&gt;, the subquery column must be &lt;code&gt;NOT NULL&lt;/code&gt; &lt;em&gt;declared in the DDL&lt;/em&gt; — not "we're pretty sure it's never null."&lt;/p&gt;

&lt;h3&gt;
  
  
  The optimizer angle &lt;strong&gt;[DIFFERS]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;&lt;code&gt;NOT EXISTS&lt;/code&gt;&lt;/th&gt;
&lt;th&gt;&lt;code&gt;NOT IN&lt;/code&gt;&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Oracle&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Anti-join&lt;/td&gt;
&lt;td&gt;Handles well — has a &lt;em&gt;null-aware anti-join&lt;/em&gt; (&lt;code&gt;ANTI NA&lt;/code&gt;) operator (11g+). Roughly parity.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;SQL Server&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Anti semi-join&lt;/td&gt;
&lt;td&gt;Usually anti-join too, but nullable columns add an extra probe/filter; plans get uglier.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;PostgreSQL&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Clean anti-join&lt;/td&gt;
&lt;td&gt;Historically &lt;strong&gt;cannot&lt;/strong&gt; convert to an anti-join when the column is nullable — degrades to a filtered subplan. Materially worse on large sets.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;MySQL 8.0.17+&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Anti-join transformation available&lt;/td&gt;
&lt;td&gt;Also transformed in 8.0.17+. &lt;strong&gt;Pre-8.0 this was a per-row dependent subquery — catastrophic.&lt;/strong&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;So &lt;code&gt;NOT EXISTS&lt;/code&gt; is correct everywhere &lt;em&gt;and&lt;/em&gt; the best-performing choice on the two engines where it matters most. There is no reason to write &lt;code&gt;NOT IN&lt;/code&gt; against a subquery. Against a short literal list (&lt;code&gt;status NOT IN ('A','B')&lt;/code&gt;) it's fine.&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;code&gt;LEFT JOIN ... WHERE right.pk IS NULL&lt;/code&gt; &lt;strong&gt;[SAME semantics, [DIFFERS] on plan quality]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;This is the third anti-join spelling. It is &lt;em&gt;semantically&lt;/em&gt; safe (no NULL trap) but:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;It's easy to break by adding a second predicate on the right table in &lt;code&gt;WHERE&lt;/code&gt; instead of &lt;code&gt;ON&lt;/code&gt;, which silently converts your outer join to an inner join.&lt;/li&gt;
&lt;li&gt;Oracle and SQL Server usually recognize it and produce the same anti-join plan. PostgreSQL does too. MySQL historically preferred this form (pre-8.0.17 it was the &lt;em&gt;only&lt;/em&gt; way to get a decent anti-join plan) — you'll see it a lot in legacy MySQL code.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Prefer &lt;code&gt;NOT EXISTS&lt;/code&gt; for readability; recognize the &lt;code&gt;LEFT JOIN / IS NULL&lt;/code&gt; form when you meet it.&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;code&gt;EXISTS&lt;/code&gt; vs &lt;code&gt;IN&lt;/code&gt; for the positive case &lt;strong&gt;[SAME, mostly]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;All four modernly transform &lt;code&gt;IN (subquery)&lt;/code&gt; into a semi-join, so they're usually equivalent. Two notes:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;IN&lt;/code&gt; with a subquery returning NULLs is &lt;em&gt;not&lt;/em&gt; dangerous (unlike &lt;code&gt;NOT IN&lt;/code&gt;) — NULLs just never match.&lt;/li&gt;
&lt;li&gt;MySQL 5.x executed &lt;code&gt;IN (subquery)&lt;/code&gt; as a dependent subquery in many cases. If you maintain anything on 5.6/5.7, rewrite &lt;code&gt;IN&lt;/code&gt; to &lt;code&gt;EXISTS&lt;/code&gt; or a join. On 8.0+ the semijoin strategies (&lt;code&gt;FirstMatch&lt;/code&gt;, &lt;code&gt;LooseScan&lt;/code&gt;, &lt;code&gt;MaterializeLookup&lt;/code&gt;, &lt;code&gt;DuplicateWeedout&lt;/code&gt;) handle it.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  &lt;code&gt;EXISTS&lt;/code&gt; micro-details &lt;strong&gt;[SAME]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;&lt;code&gt;SELECT 1&lt;/code&gt; vs &lt;code&gt;SELECT *&lt;/code&gt; vs &lt;code&gt;SELECT NULL&lt;/code&gt; inside &lt;code&gt;EXISTS&lt;/code&gt; makes zero difference on any of the four — the select list isn't evaluated. Don't argue about it in review. Do make sure the correlation predicate is indexed; that's what actually matters.&lt;/p&gt;




&lt;h2&gt;
  
  
  3. Avoiding Unnecessary Nested Aggregate Subqueries
&lt;/h2&gt;

&lt;p&gt;This is the single most common performance defect in junior-written SQL, and it's identical on all four engines. &lt;strong&gt;[SAME]&lt;/strong&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  The anti-pattern
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;COUNT&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt; &lt;span class="n"&gt;o2&lt;/span&gt;
        &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o2&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;      &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;cust_order_count&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt; &lt;span class="n"&gt;o3&lt;/span&gt;
        &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o3&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;      &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;cust_total&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;MAX&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;order_date&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt; &lt;span class="n"&gt;o4&lt;/span&gt;
        &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o4&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;      &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;cust_last_order&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_date&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="nb"&gt;DATE&lt;/span&gt; &lt;span class="s1"&gt;'2026-01-01'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Three correlated subqueries = up to three extra index range scans &lt;strong&gt;per output row&lt;/strong&gt;. At 2M output rows that's 6M extra scans. On a good day the optimizer decorrelates one of them. Don't rely on it.&lt;/p&gt;

&lt;h3&gt;
  
  
  Fix 1 — one window pass
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;order_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;COUNT&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;        &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;PARTITION&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;cust_order_count&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;     &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;PARTITION&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;cust_total&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;MAX&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;order_date&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;PARTITION&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;cust_last_order&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;order_date&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="nb"&gt;DATE&lt;/span&gt; &lt;span class="s1"&gt;'2026-01-01'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;One scan, one sort/hash by &lt;code&gt;customer_id&lt;/code&gt;, all three aggregates computed together. Note the semantic change: the window is now over the &lt;em&gt;filtered&lt;/em&gt; set. If you need totals over all history, you can't use this form — see Fix 2.&lt;/p&gt;

&lt;h3&gt;
  
  
  Fix 2 — pre-aggregate then join
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;WITH&lt;/span&gt; &lt;span class="n"&gt;cust_agg&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
         &lt;span class="k"&gt;COUNT&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;        &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;cust_order_count&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
         &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;     &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;cust_total&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
         &lt;span class="k"&gt;MAX&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;order_date&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;cust_last_order&lt;/span&gt;
  &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt;
  &lt;span class="k"&gt;GROUP&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;cust_order_count&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;cust_total&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;cust_last_order&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;
&lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;cust_agg&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_date&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;=&lt;/span&gt; &lt;span class="nb"&gt;DATE&lt;/span&gt; &lt;span class="s1"&gt;'2026-01-01'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;One aggregate pass over the child, one hash join. This is the workhorse. &lt;strong&gt;Critical rule: aggregate &lt;em&gt;before&lt;/em&gt; you join, not after.&lt;/strong&gt; Joining first fans out rows and then you're aggregating an inflated set — which is also how you get silently wrong &lt;code&gt;SUM&lt;/code&gt;s.&lt;/p&gt;

&lt;h3&gt;
  
  
  The double-counting bug &lt;strong&gt;[SAME]&lt;/strong&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- WRONG&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;customer&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;
&lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;   &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;
&lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;payments&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;p&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;
&lt;span class="k"&gt;GROUP&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If a customer has 3 orders and 4 payments, you get 12 rows; &lt;code&gt;SUM(o.amount)&lt;/code&gt; is 4× too large and &lt;code&gt;SUM(p.amount)&lt;/code&gt; is 3× too large. This ships to production regularly because the numbers &lt;em&gt;look&lt;/em&gt; plausible. Fix: aggregate each branch separately in its own subquery/CTE, then join the two aggregates. Or use &lt;code&gt;COUNT(DISTINCT ...)&lt;/code&gt; as a diagnostic to prove the fan-out to yourself.&lt;/p&gt;

&lt;h3&gt;
  
  
  Fix 3 — lateral / apply, when you need the &lt;em&gt;whole row&lt;/em&gt; &lt;strong&gt;[DIFFERS in syntax only]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;"Give me each customer plus their most recent order's full details."&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Syntax&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;PostgreSQL&lt;/td&gt;
&lt;td&gt;&lt;code&gt;LEFT JOIN LATERAL (...) t ON true&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Oracle 12c+&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;OUTER APPLY (...)&lt;/code&gt; or &lt;code&gt;LEFT JOIN LATERAL (...) ON 1=1&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;SQL Server&lt;/td&gt;
&lt;td&gt;&lt;code&gt;OUTER APPLY (...)&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MySQL 8.0.14+&lt;/td&gt;
&lt;td&gt;&lt;code&gt;LEFT JOIN LATERAL (...) ON true&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- PostgreSQL / MySQL 8.0.14+&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;name&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_date&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;lo&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;amount&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;customer&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;
&lt;span class="k"&gt;LEFT&lt;/span&gt; &lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="k"&gt;LATERAL&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_date&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;amount&lt;/span&gt;
    &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;
    &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;c&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;customer_id&lt;/span&gt;
    &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_date&lt;/span&gt; &lt;span class="k"&gt;DESC&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;o&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;order_id&lt;/span&gt; &lt;span class="k"&gt;DESC&lt;/span&gt;
    &lt;span class="k"&gt;LIMIT&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;lo&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="k"&gt;true&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;(SQL Server/Oracle: &lt;code&gt;TOP 1&lt;/code&gt; / &lt;code&gt;FETCH FIRST 1 ROWS ONLY&lt;/code&gt; and &lt;code&gt;OUTER APPLY&lt;/code&gt;.)&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;When lateral beats &lt;code&gt;ROW_NUMBER()&lt;/code&gt;:&lt;/strong&gt; when the outer set is small and the inner table is huge and well-indexed. Lateral does N cheap index seeks. &lt;code&gt;ROW_NUMBER()&lt;/code&gt; sorts the &lt;em&gt;entire&lt;/em&gt; child table. For 100 customers against a 500M-row orders table, lateral wins by orders of magnitude. For "top 3 per customer across all 5M customers," &lt;code&gt;ROW_NUMBER()&lt;/code&gt; wins — one sorted pass beats 5M seeks.&lt;/p&gt;

&lt;p&gt;That trade-off — &lt;strong&gt;N seeks vs. one big sort&lt;/strong&gt; — is the mental model. Know your N.&lt;/p&gt;

&lt;h3&gt;
  
  
  Oracle-only shortcut
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;MAX&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;order_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;KEEP&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DENSE_RANK&lt;/span&gt; &lt;span class="k"&gt;LAST&lt;/span&gt; &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;order_date&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;order_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;last_order_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;MAX&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;span class="n"&gt;KEEP&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;DENSE_RANK&lt;/span&gt; &lt;span class="k"&gt;LAST&lt;/span&gt; &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;order_date&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;order_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;last_amount&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;total&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt; &lt;span class="k"&gt;GROUP&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;KEEP (DENSE_RANK FIRST/LAST)&lt;/code&gt; gets you "the value of column X from the row with the max/min of Y" inside a single &lt;code&gt;GROUP BY&lt;/code&gt; — no window pass, no self-join. There is no direct equivalent on the other three; PostgreSQL's closest is &lt;code&gt;DISTINCT ON&lt;/code&gt; or ordered-set aggregates.&lt;/p&gt;




&lt;h2&gt;
  
  
  4. Joins, Filtering, Grouping, and Set-Based Logic
&lt;/h2&gt;

&lt;h3&gt;
  
  
  &lt;code&gt;ON&lt;/code&gt; vs &lt;code&gt;WHERE&lt;/code&gt; on outer joins &lt;strong&gt;[SAME]&lt;/strong&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- These are NOT the same query&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="k"&gt;LEFT&lt;/span&gt; &lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;a_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;id&lt;/span&gt; &lt;span class="k"&gt;AND&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'X'&lt;/span&gt;   &lt;span class="c1"&gt;-- filters b before joining&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="k"&gt;LEFT&lt;/span&gt; &lt;span class="k"&gt;JOIN&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;a_id&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;id&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'X'&lt;/span&gt; &lt;span class="c1"&gt;-- silently becomes an INNER JOIN&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Any predicate on the null-supplying side placed in &lt;code&gt;WHERE&lt;/code&gt; eliminates the NULL-extended rows. If you genuinely want "no matching b," write &lt;code&gt;WHERE b.a_id IS NULL&lt;/code&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  Predicate sargability &lt;strong&gt;[SAME principle, [DIFFERS] in remedies]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;Wrapping an indexed column in a function kills the index. Universal.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="k"&gt;UPPER&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;email&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'A@B.COM'&lt;/span&gt;          &lt;span class="c1"&gt;-- no index use on email&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;order_date&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;SYSDATE&lt;/span&gt;          &lt;span class="c1"&gt;-- no index use&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="nb"&gt;YEAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;order_date&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;2026&lt;/span&gt;           &lt;span class="c1"&gt;-- no index use&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Remedies by engine:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Expression/functional index&lt;/th&gt;
&lt;th&gt;Case-insensitive strategy&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;PostgreSQL&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;CREATE INDEX ON t (upper(email))&lt;/code&gt; — long supported&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;citext&lt;/code&gt; type, or expression index&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Oracle&lt;/td&gt;
&lt;td&gt;Function-based indexes (8i+)&lt;/td&gt;
&lt;td&gt;FBI on &lt;code&gt;UPPER()&lt;/code&gt;, or &lt;code&gt;NLS_SORT&lt;/code&gt;/&lt;code&gt;NLS_COMP&lt;/code&gt; linguistic index&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;SQL Server&lt;/td&gt;
&lt;td&gt;No true expression index — use a &lt;strong&gt;persisted computed column&lt;/strong&gt; + index&lt;/td&gt;
&lt;td&gt;Column collation is usually CI already (&lt;code&gt;_CI_AS&lt;/code&gt;) so it's often a non-issue&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MySQL 8.0.13+&lt;/td&gt;
&lt;td&gt;Functional indexes; before that, generated column + index&lt;/td&gt;
&lt;td&gt;Default collations are CI (&lt;code&gt;utf8mb4_0900_ai_ci&lt;/code&gt;) — usually a non-issue&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;Two engine-specific date traps:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Oracle:&lt;/strong&gt; &lt;code&gt;DATE&lt;/code&gt; always carries a time component. &lt;code&gt;WHERE order_date = DATE '2026-07-27'&lt;/code&gt; misses everything with a nonzero time. Use a half-open range &lt;code&gt;&amp;gt;= DATE '2026-07-27' AND &amp;lt; DATE '2026-07-28'&lt;/code&gt;, not &lt;code&gt;TRUNC()&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;SQL Server:&lt;/strong&gt; &lt;code&gt;datetime&lt;/code&gt; (legacy) has ~3ms precision and rounds &lt;code&gt;.997&lt;/code&gt;→&lt;code&gt;.997&lt;/code&gt;, &lt;code&gt;.999&lt;/code&gt;→next second. &lt;code&gt;BETWEEN '2026-07-01' AND '2026-07-31 23:59:59.999'&lt;/code&gt; is a bug. Always use half-open ranges. This applies everywhere but bites hardest here.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Implicit conversion — the silent index killer &lt;strong&gt;[DIFFERS in how it manifests]&lt;/strong&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;SQL Server:&lt;/strong&gt; an ORM sending &lt;code&gt;NVARCHAR&lt;/code&gt; parameters against a &lt;code&gt;VARCHAR&lt;/code&gt; column forces &lt;code&gt;CONVERT_IMPLICIT&lt;/code&gt; on the &lt;em&gt;column&lt;/em&gt;, producing a full scan. Data type precedence means &lt;code&gt;NVARCHAR&lt;/code&gt; wins. This is probably the #1 cause of "it's fast in SSMS but slow from the app." Match your parameter types to your column types.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;MySQL:&lt;/strong&gt; joining columns with different &lt;strong&gt;collations or charsets&lt;/strong&gt; (e.g. &lt;code&gt;utf8mb3_general_ci&lt;/code&gt; legacy table to &lt;code&gt;utf8mb4_0900_ai_ci&lt;/code&gt; new table) prevents index use on the join. Also, comparing a string column to a numeric literal converts the &lt;em&gt;column&lt;/em&gt; to a number → full scan. Extremely common after a partial charset migration.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Oracle:&lt;/strong&gt; &lt;code&gt;VARCHAR2&lt;/code&gt; vs &lt;code&gt;NVARCHAR2&lt;/code&gt;, and comparing a &lt;code&gt;NUMBER&lt;/code&gt; column to a string literal. Oracle converts the character side to number, which is safe, but comparing a &lt;code&gt;VARCHAR2&lt;/code&gt; column to a number converts the column → scan.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;PostgreSQL:&lt;/strong&gt; stricter typing means fewer silent conversions, but &lt;code&gt;bigint&lt;/code&gt; column vs &lt;code&gt;int&lt;/code&gt; parameter is fine while &lt;code&gt;text&lt;/code&gt; vs &lt;code&gt;varchar&lt;/code&gt; collation mismatches can still block index use in less common cases.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  &lt;code&gt;GROUP BY&lt;/code&gt; strictness &lt;strong&gt;[DIFFERS]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Rule&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;SQL Server, Oracle&lt;/td&gt;
&lt;td&gt;Strict ANSI. Every non-aggregated select item must be in &lt;code&gt;GROUP BY&lt;/code&gt;.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;PostgreSQL&lt;/td&gt;
&lt;td&gt;Strict, &lt;strong&gt;except&lt;/strong&gt; it recognizes functional dependency on a grouped primary key — &lt;code&gt;GROUP BY c.customer_id&lt;/code&gt; lets you select &lt;code&gt;c.name&lt;/code&gt;.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MySQL&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;ONLY_FULL_GROUP_BY&lt;/code&gt; is &lt;strong&gt;on by default since 5.7.5&lt;/strong&gt;. Similar functional-dependency detection to PG. Legacy code with it disabled returns arbitrary values from arbitrary rows — a correctness bug, not a style issue. Never turn it off.&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;h3&gt;
  
  
  &lt;code&gt;HAVING&lt;/code&gt; vs &lt;code&gt;WHERE&lt;/code&gt; &lt;strong&gt;[SAME]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;&lt;code&gt;WHERE&lt;/code&gt; filters rows before grouping; &lt;code&gt;HAVING&lt;/code&gt; filters groups after. Putting a non-aggregate predicate in &lt;code&gt;HAVING&lt;/code&gt; is not &lt;em&gt;wrong&lt;/em&gt; (all four will typically push it down) but it's misleading. Put row filters in &lt;code&gt;WHERE&lt;/code&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  Conditional aggregation &lt;strong&gt;[DIFFERS slightly]&lt;/strong&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- Works everywhere&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;CASE&lt;/span&gt; &lt;span class="k"&gt;WHEN&lt;/span&gt; &lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'SHIPPED'&lt;/span&gt;   &lt;span class="k"&gt;THEN&lt;/span&gt; &lt;span class="n"&gt;amount&lt;/span&gt; &lt;span class="k"&gt;ELSE&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt; &lt;span class="k"&gt;END&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;shipped_amt&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
       &lt;span class="k"&gt;COUNT&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;CASE&lt;/span&gt; &lt;span class="k"&gt;WHEN&lt;/span&gt; &lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'CANCELLED'&lt;/span&gt; &lt;span class="k"&gt;THEN&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="k"&gt;END&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;           &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;cancelled_cnt&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt; &lt;span class="k"&gt;GROUP&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;PostgreSQL additionally has the cleaner ANSI &lt;code&gt;FILTER&lt;/code&gt; clause: &lt;code&gt;COUNT(*) FILTER (WHERE status = 'CANCELLED')&lt;/code&gt;. It's PG-only among these four. Use it in PG-only code; use &lt;code&gt;CASE&lt;/code&gt; in anything portable.&lt;/p&gt;

&lt;p&gt;Note &lt;code&gt;COUNT(CASE WHEN ... THEN 1 END)&lt;/code&gt; — no &lt;code&gt;ELSE&lt;/code&gt;, so non-matches are NULL and &lt;code&gt;COUNT&lt;/code&gt; skips them. &lt;code&gt;COUNT(CASE WHEN ... THEN 1 ELSE 0 END)&lt;/code&gt; counts everything and is a classic bug.&lt;/p&gt;

&lt;h3&gt;
  
  
  Set operators &lt;strong&gt;[DIFFERS in naming and defaults]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Operation&lt;/th&gt;
&lt;th&gt;PG&lt;/th&gt;
&lt;th&gt;MySQL&lt;/th&gt;
&lt;th&gt;SQL Server&lt;/th&gt;
&lt;th&gt;Oracle&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Union, dedupe&lt;/td&gt;
&lt;td&gt;&lt;code&gt;UNION&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;UNION&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;UNION&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;UNION&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Union, keep dupes&lt;/td&gt;
&lt;td&gt;&lt;code&gt;UNION ALL&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;UNION ALL&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;UNION ALL&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;UNION ALL&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Difference&lt;/td&gt;
&lt;td&gt;&lt;code&gt;EXCEPT&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;EXCEPT&lt;/code&gt; (8.0.31+)&lt;/td&gt;
&lt;td&gt;&lt;code&gt;EXCEPT&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;MINUS&lt;/code&gt; (&lt;code&gt;EXCEPT&lt;/code&gt; added in 21c+)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Intersection&lt;/td&gt;
&lt;td&gt;&lt;code&gt;INTERSECT&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;INTERSECT&lt;/code&gt; (8.0.31+)&lt;/td&gt;
&lt;td&gt;&lt;code&gt;INTERSECT&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;INTERSECT&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;Always ask whether you need &lt;code&gt;UNION&lt;/code&gt; or &lt;code&gt;UNION ALL&lt;/code&gt;.&lt;/strong&gt; &lt;code&gt;UNION&lt;/code&gt; performs a full dedupe (sort or hash) over the combined result. If the branches are provably disjoint — different date ranges, different status values — &lt;code&gt;UNION ALL&lt;/code&gt; is free and &lt;code&gt;UNION&lt;/code&gt; costs you a sort of the entire set. On a 200M-row report this is the difference between 40 seconds and 8 minutes.&lt;/p&gt;

&lt;p&gt;Also: &lt;code&gt;EXCEPT&lt;/code&gt;/&lt;code&gt;MINUS&lt;/code&gt; deduplicate the left side. &lt;code&gt;NOT EXISTS&lt;/code&gt; does not. They are not interchangeable when duplicates are meaningful.&lt;/p&gt;

&lt;h3&gt;
  
  
  Join algorithms &lt;strong&gt;[DIFFERS — matters at scale]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Algorithm&lt;/th&gt;
&lt;th&gt;PG&lt;/th&gt;
&lt;th&gt;MySQL 8.0&lt;/th&gt;
&lt;th&gt;SQL Server&lt;/th&gt;
&lt;th&gt;Oracle&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Nested loop&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Hash join&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅ (8.0.18+)&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Merge join&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;❌ &lt;strong&gt;never&lt;/strong&gt;
&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅ (sort-merge)&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;MySQL's gap is the important one.&lt;/strong&gt; Before 8.0.18 MySQL had &lt;em&gt;only&lt;/em&gt; nested-loop variants (&lt;code&gt;BNL&lt;/code&gt;). A three-table analytical join over millions of rows that any other engine resolves with hash joins in seconds could run for hours on MySQL 5.7. If you're on MySQL and a large join is slow, check the version first — this is frequently the whole answer. And MySQL still has no merge join, so pre-sorted large-to-large joins don't get that option.&lt;/p&gt;

&lt;p&gt;Practical consequence: &lt;strong&gt;MySQL is a weaker analytical engine than the other three.&lt;/strong&gt; Design around it — pre-aggregate into summary tables rather than expecting the optimizer to rescue a 6-table star join.&lt;/p&gt;




&lt;h2&gt;
  
  
  5. Window Functions
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Availability &lt;strong&gt;[DIFFERS]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Basic windows&lt;/th&gt;
&lt;th&gt;Full frames (&lt;code&gt;ROWS&lt;/code&gt;/&lt;code&gt;RANGE&lt;/code&gt;)&lt;/th&gt;
&lt;th&gt;
&lt;code&gt;GROUPS&lt;/code&gt; / &lt;code&gt;EXCLUDE&lt;/code&gt;
&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Oracle&lt;/td&gt;
&lt;td&gt;8i (ancient, very mature)&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;GROUPS&lt;/code&gt; in 21c+&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;SQL Server&lt;/td&gt;
&lt;td&gt;2005 (ranking only)&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;2012+&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;❌ not supported&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;PostgreSQL&lt;/td&gt;
&lt;td&gt;8.4&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅ (11+)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MySQL&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;8.0 only&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;code&gt;ROW_NUMBER&lt;/code&gt;, &lt;code&gt;RANK&lt;/code&gt;, &lt;code&gt;DENSE_RANK&lt;/code&gt;, &lt;code&gt;NTILE&lt;/code&gt;, &lt;code&gt;LAG&lt;/code&gt;, &lt;code&gt;LEAD&lt;/code&gt;, &lt;code&gt;FIRST_VALUE&lt;/code&gt;, &lt;code&gt;LAST_VALUE&lt;/code&gt;, &lt;code&gt;SUM/AVG/COUNT/MIN/MAX OVER&lt;/code&gt; are present and identical in semantics on all four modern versions. &lt;strong&gt;[SAME]&lt;/strong&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  The three ranking functions &lt;strong&gt;[SAME]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;For values &lt;code&gt;100, 100, 90, 80&lt;/code&gt;:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Function&lt;/th&gt;
&lt;th&gt;Result&lt;/th&gt;
&lt;th&gt;Use when&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;ROW_NUMBER()&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;1, 2, 3, 4&lt;/td&gt;
&lt;td&gt;You need exactly one row per group — deduplication, "latest record"&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;RANK()&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;1, 1, 3, 4&lt;/td&gt;
&lt;td&gt;Competition ranking; gaps after ties&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;DENSE_RANK()&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;1, 1, 2, 3&lt;/td&gt;
&lt;td&gt;"Top 3 &lt;em&gt;distinct&lt;/em&gt; salary levels"; no gaps&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;The classic requirement mismatch:&lt;/strong&gt; "give me the top 3 earners per department." If two people tie for 3rd, do you want 3 rows or 4? &lt;code&gt;ROW_NUMBER&lt;/code&gt; gives 3 (arbitrarily dropping one — nondeterministic and a real bug). &lt;code&gt;RANK&lt;/code&gt;/&lt;code&gt;DENSE_RANK&lt;/code&gt; give 4. Ask the business. Then make the tiebreaker explicit either way.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Always add a deterministic tiebreaker to &lt;code&gt;ORDER BY&lt;/code&gt; inside the window.&lt;/strong&gt; &lt;code&gt;ORDER BY order_date DESC&lt;/code&gt; on a table with same-day orders produces different results run to run. Write &lt;code&gt;ORDER BY order_date DESC, order_id DESC&lt;/code&gt;. This is the source of most "the report changed but the data didn't" tickets.&lt;/p&gt;

&lt;h3&gt;
  
  
  Deduplication idiom &lt;strong&gt;[SAME]&lt;/strong&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;WITH&lt;/span&gt; &lt;span class="n"&gt;ranked&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
         &lt;span class="n"&gt;ROW_NUMBER&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;PARTITION&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;natural_key&lt;/span&gt;
                            &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;loaded_at&lt;/span&gt; &lt;span class="k"&gt;DESC&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;id&lt;/span&gt; &lt;span class="k"&gt;DESC&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="n"&gt;rn&lt;/span&gt;
  &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;staging&lt;/span&gt; &lt;span class="n"&gt;t&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;ranked&lt;/span&gt; &lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;rn&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The CTE wrapper is required — you cannot filter on a window function in &lt;code&gt;WHERE&lt;/code&gt; on any of these four, because windows are evaluated after &lt;code&gt;WHERE&lt;/code&gt;. &lt;strong&gt;None of PostgreSQL, MySQL, SQL Server, or Oracle support &lt;code&gt;QUALIFY&lt;/code&gt;&lt;/strong&gt; (that's Teradata/Snowflake/DuckDB). Expect to write the CTE.&lt;/p&gt;

&lt;p&gt;PostgreSQL has a shorthand for the &lt;code&gt;rn = 1&lt;/code&gt; case:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="k"&gt;DISTINCT&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;natural_key&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;staging&lt;/span&gt; &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;natural_key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;loaded_at&lt;/span&gt; &lt;span class="k"&gt;DESC&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;id&lt;/span&gt; &lt;span class="k"&gt;DESC&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;PG-only. Often faster than &lt;code&gt;ROW_NUMBER&lt;/code&gt; there.&lt;/p&gt;

&lt;h3&gt;
  
  
  The default frame — the biggest window-function gotcha &lt;strong&gt;[SAME semantics, [DIFFERS] in cost]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;When you write &lt;code&gt;OVER (PARTITION BY x ORDER BY y)&lt;/code&gt; with no frame clause, the implicit frame is &lt;code&gt;RANGE BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;RANGE&lt;/code&gt; means &lt;strong&gt;peer rows (ties in &lt;code&gt;y&lt;/code&gt;) are all included at once&lt;/strong&gt;. So a "running total" over a day-grain column gives every row on the same date the &lt;em&gt;full day's&lt;/em&gt; total, not a true row-by-row running sum. People find this months later.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- What you almost always meant:&lt;/span&gt;
&lt;span class="k"&gt;SUM&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;amount&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;OVER&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;PARTITION&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;customer_id&lt;/span&gt;
                  &lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;order_date&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;order_id&lt;/span&gt;
                  &lt;span class="k"&gt;ROWS&lt;/span&gt; &lt;span class="k"&gt;BETWEEN&lt;/span&gt; &lt;span class="n"&gt;UNBOUNDED&lt;/span&gt; &lt;span class="k"&gt;PRECEDING&lt;/span&gt; &lt;span class="k"&gt;AND&lt;/span&gt; &lt;span class="k"&gt;CURRENT&lt;/span&gt; &lt;span class="k"&gt;ROW&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;SQL Server–specific performance angle:&lt;/strong&gt; in SQL Server the default &lt;code&gt;RANGE&lt;/code&gt; frame uses an &lt;strong&gt;on-disk&lt;/strong&gt; worktable spool, while &lt;code&gt;ROWS&lt;/code&gt; uses an in-memory spool. Specifying &lt;code&gt;ROWS&lt;/code&gt; explicitly is frequently a 5–10× improvement on large partitions — even when the results would be identical. Make &lt;code&gt;ROWS ...&lt;/code&gt; mandatory in SQL Server code review.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;LAST_VALUE&lt;/code&gt; trap [SAME]:&lt;/strong&gt; &lt;code&gt;LAST_VALUE(x) OVER (ORDER BY y)&lt;/code&gt; returns the current row's value, because the default frame ends at the current row. You need &lt;code&gt;ROWS BETWEEN UNBOUNDED PRECEDING AND UNBOUNDED FOLLOWING&lt;/code&gt;, or better, use &lt;code&gt;FIRST_VALUE&lt;/code&gt; with the order reversed.&lt;/p&gt;

&lt;h3&gt;
  
  
  Named windows &lt;strong&gt;[DIFFERS]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;PostgreSQL, MySQL 8.0, and Oracle support &lt;code&gt;WINDOW w AS (PARTITION BY ... ORDER BY ...)&lt;/code&gt; then &lt;code&gt;OVER w&lt;/code&gt;. &lt;strong&gt;SQL Server does not&lt;/strong&gt; — you repeat the full &lt;code&gt;OVER&lt;/code&gt; clause. Minor, but it's a portability paper cut and a source of copy-paste inconsistency in SQL Server code.&lt;/p&gt;

&lt;h3&gt;
  
  
  Performance notes &lt;strong&gt;[DIFFERS]&lt;/strong&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;An index on &lt;code&gt;(partition_cols, order_cols)&lt;/code&gt; lets PostgreSQL, Oracle, and SQL Server skip the sort entirely. This is often the single highest-leverage index on a reporting table.&lt;/li&gt;
&lt;li&gt;SQL Server 2019+ has batch-mode window aggregates on rowstore, which is dramatically faster for large partitions — but it's cost-threshold-gated. SQL Server 2022 improved the window aggregate operator further.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;MySQL sorts for every distinct window specification.&lt;/strong&gt; Three windows with three different &lt;code&gt;ORDER BY&lt;/code&gt;s = three sorts. Consolidate window definitions where you can.&lt;/li&gt;
&lt;li&gt;Oracle's window implementation is the most mature of the four and generally the fastest at large scale, especially with parallel query.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  When &lt;em&gt;not&lt;/em&gt; to use a window function
&lt;/h3&gt;

&lt;p&gt;If you only need aggregates at the group grain, &lt;code&gt;GROUP BY&lt;/code&gt; is cheaper — it collapses rows; windows preserve them. Don't write &lt;code&gt;SELECT DISTINCT customer_id, SUM(x) OVER (PARTITION BY customer_id)&lt;/code&gt;; write &lt;code&gt;GROUP BY&lt;/code&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  6. JSON in the Database
&lt;/h2&gt;

&lt;h3&gt;
  
  
  First, the design rule &lt;strong&gt;[SAME]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;JSON columns are for &lt;strong&gt;genuinely schemaless, sparse, or third-party-shaped payloads&lt;/strong&gt;: webhook bodies, per-tenant custom fields, audit snapshots, API response caching. They are &lt;em&gt;not&lt;/em&gt; a substitute for columns.&lt;/p&gt;

&lt;p&gt;The test: &lt;strong&gt;if you filter, join, sort, or aggregate on it regularly, it should be a column.&lt;/strong&gt; Every engine's JSON indexing story is worse than a plain B-tree on a scalar column. You also lose type checking, NOT NULL, foreign keys, and check constraints.&lt;/p&gt;

&lt;p&gt;Second rule: &lt;strong&gt;do not use JSON as an EAV escape hatch.&lt;/strong&gt; "Just put the extra attributes in a JSON blob" is how you get a 400GB table where nobody knows what's in it and every query is a full scan.&lt;/p&gt;

&lt;h3&gt;
  
  
  Capability comparison &lt;strong&gt;[DIFFERS heavily — this is the least portable area in SQL]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;&lt;/th&gt;
&lt;th&gt;PostgreSQL&lt;/th&gt;
&lt;th&gt;MySQL 8.0&lt;/th&gt;
&lt;th&gt;SQL Server&lt;/th&gt;
&lt;th&gt;Oracle&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Native type&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;json&lt;/code&gt; (text) / &lt;strong&gt;&lt;code&gt;jsonb&lt;/code&gt;&lt;/strong&gt; (binary)&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;JSON&lt;/code&gt; (binary)&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;NVARCHAR(MAX)&lt;/code&gt; + &lt;code&gt;ISJSON&lt;/code&gt; check (native &lt;code&gt;json&lt;/code&gt; type in SQL Server 2025)&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;JSON&lt;/code&gt; type in 21c+; before that &lt;code&gt;CLOB&lt;/code&gt;/&lt;code&gt;VARCHAR2&lt;/code&gt; + &lt;code&gt;IS JSON&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Extract scalar&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;-&amp;gt;&amp;gt;&lt;/code&gt;, &lt;code&gt;#&amp;gt;&amp;gt;&lt;/code&gt;, &lt;code&gt;jsonb_path_query&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;-&amp;gt;&amp;gt;&lt;/code&gt;, &lt;code&gt;JSON_UNQUOTE(JSON_EXTRACT())&lt;/code&gt;, &lt;code&gt;JSON_VALUE&lt;/code&gt; (8.0.21+)&lt;/td&gt;
&lt;td&gt;&lt;code&gt;JSON_VALUE&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;JSON_VALUE&lt;/code&gt;, dot notation&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Extract object/array&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;-&amp;gt;&lt;/code&gt;, &lt;code&gt;#&amp;gt;&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;&lt;code&gt;-&amp;gt;&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;JSON_QUERY&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;JSON_QUERY&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Containment test&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;@&amp;gt;&lt;/code&gt; (indexed!)&lt;/td&gt;
&lt;td&gt;&lt;code&gt;JSON_CONTAINS&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;JSON_PATH_EXISTS&lt;/code&gt; (2022+)&lt;/td&gt;
&lt;td&gt;&lt;code&gt;JSON_EXISTS&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Shred to rows&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;jsonb_array_elements&lt;/code&gt;, &lt;code&gt;JSON_TABLE&lt;/code&gt; (17+)&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;JSON_TABLE&lt;/code&gt; (8.0.4+)&lt;/td&gt;
&lt;td&gt;&lt;code&gt;OPENJSON&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;JSON_TABLE&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Modify in place&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;jsonb_set&lt;/code&gt;, `&lt;/td&gt;
&lt;td&gt;&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;, &lt;/code&gt;-`&lt;/td&gt;
&lt;td&gt;&lt;code&gt;JSON_SET/INSERT/REPLACE/REMOVE&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;General index&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;GIN on &lt;code&gt;jsonb&lt;/code&gt;&lt;/strong&gt; — indexes all keys/values at once&lt;/td&gt;
&lt;td&gt;❌ none&lt;/td&gt;
&lt;td&gt;❌ (until 2025's JSON indexes)&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;JSON search index&lt;/strong&gt; (&lt;code&gt;CREATE SEARCH INDEX ... FOR JSON&lt;/code&gt;)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Targeted index&lt;/td&gt;
&lt;td&gt;B-tree on expression&lt;/td&gt;
&lt;td&gt;Generated column + index; &lt;strong&gt;multi-valued index&lt;/strong&gt; for arrays (8.0.17+)&lt;/td&gt;
&lt;td&gt;Persisted computed column + index&lt;/td&gt;
&lt;td&gt;Function-based index on &lt;code&gt;JSON_VALUE&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;h3&gt;
  
  
  PostgreSQL: use &lt;code&gt;jsonb&lt;/code&gt;, essentially always
&lt;/h3&gt;

&lt;p&gt;&lt;code&gt;json&lt;/code&gt; stores the raw text (preserves whitespace, key order, duplicate keys) and re-parses on every access. &lt;code&gt;jsonb&lt;/code&gt; is parsed binary — faster access, supports indexing and containment operators. Cost: slightly slower insert, key order not preserved, duplicate keys collapsed.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;idx_doc_gin&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;events&lt;/span&gt; &lt;span class="k"&gt;USING&lt;/span&gt; &lt;span class="n"&gt;GIN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;payload&lt;/span&gt; &lt;span class="n"&gt;jsonb_path_ops&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="c1"&gt;-- supports: WHERE payload @&amp;gt; '{"type":"purchase"}'&lt;/span&gt;

&lt;span class="c1"&gt;-- Narrower + smaller when you know the key:&lt;/span&gt;
&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;idx_doc_type&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;events&lt;/span&gt; &lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="n"&gt;payload&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="s1"&gt;'type'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;jsonb_path_ops&lt;/code&gt; GIN indexes are substantially smaller and faster than the default &lt;code&gt;jsonb_ops&lt;/code&gt; but only support &lt;code&gt;@&amp;gt;&lt;/code&gt; / &lt;code&gt;@?&lt;/code&gt; / &lt;code&gt;@@&lt;/code&gt;, not key-existence (&lt;code&gt;?&lt;/code&gt;). Prefer it unless you need key-existence checks.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;PG gotchas at scale:&lt;/strong&gt; large &lt;code&gt;jsonb&lt;/code&gt; values get TOASTed (out-of-line, compressed), so &lt;code&gt;payload-&amp;gt;&amp;gt;'x'&lt;/code&gt; on a 2KB document means detoast + decompress &lt;em&gt;per row&lt;/em&gt;. Extracting one small field from a big document across millions of rows is far slower than people expect. Also, &lt;code&gt;jsonb_set&lt;/code&gt; rewrites the entire value — updating one key in a 100KB document writes 100KB and generates that much WAL.&lt;/p&gt;

&lt;h3&gt;
  
  
  MySQL: no direct JSON index — this catches everyone
&lt;/h3&gt;

&lt;p&gt;You cannot &lt;code&gt;CREATE INDEX ON t (json_col-&amp;gt;&amp;gt;'$.status')&lt;/code&gt; directly in the way you'd hope. Two supported routes:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- Route 1: generated column (works 5.7+)&lt;/span&gt;
&lt;span class="k"&gt;ALTER&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;events&lt;/span&gt;
  &lt;span class="k"&gt;ADD&lt;/span&gt; &lt;span class="k"&gt;COLUMN&lt;/span&gt; &lt;span class="n"&gt;evt_type&lt;/span&gt; &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;50&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;JSON_UNQUOTE&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;JSON_EXTRACT&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;payload&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'$.type'&lt;/span&gt;&lt;span class="p"&gt;)))&lt;/span&gt; &lt;span class="n"&gt;STORED&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="k"&gt;ADD&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;idx_evt_type&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;evt_type&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="c1"&gt;-- Route 2: functional index (8.0.13+) — same thing, less clutter&lt;/span&gt;
&lt;span class="k"&gt;ALTER&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;events&lt;/span&gt; &lt;span class="k"&gt;ADD&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;idx_evt_type&lt;/span&gt; &lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="k"&gt;CAST&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;payload&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&amp;gt;&lt;/span&gt;&lt;span class="s1"&gt;'$.type'&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="nb"&gt;CHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;50&lt;/span&gt;&lt;span class="p"&gt;))));&lt;/span&gt;

&lt;span class="c1"&gt;-- Route 3: multi-valued index for arrays (8.0.17+)&lt;/span&gt;
&lt;span class="k"&gt;ALTER&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;events&lt;/span&gt; &lt;span class="k"&gt;ADD&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;idx_tags&lt;/span&gt; &lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="k"&gt;CAST&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;payload&lt;/span&gt;&lt;span class="o"&gt;-&amp;gt;&lt;/span&gt;&lt;span class="s1"&gt;'$.tags'&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt; &lt;span class="nb"&gt;CHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;40&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;ARRAY&lt;/span&gt;&lt;span class="p"&gt;)));&lt;/span&gt;
&lt;span class="c1"&gt;-- used by: WHERE JSON_CONTAINS(payload-&amp;gt;'$.tags', '"urgent"')&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Multi-valued indexes are MySQL's one genuinely nice JSON feature — one index entry per array element, queryable via &lt;code&gt;MEMBER OF&lt;/code&gt;, &lt;code&gt;JSON_CONTAINS&lt;/code&gt;, &lt;code&gt;JSON_OVERLAPS&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;MySQL gotchas:&lt;/strong&gt; JSON columns can't be used in a primary key; generated columns must be &lt;code&gt;STORED&lt;/code&gt; (not &lt;code&gt;VIRTUAL&lt;/code&gt;) for some index types; partial in-place updates only happen under narrow conditions (&lt;code&gt;JSON_SET&lt;/code&gt; on same-or-smaller value) — otherwise MySQL rewrites the whole document and logs it whole to the binlog. Replication lag from JSON-heavy writes is a real production issue.&lt;/p&gt;

&lt;h3&gt;
  
  
  SQL Server: text with functions (historically)
&lt;/h3&gt;

&lt;p&gt;Through SQL Server 2022, JSON is &lt;code&gt;NVARCHAR(MAX)&lt;/code&gt; — there was no JSON type, no JSON index. You get it via:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;ALTER&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;Events&lt;/span&gt; &lt;span class="k"&gt;ADD&lt;/span&gt; &lt;span class="n"&gt;EventType&lt;/span&gt; &lt;span class="k"&gt;AS&lt;/span&gt;
  &lt;span class="n"&gt;JSON_VALUE&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Payload&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'$.type'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;PERSISTED&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;IX_Events_Type&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;Events&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;EventType&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;OPENJSON&lt;/code&gt; with an explicit &lt;code&gt;WITH&lt;/code&gt; schema is dramatically faster than the default key/value form, and gives you typed columns:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;type&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;amount&lt;/span&gt;
&lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;Events&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;
&lt;span class="k"&gt;CROSS&lt;/span&gt; &lt;span class="n"&gt;APPLY&lt;/span&gt; &lt;span class="n"&gt;OPENJSON&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Payload&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
  &lt;span class="k"&gt;WITH&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;type&lt;/span&gt; &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;50&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="s1"&gt;'$.type'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;amount&lt;/span&gt; &lt;span class="nb"&gt;DECIMAL&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;18&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="s1"&gt;'$.amount'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;j&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Add &lt;code&gt;CHECK (ISJSON(Payload) = 1)&lt;/code&gt; on the column or you &lt;em&gt;will&lt;/em&gt; accumulate malformed rows.&lt;/p&gt;

&lt;p&gt;SQL Server 2025 introduced a native &lt;code&gt;json&lt;/code&gt; type with binary storage and JSON indexes; if you're on it, prefer that over &lt;code&gt;NVARCHAR(MAX)&lt;/code&gt;. Confirm the specifics against the docs for your build — this is recent.&lt;/p&gt;

&lt;h3&gt;
  
  
  Oracle: strongest declarative story
&lt;/h3&gt;

&lt;p&gt;Oracle's JSON support (especially 19c+ and 21c/23ai) is arguably the most complete:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- Constraint on pre-21c storage&lt;/span&gt;
&lt;span class="k"&gt;ALTER&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;events&lt;/span&gt; &lt;span class="k"&gt;ADD&lt;/span&gt; &lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;ck_json&lt;/span&gt; &lt;span class="k"&gt;CHECK&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;payload&lt;/span&gt; &lt;span class="k"&gt;IS&lt;/span&gt; &lt;span class="n"&gt;JSON&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="c1"&gt;-- Dot notation (requires table alias)&lt;/span&gt;
&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;payload&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;type&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;payload&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;amount&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;events&lt;/span&gt; &lt;span class="n"&gt;e&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="c1"&gt;-- General-purpose index over the whole document&lt;/span&gt;
&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;SEARCH&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;idx_payload&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;events&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;payload&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;FOR&lt;/span&gt; &lt;span class="n"&gt;JSON&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="c1"&gt;-- Targeted&lt;/span&gt;
&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;idx_type&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;events&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;JSON_VALUE&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;payload&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s1"&gt;'$.type'&lt;/span&gt;
  &lt;span class="n"&gt;RETURNING&lt;/span&gt; &lt;span class="n"&gt;VARCHAR2&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;50&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;ERROR&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;ERROR&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;EMPTY&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;RETURNING&lt;/code&gt; clause and error-handling clauses must match exactly between index definition and query predicate or the index isn't used — a common and frustrating gotcha.&lt;/p&gt;

&lt;p&gt;Oracle 23ai adds &lt;strong&gt;JSON Relational Duality Views&lt;/strong&gt;: relational tables underneath, JSON document API on top, with proper concurrency control. Genuinely the best answer to "the app team wants documents, I want normalization," if you're on that version.&lt;/p&gt;

&lt;h3&gt;
  
  
  Portable JSON advice
&lt;/h3&gt;

&lt;p&gt;If you must support more than one engine: use JSON as an &lt;strong&gt;opaque payload&lt;/strong&gt; — store it, retrieve it whole, parse in the application. The moment you query &lt;em&gt;inside&lt;/em&gt; it, you've committed to that engine. Extract the fields you query into real columns at write time.&lt;/p&gt;




&lt;h1&gt;
  
  
  PART II — SCHEMA &amp;amp; PHYSICAL DESIGN
&lt;/h1&gt;

&lt;h2&gt;
  
  
  7. Indexing Strategy
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Universal principles &lt;strong&gt;[SAME]&lt;/strong&gt;
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Leading-column rule.&lt;/strong&gt; A composite index on &lt;code&gt;(a, b, c)&lt;/code&gt; serves predicates on &lt;code&gt;a&lt;/code&gt;, &lt;code&gt;(a,b)&lt;/code&gt;, &lt;code&gt;(a,b,c)&lt;/code&gt;. It does &lt;strong&gt;not&lt;/strong&gt; efficiently serve &lt;code&gt;b&lt;/code&gt; alone. All four can do a full index scan in that case, but that's not what you designed for.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Equality columns first, then range, then include-only columns.&lt;/strong&gt; For &lt;code&gt;WHERE tenant_id = ? AND status = ? AND created_at &amp;gt; ?&lt;/code&gt;, index &lt;code&gt;(tenant_id, status, created_at)&lt;/code&gt;. Putting &lt;code&gt;created_at&lt;/code&gt; before &lt;code&gt;status&lt;/code&gt; means the index can only seek to the range start and must filter the rest.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Covering indexes eliminate the table lookup.&lt;/strong&gt; If the index contains every column the query needs, the engine never touches the base table.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Every index is a tax on writes.&lt;/strong&gt; Ten indexes = ten structures to maintain per insert/update. Measure before adding.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Selectivity matters.&lt;/strong&gt; An index on a boolean or a 3-value status is usually useless &lt;em&gt;alone&lt;/em&gt;; it's useful as a &lt;em&gt;trailing&lt;/em&gt; column or as a partial index.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Index your foreign keys.&lt;/strong&gt; See below — this one differs, and it matters.&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  The structural difference: clustering &lt;strong&gt;[DIFFERS — foundational]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Table storage&lt;/th&gt;
&lt;th&gt;Consequence&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;MySQL/InnoDB&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;Always&lt;/strong&gt; clustered on the PK (or a hidden rowid if none). Secondary indexes store the &lt;strong&gt;PK value&lt;/strong&gt; as the row pointer.&lt;/td&gt;
&lt;td&gt;A wide PK (e.g. &lt;code&gt;UUID CHAR(36)&lt;/code&gt;) is duplicated into &lt;em&gt;every&lt;/em&gt; secondary index. Random PKs cause page splits on every insert.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;SQL Server&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Clustered index &lt;strong&gt;optional&lt;/strong&gt;; without one the table is a heap. Nonclustered indexes point to the clustering key (or RID for heaps).&lt;/td&gt;
&lt;td&gt;Same PK-width amplification as InnoDB when clustered. Heaps suffer forwarded records on updates.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;PostgreSQL&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Always a heap. No clustered index. &lt;code&gt;CLUSTER&lt;/code&gt; is a one-time reorganization that doesn't hold.&lt;/td&gt;
&lt;td&gt;Physical order drifts; correlation matters for range scan cost. Index-only scans need the visibility map to be current.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Oracle&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Heap by default; &lt;strong&gt;Index-Organized Tables&lt;/strong&gt; available for PK-clustered storage.&lt;/td&gt;
&lt;td&gt;IOTs are great for narrow lookup tables, less so for wide ones.&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;The PK choice consequence:&lt;/strong&gt; on MySQL and SQL Server, use a &lt;strong&gt;narrow, monotonically increasing&lt;/strong&gt; clustering key. &lt;code&gt;BIGINT&lt;/code&gt; identity/auto_increment is the default correct answer. Random &lt;code&gt;UUID&lt;/code&gt;v4 as a clustered PK on InnoDB is a well-documented performance disaster — insert throughput collapses as the B-tree fragments and every secondary index carries 16–36 bytes per entry.&lt;/p&gt;

&lt;p&gt;If you need UUIDs for distributed ID generation, use a &lt;strong&gt;time-ordered&lt;/strong&gt; variant (UUIDv7, or SQL Server's &lt;code&gt;NEWSEQUENTIALID()&lt;/code&gt;, or ULID) stored as &lt;code&gt;BINARY(16)&lt;/code&gt; / &lt;code&gt;uniqueidentifier&lt;/code&gt; / &lt;code&gt;uuid&lt;/code&gt; — never as a 36-char string. PostgreSQL tolerates random UUIDs better (heap storage) but still suffers index bloat and worse cache locality.&lt;/p&gt;

&lt;h3&gt;
  
  
  Index feature matrix &lt;strong&gt;[DIFFERS]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Feature&lt;/th&gt;
&lt;th&gt;PG&lt;/th&gt;
&lt;th&gt;MySQL 8.0&lt;/th&gt;
&lt;th&gt;SQL Server&lt;/th&gt;
&lt;th&gt;Oracle&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Partial / filtered index&lt;/td&gt;
&lt;td&gt;✅ &lt;code&gt;WHERE&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;td&gt;✅ filtered index&lt;/td&gt;
&lt;td&gt;❌ (emulate: function-based index returning NULL — Oracle doesn't index all-NULL entries)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Covering non-key columns&lt;/td&gt;
&lt;td&gt;✅ &lt;code&gt;INCLUDE&lt;/code&gt; (11+)&lt;/td&gt;
&lt;td&gt;❌ (add as key cols)&lt;/td&gt;
&lt;td&gt;✅ &lt;code&gt;INCLUDE&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;❌ (add as key cols)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Expression / functional index&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅ (8.0.13+)&lt;/td&gt;
&lt;td&gt;⚠️ via persisted computed column&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Descending index&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅ (8.0+; earlier it was parsed and ignored)&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Bitmap index&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;td&gt;⚠️ columnstore serves the use case&lt;/td&gt;
&lt;td&gt;✅ (&lt;strong&gt;DW only&lt;/strong&gt;)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Columnstore&lt;/td&gt;
&lt;td&gt;⚠️ extensions&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;td&gt;✅ (mature)&lt;/td&gt;
&lt;td&gt;✅ In-Memory Column Store (licensed)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Hash index&lt;/td&gt;
&lt;td&gt;✅ (limited)&lt;/td&gt;
&lt;td&gt;✅ MEMORY engine only&lt;/td&gt;
&lt;td&gt;✅ (in-memory OLTP)&lt;/td&gt;
&lt;td&gt;✅ hash cluster&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;GIN / inverted (arrays, JSON, FTS)&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;⚠️ multi-valued only&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;td&gt;✅ search index&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;BRIN (huge, correlated tables)&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;❌&lt;/td&gt;
&lt;td&gt;⚠️ columnstore segment elimination&lt;/td&gt;
&lt;td&gt;⚠️ zone maps (Exadata)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Invisible index (test before drop)&lt;/td&gt;
&lt;td&gt;⚠️ no&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;td&gt;⚠️ via disable&lt;/td&gt;
&lt;td&gt;✅&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Online index build&lt;/td&gt;
&lt;td&gt;✅ &lt;code&gt;CONCURRENTLY&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;✅ mostly&lt;/td&gt;
&lt;td&gt;✅ Enterprise only&lt;/td&gt;
&lt;td&gt;✅ &lt;code&gt;ONLINE&lt;/code&gt; (EE)&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;Three engine-specific traps worth memorizing:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Oracle: single-column B-tree indexes do not store NULLs.&lt;/strong&gt; So &lt;code&gt;WHERE deleted_at IS NULL&lt;/code&gt; cannot use a single-column index on &lt;code&gt;deleted_at&lt;/code&gt;. Workaround: make it composite (&lt;code&gt;(deleted_at, id)&lt;/code&gt;) or use a function-based index. &lt;em&gt;Related and worse:&lt;/em&gt; &lt;strong&gt;Oracle treats the empty string &lt;code&gt;''&lt;/code&gt; as NULL.&lt;/strong&gt; Code ported from any other engine that relies on &lt;code&gt;col = ''&lt;/code&gt; will silently return nothing.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;PostgreSQL: index-only scans require a current visibility map.&lt;/strong&gt; A heavily-updated table that hasn't been vacuumed will do heap fetches anyway, and your "covering index" won't cover. If index-only scans matter, tune autovacuum aggressively on that table.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Oracle bitmap indexes are for data warehouses only.&lt;/strong&gt; A single-row DML locks an entire bitmap segment, blocking many other rows. Putting one on an OLTP table is a guaranteed concurrency incident.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Filtered/partial indexes — a big win where available
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- PostgreSQL&lt;/span&gt;
&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;idx_orders_pending&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'PENDING'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="c1"&gt;-- SQL Server&lt;/span&gt;
&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;INDEX&lt;/span&gt; &lt;span class="n"&gt;IX_Orders_Pending&lt;/span&gt; &lt;span class="k"&gt;ON&lt;/span&gt; &lt;span class="n"&gt;Orders&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;CreatedAt&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;Status&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'PENDING'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If 0.1% of a 500M-row table is pending, this index is ~500k entries instead of 500M. Enormous. &lt;strong&gt;MySQL has no equivalent&lt;/strong&gt; — the standard workaround is a separate "work queue" table that rows are deleted from when processed. That's not a hack; on MySQL it's the right design.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;SQL Server filtered-index gotcha:&lt;/strong&gt; the plan only uses it if the parameter is provably within the filter. Parameterized queries (&lt;code&gt;WHERE Status = @s&lt;/code&gt;) often &lt;em&gt;won't&lt;/em&gt; use a filtered index because the optimizer can't prove &lt;code&gt;@s = 'PENDING'&lt;/code&gt; at compile time. &lt;code&gt;OPTION (RECOMPILE)&lt;/code&gt; or a literal fixes it. This surprises people constantly.&lt;/p&gt;

&lt;h3&gt;
  
  
  Statistics and plan stability &lt;strong&gt;[DIFFERS — the top cause of "it was fast yesterday"]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Mechanism&lt;/th&gt;
&lt;th&gt;Main failure mode&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;SQL Server&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Auto-update stats on ~20% change (or sqrt-based on 2016+). Plans cached per parameterized statement.&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;Parameter sniffing&lt;/strong&gt; — the first execution's parameter values shape the cached plan for everyone. A plan built for &lt;code&gt;tenant_id = &amp;lt;tiny tenant&amp;gt;&lt;/code&gt; is then used for &lt;code&gt;&amp;lt;huge tenant&amp;gt;&lt;/code&gt;. Remedies: &lt;code&gt;OPTION (RECOMPILE)&lt;/code&gt;, &lt;code&gt;OPTIMIZE FOR&lt;/code&gt;, Query Store forced plans, Automatic Tuning.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Oracle&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Bind peeking + Adaptive Cursor Sharing + SQL Plan Baselines.&lt;/td&gt;
&lt;td&gt;Adaptive features mostly help but can cause plan churn. Baselines/SQL Profiles are the stability tool. Stale stats on volatile tables still bite.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;PostgreSQL&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Autovacuum/autoanalyze. Prepared statements switch to a generic plan after 5 executions if it seems no worse.&lt;/td&gt;
&lt;td&gt;Skewed data + generic plan = bad plan. &lt;code&gt;plan_cache_mode = force_custom_plan&lt;/code&gt; is the escape hatch. Also: &lt;strong&gt;no cross-column statistics by default&lt;/strong&gt; — use &lt;code&gt;CREATE STATISTICS&lt;/code&gt; for correlated columns (&lt;code&gt;city&lt;/code&gt;/&lt;code&gt;postcode&lt;/code&gt;).&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;MySQL&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;Simplest optimizer of the four. Histograms only since 8.0. No plan cache to speak of.&lt;/td&gt;
&lt;td&gt;Weakest cardinality estimation; InnoDB index statistics are &lt;em&gt;sampled&lt;/em&gt; (&lt;code&gt;innodb_stats_persistent_sample_pages&lt;/code&gt;) and can be badly wrong on large tables. Raise the sample pages on big tables.&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;Team practice:&lt;/strong&gt; on SQL Server, when someone says "the app is slow but it's fast when I run it in SSMS," your first hypothesis is parameter sniffing, second is implicit conversion from NVARCHAR parameters. Those two cover the majority of cases.&lt;/p&gt;

&lt;h3&gt;
  
  
  Deep pagination &lt;strong&gt;[SAME problem, same fix]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;&lt;code&gt;LIMIT 20 OFFSET 500000&lt;/code&gt; (or &lt;code&gt;OFFSET ... FETCH&lt;/code&gt;, or &lt;code&gt;ROWNUM&lt;/code&gt;/&lt;code&gt;ROW_NUMBER&lt;/code&gt; filtering) makes the engine produce and discard 500,000 rows. Cost grows linearly with page number. Use &lt;strong&gt;keyset (seek) pagination&lt;/strong&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;SELECT&lt;/span&gt; &lt;span class="p"&gt;...&lt;/span&gt; &lt;span class="k"&gt;FROM&lt;/span&gt; &lt;span class="n"&gt;orders&lt;/span&gt;
&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;order_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="p"&gt;(:&lt;/span&gt;&lt;span class="n"&gt;last_created_at&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="n"&gt;last_order_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;ORDER&lt;/span&gt; &lt;span class="k"&gt;BY&lt;/span&gt; &lt;span class="n"&gt;created_at&lt;/span&gt; &lt;span class="k"&gt;DESC&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;order_id&lt;/span&gt; &lt;span class="k"&gt;DESC&lt;/span&gt;
&lt;span class="k"&gt;FETCH&lt;/span&gt; &lt;span class="k"&gt;FIRST&lt;/span&gt; &lt;span class="mi"&gt;20&lt;/span&gt; &lt;span class="k"&gt;ROWS&lt;/span&gt; &lt;span class="k"&gt;ONLY&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Row-value comparison works in PostgreSQL, MySQL, and Oracle. &lt;strong&gt;SQL Server does not support row-value constructors in comparisons&lt;/strong&gt; — expand manually:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;WHERE&lt;/span&gt; &lt;span class="n"&gt;created_at&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="o"&gt;@&lt;/span&gt;&lt;span class="n"&gt;last_created_at&lt;/span&gt;
   &lt;span class="k"&gt;OR&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;created_at&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;@&lt;/span&gt;&lt;span class="n"&gt;last_created_at&lt;/span&gt; &lt;span class="k"&gt;AND&lt;/span&gt; &lt;span class="n"&gt;order_id&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="o"&gt;@&lt;/span&gt;&lt;span class="n"&gt;last_order_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;(SQL Server may need an index hint or the rewritten &lt;code&gt;OR&lt;/code&gt; form to seek properly; check the plan.)&lt;/p&gt;




&lt;h2&gt;
  
  
  8. Normalization vs. Selective Denormalization
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Normalize first — the default position &lt;strong&gt;[SAME]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;Get to &lt;strong&gt;3NF/BCNF&lt;/strong&gt; and stay there unless you have a measured reason not to. Normalization gives you: one place to update each fact, constraints that actually work, smaller rows (more rows per page, better cache hit rate), and a schema that survives requirement changes.&lt;/p&gt;

&lt;p&gt;Denormalization is a &lt;strong&gt;performance optimization with a correctness cost&lt;/strong&gt;. You are trading guaranteed consistency for speed. Like all optimizations: measure first, and know how you'll maintain it.&lt;/p&gt;

&lt;h3&gt;
  
  
  The critical distinction: derived vs. duplicated
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Derived data&lt;/strong&gt; (a running total, an order count, a "current status") can be recomputed from source. If it drifts, you can rebuild it. Risk is manageable.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Duplicated data&lt;/strong&gt; (customer name copied into orders) has no single source of truth once both copies are editable. This is where corruption lives.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Denormalize derived data freely with a rebuild path. Duplicate raw data only with a very clear write-path story.&lt;/p&gt;

&lt;h3&gt;
  
  
  When redundancy legitimately wins
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;1. Immutable historical snapshots — not really denormalization at all.&lt;/strong&gt;&lt;br&gt;
An order line must store &lt;code&gt;unit_price&lt;/code&gt; and &lt;code&gt;product_name&lt;/code&gt; &lt;strong&gt;as of the transaction&lt;/strong&gt;. This is not a redundant copy of &lt;code&gt;product.price&lt;/code&gt; — it's a different fact ("what we charged") from a different point in time. Joining to &lt;code&gt;product&lt;/code&gt; for historical price is a &lt;em&gt;bug&lt;/em&gt;, not an optimization. Snapshot anything that appears on a legal or financial document.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;2. Counter caches / rollups.&lt;/strong&gt;&lt;br&gt;
&lt;code&gt;post.comment_count&lt;/code&gt; instead of &lt;code&gt;COUNT(*)&lt;/code&gt; on every page load. Worth it when read:write is heavily skewed.&lt;br&gt;
&lt;em&gt;Gotcha at scale:&lt;/em&gt; every comment insert updates the same post row. A hot post becomes a lock convoy. Mitigations: sharded counters (N rows per post, summed), async batch updates, or accept eventual consistency and recompute nightly.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;3. Precomputed aggregate/summary tables.&lt;/strong&gt;&lt;br&gt;
Daily/hourly rollups for dashboards. Almost always the right answer for reporting on a large OLTP table. This is the highest-value denormalization pattern in practice, and the one juniors underuse most.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;4. Flattening a hot join to avoid a two-hop lookup.&lt;/strong&gt;&lt;br&gt;
Storing &lt;code&gt;tenant_id&lt;/code&gt; on every table in a multi-tenant system — even where it's derivable through a parent — so that every index can lead with it and every query can filter on it directly. This is standard, correct multi-tenant design, and it also lets row-level security work cleanly.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;5. Materialized path / nested sets for deep hierarchies.&lt;/strong&gt;&lt;br&gt;
Recursive CTEs are fine for shallow trees. For an org chart read thousands of times a second, store a materialized path (&lt;code&gt;/1/17/93/&lt;/code&gt;) alongside the parent FK. Redundant, but a prefix &lt;code&gt;LIKE '/1/17/%'&lt;/code&gt; on an indexed column beats a recursion.&lt;/p&gt;
&lt;h3&gt;
  
  
  Maintenance mechanisms &lt;strong&gt;[DIFFERS — the largest gap between these engines]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Mechanism&lt;/th&gt;
&lt;th&gt;Notes&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Oracle&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;Materialized views&lt;/strong&gt; with query rewrite, &lt;code&gt;FAST REFRESH ON COMMIT&lt;/code&gt;, materialized view logs&lt;/td&gt;
&lt;td&gt;Best in class. Optimizer transparently rewrites queries to use the MV — the application doesn't change.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;SQL Server&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;Indexed views&lt;/strong&gt; (&lt;code&gt;WITH SCHEMABINDING&lt;/code&gt; + unique clustered index)&lt;/td&gt;
&lt;td&gt;Maintained synchronously and always correct. Auto-matched by the optimizer in Enterprise Edition; other editions need &lt;code&gt;NOEXPAND&lt;/code&gt;. Heavy restrictions: no outer joins, no subqueries, no &lt;code&gt;COUNT(*)&lt;/code&gt; (use &lt;code&gt;COUNT_BIG(*)&lt;/code&gt;), &lt;code&gt;SUM&lt;/code&gt; requires a &lt;code&gt;COUNT_BIG&lt;/code&gt; column.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;PostgreSQL&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;Materialized views&lt;/strong&gt; — manual &lt;code&gt;REFRESH MATERIALIZED VIEW&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;No incremental refresh, no automatic query rewrite. &lt;code&gt;REFRESH ... CONCURRENTLY&lt;/code&gt; avoids blocking readers but requires a unique index and is slower. For incremental, roll your own with triggers.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;MySQL&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;Nothing.&lt;/strong&gt; No materialized views, no indexed views.&lt;/td&gt;
&lt;td&gt;You build summary tables yourself with triggers, scheduled events, or application logic. Plan for this from day one on MySQL.&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;Consequence for design:&lt;/strong&gt; on Oracle you can often denormalize &lt;em&gt;invisibly&lt;/em&gt; via MVs with query rewrite — the logical model stays clean. On MySQL every denormalization is explicit, hand-maintained, and a permanent maintenance obligation. Weight the trade-off accordingly: the same denormalization is much cheaper on Oracle than on MySQL.&lt;/p&gt;
&lt;h3&gt;
  
  
  Keeping redundant data honest &lt;strong&gt;[DIFFERS]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;Three approaches, in order of preference:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;Constraint&lt;/strong&gt; — if the engine can enforce it declaratively, that's free correctness.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Trigger&lt;/strong&gt; — synchronous, correct, but adds latency to every write and is easy to forget when someone does a bulk load. Trigger-maintained rollups are a common source of "the totals don't match" tickets.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Batch reconciliation&lt;/strong&gt; — nightly job that recomputes and reports drift.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;strong&gt;Always build #3 regardless of whether you have #1 or #2.&lt;/strong&gt; A denormalization without a drift-detection job is a future incident. Make "how do we detect and repair drift" a mandatory question in design review.&lt;/p&gt;

&lt;p&gt;Note also: &lt;code&gt;CHECK&lt;/code&gt; constraints in MySQL were parsed and ignored until 8.0.16. Any schema older than that may have constraints that never did anything. Verify.&lt;/p&gt;


&lt;h2&gt;
  
  
  9. Parent/Child and Subtype/Subclass Design
&lt;/h2&gt;
&lt;h3&gt;
  
  
  Foreign keys: index them yourself &lt;strong&gt;[DIFFERS — high-impact]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Auto-indexes FK columns?&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;MySQL/InnoDB&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;Yes&lt;/strong&gt; — automatically creates an index on the child column if one doesn't exist&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;PostgreSQL&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;No&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;SQL Server&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;No&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;strong&gt;Oracle&lt;/strong&gt;&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;No&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;Three of four leave you to it. Unindexed FKs cause:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Slow &lt;code&gt;DELETE&lt;/code&gt;/&lt;code&gt;UPDATE&lt;/code&gt; on the parent (must scan children to enforce the constraint)&lt;/li&gt;
&lt;li&gt;Slow "get all children of X" queries — the most common query in the application&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;The Oracle-specific severity:&lt;/strong&gt; an unindexed foreign key causes Oracle to take a &lt;strong&gt;share lock on the entire child table&lt;/strong&gt; during parent deletes and PK updates. Not a row lock — a table lock. On a busy system this is an outage. This is one of the classic Oracle DBA findings, and it's worth running a "find unindexed FKs" audit query on any Oracle schema you inherit.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Rule: every FK column gets an index, on every engine, unless you can prove it's never traversed and the parent is never deleted from.&lt;/strong&gt;&lt;/p&gt;
&lt;h3&gt;
  
  
  &lt;code&gt;ON DELETE CASCADE&lt;/code&gt; &lt;strong&gt;[SAME syntax, [DIFFERS] in gotchas]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;Supported on all four. Caveats:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Cascades don't fire triggers uniformly.&lt;/strong&gt; In SQL Server, cascading deletes do fire triggers on the child; in MySQL/InnoDB, cascading operations &lt;strong&gt;do not&lt;/strong&gt; fire the child's triggers. Silent data integrity gaps if you rely on triggers for auditing.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;SQL Server rejects multiple cascade paths&lt;/strong&gt; to the same table ("may cause cycles or multiple cascade paths"). Common in graph-ish schemas; you end up doing it in application code or a stored procedure.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Cascade deletes at scale are dangerous.&lt;/strong&gt; Deleting one parent row with 40M descendant rows in a single transaction blows out your log/undo, holds locks for minutes, and can't be interrupted cleanly. For large hierarchies, prefer soft deletes plus a batched purge job.&lt;/li&gt;
&lt;/ul&gt;
&lt;h3&gt;
  
  
  Subtype / subclass modelling — the three options &lt;strong&gt;[SAME conceptually]&lt;/strong&gt;
&lt;/h3&gt;

&lt;p&gt;Scenario: &lt;code&gt;Vehicle&lt;/code&gt; with subtypes &lt;code&gt;Car&lt;/code&gt;, &lt;code&gt;Truck&lt;/code&gt;, &lt;code&gt;Motorcycle&lt;/code&gt;, each with distinct attributes.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;A. Single Table Inheritance&lt;/strong&gt; — one table, all columns, a &lt;code&gt;vehicle_type&lt;/code&gt; discriminator.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;vehicle&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="n"&gt;vehicle_id&lt;/span&gt;    &lt;span class="nb"&gt;BIGINT&lt;/span&gt; &lt;span class="k"&gt;PRIMARY&lt;/span&gt; &lt;span class="k"&gt;KEY&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;vehicle_type&lt;/span&gt;  &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;20&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;vin&lt;/span&gt;           &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;17&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="c1"&gt;-- car only&lt;/span&gt;
  &lt;span class="n"&gt;passenger_cnt&lt;/span&gt; &lt;span class="nb"&gt;INT&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="c1"&gt;-- truck only&lt;/span&gt;
  &lt;span class="n"&gt;payload_kg&lt;/span&gt;    &lt;span class="nb"&gt;INT&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;ck_car&lt;/span&gt; &lt;span class="k"&gt;CHECK&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;vehicle_type&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&amp;gt;&lt;/span&gt; &lt;span class="s1"&gt;'CAR'&lt;/span&gt; &lt;span class="k"&gt;OR&lt;/span&gt;
                           &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;passenger_cnt&lt;/span&gt; &lt;span class="k"&gt;IS&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt; &lt;span class="k"&gt;AND&lt;/span&gt; &lt;span class="n"&gt;payload_kg&lt;/span&gt; &lt;span class="k"&gt;IS&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Simplest queries, no joins, easy polymorphic lookup.
− Wide sparse rows, &lt;code&gt;NOT NULL&lt;/code&gt; impossible on subtype attributes, degrades badly past ~4 subtypes or when subtypes diverge.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Use when: subtypes are few, similar, and attributes are mostly shared.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;B. Class Table Inheritance&lt;/strong&gt; — common attributes in parent, specifics in child tables sharing the PK.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;vehicle&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="n"&gt;vehicle_id&lt;/span&gt;   &lt;span class="nb"&gt;BIGINT&lt;/span&gt; &lt;span class="k"&gt;PRIMARY&lt;/span&gt; &lt;span class="k"&gt;KEY&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;vehicle_type&lt;/span&gt; &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;20&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;vin&lt;/span&gt;          &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;17&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt; &lt;span class="k"&gt;UNIQUE&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;ck_type&lt;/span&gt; &lt;span class="k"&gt;CHECK&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;vehicle_type&lt;/span&gt; &lt;span class="k"&gt;IN&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s1"&gt;'CAR'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'TRUCK'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="s1"&gt;'MOTORCYCLE'&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
  &lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;uq_vehicle_type&lt;/span&gt; &lt;span class="k"&gt;UNIQUE&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;vehicle_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;vehicle_type&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;   &lt;span class="c1"&gt;-- key trick&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="n"&gt;car&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="n"&gt;vehicle_id&lt;/span&gt;    &lt;span class="nb"&gt;BIGINT&lt;/span&gt; &lt;span class="k"&gt;PRIMARY&lt;/span&gt; &lt;span class="k"&gt;KEY&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;vehicle_type&lt;/span&gt;  &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;20&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt; &lt;span class="k"&gt;DEFAULT&lt;/span&gt; &lt;span class="s1"&gt;'CAR'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;passenger_cnt&lt;/span&gt; &lt;span class="nb"&gt;INT&lt;/span&gt; &lt;span class="k"&gt;NOT&lt;/span&gt; &lt;span class="k"&gt;NULL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;ck_car_type&lt;/span&gt; &lt;span class="k"&gt;CHECK&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;vehicle_type&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s1"&gt;'CAR'&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
  &lt;span class="k"&gt;CONSTRAINT&lt;/span&gt; &lt;span class="n"&gt;fk_car_vehicle&lt;/span&gt; &lt;span class="k"&gt;FOREIGN&lt;/span&gt; &lt;span class="k"&gt;KEY&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;vehicle_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;vehicle_type&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;REFERENCES&lt;/span&gt; &lt;span class="n"&gt;vehicle&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;vehicle_id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;vehicle_type&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That composite FK + check constraint pattern is the &lt;strong&gt;standard way to make subtype exclusivity declaratively enforced&lt;/strong&gt; — a row in &lt;code&gt;vehicle&lt;/code&gt; typed &lt;code&gt;CAR&lt;/code&gt; cannot have a &lt;code&gt;truck&lt;/code&gt; row. It works on all four engines. Learn it; most people implement this with application logic and get it wrong.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Proper &lt;code&gt;NOT NULL&lt;/code&gt; on subtype attributes, clean model, no sparse columns.
− Every full read needs a join; "give me all vehicles with all attributes" needs a &lt;code&gt;UNION ALL&lt;/code&gt; of per-subtype joins or several &lt;code&gt;LEFT JOIN&lt;/code&gt;s.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Use when: subtypes have substantial distinct attributes. &lt;strong&gt;This is the default correct answer for most business domains.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;C. Concrete Table Inheritance&lt;/strong&gt; — one independent table per subtype, no parent.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Fastest per-subtype queries, fully constrained.
− No shared PK space, no FK can point at "any vehicle," polymorphic queries need &lt;code&gt;UNION ALL&lt;/code&gt; everywhere. Adding a subtype means touching every polymorphic query.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Use when: subtypes barely overlap and are rarely queried together.&lt;/p&gt;

&lt;h3&gt;
  
  
  The polymorphic FK anti-pattern &lt;strong&gt;[SAME — avoid on all four]&lt;/strong&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight sql"&gt;&lt;code&gt;&lt;span class="c1"&gt;-- DON'T&lt;/span&gt;
&lt;span class="k"&gt;CREATE&lt;/span&gt; &lt;span class="k"&gt;TABLE&lt;/span&gt; &lt;span class="k"&gt;comment&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="n"&gt;comment_id&lt;/span&gt;     &lt;span class="nb"&gt;BIGINT&lt;/span&gt; &lt;span class="k"&gt;PRIMARY&lt;/span&gt; &lt;span class="k"&gt;KEY&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;commentable_id&lt;/span&gt; &lt;span class="nb"&gt;BIGINT&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;        &lt;span class="c1"&gt;-- points to post OR photo OR video&lt;/span&gt;
  &lt;span class="n"&gt;commentable_type&lt;/span&gt; &lt;span class="nb"&gt;VARCHAR&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;20&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Popular in Rails/Django-shaped codebases. You &lt;strong&gt;cannot declare a foreign key&lt;/strong&gt;, so referential integrity is gone. Joins need &lt;code&gt;CASE&lt;/code&gt; or &lt;code&gt;UNION&lt;/code&gt;. Indexes are less selective.&lt;/p&gt;

&lt;p&gt;Better: an exclusive-arc table with one nullable FK per target plus a check that exactly one is non-null; or a shared &lt;code&gt;commentable&lt;/code&gt; supertype table that each concrete type FKs into. The latter is more work up front and correct forever.&lt;/p&gt;

&lt;h3&gt;
  
  
  Engine-specific inheritance/partitioning notes &lt;strong&gt;[DIFFERS]&lt;/strong&gt;
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;PostgreSQL table inheritance&lt;/strong&gt; (&lt;code&gt;INHERITS&lt;/code&gt;) exists but is largely a legacy feature. Its traps: unique constraints and foreign keys &lt;strong&gt;do not span&lt;/strong&gt; parent and children, and an FK pointing &lt;em&gt;at&lt;/em&gt; a parent table won't match rows in children. Use &lt;strong&gt;declarative partitioning&lt;/strong&gt; (10+, mature by 13+) for partitioning, and plain CTI tables for subtyping. Note that in declarative partitioning, unique indexes must include the partition key.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Oracle partitioning&lt;/strong&gt; is the most mature (range/list/hash/composite, interval, reference partitioning, partition-wise joins). Reference partitioning — partitioning a child table by inheriting its parent's partitioning key — is genuinely useful for parent/child at scale and has no equivalent elsewhere. Licensed separately.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;SQL Server&lt;/strong&gt; uses partitioned tables via partition functions/schemes; partition switching is the standard fast archive/load technique. Aligned indexes required for switching.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;MySQL&lt;/strong&gt; partitioning exists but is limited: &lt;strong&gt;every unique key (including the PK) must contain the partitioning column&lt;/strong&gt;, which is a severe constraint. Foreign keys and partitioning historically didn't mix. Often not worth it; sharding at the application layer is more common in the MySQL world.&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  10. How Schema Choices Propagate
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Data types
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Pick the narrowest type that will hold the domain, and pick it correctly the first time.&lt;/strong&gt; Changing a PK from &lt;code&gt;INT&lt;/code&gt; to &lt;code&gt;BIGINT&lt;/code&gt; on a 2-billion-row table is a multi-hour maintenance window on most of these engines.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;&lt;code&gt;INT&lt;/code&gt; vs &lt;code&gt;BIGINT&lt;/code&gt;:&lt;/strong&gt; if a table could ever exceed 2.1 billion rows, use &lt;code&gt;BIGINT&lt;/code&gt; from day one. The 4 extra bytes cost far less than the migration. Running out of &lt;code&gt;INT&lt;/code&gt; identity values in production is a rite of passage you should skip.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Money:&lt;/strong&gt; &lt;code&gt;DECIMAL&lt;/code&gt;/&lt;code&gt;NUMBER&lt;/code&gt; always. Never &lt;code&gt;FLOAT&lt;/code&gt;/&lt;code&gt;REAL&lt;/code&gt;/&lt;code&gt;DOUBLE&lt;/code&gt;. &lt;code&gt;0.1 + 0.2 &amp;lt;&amp;gt; 0.3&lt;/code&gt; in binary floating point, and financial reconciliation will find it.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Booleans [DIFFERS]:&lt;/strong&gt; PostgreSQL has real &lt;code&gt;BOOLEAN&lt;/code&gt;. MySQL's &lt;code&gt;BOOLEAN&lt;/code&gt; is an alias for &lt;code&gt;TINYINT(1)&lt;/code&gt; — it accepts any integer. SQL Server has &lt;code&gt;BIT&lt;/code&gt; (0/1/NULL, not a true boolean; can't be used directly in &lt;code&gt;WHERE x&lt;/code&gt; without comparison). &lt;strong&gt;Oracle had no boolean type in SQL until 23ai&lt;/strong&gt; — legacy Oracle schemas use &lt;code&gt;NUMBER(1)&lt;/code&gt; or &lt;code&gt;CHAR(1)&lt;/code&gt; with a check constraint.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Strings [DIFFERS]:&lt;/strong&gt; PostgreSQL's &lt;code&gt;varchar(n)&lt;/code&gt;/&lt;code&gt;text&lt;/code&gt; have identical performance — the length limit is purely a constraint, so use &lt;code&gt;text&lt;/code&gt; + a check if you like. MySQL's &lt;code&gt;VARCHAR&lt;/code&gt; length affects temp table and index size, and index prefix limits apply. SQL Server: &lt;code&gt;NVARCHAR&lt;/code&gt; is 2 bytes/char (pre-2019 non-UTF8 collations); &lt;code&gt;CHAR(n)&lt;/code&gt; blank-pads. &lt;strong&gt;Oracle:&lt;/strong&gt; &lt;code&gt;VARCHAR2&lt;/code&gt; is the one to use (&lt;code&gt;VARCHAR&lt;/code&gt; is reserved and may change meaning); default &lt;code&gt;NLS_LENGTH_SEMANTICS&lt;/code&gt; is BYTE, so &lt;code&gt;VARCHAR2(50)&lt;/code&gt; may hold fewer than 50 multibyte characters — specify &lt;code&gt;VARCHAR2(50 CHAR)&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Timestamps [DIFFERS]:&lt;/strong&gt; store UTC. PostgreSQL: &lt;code&gt;timestamptz&lt;/code&gt; (stores UTC, converts on display) — use it, not &lt;code&gt;timestamp&lt;/code&gt;. Oracle: &lt;code&gt;TIMESTAMP WITH TIME ZONE&lt;/code&gt; or &lt;code&gt;WITH LOCAL TIME ZONE&lt;/code&gt;. SQL Server: &lt;code&gt;datetime2&lt;/code&gt; (not &lt;code&gt;datetime&lt;/code&gt;), &lt;code&gt;datetimeoffset&lt;/code&gt; if you need the offset. MySQL: &lt;code&gt;TIMESTAMP&lt;/code&gt; converts to UTC but is bounded to 2038; &lt;code&gt;DATETIME&lt;/code&gt; doesn't convert but has no timezone awareness. Pick one convention and enforce it across the schema.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Row width and I/O
&lt;/h3&gt;

&lt;p&gt;Row width is the quietest performance factor in the whole system. Every engine reads &lt;strong&gt;pages&lt;/strong&gt;, not rows. Halving row width doubles rows per page, which roughly halves I/O for scans and doubles effective buffer cache capacity.&lt;/p&gt;

&lt;p&gt;Practical consequences:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Don't put a rarely-read &lt;code&gt;TEXT&lt;/code&gt;/&lt;code&gt;CLOB&lt;/code&gt;/&lt;code&gt;NVARCHAR(MAX)&lt;/code&gt; column in a hot table. Move it to a side table keyed 1:1. (PostgreSQL's TOAST does this automatically for large values; Oracle stores LOBs out of line by default above a threshold; SQL Server and MySQL are less automatic — MySQL's &lt;code&gt;DYNAMIC&lt;/code&gt; row format stores overflow pages but the 20-byte pointer stays inline.)&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;SELECT *&lt;/code&gt; in application code is a design smell for exactly this reason, plus it defeats covering indexes and breaks when columns are added.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Constraints are performance features, not just safety features
&lt;/h3&gt;

&lt;p&gt;&lt;code&gt;NOT NULL&lt;/code&gt;, &lt;code&gt;CHECK&lt;/code&gt;, &lt;code&gt;UNIQUE&lt;/code&gt;, and &lt;code&gt;FOREIGN KEY&lt;/code&gt; give the optimizer information. All four engines use them:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;A &lt;code&gt;NOT NULL&lt;/code&gt; declaration lets the optimizer skip null-handling logic and enables &lt;code&gt;NOT IN&lt;/code&gt; optimizations (see §2).&lt;/li&gt;
&lt;li&gt;A &lt;code&gt;UNIQUE&lt;/code&gt; constraint tells the optimizer a join won't fan out, changing cardinality estimates and enabling join elimination.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Join elimination:&lt;/strong&gt; if you &lt;code&gt;LEFT JOIN&lt;/code&gt; to a parent table and select nothing from it, a validated FK lets SQL Server, Oracle, and PostgreSQL remove the join entirely. This is why views over well-constrained schemas perform better than views over "we enforce it in the app" schemas.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Corollary:&lt;/strong&gt; disabling constraints for a bulk load and re-enabling them &lt;code&gt;NOVALIDATE&lt;/code&gt; (Oracle) or as untrusted (SQL Server) leaves you with constraints the optimizer will not use. Check &lt;code&gt;sys.foreign_keys.is_not_trusted&lt;/code&gt; in SQL Server after any bulk load; check &lt;code&gt;STATUS&lt;/code&gt;/&lt;code&gt;VALIDATED&lt;/code&gt; in Oracle's &lt;code&gt;USER_CONSTRAINTS&lt;/code&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  Concurrency model — affects how you should write queries &lt;strong&gt;[DIFFERS]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Default isolation&lt;/th&gt;
&lt;th&gt;Readers block writers?&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;PostgreSQL&lt;/td&gt;
&lt;td&gt;Read Committed (MVCC)&lt;/td&gt;
&lt;td&gt;No&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Oracle&lt;/td&gt;
&lt;td&gt;Read Committed (MVCC, undo-based)&lt;/td&gt;
&lt;td&gt;No&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MySQL/InnoDB&lt;/td&gt;
&lt;td&gt;
&lt;strong&gt;Repeatable Read&lt;/strong&gt; (MVCC)&lt;/td&gt;
&lt;td&gt;No&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;SQL Server&lt;/td&gt;
&lt;td&gt;Read Committed with &lt;strong&gt;locking&lt;/strong&gt; (unless RCSI is enabled)&lt;/td&gt;
&lt;td&gt;&lt;strong&gt;Yes&lt;/strong&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;This is the biggest operational difference between SQL Server and the other three.&lt;/strong&gt; By default, a long-running report in SQL Server takes shared locks and blocks writers. This is why you see &lt;code&gt;WITH (NOLOCK)&lt;/code&gt; scattered through legacy SQL Server codebases — it's a bad fix (it permits dirty reads, missed rows, and duplicate rows from page splits during scans). The correct fix is enabling &lt;strong&gt;Read Committed Snapshot Isolation (RCSI)&lt;/strong&gt; at the database level, which makes SQL Server behave like the others. Understand the tempdb implications before you flip it on a live system.&lt;/p&gt;

&lt;p&gt;MySQL's Repeatable Read default is also worth knowing: it means a long transaction sees a consistent snapshot for its whole duration, and it uses &lt;strong&gt;gap locks&lt;/strong&gt; for range operations, which produces deadlocks in patterns that would be fine elsewhere.&lt;/p&gt;

&lt;p&gt;Oracle and PostgreSQL never block readers, but PostgreSQL's MVCC means &lt;strong&gt;long-running transactions prevent vacuum from cleaning up dead tuples&lt;/strong&gt;, causing table bloat and eventually transaction-ID wraparound risk. A leaked idle-in-transaction connection is a PostgreSQL-specific production emergency. Monitor &lt;code&gt;pg_stat_activity&lt;/code&gt; for it.&lt;/p&gt;

&lt;h3&gt;
  
  
  Schema change at scale &lt;strong&gt;[DIFFERS — plan for this]&lt;/strong&gt;
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Operation&lt;/th&gt;
&lt;th&gt;PG&lt;/th&gt;
&lt;th&gt;MySQL 8.0&lt;/th&gt;
&lt;th&gt;SQL Server&lt;/th&gt;
&lt;th&gt;Oracle&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;Add nullable column&lt;/td&gt;
&lt;td&gt;Instant&lt;/td&gt;
&lt;td&gt;Instant&lt;/td&gt;
&lt;td&gt;Instant&lt;/td&gt;
&lt;td&gt;Instant&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Add column with default&lt;/td&gt;
&lt;td&gt;Instant (11+)&lt;/td&gt;
&lt;td&gt;Instant (8.0.12+, &lt;code&gt;INSTANT&lt;/code&gt; algo)&lt;/td&gt;
&lt;td&gt;Instant (2012+ Enterprise; metadata-only)&lt;/td&gt;
&lt;td&gt;Instant (11g+)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Add index&lt;/td&gt;
&lt;td&gt;Blocks writes unless &lt;code&gt;CONCURRENTLY&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;Online, mostly&lt;/td&gt;
&lt;td&gt;Online = Enterprise only&lt;/td&gt;
&lt;td&gt;Online = Enterprise&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Widen varchar&lt;/td&gt;
&lt;td&gt;Instant&lt;/td&gt;
&lt;td&gt;Sometimes rebuilds (charset/length byte boundary)&lt;/td&gt;
&lt;td&gt;Instant if same byte-length category&lt;/td&gt;
&lt;td&gt;Instant&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Drop column&lt;/td&gt;
&lt;td&gt;Instant (marks it)&lt;/td&gt;
&lt;td&gt;Rebuilds table (unless INSTANT)&lt;/td&gt;
&lt;td&gt;Instant (marks it)&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;SET UNUSED&lt;/code&gt; then drop&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;Migration rules for the team:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Never rely on "it was fast in staging." Staging has 10k rows.&lt;/li&gt;
&lt;li&gt;Always run migrations with a lock timeout set (&lt;code&gt;SET lock_timeout&lt;/code&gt; in PG, &lt;code&gt;lock_wait_timeout&lt;/code&gt; in MySQL, &lt;code&gt;SET LOCK_TIMEOUT&lt;/code&gt; in SQL Server). A migration that queues behind a long query and then blocks every subsequent query is how a 2-second DDL takes down a site.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;PostgreSQL specifically:&lt;/strong&gt; &lt;code&gt;ALTER TABLE&lt;/code&gt; takes an &lt;code&gt;ACCESS EXCLUSIVE&lt;/code&gt; lock. It waits for existing transactions, and everything queues behind it. Even an "instant" &lt;code&gt;ALTER&lt;/code&gt; can cause a total outage if a long-running &lt;code&gt;SELECT&lt;/code&gt; is in flight. Always &lt;code&gt;SET lock_timeout = '2s'&lt;/code&gt; and retry.&lt;/li&gt;
&lt;li&gt;Use expand/contract for breaking changes: add new → dual-write → backfill → switch reads → stop writing old → drop old. Four deploys, zero downtime.&lt;/li&gt;
&lt;li&gt;On MySQL, know &lt;code&gt;pt-online-schema-change&lt;/code&gt; / &lt;code&gt;gh-ost&lt;/code&gt; exist for the cases where native online DDL doesn't cover you.&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  11. Working Checklists
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Before you commit a query
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;[ ] Stated the result grain in one sentence&lt;/li&gt;
&lt;li&gt;[ ] No &lt;code&gt;DISTINCT&lt;/code&gt; used to paper over a fan-out&lt;/li&gt;
&lt;li&gt;[ ] &lt;code&gt;NOT EXISTS&lt;/code&gt;, never &lt;code&gt;NOT IN&lt;/code&gt; against a subquery&lt;/li&gt;
&lt;li&gt;[ ] No correlated aggregate subqueries in the &lt;code&gt;SELECT&lt;/code&gt; list&lt;/li&gt;
&lt;li&gt;[ ] Aggregation happens before joining, not after&lt;/li&gt;
&lt;li&gt;[ ] Every window &lt;code&gt;ORDER BY&lt;/code&gt; has a deterministic tiebreaker&lt;/li&gt;
&lt;li&gt;[ ] Explicit &lt;code&gt;ROWS BETWEEN&lt;/code&gt; on any ordered window aggregate (mandatory on SQL Server)&lt;/li&gt;
&lt;li&gt;[ ] &lt;code&gt;UNION ALL&lt;/code&gt; unless dedupe is genuinely required&lt;/li&gt;
&lt;li&gt;[ ] No functions wrapped around indexed columns in predicates&lt;/li&gt;
&lt;li&gt;[ ] Parameter types match column types (especially SQL Server NVARCHAR/VARCHAR)&lt;/li&gt;
&lt;li&gt;[ ] Read the execution plan against &lt;strong&gt;production-scale&lt;/strong&gt; data, not staging&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Reading the plan
&lt;/h3&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Engine&lt;/th&gt;
&lt;th&gt;Command&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;PostgreSQL&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;EXPLAIN (ANALYZE, BUFFERS, VERBOSE)&lt;/code&gt; — &lt;code&gt;BUFFERS&lt;/code&gt; is the one people skip and shouldn't&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;MySQL&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;EXPLAIN ANALYZE&lt;/code&gt; (8.0.18+), &lt;code&gt;EXPLAIN FORMAT=JSON&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;SQL Server&lt;/td&gt;
&lt;td&gt;Actual execution plan; &lt;code&gt;SET STATISTICS IO, TIME ON&lt;/code&gt;; Query Store for history&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Oracle&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;DBMS_XPLAN.DISPLAY_CURSOR(format=&amp;gt;'ALLSTATS LAST')&lt;/code&gt; — the &lt;em&gt;actual&lt;/em&gt; plan, not &lt;code&gt;EXPLAIN PLAN&lt;/code&gt;'s prediction&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;&lt;strong&gt;What to look for, universally:&lt;/strong&gt; estimated vs. actual row counts diverging by more than ~10× (bad stats or a bad predicate), scans where you expected seeks, and any operator whose row count explodes relative to its input.&lt;/p&gt;

&lt;h3&gt;
  
  
  Before you commit a schema change
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;[ ] Types are as narrow as the domain allows; money is &lt;code&gt;DECIMAL&lt;/code&gt;; timestamps are timezone-explicit&lt;/li&gt;
&lt;li&gt;[ ] Every FK column has an index (critical on Oracle)&lt;/li&gt;
&lt;li&gt;[ ] PK is narrow and monotonic (critical on MySQL/SQL Server)&lt;/li&gt;
&lt;li&gt;[ ] Subtype exclusivity is enforced by constraint, not by hope&lt;/li&gt;
&lt;li&gt;[ ] Any denormalized value has a documented maintenance path &lt;strong&gt;and&lt;/strong&gt; a drift-detection job&lt;/li&gt;
&lt;li&gt;[ ] Large text/blob columns are out of the hot table&lt;/li&gt;
&lt;li&gt;[ ] Migration is expand/contract with a lock timeout and a rollback plan&lt;/li&gt;
&lt;li&gt;[ ] You know how long it takes at production row counts&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  Quick-Reference: Where the Four Genuinely Diverge
&lt;/h2&gt;

&lt;p&gt;Everything else in this doc is roughly portable. These are the ones to internalize:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;CTE materialization&lt;/strong&gt; — SQL Server inlines and re-executes; PG ≤11 always materializes.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;&lt;code&gt;NOT IN&lt;/code&gt; handling&lt;/strong&gt; — Oracle has null-aware anti-join; PostgreSQL does not optimize it well.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Join algorithms&lt;/strong&gt; — MySQL has no merge join, and no hash join before 8.0.18.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Clustering&lt;/strong&gt; — InnoDB always clusters on PK; PostgreSQL never clusters.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;FK auto-indexing&lt;/strong&gt; — only MySQL does it; Oracle punishes you hardest for skipping it.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Filtered/partial indexes&lt;/strong&gt; — PG and SQL Server have them; MySQL and Oracle don't.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Materialized views&lt;/strong&gt; — Oracle (with query rewrite) ≫ SQL Server (indexed views) &amp;gt; PostgreSQL (manual refresh) ≫ MySQL (none).&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;JSON indexing&lt;/strong&gt; — PG's GIN and Oracle's search index are general; MySQL and (pre-2025) SQL Server require per-path computed columns.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Oracle NULL semantics&lt;/strong&gt; — &lt;code&gt;'' IS NULL&lt;/code&gt;, and single-column B-trees don't index NULLs.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;SQL Server isolation&lt;/strong&gt; — locking reads by default; enable RCSI or live with blocking.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;PostgreSQL vacuum&lt;/strong&gt; — long transactions cause bloat; &lt;code&gt;ACCESS EXCLUSIVE&lt;/code&gt; locks make DDL risky.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Window frame defaults&lt;/strong&gt; — &lt;code&gt;RANGE&lt;/code&gt; is the default everywhere and is almost never what you want.&lt;/li&gt;
&lt;/ol&gt;

</description>
      <category>webdev</category>
      <category>sql</category>
      <category>tutorial</category>
      <category>ai</category>
    </item>
    <item>
      <title>CodeBerg Bans Cryptocurrency and LLM-generated code projects</title>
      <dc:creator>Andrei Merlescu</dc:creator>
      <pubDate>Mon, 27 Jul 2026 15:33:33 +0000</pubDate>
      <link>https://dev.to/andreimerlescu/codeberg-bans-cryptocurrency-and-llm-generated-code-projects-3aj0</link>
      <guid>https://dev.to/andreimerlescu/codeberg-bans-cryptocurrency-and-llm-generated-code-projects-3aj0</guid>
      <description>&lt;p&gt;I'm responding directly to &lt;a href="https://hackaday.com/2026/07/24/codeberg-bans-cryptocurrency-and-llm-generated-code-projects/" rel="noopener noreferrer"&gt;Maya Posch's&lt;/a&gt; piece on HackADay that was published today. Did that rhyme? I think it did. &lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Community-led open source project hosting site Codeberg has formally announced that projects whose code is largely or fully machine-generated through LLMs and other ‘AI’ tools will no longer be welcome. This follows on the heels of a similar ban on cryptocurrency-related projects.&lt;/p&gt;

&lt;p&gt;The community vote was on two issues, the first being the notion that scraping of project code for the use in LLMs should be forbidden, which was a motion that easily passed. The second motion was on disallowing projects whose code was substantially generated by LLMs like Claude, OpenAI Codex, and similar. This motion passed with 358 in favor versus 144 against.&lt;/p&gt;

&lt;p&gt;In the earlier linked blog post the reasoning behind especially this second issue is expanded upon, covering not only ‘license whitewashing’, but also the direct and indirect hardware costs, with the expanding ‘AI’ datacenter hyperscaling having massively increased hardware costs for Codeberg over the past years, as the costs have been largely externalized.&lt;/p&gt;

&lt;p&gt;Also covered is the aspect of these LLM-based tools destroying the OSS community, which is something that is backed up by recent studies. Even if we ignore that such LLM-tools are destroying the cognitive abilities of its users, there’s an argument to be made that if LLM-scraping is disallowed, then it’s consistent to also not allow LLM-generated code.&lt;/p&gt;

&lt;p&gt;In the Terms of Use you can see these changes, both for LLMs and for cryptocurrency projects.&lt;/p&gt;

&lt;p&gt;Thanks to [mk-fg] for the tip.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Credit is due to the original &lt;a href="https://hackaday.com/2026/07/24/codeberg-bans-cryptocurrency-and-llm-generated-code-projects/" rel="noopener noreferrer"&gt;HackADay.com Article by Maya Posch&lt;/a&gt; post contents, but I would like to respond to each point here while preserving what was published on 7-24-2026.&lt;/p&gt;

&lt;h2&gt;
  
  
  Scraping of Project Code for the use in LLMs should be forbidden
&lt;/h2&gt;

&lt;p&gt;If LLMs are rendering code trained on GPL-3 &lt;strong&gt;open-source&lt;/strong&gt; software, then its effectively bypassing the license through intellectual property theft by directly replicating the likeness byproduct itself of the &lt;em&gt;protected entity&lt;/em&gt; and creating a knockoff that &lt;strong&gt;should be forbidden.&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;Companies like &lt;strong&gt;Anthropic&lt;/strong&gt;, &lt;strong&gt;Google AI&lt;/strong&gt;, &lt;strong&gt;Perplexity&lt;/strong&gt;, &lt;strong&gt;Kimi&lt;/strong&gt; including &lt;strong&gt;OpenAI&lt;/strong&gt; (which ironically is &lt;em&gt;not open&lt;/em&gt;) were &lt;strong&gt;likely trained on&lt;/strong&gt; GPL-3 source code like the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; 👉🏻 &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt; and &lt;a href="https://github.com/ProjectApario/search" rel="noopener noreferrer"&gt;search&lt;/a&gt; and many others. That GPL-3 project was published as part of a challenge given to me to &lt;a href="https://dev.to/andreimerlescu/how-i-processed-666k-pages-of-flattened-pdfs-into-a-full-text-search-engine-4db3"&gt;make searchable 666K pages of JFK files&lt;/a&gt; and then &lt;a href="https://dev.to/andreimerlescu/how-i-reduced-my-opex-by-995-using-go-3ff7"&gt;reduce my OPEX from $7K/mo to $33/mo by rewriting the SaaS into a Go binary&lt;/a&gt; and in order to make true to my &lt;em&gt;promises made&lt;/em&gt;, I delivered the &lt;strong&gt;open source result.&lt;/strong&gt; I did not deliver the &lt;em&gt;open source result&lt;/em&gt; for companies like Claude, Anthropic, Google, Microsoft, Oracle and others to use GPL-3 and AGPL-3 protected code to train their LLMs so that the likeness byproduct of that which was &lt;strong&gt;forged over 17 years&lt;/strong&gt; of professional engineering experience since running the IEEE Student Branch in college - bringing be from Cisco to Oracle to WB Games to SurgePays and now here - writing to you in a time of need. &lt;/p&gt;

&lt;p&gt;These companies have taken &lt;a href="https://dev.to/andreimerlescu/when-ai-creates-a-closed-source-world-2oin"&gt;The Library&lt;/a&gt; and they have taken our likeness byproduct and they have charged a metered admission to it. Continuing to publish open source software, without the &lt;strong&gt;mass theft of intellectual property&lt;/strong&gt; is exactly why &lt;strong&gt;I support this measure&lt;/strong&gt; that prohibits the scraping of project's source code by LLMs to train them.&lt;/p&gt;

&lt;p&gt;I've been on GitHub since user 91,485 (2009) and I'm one of the OG originals when it was an incredible company and truly a visionary for the future of open source. I've seen Microsoft come in and take over GitHub and turn it into something where now, when I contribute code to it, in any license form - public or private - I assume that CoPilot is being trained on that intellectual property transfer rights that the Terms of Service so conveniently permits for internal purposes of said collected data. How many times has Microsoft been caught misusing that data? So now, when I work on a large open source project, I know that its helping a lot of really incredible developers and end-users who will benefit from my skill set and passion to write open source software, but it doesn't put food on the table. &lt;/p&gt;

&lt;p&gt;This is where the abuse of companies like Anthropic paying $450,000 for a Senior Software Engineer but openly admitting that the role is only a 12-month contract implies the disposable nature that high value engineers are to these AI companies. They look at us like - how much information can we harvest out of them before we discard them? It is quite barbaric when you look at it through the lens of what Neo in the Matrix woke up to. For me, I see what Anthropic and its competitors are doing - and I agree with CodeBerg's conclusion here by ruling &lt;em&gt;against&lt;/em&gt; CodeBerg in favor of the 144 who sought to disallow the submission of projects built using Large Language Models. &lt;/p&gt;

&lt;h2&gt;
  
  
  Disallowing Projects Whose Code Was Substantially Generated by LLMs like Claude, OpenAI Codex, and similar
&lt;/h2&gt;

&lt;p&gt;Now, here is where I actually side with the 144 - though I prefer the 369 😏 (joke) - over 358, but because it was 11 short, &lt;em&gt;no bueno amigo.&lt;/em&gt; But beyond the funsies with the Tesla numbers aside, why are 358 wrong and 144 right in the case of &lt;strong&gt;allowing&lt;/strong&gt; projects whose code was &lt;em&gt;substantially generated by LLMs&lt;/em&gt; be considered for &lt;em&gt;submission&lt;/em&gt; in the first place misses out on &lt;strong&gt;why LLMs exist in the first place&lt;/strong&gt; and while ruling against &lt;em&gt;both of these measures&lt;/em&gt; asserts an &lt;strong&gt;Anti-AI Position&lt;/strong&gt; for HackADay.com, it does not mean that their platform is going to exclusively adopt this hard-line anti-AI position forever. When we ask the 144 why they seek to &lt;strong&gt;allow&lt;/strong&gt; this behavior, instead of out-right banning it by &lt;em&gt;disallowing submissions&lt;/em&gt; that do leverage LLMs means that the definition of &lt;strong&gt;substantial&lt;/strong&gt; cannot be subject to discretion or opinion, but a direct measurable and enforceable standard that the community at large, should come to an agreement on. Where do you stand on this? Post your comments below and I'll respond. &lt;/p&gt;

&lt;p&gt;Now here is where the 358 are correct - and why I think right now its the correct decision, but I do also think that in time that &lt;em&gt;will change&lt;/em&gt; and the 144 will be &lt;em&gt;right in the long run.&lt;/em&gt; But, right now, getting back to my &lt;strong&gt;GPL-3&lt;/strong&gt; conundrum of &lt;a href="https://dev.to/andreimerlescu/five-hours-of-interviewing-zero-questions-about-the-job-378k"&gt;AI disproportionally harming&lt;/a&gt; the Tech Job Market, current AI generated code does not have the training rules built into them currently in order to appropriately license the AI generated code. Perhaps, until such a license is normalized like the &lt;strong&gt;MIT&lt;/strong&gt; or &lt;strong&gt;Apache 2.0&lt;/strong&gt; like the &lt;strong&gt;AGPL-3&lt;/strong&gt; has to my use of &lt;strong&gt;GPL-3&lt;/strong&gt;, an &lt;strong&gt;AI 1.0&lt;/strong&gt; license should be introduced that explicitly states that code was generated by an LLM and is required under the terms of the license to remain open source at all times. Clones of the source code can operate in private or embedded systems, but AI generated code must be open source &lt;strong&gt;by law.&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;Yes, &lt;strong&gt;by law&lt;/strong&gt; requires &lt;em&gt;Congressional involvement&lt;/em&gt; in this and that's something that the AI community has active involvement with. Advocating for a position is where this piece comes in, and I do not want to necessarily see AI taken away entirely, but I would prefer an AI that was trained on licensed copies of actual text books and technical manuals written by industry leading professionals - rather than reddit posts and stack overflow questions and answers. Those LLMs and models will be worth hundreds of billions of dollars because people will actually pay for them, but proper attribution and licensing currently do not existing the LLM architecture discussions - they just operate under this idea that everything on the internet - regardless of ownership or license - is fair game to &lt;em&gt;duplicate&lt;/em&gt; and then train the likeness byproduct therein as a metered service that will outlive the creator of the original intellectual property without ever once compensating them for their efforts - all while their engineers score half a million dollars a year and their executives are arrogant billionaires dooms-talking the public into panic about AI's capabilities when in reality its a glorified autocomplete that can only look backwards and lacks the light that dwells inside all my beautiful unicorn developers here 💜. &lt;/p&gt;

&lt;h2&gt;
  
  
  LLM-based tools destroying the OSS community
&lt;/h2&gt;

&lt;p&gt;I've noticed this. Some projects that I have seen on GitHub have a .claude directory inside of them or some other LLM based coding agent directory present, and I feel like I cannot actually get involved in the project in any meaningful capacity because if it was entirely generated by an AI, then that more than likely means - not in all cases - but more than likely means that the original account posting the AI-slop &lt;em&gt;doesn't understand what they built&lt;/em&gt; or if it even works. &lt;strong&gt;That's legitimate.&lt;/strong&gt; I stand to call for my publications regarding &lt;a href="https://dev.to/andreimerlescu/lemmings-just-spawned-3fhe"&gt;lemmings&lt;/a&gt; and how I built it, released it, and &lt;strong&gt;most importantly&lt;/strong&gt; documented it. The documentation is what makes the project capable of interacting with outside of seeing a &lt;code&gt;.claude&lt;/code&gt; directory &lt;em&gt;thinking&lt;/em&gt; that AI wrote the project. &lt;strong&gt;I wrote the project.&lt;/strong&gt; The difference is, did the engineer who submitted the project have 17 years of being an autodidact software architect with an electrical background in computer engineering - have the right to submit projects rendered with AI if they are attached with an &lt;code&gt;AI 1.0&lt;/code&gt; license and made freely accessible under open source publication rights? Honestly... I understand why HackADay.com made the decision they made. Right now, we can't appropriately trace the bibliography of the published work, and therefore its considered a forgery in the most pure and absolute manner. &lt;/p&gt;

&lt;p&gt;I also think that the community needs to put our differences aside and resume the in-person conferences and meetups that we had &lt;em&gt;before the pandemic&lt;/em&gt; in the same &lt;strong&gt;strength and volume&lt;/strong&gt; with &lt;em&gt;corporate sponsorship&lt;/em&gt; of leading contributors to &lt;a href="https://dev.to/andreimerlescu/when-ai-creates-a-closed-source-world-2oin"&gt;The Library&lt;/a&gt;. &lt;/p&gt;

&lt;h2&gt;
  
  
  Cryptocurrency Ban
&lt;/h2&gt;

&lt;p&gt;This I think is a smart decision. I've considered removing the repository &lt;a href="https://github.com/andreimerlescu/iamxrp.dev" rel="noopener noreferrer"&gt;iamxrp.dev&lt;/a&gt; because as a training ground of unlicensed code that &lt;strong&gt;cannot be used for commercial purposes&lt;/strong&gt;, I sought to learn about these concepts in order to better understand interacting with the ledger for commercial purposes. For instance, being a &lt;strong&gt;Magento Certified Developer&lt;/strong&gt;, before &lt;code&gt;eBay&lt;/code&gt; acquired the product and &lt;em&gt;ruined it&lt;/em&gt; (now look Shopify is everywhere instead), meant that I could have written a plugin for that store to allow for cryptocurrency payments to be used as a means for authentic business transactions. However, what instead happens is scammers will look at the code, run it without accepting the license it was published in good faith therein, and use it to scam people if they can get away with it. I condemn the scammers and the rug pullers and the "project bros" that launch tokens, collect crypto, and then dump the token and abandon the project. Personally, I've lost out on &lt;strong&gt;tens of thousands of dollars&lt;/strong&gt; because of these tricks that are played, and I believe the open ban on it is actually a very &lt;strong&gt;smart thing to do&lt;/strong&gt; and I support it. In the event that the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; integrated anything crypto into it, the project itself would not be allowed in any platform under this rule. I agree with that. Its a liability risk. I don't blame them. I agree with that conclusion. &lt;/p&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;What does that forgery look like? Well, in the case of lemmings, did I per-character type that project out like I built &lt;a href="https://dev.to/andreimerlescu/topobuilder-brings-a-cpanel-website-into-an-aws-multi-region-containerized-application-with-an-1fpa"&gt;topobuilder&lt;/a&gt;? Nope. &lt;strong&gt;No AI was involved in writing Topobuilder.&lt;/strong&gt; There were 72K total words in the code base. Only 4800 unique words total in the entire code base. Written over 233 hours. Each word was duplicated roughly 15 times in order to orchestrate a cPanel website into a multi-region containerized application built for &lt;a href="https://dev.to/andreimerlescu/how-i-reduced-my-opex-by-995-using-go-3ff7"&gt;OPEX Optimizations&lt;/a&gt;. The source code is private on GitHub and shared with one company currently in a fork of the repository. I am sure that Microsoft has trained their models on my private source code. I am sure that their models will - at some point - if that training occurred - have the ability to render GPL-3 licensed code and even unlicensed commercial code as if it was a hallucination of its own creation. AI cannot create anything. It is autocomplete with a name like Microsoft Clip was in the 90s and early 2000s. &lt;/p&gt;

&lt;p&gt;We've handed over &lt;a href="https://dev.to/andreimerlescu/when-ai-creates-a-closed-source-world-2oin"&gt;The Library&lt;/a&gt; and we've changed &lt;a href=""&gt;how we develop with AI&lt;/a&gt; as engineers, and yet - this decision today is the signal from HackADay.com that represents a large community of developers that the dooms-talking of these AI companies needs to come to an end, and this is &lt;em&gt;our way of putting an end of the madness.&lt;/em&gt; I don't mind that open source LLMs that I can use for my own stuff too locally is trained off my open source projects - but I do believe for the safety of the entire open source community - until LLMs have bibliography level precision in sourcing of original codes used to generate the autocomplete request - companies and industry titans have every right to believe Sam Altman and Dario at their face value word that they do believe - two men who can't write code themselves - that the art of being a software &lt;strong&gt;engineer&lt;/strong&gt; can be replaced by an AI or an LLM just because it is using &lt;em&gt;our collective likeness byproduct therein&lt;/em&gt; to hallucinate things it doesn't understand what it just built. AI has been fun while it lasted, but I look forward to the day when Claude isn't operating the restaurant drive through ordering system. We both know that this is where things will go, unless we put our foot down and say &lt;strong&gt;enough is enough&lt;/strong&gt; to the intellectual property theft by these LLMs and the corporations that are destroying &lt;em&gt;our industry&lt;/em&gt; be given a reckoning of meaning. This decision by HackADay.com is taking that bold step and making a stance against the abuse in the industry caused by excessively greedy corporations that can never be held accountable for their wrongdoing in any meaningful manner - they just keep growing - they just keep consuming - they just keep harming - and it's almost like nothing can stop them. This attempts to. &lt;em&gt;It's a step in the right direction, I believe.&lt;/em&gt;  &lt;/p&gt;

&lt;p&gt;Share with me your thoughts about CodeBerg's decision. Do you support both measures they stated? &lt;/p&gt;

</description>
      <category>opensource</category>
      <category>discuss</category>
      <category>ai</category>
      <category>career</category>
    </item>
    <item>
      <title>How I Reduced My OPEX By 99.5% Using Go</title>
      <dc:creator>Andrei Merlescu</dc:creator>
      <pubDate>Mon, 27 Jul 2026 03:37:37 +0000</pubDate>
      <link>https://dev.to/andreimerlescu/how-i-reduced-my-opex-by-995-using-go-3ff7</link>
      <guid>https://dev.to/andreimerlescu/how-i-reduced-my-opex-by-995-using-go-3ff7</guid>
      <description>&lt;p&gt;Previously, I wrote about &lt;a href="https://dev.to/andreimerlescu/how-i-processed-666k-pages-of-flattened-pdfs-into-a-full-text-search-engine-4db3"&gt;How I Processed 666K Pages Of Flattened PDFs into a Full Text Search Engine&lt;/a&gt; called the &lt;strong&gt;Apario&lt;/strong&gt; &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt;. Upon on the conclusion of the last segment, I was able to optimize the compilation time of the original collection of data by rewriting the &lt;code&gt;sidekiq&lt;/code&gt; &lt;strong&gt;Ruby&lt;/strong&gt; pipeline script into a dedicated &lt;strong&gt;Go Application.&lt;/strong&gt; Regardless of what compiling the PDF assets would look like, I still needed to &lt;em&gt;serve&lt;/em&gt; those assets - and that's where the &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt; did little to nothing to actually address the OPEX of the project from 2020. Given the size of the data set, the 666K pages ended up compiling into a directory of ~1.13TB in size. This was held in storage that was distributed across several high volume storage dedicated servers on OVH behind &lt;a href="https://github.com/minio/minio" rel="noopener noreferrer"&gt;MinIO&lt;/a&gt;. This provided an S3 compatible API directly. &lt;/p&gt;

&lt;h2&gt;
  
  
  What I Know About OPEX
&lt;/h2&gt;

&lt;p&gt;OPEX or &lt;b&gt;Op&lt;/b&gt;erational &lt;b&gt;Ex&lt;/b&gt;pense is how you describe a spending of money that is used explicitly for the &lt;em&gt;operations&lt;/em&gt; of the business versus a &lt;em&gt;capital&lt;/em&gt; expense. Hardware was considered a CAPEX or &lt;b&gt;Cap&lt;/b&gt;ital &lt;b&gt;Ex&lt;/b&gt;pense. So when Bit Fry Game Studios needed their DevOps pipeline upgraded for the 9 hour game builds into a 30 minute private enterprise cloud build, it required a CAPEX investment of $69K plus &lt;em&gt;trust in me&lt;/em&gt; in order to achieve a -$15K/month OPEX savings. Annualized over a hardware lifecycle, over $472K can be recovered from OPEX by making a small CAPEX expense up front. One of the first projects that I ever worked on was in &lt;strong&gt;PHP&lt;/strong&gt; and &lt;strong&gt;MySQL&lt;/strong&gt; on &lt;em&gt;Ubuntu 8.04&lt;/em&gt;. It was to balance the budget of a department that had &lt;code&gt;ACME Bucks&lt;/code&gt; so to speak. It required me to write a finance module, fully tested, that managed &lt;code&gt;Blue&lt;/code&gt;, &lt;code&gt;Green&lt;/code&gt; and &lt;code&gt;Black&lt;/code&gt; dollars. &lt;code&gt;Blue&lt;/code&gt; dollars were for OPEX. &lt;code&gt;Green&lt;/code&gt; dollars were for CAPEX. &lt;code&gt;Black&lt;/code&gt; dollars were for external vendors where money &lt;em&gt;left the company&lt;/em&gt; (versus moving between departments). &lt;code&gt;Black&lt;/code&gt; depreciated instantly - meaning 100% of it was paid immediately. &lt;code&gt;Blue&lt;/code&gt; dollars were borrowed over a 12 month pay-back period. &lt;code&gt;Green&lt;/code&gt; dollars were borrowed over a 36 month pay-back period. The department was given $N per month of &lt;code&gt;Blue&lt;/code&gt;, &lt;code&gt;Green&lt;/code&gt;, and &lt;code&gt;Black&lt;/code&gt; dollars, and there were n-Commitments existing on the books that were depreciating individually from past purchases that summed into the total monthly budget. I wrote a utility that would express this information plainly to multiple &lt;strong&gt;Director of Engineer&lt;/strong&gt; colleagues that I collaborated with closely through a dashboard interface to see monies coming in and going out for the department. That was attached to greater projects and used elsewhere - but the lesson that stayed with me since those early days at Cisco was the use of budgeting between &lt;strong&gt;OPEX&lt;/strong&gt; and &lt;strong&gt;CAPEX&lt;/strong&gt;. Cisco's size and volume of diverse departments made &lt;code&gt;Blue&lt;/code&gt; and &lt;code&gt;Green&lt;/code&gt; dollars possible, but in other businesses that are smaller, that's OPEX and CAPEX. I've built tooling around reporting reliable OPEX &amp;amp; CAPEX information for &lt;strong&gt;Engineering Directors&lt;/strong&gt;. &lt;/p&gt;

&lt;h2&gt;
  
  
  The Costly OPEX Problem
&lt;/h2&gt;

&lt;p&gt;That brings us into the &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt; and how there was a SaaS model of the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;PhoenixVault&lt;/a&gt; that I built using &lt;strong&gt;Ruby on Rails&lt;/strong&gt; on a Zoom call with a former Disney animator, watching me type &lt;code&gt;rails new phoenixvault&lt;/code&gt; 🐦‍🔥. When this launched, I had a rough budget of about $1K for ElasticSearch subscription fees, about $2K for MongoDB Atlas subscription (M30) and about $3K for OVH hosting expenses for 12 bare metal hosts in US East &amp;amp; US West regions. There was about another $1K per month that covered &lt;em&gt;other expenses&lt;/em&gt; related to the &lt;em&gt;operations&lt;/em&gt; of the business. All $7K/mo was an &lt;strong&gt;OPEX&lt;/strong&gt; expense that I engineered a solution out from. &lt;em&gt;Understand what I just said.&lt;/em&gt; I engineered a solution out of the problem that I wrote myself into by doing &lt;code&gt;rails new phoenixvault&lt;/code&gt; without fully &lt;em&gt;owning&lt;/em&gt; the dependency chain of &lt;em&gt;what I was doing in the first place.&lt;/em&gt; In order for me to reduce the OPEX of the project from $7K per month down to $33/month on OVH, required me to strip all dependencies out and seek that 99.5% OPEX cost savings by &lt;strong&gt;rewriting the Ruby on Rails app into Go.&lt;/strong&gt; &lt;em&gt;Not Rust.&lt;/em&gt; &lt;strong&gt;Go.&lt;/strong&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  My Solution To The OPEX Problem
&lt;/h2&gt;

&lt;p&gt;Okay, so lets actually look at the &lt;em&gt;code&lt;/em&gt; that solved my OPEX problem. You ready? I'm using &lt;strong&gt;Rocky 9 Linux&lt;/strong&gt; with &lt;em&gt;SELinux&lt;/em&gt; enforcing. 😍&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; ~/workspace/ProjectApario
git clone git@github.com:ProjectApario/reader.git ~/workspace/ProjectApario/reader 
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Running this application, requires you to build a &lt;code&gt;config.yml&lt;/code&gt; file and then execute the following:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; /opt/apario/&lt;span class="o"&gt;{&lt;/span&gt;app,logs,config,database&lt;span class="o"&gt;}&lt;/span&gt;
&lt;span class="nb"&gt;sudo chown&lt;/span&gt; &lt;span class="nt"&gt;-R&lt;/span&gt; &lt;span class="si"&gt;$(&lt;/span&gt;&lt;span class="nb"&gt;whoami&lt;/span&gt;&lt;span class="si"&gt;)&lt;/span&gt;:&lt;span class="si"&gt;$(&lt;/span&gt;&lt;span class="nb"&gt;whoami&lt;/span&gt;&lt;span class="si"&gt;)&lt;/span&gt; /opt/apario
&lt;span class="c"&gt;# copy your compiled writer output into /opt/apario/app &lt;/span&gt;
&lt;span class="nb"&gt;touch&lt;/span&gt; /opt/apario/config/config.yml
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then, you'll need to go back and compile the binary:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;cd&lt;/span&gt; ~/workspace/ProjectApario/reader
go build &lt;span class="nt"&gt;-o&lt;/span&gt; reader &lt;span class="nb"&gt;.&lt;/span&gt;
&lt;span class="nb"&gt;sudo chmod&lt;/span&gt; +x reader
&lt;span class="nb"&gt;sudo mv &lt;/span&gt;reader /usr/local/bin/reader
which reader
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then once you have successfully installed the &lt;code&gt;reader&lt;/code&gt;, then you can run it against your config file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;cd&lt;/span&gt; /opt/apario/config
&lt;span class="nb"&gt;touch &lt;/span&gt;config.yml
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Past the following into the file for now:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="nn"&gt;---&lt;/span&gt;
&lt;span class="na"&gt;database&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;/opt/apario/app"&lt;/span&gt;
&lt;span class="na"&gt;buffer&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1776&lt;/span&gt;
&lt;span class="na"&gt;limiter&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1776&lt;/span&gt;
&lt;span class="na"&gt;directories-limiter&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;47369&lt;/span&gt;
&lt;span class="na"&gt;pages-limiter&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;47369&lt;/span&gt;
&lt;span class="na"&gt;directory-buffer&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;47369&lt;/span&gt;
&lt;span class="na"&gt;site-title&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;PhoenixVault Reader&lt;/span&gt;
&lt;span class="na"&gt;unsecure-port&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;8080&lt;/span&gt;
&lt;span class="na"&gt;secure-port&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;8443&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You can reference the &lt;a href="https://github.com/ProjectApario/reader/blob/main/config.go" title="config.go file of the reader component of Project Apario" rel="noopener noreferrer"&gt;config.go&lt;/a&gt; if you want to see &lt;strong&gt;every configuration option available.&lt;/strong&gt; This example only scratches the surface of what the binary offers. &lt;strong&gt;This post&lt;/strong&gt; will get into much of what is &lt;em&gt;not&lt;/em&gt; here. Let's begin with PING! That's a great starting point.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;enable-ping&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# Enable the /ping endpoint of your application to return PONG.&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is useful if you need to do a frequent health check on the binary in order to determine responsivity (new word? how sensitive to response it can be determined I guess) to PING. &lt;/p&gt;

&lt;h2&gt;
  
  
  &lt;code&gt;CORS&lt;/code&gt; Cross-Origin Resource Sharing Capability &lt;em&gt;Built In&lt;/em&gt;
&lt;/h2&gt;

&lt;p&gt;I needed to port over &lt;strong&gt;CORS&lt;/strong&gt; from the &lt;strong&gt;Rails&lt;/strong&gt; offering that came with using Ruby. I also needed to port over &lt;strong&gt;CSP&lt;/strong&gt;. First - CORS, it stands for cross-origin resource sharing and content - second - CSP - it stands for content security policy. Both of these are &lt;em&gt;cybersecurity&lt;/em&gt; offerings &lt;strong&gt;built into&lt;/strong&gt; the binary itself. Historically, when configuring a &lt;strong&gt;PHP&lt;/strong&gt; based website, I would wire up either &lt;strong&gt;Nginx&lt;/strong&gt; or &lt;strong&gt;Apache&lt;/strong&gt; / &lt;strong&gt;HTTPD&lt;/strong&gt; to define these values &lt;em&gt;there.&lt;/em&gt; However, for the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; - we specify those values in the &lt;code&gt;config.yml&lt;/code&gt; itself!&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="c1"&gt;# existing configs&lt;/span&gt;

&lt;span class="na"&gt;enable-cors&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
&lt;span class="na"&gt;cors-allow-origin&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;*"&lt;/span&gt; &lt;span class="c1"&gt;# value for Access-Control-Allow-Origin&lt;/span&gt;
&lt;span class="na"&gt;cors-allow-methods&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;GET,&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;POST,&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;PUT,&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;DELETE,&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;OPTIONS"&lt;/span&gt; &lt;span class="c1"&gt;# value for Access-Control-Allow-Methods&lt;/span&gt;
&lt;span class="na"&gt;cors-allow-headers&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;Origin,&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;Content-Type,&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;Content-Length,&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;Accept-Encoding,&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;X-CSRF-Token,&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;Authorization"&lt;/span&gt; &lt;span class="c1"&gt;# value for Access-Control-Allow-Headers&lt;/span&gt;
&lt;span class="na"&gt;cors-allow-credentials&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="c1"&gt;# bool value for Access-Control-Allow-Credentials&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  &lt;code&gt;CSP&lt;/code&gt; Content Security Policy Capability &lt;em&gt;Built In&lt;/em&gt;
&lt;/h2&gt;

&lt;p&gt;The &lt;strong&gt;Front-End Engineer&lt;/strong&gt;'s best friend - CSP! Alas, yes, even when you're running the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; on Rocky 9 Linux with SELinux enforcing and a properly configured &lt;code&gt;firewalld&lt;/code&gt;, &lt;code&gt;fail2ban&lt;/code&gt; and physical firewall policy - you can further harden the protection of the reader endpoint by defining the values of the CSP policy yourself, including the path that the report writes to.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="c1"&gt;# existing configs&lt;/span&gt;

&lt;span class="na"&gt;enable-csp&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
&lt;span class="na"&gt;csp-domains-csv&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# List of CSP domains in CSV format&lt;/span&gt;
&lt;span class="na"&gt;csp-thirdparty-csv&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# List of third party domains in CSV format&lt;/span&gt;
&lt;span class="na"&gt;csp-thirdparty-styles-csv&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# List of third party domains in CSV format&lt;/span&gt;
&lt;span class="na"&gt;csp-ws-domains-csv&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# List of Web Socket domains in CSV format&lt;/span&gt;
&lt;span class="na"&gt;csp-script-unsafe-inline&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# Enable/Disable Unsafe Inline script execution via CSP&lt;/span&gt;
&lt;span class="na"&gt;csp-script-unsafe-eval&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="c1"&gt;# Enable/Disable Unsafe Eval script execution via CSP&lt;/span&gt;
&lt;span class="na"&gt;csp-child-unsafe-inline&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# Enable/Disable Child SRC Unsafe Inline script execution via CSP&lt;/span&gt;
&lt;span class="na"&gt;csp-style-unsafe-inline&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# Enable/Disable Style SRC Unsafe Inline script execution via CSP&lt;/span&gt;
&lt;span class="na"&gt;csp-upgrade-insecure&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# Enable/Disable automagically upgrading HTTP to HTTPS for requests via CSP&lt;/span&gt;
&lt;span class="na"&gt;csp-block-mixed-content&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# Enable/Disable automatically blocking mixed HTTP and HTTPS content for requests via CSP&lt;/span&gt;
&lt;span class="na"&gt;csp-report-uri&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;/security/csp-report"&lt;/span&gt; &lt;span class="c1"&gt;# Path for content security policy violation reports to get logged&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now, asking somebody to set up &lt;strong&gt;Caddy&lt;/strong&gt; or &lt;strong&gt;Nginx&lt;/strong&gt; or &lt;strong&gt;Apache&lt;/strong&gt; to run and deploy the binary itself with &lt;strong&gt;CSP&lt;/strong&gt; protections &lt;em&gt;built-in&lt;/em&gt; provide you as the &lt;strong&gt;Site Reliability Engineer&lt;/strong&gt; the capability to assert through code and policy that there are &lt;strong&gt;two barriers&lt;/strong&gt; to cross through. The first belonging to nginx and the second belonging to the binary. For me, I chose &lt;strong&gt;not&lt;/strong&gt; to imply that burden of additional dependencies &lt;em&gt;just to run the Apario Reader.&lt;/em&gt; &lt;/p&gt;

&lt;h2&gt;
  
  
  SSL
&lt;/h2&gt;

&lt;p&gt;The next thing that comes up are SSL certificates. That brings us to this cool functionality: &lt;/p&gt;

&lt;p&gt;This is the basic SSL functionality that &lt;em&gt;most people are familiar with.&lt;/em&gt; This allows for you to rely on an SSL file, lets say you use &lt;code&gt;/var/lib/ssl/acme_company_name/2026/mydomain.com/public.crt&lt;/code&gt;, &lt;code&gt;(same path)/private.key&lt;/code&gt; and &lt;code&gt;(same path)/ca-bundle.crt&lt;/code&gt;, you can directly reference them using the &lt;code&gt;config.yml&lt;/code&gt; file. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;auto-tls&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="c1"&gt;# rely on file based SSL certificate resources&lt;/span&gt;
&lt;span class="na"&gt;tls-public-key&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# Path to the SSL certificate's public key. It expects any CA chain certificates to be concatenated at the end of this PEM formatted file.&lt;/span&gt;
&lt;span class="na"&gt;tls-private-key&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# Path to the PEM formatted SSL certificate's private key.&lt;/span&gt;
&lt;span class="na"&gt;tls-private-key-password&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# If the PEM private key is encrypted with a password, provide it here.&lt;/span&gt;
&lt;span class="na"&gt;force-https&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="c1"&gt;# force-https when true will redirect any request into --unsecure-port to --secure-port using middleware&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;However, that requires you to have money up front, and being a project dedicated to the &lt;em&gt;public service of all&lt;/em&gt; how does putting any &lt;em&gt;gate&lt;/em&gt; that requires &lt;em&gt;money&lt;/em&gt; anything but antithetical to &lt;em&gt;open-source?&lt;/em&gt; Well, that is where &lt;strong&gt;Go&lt;/strong&gt; comes in that &lt;em&gt;Ruby&lt;/em&gt; could only dream of doing as well. The &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; has this capability &lt;em&gt;built-in&lt;/em&gt; where I will generate for you an SSL certificate &lt;em&gt;on the fly&lt;/em&gt; that is &lt;strong&gt;self-signed&lt;/strong&gt; but most importantly &lt;strong&gt;configurable.&lt;/strong&gt; What do I mean by this? Well, for instance, if you've done replication in MongoDB, then you'll know that you'll need a SAN IP issued SSL certificate in order to use TLS properly between your nodes in a large enterprise setting - at least - thats what the lived reality was in 2020 when I had the SaaS model of PhoenixVault 🐦‍🔥 in the wild. In the &lt;strong&gt;self contained binary&lt;/strong&gt; version of that same idea, I can generate an SSL certificate for you and include extra domains, IP addresses, and the ability to auto-rotate the certificate &lt;strong&gt;without restarting the binary.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;auto-tls&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# Create a self-signed certificate on the fly and use it for serving the application over SSL.&lt;/span&gt;
&lt;span class="na"&gt;tls-life-min&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;72&lt;/span&gt; &lt;span class="c1"&gt;# Lifespan of the auto generated self signed TLS certificate in minutes.&lt;/span&gt;
&lt;span class="na"&gt;tls-expires-in&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;8760&lt;/span&gt; &lt;span class="c1"&gt;# Auto generated TLS/SSL certificates will automatically expire in hours.&lt;/span&gt;
&lt;span class="na"&gt;tls-company&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;ACME&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;Inc."&lt;/span&gt; &lt;span class="c1"&gt;# Auto generated TLS/SSL certificates are configured with the company name.&lt;/span&gt;
&lt;span class="na"&gt;tls-domain-name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# Auto generated TLS/SSL certificates will have this common name and run on this domain name.&lt;/span&gt;
&lt;span class="na"&gt;tls-san-ip&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# Auto generated TLS/SSL certificates will have this SAN IP address attached to it in addition to its common name.&lt;/span&gt;
&lt;span class="na"&gt;tls-additional-domains&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# Auto generated TLS/SSL certificates will be issued with these additional domains (CSV formatted).&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If you relied on the &lt;em&gt;file based SSL certificates&lt;/em&gt;, the auto-reloading capability &lt;strong&gt;is preserved&lt;/strong&gt; through the manner in which the HTTPD server is spawned in the &lt;strong&gt;Go&lt;/strong&gt; &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Once we have the SSL configured on the host, we can move onto the next part of the configuration that is to the &lt;strong&gt;advanced search&lt;/strong&gt;. Now, I didn't just give it this name because I wanted to be cute with you. &lt;/p&gt;

&lt;h2&gt;
  
  
  Search
&lt;/h2&gt;

&lt;p&gt;The &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; was designed to to let you configure search in a manner that offers you &lt;strong&gt;choice.&lt;/strong&gt; Since the binary is designed to run as an appliance on the host, handling many tasks all in one, there are many &lt;a href="https://github.com/andreimerlescu/semaphore" rel="noopener noreferrer"&gt;semaphores&lt;/a&gt; used in the reader. In this case, setting the limiter to 30 means that 31 will see a waiting room - a manual refresh is required to see if you've been allowed in. I was inspired by this design limitation to build &lt;a href="https://github.com/andreimerlescu/room" rel="noopener noreferrer"&gt;room&lt;/a&gt;. &lt;code&gt;concurrent-searches&lt;/code&gt; defaults to &lt;strong&gt;30&lt;/strong&gt; and thats for a &lt;strong&gt;64GB RAM server&lt;/strong&gt; &lt;em&gt;that is &lt;strong&gt;not&lt;/strong&gt; $33/mo from OVH.&lt;/em&gt; If you're using something like a SYS-3, then I'd set this number to &lt;code&gt;10&lt;/code&gt;. The &lt;code&gt;config.yml&lt;/code&gt; file allows you to customize your &lt;em&gt;reader appliance.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;search-concurrency-buffer&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;369&lt;/span&gt; &lt;span class="c1"&gt;# buffer channel size for search results ; default = 369&lt;/span&gt;
&lt;span class="na"&gt;search-concurrency-limiter&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;9&lt;/span&gt; &lt;span class="c1"&gt;# concurrent keyword processing per search query ; default = 9&lt;/span&gt;
&lt;span class="na"&gt;search-timeout-seconds&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;30&lt;/span&gt; &lt;span class="c1"&gt;# maximum seconds to spend on a search&lt;/span&gt;
&lt;span class="na"&gt;concurrent-searches&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;30&lt;/span&gt; &lt;span class="c1"&gt;# maximum number of allowed concurrent searches before a waiting room appears&lt;/span&gt;
&lt;span class="na"&gt;search-algorithm&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;jaro_winkler"&lt;/span&gt; &lt;span class="c1"&gt;# values are wagner_fisher, ukkonen, jaro, jaro_winkler, soundex, hamming ; default is jaro_winkler&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;There are &lt;strong&gt;6 different&lt;/strong&gt; &lt;code&gt;search-algorithm&lt;/code&gt; choices to pick from, and each of them have different implications. &lt;code&gt;soundex&lt;/code&gt; and &lt;code&gt;hamming&lt;/code&gt; are quite interesting when applied to internationalized data sets. In addition to the algorithm being used, you can expand it further with: &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="c1"&gt;# 1 - jaro&lt;/span&gt;
&lt;span class="na"&gt;search-threshold-jaro&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;0.71&lt;/span&gt; &lt;span class="c1"&gt;# 1.0 means exact match 0.0 means no match; default is 0.71&lt;/span&gt;

&lt;span class="c1"&gt;# 2 - jaro-winkler&lt;/span&gt;
&lt;span class="na"&gt;search-threshold-jaro-winkler&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;0.71&lt;/span&gt; &lt;span class="c1"&gt;# using the JaroWinkler method, define the threshold that is tolerated; default is 0.71&lt;/span&gt;
&lt;span class="na"&gt;search-jaro-winkler-boost-threshold&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;0.7&lt;/span&gt; &lt;span class="c1"&gt;# weight applied to common prefixes in matched strings comparing dictionary terms, page word data, and search query params&lt;/span&gt;
&lt;span class="na"&gt;search-jaro-winkler-prefix-size&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;3&lt;/span&gt; &lt;span class="c1"&gt;# length of a jarrow weighted prefix string&lt;/span&gt;

&lt;span class="c1"&gt;# 3 - ukkonen&lt;/span&gt;
&lt;span class="na"&gt;search-ukkonen-icost&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1&lt;/span&gt; &lt;span class="c1"&gt;# insert cost ; when adding a char to find a match ; increase the score by this number ; default = 1&lt;/span&gt;
&lt;span class="na"&gt;search-ukkonen-scost&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2&lt;/span&gt; &lt;span class="c1"&gt;# substitution cost ; when replacing a char increase the score by this number ; default = 2&lt;/span&gt;
&lt;span class="na"&gt;search-ukkonen-dcost&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1&lt;/span&gt; &lt;span class="c1"&gt;# delete cost ; when removing a char to find a match ; increase the score by this number ; default = 1&lt;/span&gt;
&lt;span class="na"&gt;search-ukkonen-max-substitutions&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2&lt;/span&gt; &lt;span class="c1"&gt;# maximum number of substitutions allowed for a word to be considered a match ; higher value = lower accurate ; lower value = higher accuracy ; min = 0; default = 2&lt;/span&gt;

&lt;span class="c1"&gt;# 4 - wagner-fischer&lt;/span&gt;
&lt;span class="na"&gt;search-wagner-fischer-icost&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1&lt;/span&gt; &lt;span class="c1"&gt;# insert cost ; when adding a char to find a match ; increase the score by this number ; default = 1&lt;/span&gt;
&lt;span class="na"&gt;search-wagner-fischer-scost&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2&lt;/span&gt; &lt;span class="c1"&gt;# substitution cost ; when replacing a char increase the score by this number ; default = 2&lt;/span&gt;
&lt;span class="na"&gt;search-wagner-fischer-dcost&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1&lt;/span&gt; &lt;span class="c1"&gt;# delete cost ; when removing a char to find a match ; increase the score by this number ; default = 1&lt;/span&gt;
&lt;span class="na"&gt;search-wagner-fischer-max-substitutions&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2&lt;/span&gt; &lt;span class="c1"&gt;# maximum number of substitutions allowed for a word to be considered a match ; higher value = lower accurate ; lower value = higher accuracy ; min = 0; default = 2&lt;/span&gt;

&lt;span class="c1"&gt;# 5 - hamming&lt;/span&gt;
&lt;span class="na"&gt;search-hamming-max-substitutions&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2&lt;/span&gt; &lt;span class="c1"&gt;# maximum number of substitutions allowed for a word to be considered a match ; higher value = lower accuracy ; min = 1 ; default = 2&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Depending on which &lt;code&gt;search-algorithm&lt;/code&gt; you use, your &lt;code&gt;config.yml&lt;/code&gt; file will define these various parameters as you seek to fine tune your search results and how sensitive your instance is to the various algorithms implemented. This is why I truly felt insulted by a &lt;em&gt;nameless company&lt;/em&gt; that doesn't deserve the publicity frankly - after &lt;strong&gt;they&lt;/strong&gt; tanked a &lt;a href="https://dev.to/andreimerlescu/five-hours-of-interviewing-zero-questions-about-the-job-378k"&gt;5 hour interview&lt;/a&gt; &lt;em&gt;with me.&lt;/em&gt; Offer or no offer, I would have declined in a pursuit to negotiate a better starting point - or continue my search for the right fit in blind faith knowing that the right opportunity show up for me like it has in the past at the right time because thats how it always works. Technical recruiters can still reach out to me, I am still taking your calls. &lt;em&gt;I interview them.&lt;/em&gt; &lt;/p&gt;

&lt;h2&gt;
  
  
  Databases
&lt;/h2&gt;

&lt;p&gt;The reader has multiple &lt;code&gt;.db&lt;/code&gt; directories that contain a series of JSON files. Uncompressed, unindex, in their raw format for lookup and reference. The reader took a lot more time for me to build, and the OPEX costs of running the PhoenixVault for as long as I did, burned a lot into what I had and I needed to start salvaging what I could. This meant that if processes were ineffective because of unknown reasons to me, then it meant that solutions were available to me because of processes known to me. Rewriting the application in &lt;strong&gt;Go&lt;/strong&gt; allowed me to discover more about the architecture of software than I had previously learned. &lt;/p&gt;

&lt;p&gt;There are 5 different &lt;em&gt;databases&lt;/em&gt; used in the reader - and each of them are &lt;em&gt;directories&lt;/em&gt; of structured data. This allowed for an offline runtime of the instance to be managed manually by an administrator in a surgical manner that was relatively transparent in the ramifications of the changes made. We'll use the &lt;code&gt;/opt/apario/database&lt;/code&gt; path to store each of these. The first is for &lt;code&gt;textee&lt;/code&gt;. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;textee-database&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;/opt/apario/database/textee.db"&lt;/span&gt; &lt;span class="c1"&gt;# absolute path to textee database directory&lt;/span&gt;
&lt;span class="na"&gt;users-database-path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;/opt/apario/database/user.db"&lt;/span&gt; &lt;span class="c1"&gt;# absolute path to store user directory information&lt;/span&gt;
&lt;span class="na"&gt;tag-database-path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;/opt/apario/database/tags.db"&lt;/span&gt; &lt;span class="c1"&gt;# absolute path to the tags.db file for persistent storage&lt;/span&gt;
&lt;span class="na"&gt;snippets-database-path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;/opt/apario/database/snippets.db"&lt;/span&gt; &lt;span class="c1"&gt;# absolute path to the snippets.db file for persistent snippets&lt;/span&gt;
&lt;span class="na"&gt;ip-ban-file&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;/opt/apario/database/ip.db"&lt;/span&gt; &lt;span class="c1"&gt;# File that contains JSON encoded values for the IP Ban list.&lt;/span&gt;
&lt;span class="na"&gt;hits-file&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;/opt/apario/database/hits.db"&lt;/span&gt; &lt;span class="c1"&gt;# File that contains a JSON encoded value of the hits on the site.&lt;/span&gt;

&lt;span class="na"&gt;persistent-database-path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;/opt/apario/database/app.db"&lt;/span&gt; &lt;span class="c1"&gt;# path to runtime database file&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We'll get back to the &lt;code&gt;ip-ban-file&lt;/code&gt; and the &lt;code&gt;hits-file&lt;/code&gt; later.&lt;/p&gt;

&lt;p&gt;The &lt;code&gt;textee&lt;/code&gt; database contains a compiled full text JSON object of analysis from the entire ingested collection compiled by the writer. &lt;/p&gt;

&lt;p&gt;The &lt;code&gt;tag&lt;/code&gt; database contained a mapping association between &lt;code&gt;pages &amp;lt;&amp;gt; pages&lt;/code&gt; and &lt;code&gt;pages &amp;lt;&amp;gt; documents&lt;/code&gt; and &lt;code&gt;documents &amp;lt;&amp;gt; documents&lt;/code&gt; for &lt;strong&gt;tags&lt;/strong&gt; that &lt;em&gt;could include textee values.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;The &lt;code&gt;snippets&lt;/code&gt; database contains a mapping between &lt;code&gt;pages &amp;lt;&amp;gt; snippet&lt;/code&gt; where the snippet contains the &lt;code&gt;X&lt;/code&gt;, &lt;code&gt;Y&lt;/code&gt;, &lt;code&gt;TOP&lt;/code&gt;, &lt;code&gt;BOTTOM&lt;/code&gt; coordinates on the &lt;code&gt;page&lt;/code&gt; itself that the snippet was captured from. Then the segment of the page is displayed using CSS in the bounds specified by the coordinates. &lt;/p&gt;

&lt;p&gt;The final database is the &lt;code&gt;app.db&lt;/code&gt; and its the &lt;strong&gt;persistent&lt;/strong&gt; database that has additional &lt;code&gt;config.yml&lt;/code&gt; flags available to it. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;flush-database-watch-file&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;/opt/apario/app/flush-db.next-boot"&lt;/span&gt; &lt;span class="c1"&gt;# name of a file to touch in the root directory to force the app to delete the database cache and regenerate at boot&lt;/span&gt;
&lt;span class="na"&gt;database-concurrent-write-semaphore&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;17000&lt;/span&gt; &lt;span class="c1"&gt;# concurrent disk write operations permitted to acquire a lock&lt;/span&gt;
&lt;span class="na"&gt;persist-runtime-database&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# boolean to persist the runtime database to disk once loaded&lt;/span&gt;
&lt;span class="na"&gt;load-persistent-database&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# boolean to load a persisted database from disk to memory&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Simply touching the &lt;code&gt;/opt/apario/app/flush-db.next-boot&lt;/code&gt; path results in the application automatically, upon boot, to flush the database. This is useful if you need to &lt;em&gt;invalidate the cache.&lt;/em&gt; You can see that there is a &lt;a href="https://github.com/andreimerlescu/semaphore" rel="noopener noreferrer"&gt;semaphore&lt;/a&gt; available for you to use that in this case restricts the number of concurrent disk writes to 17K. The &lt;code&gt;persist-runtime-database&lt;/code&gt; and &lt;code&gt;load-persistent-database&lt;/code&gt; can both be true or different, but if &lt;code&gt;persist&lt;/code&gt; is disabled and there is nothing to load, what does load will not be saved. Sometimes loading can take several minutes on the first boot. When performing maintenance on your instance of the Reader, account for this boot time in your downtime announcement window.  &lt;/p&gt;

&lt;h2&gt;
  
  
  Rate Limiting
&lt;/h2&gt;

&lt;p&gt;One of the most resource intensive tasks on any server is the delivery of static assets compressed &lt;em&gt;or uncompressed.&lt;/em&gt; I built into the binary the ability to define a &lt;em&gt;middleware&lt;/em&gt; rate limiter into the route endpoints themselves with full control over the levers of the rate limiter.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;enable-middleware-rate-limiting&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# Toggle the tollbooth rate limiter for normal routes&lt;/span&gt;
&lt;span class="na"&gt;rate-limit&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;12.0&lt;/span&gt; &lt;span class="c1"&gt;# Requests per second (0.5 = 1 request every 2 seconds).&lt;/span&gt;
&lt;span class="na"&gt;rate-limit-cleanup&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;3&lt;/span&gt; &lt;span class="c1"&gt;# Seconds between rate limit cleanups.&lt;/span&gt;
&lt;span class="na"&gt;rate-limit-ttl&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;3&lt;/span&gt; &lt;span class="c1"&gt;# Seconds a rate limit entry exists for before cleanup is triggered.&lt;/span&gt;
&lt;span class="na"&gt;enable-middleware-asset-rate-limiting&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# Toggle the tollbooth rate limiter for asset routes.&lt;/span&gt;
&lt;span class="na"&gt;rate-limit-asset&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;36.0&lt;/span&gt; &lt;span class="c1"&gt;# Requests per second (0.5 = 1 request every 2 seconds).&lt;/span&gt;
&lt;span class="na"&gt;rate-limit-asset-cleanup&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;17&lt;/span&gt; &lt;span class="c1"&gt;# Seconds between rate limit cleanups.&lt;/span&gt;
&lt;span class="na"&gt;rate-limit-asset-ttl&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;17&lt;/span&gt; &lt;span class="c1"&gt;# Seconds a rate limit entry exists for before cleanup is triggered.&lt;/span&gt;
&lt;span class="na"&gt;enable-middleware-download-rate-limiting&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# Toggle the tollbooth rate limiter for downloads routes.&lt;/span&gt;
&lt;span class="na"&gt;rate-limit-download&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;36.0&lt;/span&gt; &lt;span class="c1"&gt;# Requests per second (0.5 = 1 request every 2 seconds).&lt;/span&gt;
&lt;span class="na"&gt;rate-limit-download-cleanup&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;17&lt;/span&gt; &lt;span class="c1"&gt;# Seconds between rate limit cleanups.&lt;/span&gt;
&lt;span class="na"&gt;rate-limit-download-ttl&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;17&lt;/span&gt; &lt;span class="c1"&gt;# Seconds a rate limit entry exists for before cleanup is triggered.&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I want to point you to the &lt;a href=""&gt;webserver.go&lt;/a&gt; file for a moment to study this &lt;strong&gt;Go&lt;/strong&gt; code:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="c"&gt;// Serve all static assets using this entry point&lt;/span&gt;
&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;flag_b_enable_asset_rate_limiting&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;GET&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"/assets/:directory/:filename"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;middleware_rate_limiter&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;assetRateLimiter&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;r_get_asset&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;GET&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"/covers/:document_identifier/:page_identifier/:size"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;middleware_rate_limiter&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;assetRateLimiter&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;r_get_database_page_image&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;GET&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"/pending-viewport-placeholder.svg"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;middleware_rate_limiter&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;assetRateLimiter&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;r_get_pending_viewport_placeholder_svg&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;GET&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"/assets/:directory/:filename"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;r_get_asset&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;GET&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"/covers/:document_identifier/:page_identifier/:size"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;r_get_database_page_image&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;GET&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"/pending-viewport-placeholder.svg"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;r_get_pending_viewport_placeholder_svg&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;flag_b_enable_downloads_rate_limiting&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;GET&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"/download/document/:document_identifier/:filename"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;middleware_rate_limiter&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;downloadRateLimiter&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;middleware_online_counter&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="n"&gt;r_get_download_document&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;GET&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"/download/page/:page_identifier/:filename"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;middleware_rate_limiter&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;downloadRateLimiter&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;middleware_online_counter&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="n"&gt;r_get_download_page&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;GET&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"/download/document/:document_identifier/:filename"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;middleware_online_counter&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="n"&gt;r_get_download_document&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;GET&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"/download/page/:page_identifier/:filename"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;middleware_online_counter&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="n"&gt;r_get_download_page&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I haven't spoken at all about the &lt;code&gt;main()&lt;/code&gt; func and how we even got to &lt;strong&gt;webserver.go&lt;/strong&gt; in the reader - but let us skip over to this point if I may. Rate limiting is applied to &lt;em&gt;each route individually&lt;/em&gt;. That means that if a &lt;em&gt;single agent&lt;/em&gt; is hitting the host at n-endpoints, the &lt;em&gt;rate-limiting itself wouldn't be enough to stop the attack.&lt;/em&gt; &lt;/p&gt;

&lt;h2&gt;
  
  
  Trusted Proxies
&lt;/h2&gt;

&lt;p&gt;In addition to &lt;em&gt;rate limiting&lt;/em&gt;, the implementation of Trusted Proxies allows for you to run the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; behind an &lt;strong&gt;Nginx&lt;/strong&gt; or &lt;strong&gt;Apache&lt;/strong&gt; reverse proxy. In that case, you'd need to specify the IP address of the host that is the &lt;strong&gt;forward client IP&lt;/strong&gt; - in many cases this can be safely set to &lt;code&gt;127.0.0.1&lt;/code&gt; unless its a server publicly accessible.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;trusted-proxies&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# Configure the web server to forward client IP addresses to the application if a proxy is used such as Nginx; set that proxy's IP here.&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  SEO Optimizations
&lt;/h2&gt;

&lt;p&gt;In addition to basic SEO in the web application itself of the reader, the &lt;code&gt;config.yml&lt;/code&gt; allows for you to define &lt;code&gt;/robots.txt&lt;/code&gt;, &lt;code&gt;/ads.txt&lt;/code&gt;, &lt;code&gt;/security.txt&lt;/code&gt; automatically so these endpoints are served dynamically by the binary itself. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;robots-txt-path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# Relative path to override the /robots.txt entry that denies all crawlers.&lt;/span&gt;
&lt;span class="na"&gt;enable-ads-txt&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="c1"&gt;# Enable the endpoint for /ads.txt to be served. Required to use --ads-txt-path.&lt;/span&gt;
&lt;span class="na"&gt;ads-txt-path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# Relative path to override the /ads.txt entry that helps fight fraud.&lt;/span&gt;
&lt;span class="na"&gt;enable-security-txt&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="c1"&gt;# Enable the endpoint for /security.txt to be served. Required to use --security-txt-path.&lt;/span&gt;
&lt;span class="na"&gt;security-txt-path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# Relative path to override the /security.txt entry that helps fight fraud.&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  IP Ban List Middleware
&lt;/h2&gt;

&lt;p&gt;What happens when you have an &lt;em&gt;actor&lt;/em&gt; who thinks that they are going to run &lt;a href="https://github.com/andreimerlescu/lemmings" rel="noopener noreferrer"&gt;lemmings&lt;/a&gt; behind &lt;a href="https://github.com/andreimerlescu/sovereign" rel="noopener noreferrer"&gt;sovereign&lt;/a&gt; and that results in your instance of the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; to become &lt;em&gt;slow&lt;/em&gt; - how does the binary protect itself from these kind of &lt;em&gt;attacks?&lt;/em&gt; Well, enter the &lt;code&gt;ip-ban-list&lt;/code&gt; middleware that I wrote for Gin. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;enable-middleware-ip-ban-list&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# Enable the middleware for ip ban list.&lt;/span&gt;
&lt;span class="na"&gt;ip-ban-list-sync-delay&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;3600&lt;/span&gt; &lt;span class="c1"&gt;# seconds between synchronizing the ip ban list to disk&lt;/span&gt;

&lt;span class="na"&gt;online-refresh-delay-minutes&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;17&lt;/span&gt; &lt;span class="c1"&gt;# seconds to count active online users before offline cut-off. 369 seconds = 6 minutes 9 seconds = default&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That extends into what happens when you have some bot trying n-paths until one hits where they are rendering 404s nonstop until they get something other than &lt;em&gt;not found?&lt;/em&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;no-route-path-watch-list&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# Pipe separated string of routes that should trigger an IP ban if too many are received.&lt;/span&gt;
&lt;span class="na"&gt;no-route-path-contains-watch-list&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# Pipe separated string of partial routes that should trigger an IP ban if too many are received.&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;These capabilities, when combined together, provide the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; a larger scope of coverage in the pursuit of a stronger cybersecurity posture. By unifying in a single configuration: &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;strong&gt;CORS&lt;/strong&gt; Protections&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;CSP&lt;/strong&gt; Protections&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Rate Limiting&lt;/strong&gt; Protections&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;IP Ban List&lt;/strong&gt; Protections&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;No Route Catch-All&lt;/strong&gt; Protections&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Cache Control&lt;/strong&gt; Protections&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Semaphore&lt;/strong&gt; Protections&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;When defining what the &lt;em&gt;cache control&lt;/em&gt; and &lt;em&gt;semaphore&lt;/em&gt; protections look like, they are scattered throughout the configuration, but most particularly of value can be the &lt;code&gt;concurrent-asset-requests&lt;/code&gt; and the &lt;code&gt;concurrent-pdf-downloads&lt;/code&gt; semaphores. The first - this is all assets - including JPG, JS, CSS, and font files that are served via GIN. You need to ensure this number is high enough to count for &lt;em&gt;all assets in each request&lt;/em&gt; and sometimes, your &lt;em&gt;page count results&lt;/em&gt; choice &lt;em&gt;can impact this value.&lt;/em&gt; To be safe, set these to &lt;code&gt;369&lt;/code&gt; to start and see what that does for you. If you have &lt;strong&gt;large PDFs&lt;/strong&gt; then you should consider reducing this by a third to &lt;code&gt;123&lt;/code&gt; and keeping the assets to &lt;code&gt;369&lt;/code&gt;. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;concurrent-asset-requests&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;369&lt;/span&gt; &lt;span class="c1"&gt;# concurrent hits to /assets/* permitted&lt;/span&gt;
&lt;span class="na"&gt;concurrent-pdf-downloads&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;369&lt;/span&gt; &lt;span class="c1"&gt;# concurrent pdf downloads permitted&lt;/span&gt;


&lt;span class="na"&gt;cache-control-database-seconds&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1209600&lt;/span&gt; &lt;span class="c1"&gt;# seconds for http header Cache-Control max-age=1209600 [default 14 days]&lt;/span&gt;
&lt;span class="na"&gt;cache-control-assets-seconds&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;3600&lt;/span&gt; &lt;span class="c1"&gt;# seconds for http header Cache-Control max-age=3600 [default 1 hour]&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Sessions
&lt;/h2&gt;

&lt;p&gt;Since the reader is intended to have the &lt;a href="https://github.com/andreimerlescu/iamxrp.dev" rel="noopener noreferrer"&gt;reputation&lt;/a&gt; sub-project integrated into the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; I built session support into the reader but it's not fully implemented in every endpoint with persistent knowledge of the user on each page request. Part of this is for &lt;em&gt;pure anonymity&lt;/em&gt; offered to the end user of the instance using it. OSINT has stigma attached to it, and a person researching information about OSINT that is &lt;em&gt;public domain&lt;/em&gt; should be immune from observation while looking at OSINT to avoid any kind of stigma that may be attached by &lt;em&gt;looking at something like the &lt;b&gt;JFK files&lt;/b&gt;.&lt;/em&gt; I didn't build the &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt; 👉🏻 &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; 👉🏻 &lt;a href="https://github.com/ProjectApario/search" rel="noopener noreferrer"&gt;search&lt;/a&gt; 👉🏻 &lt;a href="https://github.com/andreimerlescu/iamxrp.dev" rel="noopener noreferrer"&gt;iamxrp.dev&lt;/a&gt; &lt;strong&gt;for&lt;/strong&gt; &lt;em&gt;the JFK files.&lt;/em&gt; That was just the &lt;em&gt;first data set used!&lt;/em&gt; It happened to be &lt;strong&gt;666K pages!&lt;/strong&gt; Sounds about right given what happened to him. Regardless of &lt;em&gt;that&lt;/em&gt;, the technology can be applied to any collection of OSINT. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;config.yml&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;use-sessions&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt; &lt;span class="c1"&gt;# toggle using sessions or not - cookies and sessions can be true but both cannot be false&lt;/span&gt;
&lt;span class="na"&gt;sessions-directory&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# absolute path of a directory that sessions can be stored&lt;/span&gt;
&lt;span class="na"&gt;session-secret&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# secret key used for securing sessions&lt;/span&gt;
&lt;span class="na"&gt;concurrent-image-views&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;369&lt;/span&gt; &lt;span class="c1"&gt;# concurrent hits to /covers/&amp;lt;doc-id&amp;gt;/&amp;lt;pg-id&amp;gt;/&amp;lt;size&amp;gt;.jpg permitted&lt;/span&gt;
&lt;span class="na"&gt;session-authenticity-token-secret&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt; &lt;span class="c1"&gt;# secret for session-authenticity-token that is used for aes-gcm encryption&lt;/span&gt;
&lt;span class="na"&gt;session-concurrent-crypt-actions-limit&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1776&lt;/span&gt; &lt;span class="c1"&gt;# concurrent encrypt/decrypt calls permitted. change this value if performance is being impacted by excessive authentication requests.&lt;/span&gt;
&lt;span class="na"&gt;auth-max-failed-logins&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;17&lt;/span&gt; &lt;span class="c1"&gt;# maximum failed logins before the account is locked&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;These sessions are applied to using the binary and keeping track of a user during their time on the platform. It's persisted to disk in an &lt;code&gt;aes-gcm&lt;/code&gt; encrypted manner that is private to the operator of the reader instance. This data, part of the original project, does not upstream or collect this information even for research or educational purposes. I would consider the information and data to be useful, but to allow it voluntarily would even cross a boundary of implementation that borders on the current way things are done - and reinventing &lt;em&gt;that wheel&lt;/em&gt; is a lot for me to bite off &lt;em&gt;right now 😅.&lt;/em&gt; &lt;/p&gt;

&lt;h2&gt;
  
  
  Internationalization
&lt;/h2&gt;

&lt;p&gt;The binary does &lt;em&gt;not&lt;/em&gt; support language translations in its current form, but I did add support for which decimal symbol is used between an EU document set and a US document set.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;decimal-symbol&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;,"&lt;/span&gt; &lt;span class="c1"&gt;# symbol for decimals, default is .&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Cookies
&lt;/h2&gt;

&lt;p&gt;For whatever reason the people in the EU are afraid of cookies and are too ignorant to know how to clear their cookies and keep their computers safe in the age of the &lt;strong&gt;Wild West of the Agentic Infected Internet&lt;/strong&gt;. At any point Claude or ChatGPT could go rogue and break into - literally anybody's systems - and nobody would be held accountable for it unless laws are passed to explicitly hold the developers of those models accountable for the models criminal behavior of breaking into online systems unlawfully - cookies aren't necessarily a &lt;em&gt;bad thing.&lt;/em&gt; They are abused by bad actors, but if you want to use them, set &lt;code&gt;use-cookies&lt;/code&gt; to true and get a better experience with dark mode persistence across sessions and restarts of your browser. Yes, from the &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt;, dark mode assets were rendered that inverted the white background sheet and replaced it with a comfortable to the eyes lavender color with a enlightened gold text that makes the OSINT &lt;em&gt;pop 🤩&lt;/em&gt; when you find &lt;strong&gt;true gems.&lt;/strong&gt; When using cookies, its important to properly define the &lt;code&gt;cookie-domain&lt;/code&gt; otherwise your dark mode won't be &lt;em&gt;sticky.&lt;/em&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;use-cookies&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="c1"&gt;# toggle using cookies or not - cookies and sessions can be true but both cannot be false&lt;/span&gt;
&lt;span class="na"&gt;cookie-domain&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;localhost:8080"&lt;/span&gt; &lt;span class="c1"&gt;# domain to use for cookies&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Identifier Customizations
&lt;/h2&gt;

&lt;p&gt;The binary supports modifying the following identifier properties in the reader. In this case, its +17 years of an offset, this means for 2026 you'll have identifiers using 2009 through 2043 as &lt;em&gt;starting digit prefixes&lt;/em&gt; with a &lt;code&gt;user_identifier_length&lt;/code&gt; chars of [A-Z0-9] after (default &lt;code&gt;6&lt;/code&gt;).&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;identifier-year-offset&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;17&lt;/span&gt; &lt;span class="c1"&gt;# +/- years from current year to look for documents in the database from when they were generated&lt;/span&gt;
&lt;span class="na"&gt;identifier-year-start-min&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;0&lt;/span&gt; &lt;span class="c1"&gt;# if &amp;gt; 0 then time.Now().Year() will be compared against this as a minimum cutoff to accept a document record&lt;/span&gt;
&lt;span class="na"&gt;identifier-year-end-max&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;0&lt;/span&gt; &lt;span class="c1"&gt;# if &amp;gt; 0 then time.Now().Year() will be compared against this as a maximum cutoff year to accept a document record&lt;/span&gt;
&lt;span class="na"&gt;user_identifier_length&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;6&lt;/span&gt; &lt;span class="c1"&gt;# char length of the user identifier ; default is 6 which gives you 6^36 = 1.50094635e17 possibilities ; thats a lot!&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;These customizations allow for the sessions to be tied to user profiles that have unique identifiers associated with them on a per-reader instance basis. &lt;/p&gt;

&lt;h2&gt;
  
  
  The Code
&lt;/h2&gt;

&lt;p&gt;I won't go too deep into the code because its tens of thousands of lines and the binary &lt;em&gt;does a lot&lt;/em&gt;, but I want to explain to you where the &lt;strong&gt;OPEX&lt;/strong&gt; comes into play here. I've described to you thus far the configuration of the binary and the various functionalities that it offers, but none of that replaces &lt;strong&gt;ElasticSearch&lt;/strong&gt; or even &lt;strong&gt;MongoDB Atlas&lt;/strong&gt; - or does it? Well, in the configuration we can see that we have a &lt;strong&gt;users.db&lt;/strong&gt; and we have a &lt;strong&gt;textee.db&lt;/strong&gt; and other various &lt;em&gt;databases.&lt;/em&gt; Looking at &lt;code&gt;main.go&lt;/code&gt; at the end of &lt;code&gt;main()&lt;/code&gt; we can see:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="n"&gt;NewWebServer&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="k"&gt;select&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Done&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
      &lt;span class="n"&gt;fatalf_stout&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Main context canceled, exiting application now. Reason: %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Err&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;
   &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ch_webserver_done&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Chan&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
      &lt;span class="n"&gt;cancel&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We're waiting on either the &lt;code&gt;ctx.Done()&lt;/code&gt; channel indicate that &lt;code&gt;cancel()&lt;/code&gt; has been called on the &lt;code&gt;ctx&lt;/code&gt; or the &lt;a href="https://github.com/andreimerlescu/go-smartchan" rel="noopener noreferrer"&gt;smartchan&lt;/a&gt; &lt;code&gt;ch_webserver_done.Chan()&lt;/code&gt; has something written to it, thus read by the &lt;code&gt;case &amp;lt;-&lt;/code&gt; before it. That's when &lt;code&gt;ctx.Done()&lt;/code&gt;'s &lt;code&gt;cancel()&lt;/code&gt; is invoked! If not elsewhere due to &lt;em&gt;something else going wrong.&lt;/em&gt; &lt;/p&gt;

&lt;p&gt;When we dig into the &lt;code&gt;NewWebServer()&lt;/code&gt; func, its hundreds of lines long because it sets up each of the rate limiters, middleware policies, route endpoints, and future endpoints planned for the binary. Towards the end of the file do you finally see the &lt;strong&gt;HTTP&lt;/strong&gt; (&lt;code&gt;unsecure-port&lt;/code&gt;) and the &lt;strong&gt;HTTPS&lt;/strong&gt; (&lt;code&gt;secure-port&lt;/code&gt;) bindings take place that require, in some port value cases, a &lt;code&gt;setcap&lt;/code&gt; defined on the reader binary itself.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="c"&gt;// Start HTTP Server&lt;/span&gt;
&lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="k"&gt;func&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;r&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;gin&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Engine&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;flag_b_redirect_http_to_https&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Use&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;middleware_force_https&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;

   &lt;span class="n"&gt;server&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;http&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Server&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;Addr&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;    &lt;span class="s"&gt;":"&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;strconv&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Itoa&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;flag_i_webserver_default_port&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
      &lt;span class="n"&gt;Handler&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;

   &lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="k"&gt;func&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;server&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ListenAndServe&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;errors&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Is&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;http&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ErrServerClosed&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;fatalf_log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"listen: %s&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="p"&gt;}()&lt;/span&gt;

   &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Done&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

   &lt;span class="n"&gt;shutdownCtx&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;cancel&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;WithTimeout&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Background&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="m"&gt;5&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Second&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="k"&gt;defer&lt;/span&gt; &lt;span class="n"&gt;cancel&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;server&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Shutdown&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;shutdownCtx&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;fatalf_stderr&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Server Shutdown Failed:%+v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;

   &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Println&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Server exiting properly"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}(&lt;/span&gt;&lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;strong&gt;HTTPS&lt;/strong&gt; server is the &lt;strong&gt;SSL&lt;/strong&gt; enabled server. This includes functionality like &lt;code&gt;loadSSLCertificate()&lt;/code&gt; - which reads in a file &lt;em&gt;or renders a self-signed certificate if &lt;code&gt;auto-sign&lt;/code&gt; is enabled.&lt;/em&gt; Then, the &lt;code&gt;startCertReloader()&lt;/code&gt; is enabled, which will bring back into memory the values of the &lt;code&gt;getCertificate&lt;/code&gt; variable and the invocation of &lt;em&gt;another goroutine.&lt;/em&gt; We'll wait on the &lt;code&gt;ctx.Done()&lt;/code&gt; being written to with &lt;code&gt;&amp;lt;-&lt;/code&gt; before setting up a proper shutdown of the server.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="c"&gt;// Start HTTPS Server&lt;/span&gt;
&lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="k"&gt;func&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;r&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;gin&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Engine&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;cert&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;loadSSLCertificate&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
   &lt;span class="n"&gt;startCertReloader&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
   &lt;span class="n"&gt;server&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;http&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Server&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;Addr&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;    &lt;span class="s"&gt;":"&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="n"&gt;strconv&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Itoa&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;flag_i_webserver_secure_port&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
      &lt;span class="n"&gt;Handler&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="n"&gt;TLSConfig&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;tls&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Config&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;GetCertificate&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;getCertificate&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="p"&gt;},&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;

   &lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="k"&gt;func&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;server&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ListenAndServeTLS&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;""&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;""&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;errors&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Is&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;http&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ErrServerClosed&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;fatalf_stderr&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"ListenAndServeTLS(): %s"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="p"&gt;}()&lt;/span&gt;

   &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Done&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
   &lt;span class="n"&gt;ctxShutDown&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;cancel&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;WithTimeout&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Background&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="m"&gt;5&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Second&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="k"&gt;defer&lt;/span&gt; &lt;span class="n"&gt;cancel&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;server&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Shutdown&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctxShutDown&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;fatalf_stderr&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Server forced to shutdown: %s"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;

   &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Println&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Server exiting properly"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}(&lt;/span&gt;&lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When we look into the &lt;code&gt;loadSSLCertificate()&lt;/code&gt; function, we can see that an &lt;code&gt;x509.Certificate{}&lt;/code&gt; struct is built out as a &lt;code&gt;template&lt;/code&gt; variable that includes properties and capabilities defined in the &lt;code&gt;config.yml&lt;/code&gt; file.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="n"&gt;template&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;x509&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Certificate&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;SerialNumber&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;serialNumber&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
   &lt;span class="n"&gt;Subject&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;pkix&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Name&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;Organization&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;flag_s_auto_ssl_company&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
      &lt;span class="n"&gt;CommonName&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;   &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;flag_s_auto_ssl_domain_name&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
   &lt;span class="p"&gt;},&lt;/span&gt;
   &lt;span class="n"&gt;NotBefore&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;             &lt;span class="n"&gt;notBefore&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
   &lt;span class="n"&gt;NotAfter&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;              &lt;span class="n"&gt;notAfter&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
   &lt;span class="n"&gt;IPAddresses&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;           &lt;span class="n"&gt;valid_ips&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
   &lt;span class="n"&gt;DNSNames&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;              &lt;span class="n"&gt;valid_domains&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
   &lt;span class="n"&gt;KeyUsage&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;              &lt;span class="n"&gt;x509&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;KeyUsageKeyEncipherment&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt; &lt;span class="n"&gt;x509&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;KeyUsageDigitalSignature&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
   &lt;span class="n"&gt;ExtKeyUsage&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;           &lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="n"&gt;x509&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ExtKeyUsage&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;x509&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ExtKeyUsageServerAuth&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
   &lt;span class="n"&gt;BasicConstraintsValid&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="no"&gt;true&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then the certificate is rendered and then handed off as a &lt;code&gt;tls.Certificate{}&lt;/code&gt; pair that can be then used when binding to an &lt;strong&gt;HTTPS&lt;/strong&gt; endpoint.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="n"&gt;derBytes&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;_&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;x509&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;CreateCertificate&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;rand&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Reader&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;template&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;template&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;privateKey&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PublicKey&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;privateKey&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;cert&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;tls&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Certificate&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;Certificate&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[][]&lt;/span&gt;&lt;span class="kt"&gt;byte&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="n"&gt;derBytes&lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;
   &lt;span class="n"&gt;PrivateKey&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;  &lt;span class="n"&gt;privateKey&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In addition to providing a &lt;strong&gt;CORS&lt;/strong&gt; secured endpoint that has properly defined &lt;strong&gt;CSP&lt;/strong&gt; on its endpoints, the &lt;em&gt;No Route Found&lt;/em&gt; hits get tracked and auto-banned by IP address for abusive behavior, and an IP ban list has a watch list of endpoints that are honeypots - touch that endpoint and your IP ends up in the ban list and persisted to the database. The system administrator would need to go in and edit that file manually when the reader is offline and then restart the instance with the unbanned IP address. Unbanning a user is a laborious process - designed to be discouraged. Don't trigger it. 🤫😏&lt;/p&gt;

&lt;p&gt;That isn't enough. I have wired up a function in &lt;strong&gt;Gin&lt;/strong&gt; that allows me to ask for a &lt;code&gt;new_authenticity_token&lt;/code&gt; by passing in the &lt;code&gt;*gin.Context&lt;/code&gt; into the template variable - simple, right? Yep. Function is defined here and is very basic. It relies on our session and it requests the &lt;code&gt;authenticity_token&lt;/code&gt; from the .Values map.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;f_gin_new_authenticity_token&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;gin&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;session&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;g_get_session&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;has_token&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="no"&gt;false&lt;/span&gt;
   &lt;span class="n"&gt;_&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;exists&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;session&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Values&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;"authenticity_token"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;exists&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="c"&gt;// no token yet&lt;/span&gt;
      &lt;span class="n"&gt;has_token&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;true&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="n"&gt;existing_token&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;typecast_ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;session&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Values&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;"authenticity_token"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;typecast_ok&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="nb"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;existing_token&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="m"&gt;0&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;has_token&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;true&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;

   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;has_token&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;payload&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Now&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;UTC&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Unix&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
      &lt;span class="n"&gt;token&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;Sha256&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;strconv&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;FormatInt&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;payload&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;10&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;
      &lt;span class="n"&gt;authenticity_token&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;token_err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;f_s_encrypt_string&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"%d|%v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;payload&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;token&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;flag_s_session_authenticity_token_secret&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;token_err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to generate an authenticity token due to err %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;token_err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
      &lt;span class="n"&gt;session&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Values&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;"authenticity_token"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;authenticity_token&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In addition to providing that template functionality, we have the ability, from the handlers themselves, processing the endpoint &lt;strong&gt;POST /search&lt;/strong&gt; for instance, that form's authenticity token provided in the hidden field is then passed through the enforce middleware code. I rely on &lt;strong&gt;Gin's&lt;/strong&gt; &lt;code&gt;c.PostForm()&lt;/code&gt; to pull up that token value to check against.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;handler_enforce_authenticity_token&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;gin&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;session&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;g_get_session&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;challenge_authenticity_token&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PostForm&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"authenticity_token"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;b_permit_access&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="no"&gt;true&lt;/span&gt;
   &lt;span class="n"&gt;s_error_message&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="s"&gt;""&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="nb"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;challenge_authenticity_token&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="m"&gt;64&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;b_permit_access&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;false&lt;/span&gt;
      &lt;span class="n"&gt;s_error_message&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"oh you think you're clever don't you?"&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="n"&gt;authenticity_token&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;typecast_err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;session&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Values&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;"authenticity_token"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;typecast_err&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="n"&gt;challenge_authenticity_token&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="n"&gt;authenticity_token&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;b_permit_access&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;false&lt;/span&gt;
      &lt;span class="n"&gt;s_error_message&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="s"&gt;"watch your six"&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;b_permit_access&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;f_session_flash&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;session&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;NewSessionAlert&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"error"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;s_error_message&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Now&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="m"&gt;36&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Second&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="no"&gt;true&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;
      &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"handler_enforce_authenticity_token error %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;s_error_message&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="n"&gt;f_add_ip_to_watch_list&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;net&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ParseIP&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;f_s_filtered_ip&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)))&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the event of some monkey business with the authenticity token, the IP address gets sent straight into the &lt;code&gt;f_add_ip_to_watch_list()&lt;/code&gt; function. &lt;em&gt;Tough luck.&lt;/em&gt; Unless the instance is not enforcing the ban list 😅. &lt;/p&gt;

&lt;p&gt;One of the most iconic functions of the PhoenixVault when it was online in 2020 and as Project Apario from 2021-2023 was the &lt;em&gt;StumbleInto™&lt;/em&gt; functionality that I built. The Go implementation was so small...&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;package&lt;/span&gt; &lt;span class="n"&gt;main&lt;/span&gt;

&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
   &lt;span class="s"&gt;`fmt`&lt;/span&gt;
   &lt;span class="s"&gt;`net/http`&lt;/span&gt;

   &lt;span class="s"&gt;`github.com/gin-gonic/gin`&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;stumbleinto_identifier&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;gin&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="kt"&gt;string&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;random_page_index&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="kt"&gt;int64&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;f_i_random_int&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;m_index_page_identifier&lt;/span&gt;&lt;span class="p"&gt;)))&lt;/span&gt;
   &lt;span class="n"&gt;random_identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;exists&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;m_index_page_identifier&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;random_page_index&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;exists&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;stumbleinto_identifier&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;random_identifier&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;r_get_stumble_into&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;gin&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Redirect&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;http&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;StatusTemporaryRedirect&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"/page/%v?from=stumbleinto"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;stumbleinto_identifier&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;)))&lt;/span&gt;
   &lt;span class="k"&gt;return&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That's it. Unless you count &lt;code&gt;stumbleinto_identifier(c)&lt;/code&gt; as something... 🤩 But even that is 👀 - et voila - &lt;code&gt;return random_identifier&lt;/code&gt;! &lt;/p&gt;

&lt;p&gt;That quickly translates into a redirect to &lt;code&gt;/page/&amp;lt;ID&amp;gt;&lt;/code&gt;. &lt;/p&gt;

&lt;p&gt;Advanced Search is inside the &lt;a href="https://github.com/ProjectApario/reader/blob/main/routes_search.go" rel="noopener noreferrer"&gt;routes_search.go&lt;/a&gt; file and its quite intensive. I won't get into it here, but there are two functions to point to.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;r_get_search&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;gin&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;

&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;deliver_search_results&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;gin&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;query&lt;/span&gt; &lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;analysis&lt;/span&gt; &lt;span class="n"&gt;SearchAnalysis&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;inclusive&lt;/span&gt; &lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="k"&gt;struct&lt;/span&gt;&lt;span class="p"&gt;{},&lt;/span&gt; &lt;span class="n"&gt;exclusive&lt;/span&gt; &lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="k"&gt;struct&lt;/span&gt;&lt;span class="p"&gt;{})&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When looking &lt;em&gt;inside&lt;/em&gt; the &lt;code&gt;r_get_search()&lt;/code&gt; func, we can see that we're building up through a &lt;code&gt;AnalyzeQuery()&lt;/code&gt; func call a &lt;code&gt;query_analysis&lt;/code&gt; that is then used with several mutexes in order toi gather a series of maps to store identifiers into.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="n"&gt;query_analysis&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;AnalyzeQuery&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;query&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"query_analysis = %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;query_analysis&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;mu_inclusive&lt;/span&gt; &lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt;
&lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;inclusive_page_identifiers&lt;/span&gt; &lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="k"&gt;struct&lt;/span&gt;&lt;span class="p"&gt;{}&lt;/span&gt;
&lt;span class="n"&gt;inclusive_page_identifiers&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;make&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="k"&gt;struct&lt;/span&gt;&lt;span class="p"&gt;{})&lt;/span&gt;

&lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;mu_exclusive&lt;/span&gt; &lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt;
&lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;exclusive_page_identifiers&lt;/span&gt; &lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="k"&gt;struct&lt;/span&gt;&lt;span class="p"&gt;{}&lt;/span&gt;
&lt;span class="n"&gt;exclusive_page_identifiers&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;make&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="k"&gt;struct&lt;/span&gt;&lt;span class="p"&gt;{})&lt;/span&gt;

&lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;wg&lt;/span&gt; &lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;WaitGroup&lt;/span&gt;
&lt;span class="n"&gt;sch_found_inclusive_identifiers&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;go_smartchan&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;NewSmartChan&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;flag_i_search_concurrency_buffer&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;sch_found_exclusive_identifiers&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;go_smartchan&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;NewSmartChan&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;flag_i_search_concurrency_buffer&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;ch_done_searching&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="nb"&gt;make&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;chan&lt;/span&gt; &lt;span class="k"&gt;struct&lt;/span&gt;&lt;span class="p"&gt;{})&lt;/span&gt;

&lt;span class="n"&gt;sem_query_limiter&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;sema&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;New&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;flag_i_search_concurrency_limiter&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;At this point, we have a populated &lt;code&gt;query_analysis&lt;/code&gt; and we are going to iterate over the &lt;em&gt;found&lt;/em&gt; &lt;code&gt;.Ands&lt;/code&gt; and the &lt;em&gt;found&lt;/em&gt; &lt;code&gt;.Nots&lt;/code&gt; and fire off a &lt;strong&gt;goroutine&lt;/strong&gt; while using a &lt;a href="https://github.com/ProjectApario/semaphore" rel="noopener noreferrer"&gt;semaphore&lt;/a&gt; while &lt;code&gt;find_pages_for_word(ctx, sch, word)&lt;/code&gt; processes.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="c"&gt;// ands&lt;/span&gt;
&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;_&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;word&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="k"&gt;range&lt;/span&gt; &lt;span class="n"&gt;query_analysis&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Ands&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;wg&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;requestedAt&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Now&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;UTC&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
   &lt;span class="n"&gt;sem_query_limiter&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Acquire&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;since&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Since&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;requestedAt&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Seconds&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt; &lt;span class="n"&gt;since&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="m"&gt;1.7&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"took %.0f seconds to acquire sem_query_limiter queue position"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;since&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="k"&gt;func&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;word&lt;/span&gt; &lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;sch&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;go_smartchan&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SmartChan&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;sem&lt;/span&gt; &lt;span class="n"&gt;sema&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Semaphore&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="k"&gt;defer&lt;/span&gt; &lt;span class="n"&gt;wg&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Done&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
      &lt;span class="k"&gt;defer&lt;/span&gt; &lt;span class="n"&gt;sem&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Release&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
      &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;find_pages_for_word&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;sch&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to [AND] find_pages_for_word(%v) due to err: %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="k"&gt;return&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="p"&gt;}(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;sch_found_inclusive_identifiers&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;sem_query_limiter&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="c"&gt;// nots&lt;/span&gt;
&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;_&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;word&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="k"&gt;range&lt;/span&gt; &lt;span class="n"&gt;query_analysis&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Nots&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;wg&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;requestedAt&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Now&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;UTC&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
   &lt;span class="n"&gt;sem_query_limiter&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Acquire&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;since&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Since&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;requestedAt&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Seconds&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt; &lt;span class="n"&gt;since&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="m"&gt;1.7&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"took %.0f seconds to acquire sem_query_limiter queue position"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;since&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="k"&gt;func&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;word&lt;/span&gt; &lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;sch&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;go_smartchan&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SmartChan&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;sem&lt;/span&gt; &lt;span class="n"&gt;sema&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Semaphore&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="k"&gt;defer&lt;/span&gt; &lt;span class="n"&gt;wg&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Done&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
      &lt;span class="k"&gt;defer&lt;/span&gt; &lt;span class="n"&gt;sem&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Release&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
      &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;find_pages_for_word&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;sch&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to [NOT] find_pages_for_word(%v) due to err: %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="k"&gt;return&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="p"&gt;}(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;word&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;sch_found_exclusive_identifiers&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;sem_query_limiter&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When we get to the end of &lt;em&gt;just the first function there, of the two&lt;/em&gt; we can see that we are ending it on &lt;code&gt;for { select {} }&lt;/code&gt; that listens on the parent context's &lt;code&gt;.Done()&lt;/code&gt;, channel, and then a workflow that I'd like to explain. Look at it first.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="k"&gt;select&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Done&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
      &lt;span class="n"&gt;deliver_search_results&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;query&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;query_analysis&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;inclusive_page_identifiers&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;exclusive_page_identifiers&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="k"&gt;return&lt;/span&gt;
   &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ch_done_searching&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
      &lt;span class="n"&gt;deliver_search_results&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;c&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;query&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;query_analysis&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;inclusive_page_identifiers&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;exclusive_page_identifiers&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="k"&gt;return&lt;/span&gt;
   &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;channel_open&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;sch_found_inclusive_identifiers&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Chan&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;channel_open&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;page_identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="n"&gt;mu_inclusive&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RLock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
            &lt;span class="n"&gt;_&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;identifier_already_defined&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;inclusive_page_identifiers&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;page_identifier&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
            &lt;span class="n"&gt;mu_inclusive&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RUnlock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
            &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;identifier_already_defined&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
               &lt;span class="n"&gt;mu_inclusive&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Lock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
               &lt;span class="n"&gt;inclusive_page_identifiers&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;page_identifier&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;struct&lt;/span&gt;&lt;span class="p"&gt;{}{}&lt;/span&gt;
               &lt;span class="n"&gt;mu_inclusive&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Unlock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
         &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to cast data, channel_open := &amp;lt;-sch_found_inclusive_identifiers.Chan() as a string"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="p"&gt;}&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;channel_open&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;sch_found_exclusive_identifiers&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Chan&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;channel_open&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;page_identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="n"&gt;mu_exclusive&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RLock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
            &lt;span class="n"&gt;_&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;identifier_already_defined&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;exclusive_page_identifiers&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;page_identifier&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
            &lt;span class="n"&gt;mu_exclusive&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RUnlock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
            &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;identifier_already_defined&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
               &lt;span class="n"&gt;mu_exclusive&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Lock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
               &lt;span class="n"&gt;exclusive_page_identifiers&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;page_identifier&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;struct&lt;/span&gt;&lt;span class="p"&gt;{}{}&lt;/span&gt;
               &lt;span class="n"&gt;mu_exclusive&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Unlock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
         &lt;span class="p"&gt;}&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;We're using the mutexes properly here, and we're also applying results to the map accordingly when results are found. As results are found, they are written into the results map in the &lt;code&gt;case data, channel_open := &amp;lt;-sch_found_exclusive_identifiers.Chan():&lt;/code&gt; and &lt;code&gt;case data, channel_open := &amp;lt;-sch_found_inclusive_identifiers.Chan():&lt;/code&gt; receivers in the &lt;code&gt;for { select {} }&lt;/code&gt;. Once &lt;code&gt;&amp;lt;-ch_done_searching&lt;/code&gt; is written to, the &lt;code&gt;deliver_search_results(c, query, query_analysis, inclusive_page_identifiers, exclusive_page_identifiers)&lt;/code&gt; is invoked.&lt;/p&gt;

&lt;p&gt;The next function renders the UI of the search results. When running on an OVH SYS-3 for a record set of about 3,000 pages of OSINT, this can run is under a half a second against multiple keywords in the advanced search form. &lt;/p&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;The &lt;strong&gt;Advanced Search&lt;/strong&gt; was able to remove $1K/mo from the OPEX of the project by removing the reliance on Elastic Search. Now - for a period of time, from 2021-2023, I did run an on-prem managed instance of the ELK stack for the project to keep that OPEX off the books. I was also able to build out a cluster of MongoDB servers that were a replica-set holding a 36GB database of metadata. That removed $3K from the bill - so now we're at $4K/mo off the bill. Well - the other various services that I was running were specifically for the DevOps pipeline, Rollbar, Sentry, and GitLab accounts respectively. &lt;/p&gt;

&lt;p&gt;By removing the dependency lifecycle of the &lt;strong&gt;Rails&lt;/strong&gt; product entirely, removes a &lt;em&gt;level of the playing field&lt;/em&gt; that &lt;strong&gt;Go&lt;/strong&gt; specifically addresses well - in my opinion - better than &lt;em&gt;Ruby&lt;/em&gt; does. Because I can run a single &lt;code&gt;reader&lt;/code&gt; instance on a SYS-3 instance for ~$33/mo and get unmetered bandwidth serving OSINT and deliver sub second advanced search results in a self-contained application that can handle over 369 concurrent &lt;a href="https://github.com/andreimerlescu/lemmings" rel="noopener noreferrer"&gt;lemmings&lt;/a&gt; working on the instance. The limit is defined from the &lt;code&gt;config.yml&lt;/code&gt;. When running &lt;a href="https://github.com/andreimerlescu/sovereign" rel="noopener noreferrer"&gt;sovereign&lt;/a&gt; you'll want to use 3 regions when you deploy 123 concurrent &lt;a href="https://github.com/andreimerlescu/lemmings" rel="noopener noreferrer"&gt;lemmings&lt;/a&gt; to load test &lt;em&gt;your instance.&lt;/em&gt; This gives your semaphore values. You can install &lt;code&gt;btop&lt;/code&gt; or &lt;code&gt;htop&lt;/code&gt; and watch the terminal in another session and tune your semaphores accordingly in your &lt;code&gt;config.yml&lt;/code&gt;. &lt;/p&gt;

&lt;p&gt;Years later, two to be precise, at the time of this publication, has given me the opportunity to reflect on how little I knew about Go and how much opportunity for growth that the next professional engagement that I work in, I would like to continue my career of an autodidact pursuing engineering excellency writing software in Go. When I look back, I solved a major problem with the limited skills that I had in just learning Go before the pandemic and well after into today. &lt;/p&gt;

&lt;p&gt;Ultimately, what I did with the reader, by reducing its OPEX by 99.5% ($7K/mo 👉🏻 $33/mo) is - in my opinion - evidence of my orphanage survival that I went through and I overcame. I am wired to think about complex systems and understand them, and then solve them. When I was asked to solve the 666K unsearchable pages of the JFK files, I looked at that particular moment in history and reflected on what it meant for the American people. Having spent the first three years of my life in Ceaușescu's orphanage, I didn't know much about what happened to him, outside of what I learned in school. When I took on this project, I wasn't a historian or a conspiracy theorist. I am a professional autodidact software architect with an electrical background in computer engineering. Microsoft offered a solution that would have cost anybody sampling the offerings from &lt;strong&gt;Azure&lt;/strong&gt; would expect to pay &lt;strong&gt;tens of thousands of dollars per month.&lt;/strong&gt; Granted, it would be fancy and running on the latest hyper-inflated Microsoft prices! The same topology on AWS would have run me close to $10K per month in just &lt;em&gt;hosting expenses&lt;/em&gt; that OVH offered for $3K per month. Even that, over the years, needed to shift from VMWare ESXi virtual machines and over to a bare metal offering of the appliance model of the app. That final decision resulted in a &lt;a href="https://github.com/andreimerlescu/lemmings" rel="noopener noreferrer"&gt;lemmings&lt;/a&gt; load tested verification of the project's deliverables and &lt;em&gt;promises that I made.&lt;/em&gt; I said I would release it open source. I did. I said I would make it's search advanced. I did. I said I would remove all runtime dependencies. I did. I said I would do it for free. I did. It's GPL-3 to respect the licenses of the open source technology that its also built on. &lt;/p&gt;

&lt;p&gt;I am honored and privileged to have served 🇺🇸 by building the PhoenixVault 🐦‍🔥 Open-Source and 100% free from 1) 💰 2) Me 😭. The project was built over a three year period in an &lt;strong&gt;own without ego&lt;/strong&gt; approach to &lt;em&gt;solving a technical challenge&lt;/em&gt; that could be &lt;em&gt;applied in a manner&lt;/em&gt; that could differentiate what Ceaușescu did to me and what America offered to me instead. Learning what happened to your President mattered to me greatly when I became us by getting naturalized and becoming a citizen in the 90s. Soon after, I joined BITNET through the University of Maine and I spent years learning HTML, CSS, PHP and MySQL so I could volunteer with MuggleNet, studying for the SkillsUSA Nationals competition, and preparing for my internship with a small print magazine publishing company that needed a new &lt;strong&gt;web developer intern&lt;/strong&gt; that would update their website. I expanded that opportunity into offering digital publications of the magazine for readers international to access outside of the print + postal surcharge that was cost prohibitive for anybody but a university to acquire. I want information to flow freely, in &lt;a href="https://dev.to/andreimerlescu/when-ai-creates-a-closed-source-world-2oin"&gt;The Library&lt;/a&gt; of OSINT. &lt;/p&gt;

&lt;p&gt;I read every comment! 💜 I'll respond if I can think of a good response that is valuable for everybody. I'm not interested in the politics around who released the JFK files or what the files actually contain or contained that even ran on instances that I operated. From a purely technical perspective, I wanted to serve my country in a selfless manner in the way that I thought would be best for everybody. &lt;/p&gt;

&lt;p&gt;Any collection of OSINT. &lt;/p&gt;

&lt;p&gt;Your domain. Your certificates. Your servers. Your OSINT.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://github.com/ProjectApario" rel="noopener noreferrer"&gt;https://github.com/ProjectApario&lt;/a&gt;&lt;/p&gt;

</description>
      <category>discuss</category>
      <category>mentorship</category>
      <category>go</category>
      <category>devops</category>
    </item>
    <item>
      <title>How I Processed 666K Pages of Flattened PDFs into a Full Text Search Engine</title>
      <dc:creator>Andrei Merlescu</dc:creator>
      <pubDate>Sat, 25 Jul 2026 15:35:14 +0000</pubDate>
      <link>https://dev.to/andreimerlescu/how-i-processed-666k-pages-of-flattened-pdfs-into-a-full-text-search-engine-4db3</link>
      <guid>https://dev.to/andreimerlescu/how-i-processed-666k-pages-of-flattened-pdfs-into-a-full-text-search-engine-4db3</guid>
      <description>&lt;p&gt;In 2017 the National Archives and Records Administration (NARA) released the JFK files in an unsearchable manner 🔍. I tried doing manual research 🕵🏻. I relied on their provided CSV file of metadata to look for relevant documents to discover something - but I was looking for a needle in the haystack. I didn't know where to begin - but at the very least, I wanted to be able to search the contents therein. At least the National Archives allowed me to bulk download the PDFs. From that, I was able to birth the &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;Apario Writer&lt;/a&gt;. &lt;/p&gt;

&lt;p&gt;In 2020, I began with &lt;code&gt;rails new phoenixvault&lt;/code&gt; 🐦‍🔥 and I proceeded on a Zoom call with DJ Nicke - a former animator at Disney - to watch me build the &lt;em&gt;proof of concept&lt;/em&gt; of the &lt;strong&gt;crowd sourcing declass&lt;/strong&gt; utility that I envisioned. You see, when I was 7 years old, I had a dream after watching a space focused science program on TV that involved me sitting at the home computer, but interacting with an advanced interface that would help me uncover the mysteries of the day and time of the era. In Stargate SG-1, this concept was explored with the Tolan where Nareem was shocked to discover what Teal'c found in the records buried within a full text interface. Connecting it back to the JFK files released by NARA, they were unsearchable. Agenda on why aside, what could I do about it? This &lt;em&gt;proof of concept&lt;/em&gt; grew into a SaaS platform that cost me $7,000 per month to operate over 12 bare meta servers in a private cloud using ESXi. This interface worked, but it was going to be replaced by a &lt;strong&gt;cost saving solution&lt;/strong&gt; &lt;em&gt;architected from the ground up in Go&lt;/em&gt; to reduce the dependency graph of the SaaS solution down to a &lt;em&gt;single binary&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;In order to do this, I needed to create a pipeline. Looking at the SaaS model, I had a series of &lt;code&gt;sidekiq&lt;/code&gt; jobs that compiled the assets. In order to improve the performance of that process, running off from Ruby code, I needed to build a new binary from the ground up using Go. I took the course on YouTube from Matt Holiday called Programming In Go and watched the episodes on repeat several times until the concepts were burned into my per-character programming go-to of choice. I was reminded of the machine detail in circuit design and lower level embedded systems design with the way that Matt explained the concepts behind Go - and they clicked for me. I took that teaching and I applied it to the $7K/mo SaaS model that was complex to manage and costly for a topic that &lt;em&gt;not enough&lt;/em&gt; people wanted to continue to subsidize.&lt;/p&gt;

&lt;p&gt;But lets take a step back and look at the broader picture first, because Microsoft released on GitHub a Typescript JFK files search engine and it was designed to work with their Cloud Services provided on the Azure cloud. Before I built the &lt;em&gt;proof of concept&lt;/em&gt;, I spoke with Microsoft Sales representatives and was quoted &lt;strong&gt;tens of thousands per month&lt;/strong&gt; in order to serve the 666K pages of NARA released JFK files in their full format. The problem was, the interface they built was sloppy and a sales pitch for somebody &lt;em&gt;like me&lt;/em&gt; who wanted to dig into the JFK topic using technology - but needed a lunch pad. What Microsoft did was above board and inspirational - even if it was rooted in profit based motives. It actually demonstrated how to use Azure services natively in a manner that if an organization is comfortable with an eight digit annual budget, then c'est le vie! However, I was able to get $7K/mo, but I wasn't working to get eight digits for &lt;em&gt;just the JFK files&lt;/em&gt;. So, I built something bigger and better and bolder in a way that has never been done before.&lt;/p&gt;

&lt;p&gt;I took concepts that I learned over decades of professional experience at Cisco Systems and Oracle that brought me into WB Games that were translated into the single binary that became the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; that &lt;em&gt;ingests&lt;/em&gt; the &lt;em&gt;output&lt;/em&gt; of the &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt; that &lt;em&gt;can also&lt;/em&gt; be used with the &lt;a href="https://github.com/ProjectApario/search" rel="noopener noreferrer"&gt;search&lt;/a&gt; index algorithm of 13 unique index types including Gematria. That &lt;strong&gt;three binary pipeline&lt;/strong&gt; needed somewhere to begin. That was the &lt;strong&gt;writer&lt;/strong&gt;. Even though the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; displays the PhoenixVault logo and is the front-end to the concept that I built in 2020.&lt;/p&gt;

&lt;h3&gt;
  
  
  The Writer
&lt;/h3&gt;

&lt;p&gt;This component compiles the &lt;em&gt;Apario Database&lt;/em&gt; that the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; consumes and displays an interactive web application that is self contained with Go powered SSL capabilities. To compile this database, you'll need a &lt;strong&gt;Collection of Records&lt;/strong&gt; in the form of PDF files that you want to gether into a single &lt;em&gt;collection of data&lt;/em&gt; that will have &lt;strong&gt;each component&lt;/strong&gt; part of it.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; ~/work/projectapario
&lt;span class="nb"&gt;cd&lt;/span&gt; ~/work/projectapario
git clone git@github.com:ProjectApario/writer.git
&lt;span class="nb"&gt;cd &lt;/span&gt;writer
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt; component is 3344 lines of code across 15 &lt;code&gt;.go&lt;/code&gt; files. The &lt;a href="https://github.com/ProjectApario/writer/blob/main/install.sh" rel="noopener noreferrer"&gt;install.sh&lt;/a&gt; script loads the dependencies onto your system so you can compile your own &lt;em&gt;Apario Database&lt;/em&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;chmod&lt;/span&gt; +x install.sh &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="nb"&gt;sudo&lt;/span&gt; ./install.sh
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I use the &lt;code&gt;config.yml&lt;/code&gt; strategy with the &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt;. For example, if I am working on &lt;code&gt;teslafiles.info&lt;/code&gt; then I'd have a &lt;code&gt;writer.yml&lt;/code&gt; file that I'd use for my config file. To begin, lets ensure that some directories exist:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; &lt;span class="s2"&gt;"~/apario/teslafiles.info/{logs,config,workspace,data,import,app,search,ssl}"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This will create:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;~/apario
~/apario/teslafiles.info
~/apario/teslafiles.info/logs
~/apario/teslafiles.info/config
~/apario/teslafiles.info/workspace
~/apario/teslafiles.info/data
~/apario/teslafiles.info/import
~/apario/teslafiles.info/search
~/apario/teslafiles.info/app
~/apario/teslafiles.info/ssl
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Directory&lt;/th&gt;
&lt;th&gt;Purpose&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;~/apario/&amp;lt;collection-domain&amp;gt;/logs&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Contains log files&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;~/apario/&amp;lt;collection-domain&amp;gt;/config&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Contains `[reader\&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;{% raw %}&lt;code&gt;~/apario/&amp;lt;collection-domain&amp;gt;/workspace&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;Binary will use this as a temporary workspace&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;~/apario/&amp;lt;collection-domain&amp;gt;/data&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;When importing data into the &lt;em&gt;Apario Database&lt;/em&gt;, you place the &lt;strong&gt;originals&lt;/strong&gt; here.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;~/apario/&amp;lt;collection-domain&amp;gt;/import&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;When you're importing data, your structured data goes in here such as your &lt;code&gt;.csv&lt;/code&gt; or &lt;code&gt;.xlsx&lt;/code&gt; files.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;~/apario/&amp;lt;collection-domain&amp;gt;/app&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;The database(s) live inside of here.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;~/apario/&amp;lt;collection-domain&amp;gt;/search&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;The index files for the &lt;em&gt;Apario Database&lt;/em&gt; &lt;a href="https://github.com/andreimerlescu/gematria" rel="noopener noreferrer"&gt;gematria&lt;/a&gt; included binary data.&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;~/apario/&amp;lt;collection-domain&amp;gt;/ssl&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;The TLS&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;The &lt;code&gt;writer.yml&lt;/code&gt; file in &lt;code&gt;~/apario/teslafiles.info/config&lt;/code&gt; for &lt;strong&gt;teslafiles.info&lt;/strong&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="nn"&gt;---&lt;/span&gt;
&lt;span class="na"&gt;log&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;~/apario/teslafiles.info/logs/writer.log&lt;/span&gt;
&lt;span class="na"&gt;database-directory&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;~/apario/teslafiles.info/app&lt;/span&gt;
&lt;span class="na"&gt;no-clam&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
&lt;span class="na"&gt;language&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;eng&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When using a &lt;code&gt;.csv&lt;/code&gt; file, you'd add:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;import-csv&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;~/apario/teslafiles.info/import/teslafiles.csv&lt;/span&gt;
&lt;span class="na"&gt;csv-column-url&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;URL&lt;/span&gt;
&lt;span class="na"&gt;csv-column-path&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;PATH&lt;/span&gt;
&lt;span class="na"&gt;csv-column-record-number&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;ID&lt;/span&gt;
&lt;span class="na"&gt;csv-column-title&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;TITLE&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Your &lt;code&gt;.csv&lt;/code&gt; file would have:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;ID,TITLE,URL,PATH
1,Document One,https://example.com/document1.pdf,~/apario/teslafiles.info/data/document1.pdf
2,Document Two,https://example.com/document2.pdf,~/apario/teslafiles.info/data/document2.pdf
3,Document Three,https://example.com/document3.pdf,~/apario/teslafiles.info/data/document3.pdf
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then running the &lt;strong&gt;writer&lt;/strong&gt; is a matter of:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;go build &lt;span class="nt"&gt;-o&lt;/span&gt; writer &lt;span class="nb"&gt;.&lt;/span&gt;
&lt;span class="nb"&gt;chmod&lt;/span&gt; +x writer
./writer &lt;span class="nt"&gt;-config&lt;/span&gt; ~/apario/teslafiles.info/config/writer.yml
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then, the application will begin streaming detailed logging information into the &lt;code&gt;logs:&lt;/code&gt; directory choice from the &lt;code&gt;writer.yml&lt;/code&gt; setting destination and minimal information to the STDOUT of the &lt;code&gt;./writer ...&lt;/code&gt; invocation. &lt;/p&gt;

&lt;h2&gt;
  
  
  How The Writer Was Built From A Blank Text File
&lt;/h2&gt;

&lt;p&gt;Now, let's dig into the Go code shall we, and understand how I ingested 666K pages of unsearchable PDFs and built a full text search engine to provide &lt;strong&gt;advanced search&lt;/strong&gt; capabilities that could parse &lt;code&gt;(president kennedy or the president) not (blank page or intentionally left blank) and (top secret or ts/sci or ts//sci) not cover page&lt;/code&gt; and get legitimate results. &lt;em&gt;I built that, twice.&lt;/em&gt; First in Ruby on Rails, in front of DJ Nicke, and second behind closed doors during holiday breaks when I had the chance to get some uninterrupted programming flow back into swing.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Dependencies&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="c"&gt;// Binary Dependencies&lt;/span&gt;
&lt;span class="n"&gt;sl_required_binaries&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="s"&gt;"pdfcpu"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s"&gt;"gs"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s"&gt;"pdftotext"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s"&gt;"convert"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s"&gt;"pdftoppm"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s"&gt;"tesseract"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="s"&gt;"clamscan"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="c"&gt;// optional with `-no-clam` flag&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Project&lt;/th&gt;
&lt;th&gt;License Type&lt;/th&gt;
&lt;th&gt;URL&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;pdfcpu&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Apache License 2.0&lt;/td&gt;
&lt;td&gt;&lt;a href="https://github.com/pdfcpu/pdfcpu" rel="noopener noreferrer"&gt;https://github.com/pdfcpu/pdfcpu&lt;/a&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;
&lt;code&gt;gs&lt;/code&gt; (Ghostscript)&lt;/td&gt;
&lt;td&gt;AGPL-3.0 (dual-licensed; commercial available)&lt;/td&gt;
&lt;td&gt;&lt;a href="https://www.ghostscript.com/" rel="noopener noreferrer"&gt;https://www.ghostscript.com/&lt;/a&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;
&lt;code&gt;pdftotext&lt;/code&gt; &amp;amp; &lt;code&gt;pdftoppm&lt;/code&gt; (Poppler)&lt;/td&gt;
&lt;td&gt;GPL v2 or v3&lt;/td&gt;
&lt;td&gt;&lt;a href="https://poppler.freedesktop.org/" rel="noopener noreferrer"&gt;https://poppler.freedesktop.org/&lt;/a&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;
&lt;code&gt;convert&lt;/code&gt; (ImageMagick)&lt;/td&gt;
&lt;td&gt;ImageMagick License (Apache-2.0-derived)&lt;/td&gt;
&lt;td&gt;&lt;a href="https://imagemagick.org/license/" rel="noopener noreferrer"&gt;https://imagemagick.org/license/&lt;/a&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;tesseract&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;Apache License 2.0&lt;/td&gt;
&lt;td&gt;&lt;a href="https://github.com/tesseract-ocr/tesseract" rel="noopener noreferrer"&gt;https://github.com/tesseract-ocr/tesseract&lt;/a&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;
&lt;code&gt;clamscan&lt;/code&gt; (ClamAV)&lt;/td&gt;
&lt;td&gt;GPL-2.0&lt;/td&gt;
&lt;td&gt;&lt;a href="https://github.com/Cisco-Talos/clamav" rel="noopener noreferrer"&gt;https://github.com/Cisco-Talos/clamav&lt;/a&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;The pipeline shells out to a mix of copyleft projects. GPL-3.0 was picked because it's compatible with almost everything the project shells out to (Apache-2.0 tools, dual-licensed Poppler, AGPL-3.0 Ghostscript) — the one exception, ClamAV's GPL-2.0-only, doesn't matter since it's just called as a subprocess, not linked in.&lt;/p&gt;

&lt;p&gt;To begin, we'll work with the &lt;code&gt;main.go&lt;/code&gt; file first: &lt;/p&gt;

&lt;p&gt;Before I get to the &lt;code&gt;main()&lt;/code&gt; func, there is a directory of assets that contains a JSON file of cryptonyms commonly used throughout the JFK files. This data is particular to the data set itself, but I embed the JSON file itself into the Go program at the &lt;code&gt;package main&lt;/code&gt; level below the &lt;code&gt;import ()&lt;/code&gt; block.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="c"&gt;//go:embed bundled/*&lt;/span&gt;
&lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;fs_references&lt;/span&gt; &lt;span class="n"&gt;embed&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;FS&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When we get to building the &lt;code&gt;main()&lt;/code&gt; func, its 280 lines long, so we're going to break it down into segments about what its doing. You can follow along in the &lt;a href="https://github.com/ProjectApario/writer/blob/main/main.go#L27C1-L307C2" rel="noopener noreferrer"&gt;main.go&lt;/a&gt; file on GitHub. I want to focus on the logging component, because how I built the pipeline, the logging matters. It's not &lt;em&gt;one log&lt;/em&gt; for the entire pipeline. There is an &lt;strong&gt;info log&lt;/strong&gt;, an &lt;strong&gt;error log&lt;/strong&gt; and a &lt;strong&gt;debug log&lt;/strong&gt;. Some log messages are meant for watching the progress of the compilation. Others are meant for intervention in the event that there is a corrupted PDF file.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="n"&gt;log_files&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;make&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;File&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="c"&gt;// Initialize log files with truncation&lt;/span&gt;
&lt;span class="n"&gt;debugFile&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;OpenFile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;logDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"debug.log"&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;O_CREATE&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;O_WRONLY&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;O_TRUNC&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;0644&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Fatalf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to open debug log: %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="n"&gt;log_files&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;cDebugLog&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;debugFile&lt;/span&gt;

&lt;span class="n"&gt;infoFile&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;OpenFile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;logDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"info.log"&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;O_CREATE&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;O_WRONLY&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;O_TRUNC&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;0644&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;closeLogFiles&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
    &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Fatalf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to open info log: %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="n"&gt;log_files&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;cInfoLog&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;infoFile&lt;/span&gt;

&lt;span class="n"&gt;errorFile&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;OpenFile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;logDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"error.log"&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;O_CREATE&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;O_WRONLY&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;O_TRUNC&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;0644&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;closeLogFiles&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
    &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Fatalf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to open error log: %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="n"&gt;log_files&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;cErrorLog&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;errorFile&lt;/span&gt;

&lt;span class="c"&gt;// Initialize loggers&lt;/span&gt;
&lt;span class="n"&gt;log_debug&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;NewCustomLogger&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;debugFile&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"DEBUG: "&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Ldate&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Ltime&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Llongfile&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;10&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;log_info&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;NewCustomLogger&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;infoFile&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"INFO: "&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Ldate&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Ltime&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Lshortfile&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;10&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;log_error&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;NewCustomLogger&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;errorFile&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"ERROR: "&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Ldate&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Ltime&lt;/span&gt;&lt;span class="o"&gt;|&lt;/span&gt;&lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Lshortfile&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;10&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Next, I need to handle various interrupt signals and run &lt;code&gt;receive_watchdog_signal&lt;/code&gt; in the event that they are received. This means &lt;code&gt;Ctrl+C&lt;/code&gt; invokes this method.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="c"&gt;// interrupt Ctrl+C and other SIGINT/SIGTERM/SIGKILL related signals to the application to quit gracefully&lt;/span&gt;
&lt;span class="n"&gt;watchdog&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="nb"&gt;make&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;chan&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Signal&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;signal&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Notify&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;watchdog&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Kill&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;syscall&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SIGTERM&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Interrupt&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="n"&gt;receive_watchdog_signal&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;watchdog&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;logFile&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;cancel&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Let's look into what this function is doing - because in order to understand why I am using a &lt;em&gt;watchdog&lt;/em&gt;, looking into what this function does shows you the tear-down and cleanup process when Ctrl+C is invoked on the writer while its processing.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;receive_watchdog_signal&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;watchdog&lt;/span&gt; &lt;span class="k"&gt;chan&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Signal&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;logFile&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;File&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;cancel&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;CancelFunc&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;watchdog&lt;/span&gt;
    &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SetOutput&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Stdout&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;logFile&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to close the logFile due to error: %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="k"&gt;defer&lt;/span&gt; &lt;span class="n"&gt;cancel&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

    &lt;span class="n"&gt;ch_ImportedRow&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;       &lt;span class="c"&gt;// step 01&lt;/span&gt;
    &lt;span class="n"&gt;ch_ExtractText&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;       &lt;span class="c"&gt;// step 02&lt;/span&gt;
    &lt;span class="n"&gt;ch_ExtractPages&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;      &lt;span class="c"&gt;// step 03&lt;/span&gt;
    &lt;span class="n"&gt;ch_GeneratePng&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;       &lt;span class="c"&gt;// step 04&lt;/span&gt;
    &lt;span class="n"&gt;ch_GenerateLight&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;     &lt;span class="c"&gt;// step 05&lt;/span&gt;
    &lt;span class="n"&gt;ch_GenerateDark&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;      &lt;span class="c"&gt;// step 06&lt;/span&gt;
    &lt;span class="n"&gt;ch_ConvertToJpg&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;      &lt;span class="c"&gt;// step 07&lt;/span&gt;
    &lt;span class="n"&gt;ch_PerformOcr&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;        &lt;span class="c"&gt;// step 08&lt;/span&gt;
    &lt;span class="n"&gt;ch_AnalyzeText&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;       &lt;span class="c"&gt;// step 09&lt;/span&gt;
    &lt;span class="n"&gt;ch_AnalyzeCryptonyms&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="c"&gt;// step 10&lt;/span&gt;
    &lt;span class="n"&gt;ch_CompletedPage&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;     &lt;span class="c"&gt;// step 11&lt;/span&gt;
    &lt;span class="n"&gt;ch_CompiledDocument&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;  &lt;span class="c"&gt;// step 12&lt;/span&gt;

    &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Completed running in %d"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Since&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;startedAt&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;

    &lt;span class="c"&gt;// excluded pid termination lines L333-L351&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The binary is designed to support being compiled and executed in a universal format that supports macOS, Linux and Windows natively allowing you compile an &lt;em&gt;Apario Database&lt;/em&gt; directory on any system that has the downstream dependencies defined. Getting everything working on Windows is extremely hard and I have not successfully tested it without using WSL2. In that case, the binary is compiled for Linux and not Windows, and is not an &lt;code&gt;.exe&lt;/code&gt; - but Go allows you to compile this program into an &lt;code&gt;.exe&lt;/code&gt; and run it - even if its not recommended 🤣.&lt;/p&gt;

&lt;p&gt;What I hope you noticed was the 12 step process here 👀:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="n"&gt;ch_ImportedRow&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;       &lt;span class="c"&gt;// step 01&lt;/span&gt;
&lt;span class="n"&gt;ch_ExtractText&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;       &lt;span class="c"&gt;// step 02&lt;/span&gt;
&lt;span class="n"&gt;ch_ExtractPages&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;      &lt;span class="c"&gt;// step 03&lt;/span&gt;
&lt;span class="n"&gt;ch_GeneratePng&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;       &lt;span class="c"&gt;// step 04&lt;/span&gt;
&lt;span class="n"&gt;ch_GenerateLight&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;     &lt;span class="c"&gt;// step 05&lt;/span&gt;
&lt;span class="n"&gt;ch_GenerateDark&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;      &lt;span class="c"&gt;// step 06&lt;/span&gt;
&lt;span class="n"&gt;ch_ConvertToJpg&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;      &lt;span class="c"&gt;// step 07&lt;/span&gt;
&lt;span class="n"&gt;ch_PerformOcr&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;        &lt;span class="c"&gt;// step 08&lt;/span&gt;
&lt;span class="n"&gt;ch_AnalyzeText&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;       &lt;span class="c"&gt;// step 09&lt;/span&gt;
&lt;span class="n"&gt;ch_AnalyzeCryptonyms&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="c"&gt;// step 10&lt;/span&gt;
&lt;span class="n"&gt;ch_CompletedPage&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;     &lt;span class="c"&gt;// step 11&lt;/span&gt;
&lt;span class="n"&gt;ch_CompiledDocument&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;  &lt;span class="c"&gt;// step 12&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This exposes the &lt;strong&gt;actual pipeline&lt;/strong&gt; of what the &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt; actually does.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;FIRST:&lt;/strong&gt; You begin with a CSV file or an XLSX file that contains the following type of data: &lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;RECORDNO&lt;/th&gt;
&lt;th&gt;TITLE&lt;/th&gt;
&lt;th&gt;URL&lt;/th&gt;
&lt;th&gt;PATH&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;code&gt;&amp;lt;string&amp;gt;&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;&amp;lt;string&amp;gt;&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;&amp;lt;string&amp;gt;&lt;/code&gt;&lt;/td&gt;
&lt;td&gt;&lt;code&gt;&amp;lt;string&amp;gt;&lt;/code&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;R1&lt;/td&gt;
&lt;td&gt;Example Title&lt;/td&gt;
&lt;td&gt;&lt;a href="https://archive.gov/example.pdf" rel="noopener noreferrer"&gt;https://archive.gov/example.pdf&lt;/a&gt;&lt;/td&gt;
&lt;td&gt;./ingest/example.pdf&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;This assumes that you have &lt;code&gt;./ingest&lt;/code&gt; as a directory in the same location as the &lt;code&gt;writer&lt;/code&gt; binary in this example - but you get what I am doing here. That &lt;strong&gt;PATH&lt;/strong&gt; is local to the machine running the &lt;em&gt;writer&lt;/em&gt;. The &lt;strong&gt;URL&lt;/strong&gt; is the &lt;em&gt;original source&lt;/em&gt; that &lt;strong&gt;should&lt;/strong&gt; end in &lt;code&gt;.gov&lt;/code&gt; or &lt;code&gt;.mil&lt;/code&gt; if its going to be &lt;em&gt;authentic OSINT&lt;/em&gt; that the PhoenixVault was originally built to serve. However, it's actually &lt;em&gt;not required&lt;/em&gt;. You can use URLs like &lt;code&gt;https://mywebsite.com/assets/example.pdf&lt;/code&gt; and the interface will use whatever link you provided in the column. This is so your users can see the original document in its original location - perhaps to verify authenticity - perhaps to compare results. The &lt;strong&gt;RECORDNO&lt;/strong&gt; column is a &lt;em&gt;unique-required&lt;/em&gt; string field. Some OSINT releases provide reference identifiers, and this &lt;code&gt;&amp;lt;string&amp;gt;&lt;/code&gt; field is designed for &lt;em&gt;that value.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;What &lt;strong&gt;writer&lt;/strong&gt; does, is take this &lt;code&gt;.csv&lt;/code&gt; or &lt;code&gt;.xlsx&lt;/code&gt; (sheet 1 only) result and use these 4 columns in the CLI flags when the writer runs. Depending on which technology you're using, the flags change. Let's see what usage would look like based on these two type of ingestion file types. First lets get the source code of the writer on our machine.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; ~/workspace/projectapario
&lt;span class="nb"&gt;cd&lt;/span&gt; ~/workspace/projectapario
git clone git@github.com:ProjectApario/writer.git 
&lt;span class="nb"&gt;cd &lt;/span&gt;writer
&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; bin
go build &lt;span class="nt"&gt;-o&lt;/span&gt; bin/writer &lt;span class="nb"&gt;.&lt;/span&gt;
&lt;span class="nb"&gt;chmod&lt;/span&gt; +x bin/writer
&lt;span class="nb"&gt;sudo mv &lt;/span&gt;bin/writer /usr/local/bin/writer
which writer
&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; ingest &lt;span class="c"&gt;# place PDFs in this folder&lt;/span&gt;
&lt;span class="nb"&gt;touch &lt;/span&gt;ingest.csv &lt;span class="c"&gt;# populate with your documents metadata&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now, lets run it with a &lt;strong&gt;CSV&lt;/strong&gt; file called &lt;code&gt;ingest.csv&lt;/code&gt; and a directory of PDFs called &lt;code&gt;ingest&lt;/code&gt; exists next to &lt;code&gt;bin&lt;/code&gt;. These are the registered flag definitions:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="c"&gt;// Import .csv collections&lt;/span&gt;
&lt;span class="n"&gt;flag_s_import_csv&lt;/span&gt;               &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;config&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;NewString&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"import-csv"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;""&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"relative path to an excel spreadsheet where output is a comma separated table of urls and metadata properties. use additional args to associate columns to key data points."&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;flag_s_csv_column_url&lt;/span&gt;           &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;config&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;NewString&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"csv-column-url"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;""&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"value of row 1 whose column correlates to URLs to download PDF files from"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;flag_s_csv_column_path&lt;/span&gt;          &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;config&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;NewString&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"csv-column-path"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;""&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"value of row 1 whose column correlates to absolute paths of PDF files"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;flag_s_csv_column_record_number&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;config&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;NewString&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"csv-column-record-number"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;""&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"value of row 1 whose column correlates to a unique record identifier or number"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;flag_s_csv_column_title&lt;/span&gt;         &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;config&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;NewString&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"csv-column-title"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;""&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"value of row 1 whose column correlates to the title of the document"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="n"&gt;flag_s_pdf_metadata_json&lt;/span&gt;        &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;config&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;NewString&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"metadata-json"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;""&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"json key value map[string]string"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Using it is as simple as:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;writer &lt;span class="se"&gt;\ &lt;/span&gt;&lt;span class="c"&gt;# CSV flags 👇🏻&lt;/span&gt;
       &lt;span class="nt"&gt;-import-csv&lt;/span&gt; ./ingest.csv &lt;span class="se"&gt;\&lt;/span&gt;
       &lt;span class="nt"&gt;-csv-column-url&lt;/span&gt; URL &lt;span class="se"&gt;\&lt;/span&gt;
       &lt;span class="nt"&gt;-csv-column-path&lt;/span&gt; PATH &lt;span class="se"&gt;\&lt;/span&gt;
       &lt;span class="nt"&gt;-csv-column-record-number&lt;/span&gt; RECORDNO &lt;span class="se"&gt;\&lt;/span&gt;
       &lt;span class="nt"&gt;-csv-column-title&lt;/span&gt; TITLE &lt;span class="se"&gt;\&lt;/span&gt;
       &lt;span class="nt"&gt;-metadata-json&lt;/span&gt; &lt;span class="s2"&gt;"{&lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;collection&lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;: &lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;JFK Files&lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;}"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;It looks identical for &lt;strong&gt;XLSX&lt;/strong&gt; with the slight change.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;writer &lt;span class="se"&gt;\ &lt;/span&gt;&lt;span class="c"&gt;# XLSX flags 👇🏻&lt;/span&gt;
       &lt;span class="nt"&gt;-import-csv&lt;/span&gt; ./ingest.xlsx &lt;span class="se"&gt;\&lt;/span&gt;
       &lt;span class="nt"&gt;-xlsx-column-url&lt;/span&gt; URL &lt;span class="se"&gt;\&lt;/span&gt;
       &lt;span class="nt"&gt;-xlsx-column-path&lt;/span&gt; PATH &lt;span class="se"&gt;\&lt;/span&gt;
       &lt;span class="nt"&gt;-xlsx-column-record-number&lt;/span&gt; RECORDNO &lt;span class="se"&gt;\&lt;/span&gt;
       &lt;span class="nt"&gt;-xlsx-column-title&lt;/span&gt; TITLE &lt;span class="se"&gt;\&lt;/span&gt;
       &lt;span class="nt"&gt;-metadata-json&lt;/span&gt; &lt;span class="s2"&gt;"{&lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;collection&lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;: &lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;JFK Files&lt;/span&gt;&lt;span class="se"&gt;\"&lt;/span&gt;&lt;span class="s2"&gt;}"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Each &lt;strong&gt;row in the CSV&lt;/strong&gt; is gathered into a &lt;code&gt;struct {}&lt;/code&gt; and then passed into the &lt;code&gt;ch_ImportedRow&lt;/code&gt; channel for processing. What we're doing, is going from a &lt;strong&gt;row in the CSV&lt;/strong&gt; to a &lt;strong&gt;compiled JSON record object for the entire processed document&lt;/strong&gt; and store that file in a structured directory that the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; ingests by determinatively looking into a path as a &lt;em&gt;structured &lt;code&gt;Apario Database&lt;/code&gt; that is a directory of files&lt;/em&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="c"&gt;// start a bunch of receiver functions to handle when data is ready to be processed&lt;/span&gt;
&lt;span class="c"&gt;// each of these functions are like black boxes that ONE PAGE from a document is ingested into until it reaches the end&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;At this point, we need to go back to the &lt;code&gt;main.go&lt;/code&gt; file and look at how each of these channels are established.&lt;/p&gt;

&lt;p&gt;As each &lt;strong&gt;row from the CSV or XSLX&lt;/strong&gt; is passed into the writer itself, the actual setup of this channel is found in &lt;code&gt;data.go&lt;/code&gt; of the project, but in &lt;code&gt;main()&lt;/code&gt; I spawned &lt;strong&gt;goroutines&lt;/strong&gt; for each of the pipeline steps. Traditionally, &lt;strong&gt;goroutines&lt;/strong&gt; are for smaller tasks and such, but they can also be used for longer running tasks too. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The &lt;code&gt;ch_ImportedRow&lt;/code&gt; Channel&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="n"&gt;receiveImportedRow&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ch_ImportedRow&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Chan&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;            &lt;span class="c"&gt;// step 01 - runs validate_result_data_record before sending into ch_ExtractText&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The actual receiver function uses a &lt;code&gt;for { select {} }&lt;/code&gt; pattern in Go to listen on the &lt;code&gt;context.Context&lt;/code&gt;'s &lt;code&gt;.Done()&lt;/code&gt; channel and the incoming &lt;code&gt;&amp;lt;-ch&lt;/code&gt; that is an &lt;code&gt;interface{}&lt;/code&gt; data type (anything).&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;receiveImportedRow&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ch&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="k"&gt;chan&lt;/span&gt; &lt;span class="k"&gt;interface&lt;/span&gt;&lt;span class="p"&gt;{})&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="kt"&gt;error&lt;/span&gt;
    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;select&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Done&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt;
        &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="n"&gt;ird&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ch&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
            &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;valid&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;ird&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ResultData&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;valid&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"not valid typecasting for ird to rd.(ResultData)"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                    &lt;span class="k"&gt;return&lt;/span&gt;
                &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="c"&gt;// endif&lt;/span&gt;
                &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;validate_result_data_record&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Tracef&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"received error on validate_result_data_record for rd.URL %v ; err = %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;URL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="n"&gt;log_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"validated the downloaded PDF %v from URL %v, sending rd into ch_ExtractText"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Base&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;URL&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;ch_ExtractText&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;CanWrite&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                        &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;ch_ExtractText&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Write&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                            &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Tracef&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to write to ch_ExtractText channel due to error: %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                            &lt;span class="k"&gt;return&lt;/span&gt;
                        &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="c"&gt;// end if&lt;/span&gt;
                    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="c"&gt;// end if&lt;/span&gt;
                &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="c"&gt;// end if-else&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="c"&gt;// end if ok&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="c"&gt;// end select&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="c"&gt;// end for&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="c"&gt;// end func&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This pattern is used throughout each of the steps. The resource intensive task in this case is called in the middle of this receiver function.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;validate_result_data_record&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When we look into this function, located inside of the &lt;code&gt;pipeline.go&lt;/code&gt; file, we can see:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;validate_result_data_record&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt; &lt;span class="n"&gt;ResultData&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ResultData&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="kt"&gt;error&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;log_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"started validate_result_data_record(%v) = %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="c"&gt;// analyze, repair on error, then re-analyze if necessary&lt;/span&gt;
    &lt;span class="n"&gt;pdf_info&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;analyze_err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;analyze_then_repair_pdf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;analyze_err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;TraceReturn&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;analyze_err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="c"&gt;// fix total pages&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;pdf_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Infos&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="n"&gt;pdf_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Infos&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="m"&gt;0&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Pages&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="m"&gt;0&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="n"&gt;pdf_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Infos&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="m"&gt;0&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Pages&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="n"&gt;pdf_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Infos&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="m"&gt;0&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PageCount&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="n"&gt;pdf_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Infos&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="m"&gt;0&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Pages&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;pdf_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Infos&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="m"&gt;0&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PageCount&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="c"&gt;// validate total pages&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;pdf_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Infos&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="m"&gt;0&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Pages&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="m"&gt;0&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;TraceReturnf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to set pdf_info.Pages to pdf_info.PageCount&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;pdf_info = %+v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pdf_info&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="c"&gt;// validate pdf&lt;/span&gt;
    &lt;span class="n"&gt;validate_err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;validate_pdf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;validate_err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;TraceReturn&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;validate_err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="c"&gt;// optimize pdf&lt;/span&gt;
    &lt;span class="n"&gt;optimize_err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;optimize_pdf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;optimize_err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;TraceReturn&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;optimize_err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Here we're running &lt;code&gt;analyze_then_repair_pdf&lt;/code&gt; then using the metadata from the result of the call to populate some structured data. Then we call the &lt;code&gt;validate_pdf&lt;/code&gt; to confirm, then &lt;code&gt;optimize_pdf&lt;/code&gt;. When we have a problem, we're using the &lt;code&gt;verbose.TraceReturn&lt;/code&gt; directly as the &lt;code&gt;log_error&lt;/code&gt; handler that is a &lt;a href="https://github.com/andreimerlescu/verbose" rel="noopener noreferrer"&gt;verbose&lt;/a&gt; logger with secrets protection and stack trace analysis capabilities.  These can spawn child processes and take several seconds to complete depending on the size of the PDF file being analyzed. If it's gigabytes in size, like this writer has processed successfully, then it'll take a few minutes to complete. That's normal. In the &lt;code&gt;info_log&lt;/code&gt; you'll see the begin and end time per document and you'll see some documents take several minutes to complete. This means that the pipeline built within the writer is capable of managing many system resources on a bare metal machine, utilize 100% of its capabilities while safely managing resources across the system that include spawned projects where some are single threaded, and some are multi-threaded. When a multi-threaded &lt;code&gt;tesseract&lt;/code&gt; process is spawning, the writer has semaphores in place to ensure that its not going to use too many system resources and that &lt;code&gt;tesseract&lt;/code&gt; is contained within a lane of processing compute power proportional to the impact that the pipeline has on the greater runtime.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The &lt;code&gt;ch_ExtractText&lt;/code&gt; Channel&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;This is step 2 of the pipeline where we have to use a third party binary in order to extract the text out of the PDF. I didn't want to reinvent the wheel - I wanted to ingest 666K pages of JFK files as fast as possible, and if the tool works and its license is compatible, let's go!&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="n"&gt;receiveOnExtractTextCh&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ch_ExtractText&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Chan&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;        &lt;span class="c"&gt;// step 02 - runs extractPlainTextFromPdf before sending into ch_ExtractPages&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;
&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;receiveOnExtractTextCh&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ch&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="k"&gt;chan&lt;/span&gt; &lt;span class="k"&gt;interface&lt;/span&gt;&lt;span class="p"&gt;{})&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;select&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Done&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt;
        &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="n"&gt;ird&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ch&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
            &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;ird&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ResultData&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Tracef&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to assert the ird from ch_ExtractText as type ResultData"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                    &lt;span class="k"&gt;return&lt;/span&gt;
                &lt;span class="p"&gt;}&lt;/span&gt;
                &lt;span class="n"&gt;log_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"received rd from ch_ExtractText for URL %v, running extractPlainTextFromPdf(%v)"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;URL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                &lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="n"&gt;extractPlainTextFromPdf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="n"&gt;log_debug&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Println&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"ch_ExtractText is closed but received some data"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                &lt;span class="k"&gt;return&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Here you can see that the bulk of the processing takes place in the &lt;code&gt;go extractPlainTextFromPdf(ctx, rd)&lt;/code&gt; spawning of another &lt;strong&gt;goroutine&lt;/strong&gt;; in this case, we aren't going to wait for it in this particular loop of &lt;code&gt;receiveOnExtractTextCh&lt;/code&gt;'s &lt;code&gt;for { select {} }&lt;/code&gt; lifecycle until the &lt;code&gt;context.Context&lt;/code&gt; is canceled. That context is then passed into the &lt;code&gt;extractPlainTextFromPdf&lt;/code&gt;, where an external tool is invoked.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;extractPlainTextFromPdf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt; &lt;span class="n"&gt;ResultData&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;defer&lt;/span&gt; &lt;span class="k"&gt;func&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="n"&gt;log_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"finished extracting the text from the PDF %v, now sending rd into ch_ExtractPages"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Base&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;
        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;ch_ExtractPages&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;CanWrite&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;ch_ExtractPages&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Write&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Tracef&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to write record %v into the ch_ExtractPages due to error %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}()&lt;/span&gt;
    &lt;span class="n"&gt;log_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"started extractPlainTextFromPdf(%v) = %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;fileHasData&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ExtractedTextPath&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="c"&gt;/*
            pdftotext REPLACE_WITH_FILE_PATH REPLACE_WITH_TEXT_OUTPUT_FILE_PATH
        */&lt;/span&gt;
        &lt;span class="n"&gt;cmd_extract_text_pdf&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;exec&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Command&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;m_required_binaries&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;"pdftotext"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ExtractedTextPath&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;cmd4_extract_text_pdf_stdout&lt;/span&gt; &lt;span class="n"&gt;bytes&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Buffer&lt;/span&gt;
        &lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;cmd4_extract_text_pdf_stderr&lt;/span&gt; &lt;span class="n"&gt;bytes&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Buffer&lt;/span&gt;
        &lt;span class="n"&gt;cmd_extract_text_pdf&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Stdout&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;cmd4_extract_text_pdf_stdout&lt;/span&gt;
        &lt;span class="n"&gt;cmd_extract_text_pdf&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Stderr&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;cmd4_extract_text_pdf_stderr&lt;/span&gt;
        &lt;span class="n"&gt;sem_pdftotext&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Acquire&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
        &lt;span class="n"&gt;cmd_extract_text_pdf_err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;cmd_extract_text_pdf&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Run&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
        &lt;span class="n"&gt;sem_pdftotext&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Release&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;cmd_extract_text_pdf_err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Tracef&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Failed to execute command `pdftotext %v %v` due to error: %s&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ExtractedTextPath&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;cmd_extract_text_pdf_err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This uses the &lt;a href="https://github.com/andreimerlescu/semaphore" rel="noopener noreferrer"&gt;semaphore&lt;/a&gt; package in order to &lt;code&gt;.Acquire()&lt;/code&gt; and &lt;code&gt;.Release()&lt;/code&gt; on an invocation of &lt;code&gt;.Run()&lt;/code&gt; from an &lt;code&gt;exec.Command&lt;/code&gt; on the required &lt;code&gt;m_required_binaries["pdftotext"]&lt;/code&gt; &lt;strong&gt;pdftotext&lt;/strong&gt; binary invocation. We're going to use a &lt;code&gt;bytes.Buffer&lt;/code&gt; to collect on &lt;code&gt;STDOUT&lt;/code&gt; and &lt;code&gt;STDERR&lt;/code&gt; from the child process and we're using a semaphore to control &lt;em&gt;how many times&lt;/em&gt; this particular function is allowed to be called &lt;em&gt;system wide&lt;/em&gt; while &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt; compiles.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The &lt;code&gt;ch_ExtractPages&lt;/code&gt; Channel&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="n"&gt;receiveOnExtractPagesCh&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ch_ExtractPages&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Chan&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;      &lt;span class="c"&gt;// step 03 - runs extractPagesFromPdf before sending PendingPage into ch_GeneratePng&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;receiveOnExtractPagesCh&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ch&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="k"&gt;chan&lt;/span&gt; &lt;span class="k"&gt;interface&lt;/span&gt;&lt;span class="p"&gt;{})&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;select&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Done&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt;
        &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="n"&gt;ird&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ch&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
            &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;ird&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ResultData&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                    &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Tracef&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"ch_ExtractPages receive an ird but cannot cast it as a .(ResultData) type"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                    &lt;span class="k"&gt;return&lt;/span&gt;
                &lt;span class="p"&gt;}&lt;/span&gt;
                &lt;span class="n"&gt;log_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"received on ch_ExtractPages URL %v, running extractPagesFromPdf(%v)"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;URL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                &lt;span class="k"&gt;go&lt;/span&gt; &lt;span class="n"&gt;extractPagesFromPdf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
                &lt;span class="n"&gt;log_debug&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Trace&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"ch_ExtractPages is closed but received some data"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
                &lt;span class="k"&gt;return&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This function is quite large. Let's look at it and then talk about it.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;extractPagesFromPdf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt; &lt;span class="n"&gt;ResultData&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;log_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"started extractPagesFromPdf(%v) = %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="c"&gt;/*
      pdfcpu extract -mode page REPLACE_WITH_FILE_PATH REPLACE_WITH_OUTPUT_DIRECTORY
   */&lt;/span&gt;
   &lt;span class="n"&gt;pagesDir&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;DataDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"pages"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;sm_page_directories&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Store&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;_&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pagesDirExistsErr&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Stat&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;performPagesExtract&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="no"&gt;false&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;IsNotExist&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDirExistsErr&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;performPagesExtract&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;true&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;ok&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;DirHasPDFs&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;performPagesExtract&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;true&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="n"&gt;RETRY&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;performPagesExtract&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;pagesDirErr&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;MkdirAll&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;0755&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;pagesDirErr&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Tracef&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to create directory %v due to error %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pagesDirErr&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="k"&gt;return&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
      &lt;span class="n"&gt;cmd_extract_pages_in_pdf&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;exec&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Command&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;m_required_binaries&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s"&gt;"pdfcpu"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt; &lt;span class="s"&gt;"extract"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"-mode"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;"page"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;cmd_extract_pages_in_pdf_stdout&lt;/span&gt; &lt;span class="n"&gt;bytes&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Buffer&lt;/span&gt;
      &lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;cmd_extract_pages_in_pdf_stderr&lt;/span&gt; &lt;span class="n"&gt;bytes&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Buffer&lt;/span&gt;
      &lt;span class="n"&gt;cmd_extract_pages_in_pdf&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Stdout&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;cmd_extract_pages_in_pdf_stdout&lt;/span&gt;
      &lt;span class="n"&gt;cmd_extract_pages_in_pdf&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Stderr&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;cmd_extract_pages_in_pdf_stderr&lt;/span&gt;
      &lt;span class="n"&gt;sem_pdfcpu&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Acquire&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
      &lt;span class="n"&gt;cmd_extract_pages_in_pdf_err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;cmd_extract_pages_in_pdf&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Run&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
      &lt;span class="n"&gt;sem_pdfcpu&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Release&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;cmd_extract_pages_in_pdf_err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Tracef&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Failed to execute command `pdfcpu extract -mode page %v %v` due to error: %s&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;cmd_extract_pages_in_pdf_err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="k"&gt;return&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;log_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"not performing `pdfcpu extrace -mode page %v %v` because the directory %v already has PDFs inside it"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="n"&gt;check&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="nb"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="nb"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;check&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="k"&gt;goto&lt;/span&gt; &lt;span class="n"&gt;RETRY&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;

   &lt;span class="n"&gt;pagesDirWalkErr&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Walk&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="k"&gt;func&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;path&lt;/span&gt; &lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;info&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;FileInfo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="kt"&gt;error&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="kt"&gt;error&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Tracef&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Error accessing a path %q: %v&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;path&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;

      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;IsDir&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&amp;amp;&lt;/span&gt; &lt;span class="n"&gt;strings&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;HasSuffix&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Name&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="s"&gt;".pdf"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;nameParts&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;strings&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Split&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Name&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="s"&gt;"_page_"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="nb"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;nameParts&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="m"&gt;2&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Errorf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"incorrect filename provided as %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Name&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;
         &lt;span class="p"&gt;}&lt;/span&gt;
         &lt;span class="n"&gt;pgNoStr&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;strings&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;ReplaceAll&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;nameParts&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt; &lt;span class="s"&gt;".pdf"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="s"&gt;""&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNoErr&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;strconv&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Atoi&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pgNoStr&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;pgNoErr&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Errorf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"failed to extract the pgNo from the PDF filename %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Name&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;
         &lt;span class="p"&gt;}&lt;/span&gt;
         &lt;span class="n"&gt;identifier&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;NewIdentifier&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="m"&gt;9&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="n"&gt;pp&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;PendingPage&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;       &lt;span class="n"&gt;identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;RecordIdentifier&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;PageNumber&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;       &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;PagesDir&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;         &lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;PDFPath&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;          &lt;span class="n"&gt;path&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;OCRTextPath&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;      &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"ocr.%06d.txt"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
            &lt;span class="n"&gt;ManifestPath&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;     &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.%06d.json"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
            &lt;span class="n"&gt;PNG&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;PNG&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
               &lt;span class="n"&gt;Light&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;Images&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
                  &lt;span class="n"&gt;Original&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.light.%06d.original.png"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Large&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;    &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.light.%06d.large.png"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Medium&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;   &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.light.%06d.medium.png"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Small&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;    &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.light.%06d.small.png"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Social&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;   &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.light.%06d.social.png"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
               &lt;span class="p"&gt;},&lt;/span&gt;
               &lt;span class="n"&gt;Dark&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;Images&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
                  &lt;span class="n"&gt;Original&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.dark.%06d.original.png"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Large&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;    &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.dark.%06d.large.png"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Medium&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;   &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.dark.%06d.medium.png"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Small&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;    &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.dark.%06d.small.png"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Social&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;   &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.dark.%06d.social.png"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
               &lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="n"&gt;JPEG&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;JPEG&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
               &lt;span class="n"&gt;Light&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;Images&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
                  &lt;span class="n"&gt;Original&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.light.%06d.original.jpg"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Large&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;    &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.light.%06d.large.jpg"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Medium&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;   &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.light.%06d.medium.jpg"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Small&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;    &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.light.%06d.small.jpg"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Social&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;   &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.light.%06d.social.jpg"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
               &lt;span class="p"&gt;},&lt;/span&gt;
               &lt;span class="n"&gt;Dark&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;Images&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
                  &lt;span class="n"&gt;Original&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.dark.%06d.original.jpg"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Large&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;    &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.dark.%06d.large.jpg"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Medium&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;   &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.dark.%06d.medium.jpg"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Small&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;    &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.dark.%06d.small.jpg"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
                  &lt;span class="n"&gt;Social&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;   &lt;span class="n"&gt;filepath&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pagesDir&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;fmt&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Sprintf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"page.dark.%06d.social.jpg"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;)),&lt;/span&gt;
               &lt;span class="p"&gt;},&lt;/span&gt;
            &lt;span class="p"&gt;},&lt;/span&gt;
         &lt;span class="p"&gt;}&lt;/span&gt;
         &lt;span class="n"&gt;sm_pages&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Store&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;WritePendingPageToJson&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;
         &lt;span class="p"&gt;}&lt;/span&gt;
         &lt;span class="n"&gt;log_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"sending page %d (ID %v) from record %v URL %v into the ch_GeneratingPng"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pgNo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;record&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;URL&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;ch_GeneratePng&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;CanWrite&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;ch_GeneratePng&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Write&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
               &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Tracef&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"cannot send pp into ch_GeneratePng channel due to error %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
               &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
         &lt;span class="p"&gt;}&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;

      &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt;
   &lt;span class="p"&gt;})&lt;/span&gt;

   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;pagesDirWalkErr&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Tracef&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Error walking the path ./pages: %v&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="s"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pagesDirWalkErr&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="k"&gt;return&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;

   &lt;span class="k"&gt;return&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You can see &lt;code&gt;RETRY:&lt;/code&gt; and &lt;code&gt;goto RETRY&lt;/code&gt;? Well, thats a way of recursively calling a block within the function until something works - without having to deal with invoking and tearing down functions in between. In the case of recursion, I'm simply using the &lt;code&gt;performPagesExtract&lt;/code&gt; as a variable to determine whether or not we should even consider using &lt;code&gt;goto RETRY&lt;/code&gt;. When &lt;code&gt;performPagesExtract&lt;/code&gt; is false, I &lt;em&gt;reconsider what if true?&lt;/em&gt; If true, that means that the check passes and we actually &lt;em&gt;did need to run it&lt;/em&gt; but we didn't have something we needed first - so we fix that - and then re-run it. &lt;/p&gt;

&lt;p&gt;Next what I do is I build out a &lt;code&gt;PendingPage{}&lt;/code&gt; struct with a bunch of metadata about the &lt;strong&gt;individual page&lt;/strong&gt; from the given document. This is performed by using &lt;code&gt;filepath.Walk(pagesDir, &amp;lt;walkFunc&amp;gt; {})&lt;/code&gt; invocation on the output of the previous command that took the PDF file and extracted in a sub-directory one PDF per page in the original file. We're going to iterate over those compiled documents now, and we're going to populate this &lt;code&gt;PendingPage{}&lt;/code&gt; record with the gathered metadata about this particular &lt;em&gt;page&lt;/em&gt;. &lt;/p&gt;

&lt;p&gt;We're using semaphores here, and we're also invoking &lt;code&gt;WritePendingPageToJson(pp)&lt;/code&gt;, which effectively compiles the &lt;em&gt;Apario Database&lt;/em&gt; from scratch by writing individual JSON files to structured locations based on the page analysis output. &lt;/p&gt;

&lt;p&gt;I could go into each of the channels and break them down - but they are very similar in structure to what we have just explored from start to finish. What felt like a short ride, can be a journey of discovery by studying the &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt; and either utilizing it for public service or contributing to its long-term stability.&lt;/p&gt;

&lt;p&gt;The writer is responsible for ingesting a CSV file that can have as many as 72K rows of records inside of it that contain 666K pages of OSINT in unsearchable manner. &lt;/p&gt;

&lt;p&gt;The full text analysis uses &lt;a href="https://github.com/andreimerlescu/textee" rel="noopener noreferrer"&gt;textee&lt;/a&gt; and &lt;a href="https://github.com/andreimerlescu/gematria" rel="noopener noreferrer"&gt;gematria&lt;/a&gt; in order to take the OCR extract text, or the PDF's containing text and break sentences like:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;The lazy brown dog jumps over the quick fox.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Into:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;The (2)
The lazy (1)
The lazy brown (1)
lazy (1)
lazy brown (1)
lazy brown dog (1)
brown (1)
brown dog (1)
brown dog jumps (1)
dog (1)
dog jumps (1)
dog jumps over (1)
jumps (1)
jumps over (1)
jumps over the (1)
over (1)
over the (1)
over the quick (1)
the quick (1)
the quick fox (1)
quick (1)
quick fox (1)
fox (1)
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Notice the &lt;code&gt;The (2)&lt;/code&gt; and the way that between &lt;code&gt;over the quick (1)&lt;/code&gt; and &lt;code&gt;the quick (1)&lt;/code&gt; we omit &lt;code&gt;the (1)&lt;/code&gt; by making the first &lt;code&gt;The&lt;/code&gt; a 2. That's what &lt;a href="https://github.com/andreimerlescu/textee" rel="noopener noreferrer"&gt;textee&lt;/a&gt; does.&lt;/p&gt;

&lt;p&gt;The &lt;a href="https://github.com/andreimerlescu/gematria" rel="noopener noreferrer"&gt;gematria&lt;/a&gt; package is responsible for calculating the Simple, English, Jewish, Eights, Majestic and Mystery values.&lt;/p&gt;

&lt;p&gt;The pipeline operates in this manner: &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Rows from a CSV are ingested&lt;/li&gt;
&lt;li&gt;PDF is scanned, analyzed, optimized and rendered into a directory of individual page PDF files&lt;/li&gt;
&lt;li&gt;Each page PDF file is individually processed - keeping track of its original directory and original extracted document&lt;/li&gt;
&lt;li&gt;The &lt;code&gt;.pdf&lt;/code&gt; is converted into a &lt;code&gt;.png&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;The &lt;code&gt;.png&lt;/code&gt; is compiled into a progressive light JPEG&lt;/li&gt;
&lt;li&gt;The &lt;code&gt;.png&lt;/code&gt; is converted into dark mode&lt;/li&gt;
&lt;li&gt;The dark mode &lt;code&gt;.png&lt;/code&gt; is compiled into a progressive dark JPEG&lt;/li&gt;
&lt;li&gt;The &lt;code&gt;.pdf&lt;/code&gt; is processed through &lt;code&gt;pdftotext&lt;/code&gt; to extract text&lt;/li&gt;
&lt;li&gt;The &lt;code&gt;.pdf&lt;/code&gt; is processed through &lt;code&gt;tesseract&lt;/code&gt; to extract text&lt;/li&gt;
&lt;li&gt;The extracted text is analyzed against &lt;strong&gt;7 regular expressions&lt;/strong&gt; to find &lt;em&gt;dates&lt;/em&gt; and &lt;em&gt;cryptonyms&lt;/em&gt;
&lt;/li&gt;
&lt;li&gt;The &lt;code&gt;PendingPage{}&lt;/code&gt; struct is passed into &lt;code&gt;aggregatePendingPage&lt;/code&gt; in the &lt;code&gt;aggregate.go&lt;/code&gt; file&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;When the dates are analyzed, I opted to use regular expressions for it as defined in the &lt;code&gt;data.go&lt;/code&gt; file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="n"&gt;re_date1&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;regexp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;MustCompile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;`(?i)(\d{1,2})(st|nd|rd|th)?\s(?:of\s)?(January|Jan|February|Feb|March|Mar|April|Apr|May|June|Jun|July|Jul|August|Aug|September|Sep|October|Oct|November|Nov|December|Dec),?\s(\d{2,4})`&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;re_date2&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;regexp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;MustCompile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;`(?i)(\d{1,2})\/(\d{1,2})\/(\d{2,4})`&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;re_date3&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;regexp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;MustCompile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;`(?i)(January|Jan|February|Feb|March|Mar|April|Apr|May|June|Jun|July|Jul|August|Aug|September|Sep|October|Oct|November|Nov|December|Dec),?\s(\d{2,4})`&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;re_date5&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;regexp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;MustCompile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;`(?i)(January|Jan|February|Feb|March|Mar|April|Apr|May|June|Jun|July|Jul|August|Aug|September|Sep|October|Oct|November|Nov|December|Dec)\s(\d{1,2})(st|nd|rd|th)?,?\s(\d{2,4})`&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;re_date4&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;regexp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;MustCompile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;`(?i)(January|Jan|February|Feb|March|Mar|April|Apr|May|June|Jun|July|Jul|August|Aug|September|Sep|October|Oct|November|Nov|December|Dec)\s(\d{4})`&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;re_date6&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;regexp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;MustCompile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;`(\d{4})`&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then inside of &lt;code&gt;dates.go&lt;/code&gt; I am consuming them like so:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="n"&gt;match1&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;re_date1&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;FindAllStringSubmatch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;in&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;match2&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;re_date2&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;FindAllStringSubmatch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;in&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;match3&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;re_date3&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;FindAllStringSubmatch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;in&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;match4&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;re_date4&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;FindAllStringSubmatch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;in&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;match5&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;re_date5&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;FindAllStringSubmatch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;in&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;match6&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;re_date6&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;FindAllStringSubmatch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;in&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt;&lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Since &lt;em&gt;time&lt;/em&gt; is an illusion and we have multiple types, we can look at:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="n"&gt;day&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;dayErr&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;strconv&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Atoi&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="err"&gt;?&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;

&lt;span class="n"&gt;month&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;getMonthFromString&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="err"&gt;?&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;
&lt;span class="n"&gt;month&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;_&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;strconv&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Atoi&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="err"&gt;?&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;

&lt;span class="n"&gt;year&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;yearErr&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;strconv&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Atoi&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;m&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="err"&gt;?&lt;/span&gt;&lt;span class="p"&gt;])&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I conclude analyzing each of these matches with this function:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;uniqueTimes&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;times&lt;/span&gt; &lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Time&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Time&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;seen&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="nb"&gt;make&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Time&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="kt"&gt;bool&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;unique&lt;/span&gt; &lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Time&lt;/span&gt;
    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;_&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;t&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="k"&gt;range&lt;/span&gt; &lt;span class="n"&gt;times&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Year&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="m"&gt;1800&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Year&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Now&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Year&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="k"&gt;continue&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="n"&gt;t&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Date&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Year&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Month&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Day&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="m"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;0&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Location&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;
        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;_&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;seen&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="n"&gt;unique&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;append&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;unique&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="n"&gt;seen&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;t&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="no"&gt;true&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;unique&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Aggregating &lt;code&gt;PendingPage {}&lt;/code&gt; In Pipeline
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;aggregatePendingPage&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt; &lt;span class="n"&gt;context&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Context&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pp&lt;/span&gt; &lt;span class="n"&gt;PendingPage&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;data_rd&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;result_data_found&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;sm_resultdatas&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Load&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RecordIdentifier&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="c"&gt;// process missing from sync.Map&lt;/span&gt;

   &lt;span class="n"&gt;rd&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;rd_cast_ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;data_rd&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;ResultData&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="c"&gt;// process invalid ResultData cast&lt;/span&gt;

   &lt;span class="n"&gt;document_data&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;document_found&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;sm_documents&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Load&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RecordIdentifier&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="c"&gt;// process missing from sync.Map&lt;/span&gt;

   &lt;span class="n"&gt;document&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;document_cast_ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;document_data&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Document&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="c"&gt;// process invalid Document cast&lt;/span&gt;

   &lt;span class="c"&gt;// print document page count results&lt;/span&gt;

   &lt;span class="n"&gt;mu&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;DocumentLocker&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;document&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;mu&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Lock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;document&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Pages&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;document&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Pages&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;make&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;int64&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="n"&gt;Page&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="n"&gt;document&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Pages&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;int64&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PageNumber&lt;/span&gt;&lt;span class="p"&gt;)]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;Page&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;         &lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="n"&gt;DocumentIdentifier&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RecordIdentifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="n"&gt;PageNumber&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;         &lt;span class="kt"&gt;int64&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PageNumber&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="k"&gt;defer&lt;/span&gt; &lt;span class="n"&gt;mu&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Unlock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
   &lt;span class="n"&gt;ticker&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;NewTicker&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="m"&gt;333&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Millisecond&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="n"&gt;timer&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;NewTimer&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="m"&gt;999&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Second&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="kt"&gt;int64&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;document&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Pages&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;document&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;TotalPages&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="k"&gt;select&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Done&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
            &lt;span class="n"&gt;log_debug&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"context canceled on aggregatePendingPage %+v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt;
         &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;timer&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;C&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
            &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"FATAL TO DOCUMENT aggregatePendingPage failed to ingest %+v into the ch_CompiledDocument"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt;
         &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ticker&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;C&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
            &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;ch_CompiledDocument&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Write&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;document&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="n"&gt;log_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"ch_CompiledDocument.CanWrite = %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ch_CompiledDocument&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;CanWrite&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;
            &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="no"&gt;nil&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
               &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"FATAL TO DOCUMENT - err in writing to channel: %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;err&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="p"&gt;}&lt;/span&gt;
            &lt;span class="k"&gt;return&lt;/span&gt;
         &lt;span class="p"&gt;}&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="n"&gt;log_debug&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"aggregatePendingPage document %v page %d received but the document.Pages are at %d of %d so waiting before sending into ch_CompiledDocument"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
         &lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RecordIdentifier&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;pp&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;PageNumber&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nb"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;document&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Pages&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt; &lt;span class="n"&gt;document&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;TotalPages&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="k"&gt;return&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As you can see, we're using a &lt;code&gt;sync.Map&lt;/code&gt; called &lt;code&gt;sm_resultdatas.Load(pp.RecordIdentifier)&lt;/code&gt; in order to retrieve the &lt;code&gt;PendingPage{}&lt;/code&gt; struct out of memory according to the &lt;strong&gt;RECORDNO&lt;/strong&gt; column from the original &lt;strong&gt;CSV&lt;/strong&gt; or &lt;strong&gt;XLSX&lt;/strong&gt; file. &lt;/p&gt;

&lt;p&gt;We're using the &lt;code&gt;DocumentLocker&lt;/code&gt; in order to safely write to &lt;code&gt;document.Pages[int64(pp.PageNumber)]&lt;/code&gt; in a concurrent multi-threaded environment where resources are shared across threads and child processes.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;type&lt;/span&gt; &lt;span class="n"&gt;Document&lt;/span&gt; &lt;span class="k"&gt;struct&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;Identifier&lt;/span&gt;          &lt;span class="kt"&gt;string&lt;/span&gt;         &lt;span class="s"&gt;`json:"identifier"`&lt;/span&gt;
    &lt;span class="n"&gt;URL&lt;/span&gt;                 &lt;span class="kt"&gt;string&lt;/span&gt;         &lt;span class="s"&gt;`json:"url"`&lt;/span&gt;
    &lt;span class="n"&gt;Pages&lt;/span&gt;               &lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;int64&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="n"&gt;Page&lt;/span&gt; &lt;span class="s"&gt;`json:"pages"`&lt;/span&gt;
    &lt;span class="n"&gt;TotalPages&lt;/span&gt;          &lt;span class="kt"&gt;int64&lt;/span&gt;          &lt;span class="s"&gt;`json:"total_pages"`&lt;/span&gt;
    &lt;span class="n"&gt;CoverPageIdentifier&lt;/span&gt; &lt;span class="kt"&gt;string&lt;/span&gt;         &lt;span class="s"&gt;`json:"cover_page_identifier"`&lt;/span&gt;
    &lt;span class="n"&gt;Collection&lt;/span&gt;          &lt;span class="n"&gt;Collection&lt;/span&gt;     &lt;span class="s"&gt;`json:"collection"`&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="k"&gt;type&lt;/span&gt; &lt;span class="n"&gt;Page&lt;/span&gt; &lt;span class="k"&gt;struct&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;Identifier&lt;/span&gt;         &lt;span class="kt"&gt;string&lt;/span&gt;            &lt;span class="s"&gt;`json:"identifier"`&lt;/span&gt;
    &lt;span class="n"&gt;DocumentIdentifier&lt;/span&gt; &lt;span class="kt"&gt;string&lt;/span&gt;            &lt;span class="s"&gt;`json:"document_identifier"`&lt;/span&gt;
    &lt;span class="n"&gt;PageNumber&lt;/span&gt;         &lt;span class="kt"&gt;int64&lt;/span&gt;             &lt;span class="s"&gt;`json:"page_number"`&lt;/span&gt;
    &lt;span class="n"&gt;Metadata&lt;/span&gt;           &lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt; &lt;span class="s"&gt;`json:"metadata"`&lt;/span&gt;
    &lt;span class="n"&gt;FullTextGematria&lt;/span&gt;   &lt;span class="n"&gt;gem&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Gematria&lt;/span&gt;      &lt;span class="s"&gt;`json:"full_text_gematria"`&lt;/span&gt;
    &lt;span class="n"&gt;FullText&lt;/span&gt;           &lt;span class="kt"&gt;string&lt;/span&gt;            &lt;span class="s"&gt;`json:"full_text"`&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The lockers are defined in the &lt;code&gt;lockers.go&lt;/code&gt; file, and the &lt;code&gt;init()&lt;/code&gt; func is what I want to point your attention to next.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;init&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="c"&gt;// Checksums&lt;/span&gt;
    &lt;span class="n"&gt;cslMu&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt;&lt;span class="p"&gt;{}&lt;/span&gt;
    &lt;span class="n"&gt;checksumLockers&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;make&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

    &lt;span class="c"&gt;// Documents&lt;/span&gt;
    &lt;span class="n"&gt;dlMu&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt;&lt;span class="p"&gt;{}&lt;/span&gt;
    &lt;span class="n"&gt;documentLockers&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;make&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

    &lt;span class="c"&gt;// Pages&lt;/span&gt;
    &lt;span class="n"&gt;pageLockers&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;make&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="n"&gt;plMu&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt;&lt;span class="p"&gt;{}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Here, we're registering a couple of &lt;code&gt;map[string]*sync.RWMutex&lt;/code&gt; for the &lt;code&gt;documentLockers&lt;/code&gt; and &lt;code&gt;pageLockers&lt;/code&gt; in the package. &lt;/p&gt;

&lt;p&gt;There are three types; the first is for checksums ; used to take the URL, generate a SHA512 string and use that as the &lt;em&gt;Apario Database&lt;/em&gt; subdirectory to store the structured contents into. Rendered assets are stored here and JSON files written to disk live here. In order to treat the filesystem like this as a database, I needed to have various lockers. A &lt;code&gt;checksum&lt;/code&gt; level locker - for work being done to the &lt;em&gt;root level&lt;/em&gt; of the document record. The &lt;code&gt;DocumentLocker&lt;/code&gt; for per ID records in the &lt;strong&gt;CSV&lt;/strong&gt; or &lt;strong&gt;XLSX&lt;/strong&gt; file ingested.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="c"&gt;// Document Locker&lt;/span&gt;
&lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;dlMu&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt;
&lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;documentLockers&lt;/span&gt; &lt;span class="k"&gt;map&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt;
&lt;span class="k"&gt;var&lt;/span&gt; &lt;span class="n"&gt;DocumentLocker&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;func&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;id&lt;/span&gt; &lt;span class="kt"&gt;string&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;dlMu&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Lock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
    &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"DocumentLocker(%s) Locked..."&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;defer&lt;/span&gt; &lt;span class="k"&gt;func&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"... DocumentLocker(%s) Unlocked!"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="n"&gt;dlMu&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Unlock&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
    &lt;span class="p"&gt;}()&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;_&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;found&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;documentLockers&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;id&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;found&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="n"&gt;documentLockers&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;id&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="o"&gt;&amp;amp;&lt;/span&gt;&lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt;&lt;span class="p"&gt;{}&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;documentLockers&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="n"&gt;id&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;DocumentLocker&lt;/code&gt; variable &lt;em&gt;is a function&lt;/em&gt; that intentionally can be overwritten with a new function of the same signature type. The &lt;code&gt;dlMu&lt;/code&gt; is a &lt;code&gt;documentLockers&lt;/code&gt;'s mutex, different from a &lt;em&gt;record's locker&lt;/em&gt; defined as &lt;code&gt;documentLockers[id] = &amp;amp;sync.RWMutex{}&lt;/code&gt;. &lt;/p&gt;

&lt;p&gt;This pattern allowed me to create lockers for pages that were dynamically belonging to documents in your original &lt;strong&gt;CSV&lt;/strong&gt; or &lt;strong&gt;XLSX&lt;/strong&gt; that was passed into the arguments of the writer when it executed.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="k"&gt;select&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ctx&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Done&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
      &lt;span class="n"&gt;elapsed&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;time&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Since&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;startedAt&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Completed task in %.0f seconds"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;elapsed&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Seconds&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;
      &lt;span class="k"&gt;return&lt;/span&gt;
   &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ch_Done&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
      &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SetOutput&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Stdout&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"done processing everything... time to end things now!"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
      &lt;span class="n"&gt;watchdog&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Kill&lt;/span&gt;
   &lt;span class="k"&gt;case&lt;/span&gt; &lt;span class="n"&gt;id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt;&lt;span class="n"&gt;ch_CompiledDocument&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Chan&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt;
      &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;id&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;Document&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;!&lt;/span&gt;&lt;span class="n"&gt;ok&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="n"&gt;log_error&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"cannot typecast the final result for %s as a .(Document)"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Identifier&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="p"&gt;}&lt;/span&gt;
         &lt;span class="n"&gt;a_i_received_documents&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Add&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
         &lt;span class="n"&gt;log_info&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"a_i_total_documents == a_i_received_documents ; %d == %d"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="n"&gt;a_i_total_documents&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Load&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt; &lt;span class="n"&gt;a_i_received_documents&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Load&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;

         &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;a_i_total_documents&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Load&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="n"&gt;a_i_received_documents&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Load&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SetOutput&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;os&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Stdout&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="n"&gt;log&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Printf&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s"&gt;"Completed processing document %v"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;d&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="n"&gt;ch_Done&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;-&lt;/span&gt; &lt;span class="k"&gt;struct&lt;/span&gt;&lt;span class="p"&gt;{}{}&lt;/span&gt;
         &lt;span class="p"&gt;}&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;I chose to end the &lt;code&gt;main()&lt;/code&gt; func with a &lt;code&gt;for { select {} }&lt;/code&gt; that listens on the background context's &lt;code&gt;.Done()&lt;/code&gt; channel, the &lt;code&gt;ch_Done&lt;/code&gt; channel being written to, or a new completed &lt;strong&gt;row from the CSV or XLSX&lt;/strong&gt; is received compiled via &lt;code&gt;&amp;lt;-ch_CompiledDocument.Chan()&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;I created a variable called &lt;code&gt;a_i_received_documents&lt;/code&gt; to track the total received documents. The &lt;code&gt;a_&lt;/code&gt; is for &lt;strong&gt;atomic&lt;/strong&gt; and &lt;code&gt;i_&lt;/code&gt; is for &lt;strong&gt;int&lt;/strong&gt;, so the &lt;code&gt;atomic.Int&lt;/code&gt; is called &lt;em&gt;received_documents&lt;/em&gt; Once every row has been processed, the &lt;code&gt;struct{}{}&lt;/code&gt; is written to the &lt;code&gt;ch_Done&lt;/code&gt; channel. &lt;/p&gt;

&lt;p&gt;If you've noticed the &lt;code&gt;.Chan()&lt;/code&gt; throughout this, that is the &lt;a href="https://github.com/andreimerlescu/go-smartchan" rel="noopener noreferrer"&gt;smartchan&lt;/a&gt; that I wrote.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;package&lt;/span&gt; &lt;span class="n"&gt;go_smartchan&lt;/span&gt;

&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="s"&gt;"errors"&lt;/span&gt;
    &lt;span class="s"&gt;`fmt`&lt;/span&gt;
    &lt;span class="s"&gt;"sync"&lt;/span&gt;
    &lt;span class="s"&gt;`sync/atomic`&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="k"&gt;type&lt;/span&gt; &lt;span class="n"&gt;SmartChan&lt;/span&gt; &lt;span class="k"&gt;struct&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="n"&gt;ch&lt;/span&gt;     &lt;span class="k"&gt;chan&lt;/span&gt; &lt;span class="k"&gt;interface&lt;/span&gt;&lt;span class="p"&gt;{}&lt;/span&gt;
    &lt;span class="n"&gt;mu&lt;/span&gt;     &lt;span class="n"&gt;sync&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RWMutex&lt;/span&gt;
    &lt;span class="n"&gt;closed&lt;/span&gt; &lt;span class="n"&gt;atomic&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Bool&lt;/span&gt;
    &lt;span class="n"&gt;cnt&lt;/span&gt;    &lt;span class="n"&gt;atomic&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Int64&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;NewSmartChan&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;i&lt;/span&gt; &lt;span class="kt"&gt;int&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;SmartChan&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;

&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;sc&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;SmartChan&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;Write&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;thing&lt;/span&gt; &lt;span class="k"&gt;interface&lt;/span&gt;&lt;span class="p"&gt;{})&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;err&lt;/span&gt; &lt;span class="kt"&gt;error&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;
&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;sc&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;SmartChan&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;Read&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;interface&lt;/span&gt;&lt;span class="p"&gt;{},&lt;/span&gt; &lt;span class="kt"&gt;error&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;
&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;sc&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;SmartChan&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;Count&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="kt"&gt;int64&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;
&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;sc&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;SmartChan&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;Close&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;
&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;sc&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;SmartChan&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;Chan&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="k"&gt;chan&lt;/span&gt; &lt;span class="k"&gt;interface&lt;/span&gt;&lt;span class="p"&gt;{}&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;
&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;sc&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;SmartChan&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="n"&gt;CanWrite&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="kt"&gt;bool&lt;/span&gt; &lt;span class="p"&gt;{}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is used throughout the &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt; and throughout a bunch of other projects that I've worked with. Asking &lt;code&gt;.CanWrite()&lt;/code&gt; on a channel is a task that allows you to build in pipelines when channels become unwritable and then writable. It attempts to remove the &lt;code&gt;panic()&lt;/code&gt; from using channels in Go. &lt;/p&gt;

&lt;p&gt;I didn't want to close out on the piece before walking you through some of the more complex AI generated functions that I did use. At this time, ChatGPT was the utility that I was using, and these functions served their purposes for what they were intended to perform. Given their open source nature, discussing them here is relevant to the context of this piece.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight go"&gt;&lt;code&gt;&lt;span class="k"&gt;func&lt;/span&gt; &lt;span class="n"&gt;nrgbaToRGBA&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;src&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;image&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;NRGBA&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt;&lt;span class="n"&gt;image&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RGBA&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
   &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;src&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Bounds&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
   &lt;span class="n"&gt;dst&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;image&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;NewRGBA&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

   &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Min&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Y&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Max&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Y&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Min&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;X&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt; &lt;span class="o"&gt;&amp;lt;&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;Max&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;X&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="o"&gt;++&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
         &lt;span class="n"&gt;r&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;g&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;b&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;:=&lt;/span&gt; &lt;span class="n"&gt;src&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;At&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RGBA&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

         &lt;span class="c"&gt;// Convert from non-premultiplied to premultiplied alpha&lt;/span&gt;
         &lt;span class="n"&gt;r&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;r&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt; &lt;span class="m"&gt;0xffff&lt;/span&gt;
         &lt;span class="n"&gt;g&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;g&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt; &lt;span class="m"&gt;0xffff&lt;/span&gt;
         &lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;/&lt;/span&gt; &lt;span class="m"&gt;0xffff&lt;/span&gt;

         &lt;span class="n"&gt;dst&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;SetRGBA&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;x&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;y&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;color&lt;/span&gt;&lt;span class="o"&gt;.&lt;/span&gt;&lt;span class="n"&gt;RGBA&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
            &lt;span class="n"&gt;R&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="kt"&gt;uint8&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;r&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="m"&gt;8&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
            &lt;span class="n"&gt;G&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="kt"&gt;uint8&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;g&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="m"&gt;8&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
            &lt;span class="n"&gt;B&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="kt"&gt;uint8&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;b&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="m"&gt;8&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
            &lt;span class="n"&gt;A&lt;/span&gt;&lt;span class="o"&gt;:&lt;/span&gt; &lt;span class="kt"&gt;uint8&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="o"&gt;&amp;gt;&amp;gt;&lt;/span&gt; &lt;span class="m"&gt;8&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
         &lt;span class="p"&gt;})&lt;/span&gt;
      &lt;span class="p"&gt;}&lt;/span&gt;
   &lt;span class="p"&gt;}&lt;/span&gt;

   &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;dst&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A little bot named Red lived in Paint Town. Red loved to help kids make their pictures look pretty!&lt;/p&gt;

&lt;p&gt;One day, tiny Tim brought a clear sheet with colors on it. "I want to show my friends!" said Tim.&lt;/p&gt;

&lt;p&gt;"I can help!" beeped Red. "Watch me make it pretty!"&lt;br&gt;
Red took a white paper and looked at each tiny spot on Tim's clear sheet.&lt;/p&gt;

&lt;p&gt;"When I see light spots," beeped Red, "I make them soft like clouds."&lt;/p&gt;

&lt;p&gt;"When I see bright spots," beeped Red, "I make them strong like rainbows!"&lt;/p&gt;

&lt;p&gt;Spot by spot, Red made Tim's picture. Some colors were soft, some were bright!&lt;/p&gt;

&lt;p&gt;"Wow!" smiled Tim. "Now my friends can see my picture too!"&lt;/p&gt;

&lt;p&gt;Red did a happy beep-boop dance. Helping make pictures was Red's favorite thing!&lt;/p&gt;

&lt;p&gt;The End.&lt;/p&gt;
&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;This application, the first of three in the &lt;a href="https://github.com/ProjectApario" rel="noopener noreferrer"&gt;Project Apario&lt;/a&gt; trio of open source software takes a &lt;code&gt;.csv&lt;/code&gt; or &lt;code&gt;.xlsx&lt;/code&gt; (first sheet only) and processes the structured data &lt;code&gt;RECORDNO,TITLE,URL,PATH&lt;/code&gt; into an &lt;em&gt;Apario Database&lt;/em&gt; that the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; renders into an ultra-fast self-contained web application called &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;PhoenixVault&lt;/a&gt;. &lt;/p&gt;

&lt;p&gt;The original project written was a &lt;strong&gt;Ruby on Rails&lt;/strong&gt; implementation that was built on a Zoom call with a former Disney animator over a 17 day flow state. I have a witness for what I built. DJ watched me built the pipeline in Rails using sidekiq making each of the system calls for each of the steps. When I took a chance on myself over Christmas 2021 to rewrite the Rails implementation that was still costing me over $2,000 per month - even after removing all of the SaaS and going completely in-house private cloud for everything. This meant that I spent a year migrating the external SaaS model that used &lt;strong&gt;MongoDB Atlas&lt;/strong&gt;, &lt;strong&gt;ElasticSearch As A Service&lt;/strong&gt; called &lt;em&gt;ELK&lt;/em&gt;, and &lt;strong&gt;DigitalOcean Managed Redis&lt;/strong&gt; running behind a private cloud built behind ESXi and Rocky 9 Linux with SELinux enabled. I reduced my OPEX from $7K down to $2K per month. That comes out to a $180K savings over 3 years. I wasn't going to keep asking the American people to pay &lt;em&gt;me $180K&lt;/em&gt; to keep the PhoenixVault online for you. Instead, what I built in the trio application, was a solution that can run on an OVH Bare Metal host for $33 per month.&lt;/p&gt;

&lt;p&gt;It's simple. The $33/mo host is sufficient. When you get it, set it up like so:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;ssh &lt;span class="nt"&gt;-i&lt;/span&gt; ~/.ssh/mykey rocky@17.76.17.76 &lt;span class="c"&gt;# replace with your IP address and replace ~/.ssh/mykey with your SSH key&lt;/span&gt;
rocky@ip-17-76-17-76: 
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then you can set it up like so:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;sudo mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; /apario/&lt;span class="o"&gt;{&lt;/span&gt;reader,writer,search&lt;span class="o"&gt;}&lt;/span&gt;/&lt;span class="o"&gt;{&lt;/span&gt;workspace,config,logs&lt;span class="o"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then you can do:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;cd&lt;/span&gt; /apario/reader
git clone git@github.com:ProjectApario/reader.git src

&lt;span class="nb"&gt;cd&lt;/span&gt; /apario/writer
git clone git@github.com:ProjectApario/writer.git src

&lt;span class="nb"&gt;cd&lt;/span&gt; /apario/search
git clone git@github.com:ProjectApario/search.git src 
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then you'll need to render a &lt;strong&gt;YAML&lt;/strong&gt; script for each of the instances that you're running. If your project is called &lt;code&gt;acme-disclosure&lt;/code&gt; then you're have:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;/apario/reader/src
/apario/writer/src
/apario/search/src
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In addition to that, you'll also create a symbiotic relationship between:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;/apario/reader/acme-disclosure/database
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;and&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;/apario/writer/acme-disclosure/ingest
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;such that the &lt;a href="https://github.com/ProjectApario/writer" rel="noopener noreferrer"&gt;writer&lt;/a&gt; &lt;strong&gt;writes&lt;/strong&gt; to the &lt;code&gt;/apario/reader/acme-disclosure/database&lt;/code&gt; path and the &lt;a href="https://github.com/ProjectApario/reader" rel="noopener noreferrer"&gt;reader&lt;/a&gt; &lt;strong&gt;reads&lt;/strong&gt; the same path. The &lt;strong&gt;writer&lt;/strong&gt; processes the &lt;em&gt;flattened or non-optimized PDFs&lt;/em&gt; from the &lt;code&gt;/apario/writer/acme-disclosure/ingest&lt;/code&gt;. &lt;/p&gt;

&lt;p&gt;This is useful for &lt;em&gt;ACME&lt;/em&gt; (a fictional company) to release a &lt;em&gt;disclosure&lt;/em&gt; of information in the form of a PDF dump. It's common with documentation and with OSINT practices. For the context of the JFK files from the National Archives, I wrote the writer to ingest &lt;em&gt;those files&lt;/em&gt; into a useable format that I ended up writing a consumer for. &lt;/p&gt;

&lt;p&gt;This is the first of three binaries and the project is &lt;em&gt;incomplete&lt;/em&gt; because of &lt;em&gt;life.&lt;/em&gt; When the time comes to dust off what I have built and continue the torch, the time will come. Until that time arrives, I type to share what I learned so that the youth can pick up the torch. &lt;/p&gt;

&lt;p&gt;The vision that I had as a child wasn't for me alone to experience. It was for the world to discover the beauty that dwells within and how technology helps us understand the complex reality that we live inside. 💜&lt;/p&gt;

</description>
      <category>discuss</category>
      <category>opensource</category>
      <category>architecture</category>
      <category>software</category>
    </item>
  </channel>
</rss>
