The tldr; is at the bottom, after the story mode writeup. Feel free to CTRL+END or hyper-scroll your way there, or read the machinations of my troubleshooting on your way there.
As a warning, this is long. I mean, it would have to be, really, because it's about an ERP project.
ERP stands for Enterprise Resource Planning, and ERP systems are designed to function as "systems of truth". They are meant to be the accounting system that a business uses for tracking costs, inventory, sales revenue and all other accounting-related data. From ERP data reports can be generated that satisfy audit requests, provide revenue and profitability statements for creditors or show sales trends for products and product lines.
As SMBs grow they often find that their needs for systems that encapsulate more processes or perform a specific function better change. In the course of growth the needs may change multiple times. Some small businesses might start out with a basic accounting program like QuickBooks and only record the bare minimum of financial transactions while some might use it for inventory and BOMs (Bills of Material). Some company might hang onto a mainframe from the 80's because it meets their needs until they start to expand sales to the direct to consumer (D2C) channels.
Manufacturing Company 1 (AKA MC1) did that, they held on to their HP MPE mainframe for many years. It was a great system. It was usually very responsive, it was exacting in the data it provided. It was a common platform for many years. It was this good because it required diligence in programming. You had to program nearly everything on a regular basis, like:
The number of days each week
The number of weeks in each month
The number of months in each quarter
The number of quarters in each year
Which days were holidays (ex. if January 1st is a holiday and the fiscal year started on Sunday, December 29th, 2025 you would program day 4 as a holiday)
The numbers available for transactions like invoices (ex. start with MPE0000001, the program would only accept up to so many, so you would populate the list and remove used ones and replace with new available numbers from time to time)
Each report had to specify the format of the data (CSV wasn't a known format, so you would specify something like "field <comma> field <comma> field")
etc.
Everything was programmed in a very manual way. It was a great system, but it was not meant to accommodate larger datasets or large amounts of transactions. It's a batch processing system like all mainframes, not a real-time processing system, so transactions, commands, reports, functions, etc. would all be queued with a priority. This is fine as long as users (or "operators" as they used to be called) were cognizant of what they were running.
Did Accounting mistakenly run a really big report program? Welp. now shipping has to wait for their shipping documents to print when it's done.
Did someone accidentally write a program that loops? Time to call IT to have them manually kill the process.
Did you use an intermediary service to start loading D2C sales from Amazon? Welp, it might take a while to process those 500 transactions a day.
I think you get the picture. Batch processing. Everything goes into a queue.
Aside from those points, it's also good to keep in mind that most systems like this were not very extensible by today's standards, meaning API and, in some cases, EDI. This is why it's still common for systems like IBM's AS400 to function more like a back-end for a bank while employees perform transactions and interact with the system primarily through other software interfaces that communicate with the AS400 to send and receive those data and commands.
MC1 had already started "patching" transactions in from a web interface that they used for their B2B transactions. It relied on FTP to send and receive data for sales orders. Managing sales orders in MPE was not difficult, but it was limited on what data it could display at a time, and if your sales order had 200+ lines on it you'd be spending a hour moving back and forth between pages trying to find the 1 line you needed to update, but in a more modern web interface you can just scroll or use the browser's built-in CTRL+F to find what you're looking for. So at scale within a sales order MPE had some pretty severe limitations.
And if you start adding hundreds more transactions a day the queue gets longer. The size of the transactions makes the transaction take more processing time, etc.
As MC1's business started to thrive, their reliance on MPE was showing them they had a functional limit.
Enter Nate, IT Wizard. I knew there were ways to work around the issue. Other organizations used the same or similar mainframe, but they had more modules, more programs written and other systems holding and pre-processing data before it went into queue. I also knew that the MPE platform was not nearly as prevalent as IMB's systems were, so there were fewer off-the-shelf and fewer contractor options. In fact, one of the biggest issues on the horizon is that some of the contractors MC1 had been using for years were dying or old age.
There were some options discussed with some vendors, but they were pricey to implement, pricey to maintain licensing for and would require a lot of code maintenance. But wile MC1 was growing due to product popularity, the processing scale curved much slower than the transaction scale, mostly due to some automations we put in place at nights and weekend. Some sales like Amazon would be done on the weekends or at month ends instead of during the business day. Other orders like those from Shopify stores were also processed in batches.
But with D2C growing the dependance on batch-processing orders was becoming a hindrance. And the only ways to speed it up were to drop elements that would become questionable during audits. So we needed another solution. Preferably a solution that didn't require a lot of annual licensing, one that was in the cloud instead of located at a physical plant (which had periodic electrical and internet outages, thereby making it inaccessible to other branches).
I engaged with multiple vendors to find a solution that fit the bill, the bill being cheap. Most mainstream options looked great, but MC1 was didn't like the idea of $50,000+ just for licensing, plus support, plus code changes, plus whatever else a vendor would charge for.
Enter ERPNext. Extremely customizable, flexible and extensible. It was simple to install and maintain and used JavaScript, Python and MariaDB as the primary operating languages. And it was free because it was open source. It had an active community supporting and enhancing the platform, and the framework had all sorts of features that MC1 had never had before like CRM, HRM, training modules and more. It looked like the perfect solution.
So late in 2019 we signed an SOW with our vendor of choice and dug in.
Now might be a good time to mention that MC1 had tried to move to an ERP several years before I arrived, but the project was a massive, expensive failure. MC1's business processes were not a great fit for a lot of systems, but in retrospect they might also have been trying to incorporate too many processes in the system. I think this now largely because of all the meetings where it seemed that the expectation was that ALL processes should be in-system and that they didn't want to do ANYTHING manually again. I will admit now that I didn't understand that for what it was when I was managing this project, but also allow myself the understanding that it's always easier to point the finger later and identify a contributing factor to complications and failures.
Discovery was started in earnest. A wonderful project manager (we'll call her "A") from the vendor was assigned, and we clicked immediately. We spent 2 weeks going over the systems, processes, data & workflows that I was involved with, then proceeded to loop in Accounting, Operations, Manufacturing, all 5 Sales departments, Warehouse, Logistics, Marketing, eCommerce, Purchasing, Product Development & HR. For most teams we spent multiple sessions going over processes, pain points, needs, wants, etc., after which I would convene with the PM and engineers with the vendor to discuss our findings and prioritize the requests.
This initial discovery took weeks. And our findings were frustrating. There was not uniform process for the sales teams or product manager teams. They all did things differently, and not "we use these vendors instead" different, more like "we don't include these labels on the BOM because it's a hassle" or "we use a vendor to print those instead of doing it in-house" differently, even if the base product was the same, but was just marketed to a different vertical.
Each team had different SOPs, or none at all, or had conflicting SOPs for the same process. Some had underreported labor cost because they saved $0.0001 per unit but importing them in larger packs as a component, but then relied on warehouse teams to rework the product into smaller packages.
There were regular allocation issues for popular products which led to different teams fighting for it, mostly related to poor forecasting processes (which only existed for about 75% of sales). One team even acted more like a distributor and "bought" the products from another team at a markup, then "resold" the products to their customers with a completely different pricing model than the rest of the company.
None of those examples are dealbreakers. None of them are insurmountable. All of them could be dealt with, and there were many more examples of similar patterns of differences and non-standard SOPs that happen when an organization allows each department to essentially operate as it's own company. But modern ERPs can accommodate that type of fracturing, most of them pretty easily. You can set up separate workflows by department or team. Or you can set up each as it's own company within a larger company umbrella. Issues like this can complicate & delay ERP projects, but they are easily worked through with experienced program managers like A & I were.
What's the biggest challenge and most common defeater of an ERP deployment you ask?
Apathy. Stakeholder apathy, to be more specific.
Similar to the issues I encountered when migrating MC1's data to the cloud, stakeholders and many managers didn't want to make decisions or would make decisions that were directly in conflict with the rest of the organization and/or the way the ERP would operate. Stakeholders even decided to deprioritize forecasting, which had downstream effects on MRP & MPS, warnings about which were ignored and downplayed.
When attempting to validate the formula for MRP the Purchasing and Operations teams made so many changes that the results were unrecognizable and unusable. When I called on them to take it back to basics, validate the numbers and then add in some formula changes slowly, they couldn't even understand how the formula "Demand - Material on Hand = Need to Purchase" worked.
The VP of the largest sales team delegated all ERP-related meetings to their direct subordinate, who took an entire year to go over the sales module with their team. A year to provide feedback, even with weekly stakeholder meetings on progress.
The eCommerce team was on top of it, and even assigned one team member to become an expert on the ERP and help to define the workflows and processes for them.
Another team entirely attempted to "opt out".
Accounting was onboard and actively participating, but was having a lot of trouble working out details needed for the GL accounts, let alone provide the correct mapping for different transactions.
At one point, even though I was program manager, I had to get the president to tell the stakeholders that I had total control of the project and they were expected to contribute to the effort.
Towards the end of the project my raise and bonus were being delayed until this was completed, which was something I understood conceptually, but argued against because the issues lay less with my abilities and more with the reluctance of the stakeholders.
After about 2.5 years, I decided that enough was enough. The vendor was hurting because some of their payments were assigned to milestones, I was hurting because my financial future was tied to the launching of the platform and we were all spending ungodly amounts of time on this, while other areas under my purview were starting to suffer from lack of attention.
So, as it was finished "enough" and perfection was nigh impossible with the stakeholders' participation being what it was, I launched.
And it worked.
Nothing was broken.
Sure, there were a large number of processes not yet implemented, but most were 75%+ done and the outstanding work was reliant on the decisions of one stakeholder or another.
EDI services were tied in via a service that did direct translation and communicated via API, Amazon was tied in via API, several Shopify instances were tied in via API, other internal services were tied in via API.
Sales orders flowed and were processed. Products were manufactured and prepared for shipping. Reports were working and providing new perspectives on data. Accounting...took some time to adjust to performing their tasks in a new system. Leadership had better, faster access to data than ever before.
So yes, it was a success, but...
What was missing? A few key things. Forecasting, primarily, as teams historically spent about 3 months manually curating data in spreadsheets each year to generate a forecast, but they weren't' ready to allow a system to help with that process, even though it was capable of doing so.
Because forecast was out, and the very formula of MRP was, let's be generous and say "up in the air", MRP + MPS were out. Both of which were...you know...pretty critical for managing purchasing and manufacturing.
These things can absolutely be calculated manually, and they were for several months, but they should not have been. When budgeting time came around there were very distinct discrepancies between the system generated forecast and the manually curated/created forecast. They differed on most raw materials and core products with pretty wide swings in both directions.
A couple of years later we were able to look back and see that the system was more accurate than the manual data was, but that came at the opportunity cost of a lot of sales we didn't make because MC1 opted to trust the people manipulating the data in ways that fit their preferred narrative rather than the system that only cared about counting.
I spent a lot of time after launch refining nearly every aspect of the ERP:
Adding in soft allocation in order to accommodate the way warehouse decided they were going to use the system
Building a Data Analytics team to generate reports that required a lot of data from several sources
Building an ERP Dev team to bring most code changes in-house
Further automating month end processes for Accounting, virtually eliminating their weekend workloads at the end of each month
Adding in new business units that came from acquisitions
Making the Trial Balance report for leadership and Accounting automatic
So a success, but at much higher cost than expected due to reluctance to make decisions and participate in the process by stakeholders. A total time of 2.5 years, during which A & I both pulled and pushed MC1 and its stakeholders through the entire process.
There were many lessons learned from this experience. I believe the most important ones were:
Mandate a larger ERP transition team
Mandate a dedicated training team
Disallow lack of participation due to apathy
Fight harder about onboarding an internal ERP Dev team earlier in the process
Onboard dedicated SMEs for core aspects like Accounting, Sales & Manufacturing
Fundamentally, I think "Doing an ERP on the cheap" is a bad idea, and as MC1 had that mindset they were vulnerable to delays and cost overruns. For myself, I took these lessons hard, and a bit personally, because I had asked for most of them, but was denied. I do not believe I would accept "No" as an answer to them again in my career.
tldr; "Doing ERP on the cheap" is much more expensive and time consuming than spending the money on SMEs and allowing insufficient participation from stakeholders results in delays.
Total cost: ~$1,500,000 + much of my brown hair color