That's nice article. YO anime fan here🔥😁😃
Great article is rare see people showing SOLID with functions (in not a functional way), but there are few things wrong.
The OCP is wrong, in that example you aren't extending the base object, you're modifiyng it soo breaking the OCP.
A better approach is pass objects tied by the same contract instead of an object with a type property, as in this way you'll be using polymorphism to handle the dynamic dispatch instead of implementing coupling a function to an object.
In the LSP example you're breaking the principle too. Your example makes the function depend on a union type, but the LSP is a complement to the DIP as the goal is make the sub-types behave like the base types, and a sub-types are intersection types not union types.
By making the sub-types behave like the original you can pass they interchangeably without the need of a caution because if one thing exist and behave in the base, It is the same in the sub-type. A union type goes in the oposite direction by making a function depend on a value that can be different.
Other approach you could do is in the function type instead of the param type, by applying the ideas of contravariance and covariance.
And the DIP example is good, but instead of implementing a interface-like mechanism, you could just made the function depend of other function, this effectly could have made the function depend on other abstract thing that is other function signature.
The notify function still breaks the principle as it is coupled with the function that gets the contact, that is a concrete module, receiving that as a param should fix this.
Can you reference an article that does it correctly in JS?
Uchenna Egbo Sorry, but i don't know any. But i doubt that are some there, because some principles are incompatible with procedural programming due to require the use of polymorphism.
You can apply the SRP because code cohesion is a principle thats possible in every paradigm that allows some form of logical grouping such as procedures, functions, modules, classes, objects, etc.
The SRP is just apply cohesion in the code, if 2 things change for the same motives, they are likely to be together.
OCP its a direct application of the polymorphism soo its not possible do in procedural programming, its possible apply It with functions but you'll need to use functional programming instead, as any high order function probably comply with the OCP.
Maybe you can arguee that creating various atomic functions that really do they job and only they job really well, and do some form of composition with them somewhat applies the OCP, but i think this is a bit forced.
The LSP and the ISP while cannot be applied directly to functions (in the procedural paradigm, not in the functional), If the language has some form of way to create typed structured data like the type in TS or the structs in C, you can make the argument that the Liskov sub-type definition can be applied here even If isn't the real intent of the principle, while the ISP can somewhat be applied to the creation of new types too.
The DIP isn't appliable too because in procedural programming you are always tigh coupled with the functions soo isn't possible to make a function not depend of something abstract because all the functions are concrete.
Love the article! Especially the anime cover!!!