A Case of the MUMPS (2007)
thedailywtf.com
thedailywtf.com
”Early MUMPS memory partitions were limited to 2048 bytes so aggressive abbreviation greatly aided multi-programming on severely resource limited hardware, because more than one MUMPS job could fit into the very small memories extant in hardware at the time. The ability to provide multi-user systems was another language design feature. The word "Multi-Programming" in the acronym points to this. Even the earliest machines running MUMPS supported multiple jobs running at the same time. With the change from mini-computers to micro-computers a few years later, even a "single user PC" with a single 8-bit CPU and 16K or 64K of memory could support multiple users, who could connect to it from (non-graphical) video display terminals.”
(https://en.wikipedia.org/wiki/MUMPS)
How would you design a programming language that operates concurrently on a large shared database with just 2 kilobytes of scratch memory available for each process?
Oh, and the CPU to execute these concurrent jobs clocks at 0.5 MHz, and Unix won’t even be invented for another five years, so your implementation will of course be in machine code. You’re practically designing the operating system as part of the language.
It’s fascinating and somewhat horrifying to think that a system designed for this bygone era still survives in its own special vertical.
https://www.intersystems.com/cache/
>It’s fascinating and somewhat horrifying to think that a system designed for this bygone era still survives in its own special vertical.
Why is it horrifying?
https://www.healthcareittoday.com/2017/02/21/denmarks-health...
https://ehrintelligence.com/news/uk-epic-ehr-implementation-...
Recovering from that particular 'oopsie' cost me a day and a bit, part of which was to write a rudimentary editor, without an editor. I think I got some apple pie out of that one :) I don't regret having seen the last of 'MUMPS' but it is very persistent and in healthcare and insurance you still come across it every now and then.
Mumps has some interesting aspects though, one of these is that it raises evaluation of expressions to a way of life, and in that sense it is closer to a functional language (but with statements, if that makes any sense) than your typical interpreted language from that era, which had strict barriers between code and data.
And just like predicted it’s utter dogpoo now that it’s being deployed, and has already caused a bunch of health hazards and people quitting due to its impossibly bad and confusing interface.
You can guess will it be cheap to fix it now, as it probably was delivered up to the waterfall spec, and there is that one company in the world that owns the code and can change the software.
Worst case of corruption I’ve seen, in a country where its a saying we don’t have corruption.
Edit; just going to link one of their docs https://learning.intersystems.com/course/view.php?id=417&sso...
I didn't even entertain the idea; I was aware of Epic's reputation and their awful software. Not to mention I might have had to move to their state for the job.
Since MUMPS interprets source code by context, there is no need for reserved words. You may use the names of language commands as variables, so the following is perfectly legal MUMPS code:
GREPTHIS()
NEW SET,NEW,THEN,IF,KILL,QUIT SET IF="KILL",SET="11",KILL="l1",QUIT="RETURN",THEN="KILL"
IF IF=THEN DO THEN
QUIT:$QUIT QUIT QUIT ; (quit)
THEN IF IF,SET&KILL SET SET=SET+KILL QUIT
MUMPS can be made more obfuscated by using the contracted operator syntax, as shown in this terse example derived from the example above:
GREPTHIS()
N S,N,T,I,K,Q S I="K",S="11",K="l1",Q="R",T="K"
I I=T D T
Q:$Q Q Q
T I I,S&K S S=S+K QThis snippet just sets a few variables before returning "R" if the function was called in a functional context, or quitting with no value if the caller doesn't expect a value.
Since "K" is a non-truthy, but non-null value, "l1" is never added to S in the T label. "l1" is another non-null-but-false value, so S wouldn't have changed value anyway. The entire thing is just an ugly looking no-op.
Also does anyone remember MQL ("Medical Query Language")? It was a way for doctors to write queries on the MUMPS database. As I recall it was totally imperative (unlike SQL) so basically any query started with an outer for loop over patient records. Any query even slightly complicated involved nested loops and the associated O(n^k) performance.
Edit: Found a paper describing MQL: https://www.ncbi.nlm.nih.gov/pmc/articles/PMC2578357/pdf/pro... which includes this example:
10 FOR EACH PATIENT ; WHEN PRIMARY MD IS SMITH
20 WHEN DATE AFTER TODAY-1 YEAR, DIVISION IS DX, CODE IS TUBERCULOSIS
30 LIST NAME, UNIT NUMBER, DATE, STATUS
(To be fair this is far more approachable than writing the equivalent in raw MUMPS)But reading this reminds me of my favourite article there: https://thedailywtf.com/articles/itappmonrobot
It has an odd beauty to it.
The problem I have, though, is their “set it up and knock it down” style of storytelling. It gets old, fairly fast, and once you’re over it you’re just constantly hunting for the actual meat of the story. The actual development WTF.
I don’t care that Grunthilda was a seasoned developer who had recently taken a job at a mediocre teapot manufacturer, whose boss was idiosyncratic and kept shouting “the shorter the better”. I don’t care if Francisco had just started his second job within an up and coming banana republic and all of the other developers has warned him against naming variables starting with a vowel.
Just tell me what off the wall programming mistake they were making.
However, these two facts put together mean that date-keyed associative arrays are always ordered from earliest to latest, and for reasons that I've forgotten, it was at least at one point inefficient to use the MUMPS facilities for reverse traversal of the associative arrays.
The solution? Defining another date format, which is `121531 - $d` where `$d` is a value in the standard MUMPS date representation. This was then used instead of or alongside the standard representation for indexing associative arrays.
Practically, this was a huge hazard for code correctness as you needed to be absolutely sure of which format the date number was in. This additionally marks Monday, September 27, 2173 as the festive occasion of date sorting doomsday, as it is the date on which the secondary format would cross over into negative values and probably start causing all kinds of subtle bugs throughout the system. Let's hope we will have moved on to better systems by then!
Dealing with simultaneous crashing patients and crashing EMRs is a challenge. Daily popups notifying me of out-of-bounds index errors or [insert memory safety error] that I've given up screenshotting and sending to IT, because none of them know MUMPS either. Can't order a critical medication or view the result of a critical lab result because EHR is crashing again...
In spite of at least basic familiarity with bash, python, go, rust, nix, and having at least looked into Haskell, Common Lisp, and a few others... the few snippets of our EHR's backend MUMPS I've seen completely unintelligible to me.
My understanding is that the bus factor for vast swaths of our EMR infra is ~1.
It's terse. Language commands can be abbreviated to one letter, and the syntax is whitespace-aware, so you can fit a lot of code on one computer screen, take it in, and review it.
If you're curious, I wrote a tutorial for it at https://learnxinyminutes.com/docs/m/
However, as I say don't really disagree. If you're pretty sure you "settled" because of lousy market conditions, at least be ready to start looking if things stabilize or start to turn back up.
However, casually browsing through job openings while you already have a satisfactory job is a lot less stressful, and easy to recommend.
That's why you need to look around, question things
I've been guilty of being interested in some needlessly complicated things, but not up to this point, and I could smell the BS from afar
Also staying in one place/one camp means career death (or grave disease ;) ) sooner or later
MAGIC relies on the Operating System Abstraction Layer (OSAL) to run MAGIC on top of Windows. It's almost like a stub, but when you boot the Windows box up it'll boot up, auto-log-in, and dump to a full screen OSAL console waiting for you to IPL the OS with various commands (like SCSI PLEASE to list boot devices).
Networking within OSAL (and in turn MAGIC) is performed by a protocol add-on in Windows attached to the NIC -- it itself handles the rest of TCP/IP itself in usermode once IPL'd.
I'm a former caretaker on a team that had a MAGIC system for historical data -- we moved onto 6.x from there, and then I moved on from healthcare IT at that point.
M, or MUMPS is a procedural language with a built-in NoSQL database - https://news.ycombinator.com/item?id=19388048 - March 2019 (2 comments)
MUMPS - https://news.ycombinator.com/item?id=18936990 - Jan 2019 (6 comments)
Introduction to the Mumps Language (2017) [pdf] - https://news.ycombinator.com/item?id=16309237 - Feb 2018 (42 comments)
The Mumps Programming Language - https://news.ycombinator.com/item?id=13859961 - March 2017 (178 comments)
MUMPS Instance - https://news.ycombinator.com/item?id=13618649 - Feb 2017 (1 comment)
Ask HN: Encryption and Security in MUMPS - https://news.ycombinator.com/item?id=13542953 - Feb 2017 (4 comments)
50 year old NoSQL DB that is better than MongoDB - https://news.ycombinator.com/item?id=12791425 - Oct 2016 (2 comments)
MUMPS, the Archaic Health-Care Programming Language - https://news.ycombinator.com/item?id=9895311 - July 2015 (49 comments)
I am a MUMPS programmer – Ask me anything - https://news.ycombinator.com/item?id=6312391 - Sept 2013 (68 comments)
Right. MUMPS has a key/value store where values can contain more key/value pairs. You can thus construct arbitrary trees. It's possible to hang new data items onto arbitrary places in the tree. Like JSON and XML. This is useful for medical work, which doesn't fit well into the SQL model. MUMPS eventually got transactions and ACID properties, so that multiple updates to the database interlocked properly.
If you needed that kind of data storage today, what would you use?
So, although NoSQL is a familiar framing, pre-SQL is a more appropriate designation for MUMPS, since NoSQL was a response to SQL.
The tree data structure used by MUMPS is specifically a B-tree. This is a standard data structure and doesn't on its own give MUMPS much to brag about over other DBMSs which offer B-trees. MySQL offers B-trees as an indexing option, for instance.
I kept working with MUMPS, although it became much more Caché ObjectScript over the years, until this March.
I’ve moved on to doing other things now, but I can see myself absolutely going back to it. But not until I’m much older.
It’s cozy, it’s comfortable and it does so many complicated things just more easily than so many other programming environments. The only thing I won’t miss is the complete lack of strict typing, a charge that can be laid on many other programming languages too.
The company in question is Epic Systems, maker of very popular medical records software.
So yeah, be worried.
Medical software dev in the US is a dumping ground for the under-qualified or people looking to coast the balance of their career.
The only answer is automation, and in a safety critical role like healthcare, automation has to be done with great care.
But from Epic and the higher-ups (who have to defend their expensive acquisition), it's always the same reply even to the most concrete of criticism: you just don't like change! At some point it really moved beyond just a bad excuse and became victim blaming.
(Please know that the context here - and I think in our neighbouring countries as well - is not that there was no automation, rather there were a set of mostly functional solutions in each region that were replaced by a single top-down mandated country-wide system. There was a book published recently about the process that led to the implementation of Epic's system from which I did not get the impression that this was based on merit as much politics.)
From what I understand, getting to that point required a huge amount of effort on the provider's part (many thousands of hours of contractors configuring systems deep in the bowels of hospitals or data centers). But that's not surprising: anything regarding health and IT in the US eventually grows to consume our entire economy.
Looking back I can see why post-processing SQL query results using a procedural section at least gives you an escape hatch to do business reports or other iterative tasks.
I don't miss it, but I can see why CCL was designed and written at the time.
It shows up in financial companies a bit.
Those fuckers are well aware of their captive markets and extract rent like no other. The licensing costs on such an outdated piece of technology are obscene.
They're in "good" company. Do you think its less obscene to pay the horrendous license costs to companies like Oracle or SAP?
Anyway, I'm talking about the technology, which btw. has established open source alternatives. I once had an argument with the main person in charge of hospital IT, and he made it clear that he didn't want to risk his good sleep by using technology from non-mainstream suppliers, no matter what the cost. As long as we allow such people to value their personal sleep quality over the cost to the health care system, we need not complain about the consequences.
If you don't depend on the MUMPS/ANSI-M language or don't have to be backwards compatible, a lot more alternatives with similar features are available, e.g. https://github.com/facebook/rocksdb run behind e.g. Node.js.
He had said that they had their star-programmer there who could dash out complicated MUMPS data queries in very short order. My friend said he had some fun programming in it, but he left the telemarketing company to move on to more conventional programming languages.
* Most of the non-M/MUMPS code is now written in C# with a TypeScript/JavaScript web front-end. The M stuff is all database stuff and VB is pretty much gone.
* The toolchains used to manage M code and work around all the complex idiosyncrasies of the language are vastly improved and abstract away a lot of the pain of working in it (that isn't directly the result of the language itself, of course).
* The cleverness has gone off the charts, and so has the insanity. (The company tried to force all developers to work in-office during COVID until the county told them to stop it.)
Or so I've been told.
https://www.intersystems.com/news/intersystems-iris-data-pla...
Programming is Hard, Let's Go Scripting... https://www.perl.com/pub/2007/12/06/soto-11.html/
> BASIC
> Now, however it was initially intended, I think BASIC turned out to be one of the first major scripting languages, especially the extended version that DEC put onto its minicomputers called BASIC/PLUS, which happily included recursive functions with arguments. I started out as a BASIC programmer. Some people would say that I’m permanently damaged. Some people are undoubtedly right.
> But I’m not going to apologize for that. All language designers have their occasional idiosyncracies. I’m just better at it than most. :-)