Live data from Hacker News

Your DI framework is killing your code

blog.activelylazy.co.uk

51–59 of 59 posts

Re: Your DI framework is killing your code

#51
I don’t think the author completely understood the DI frameworks. Just because a service in a DI framework is often a stateless singleton doesn’t mean they don’t allow stateful injection: EntityManager for JPA is a great example. Sure, there are other services with absolutely no state, but don’t blame the frameworks for promoting statelessness, it’s a practice promoted by many other software designs e.g. REST. I believe I have enough experience to say that state replications in a clustered environment does not scale and is not worth the pain.

Order.SubmitForPicking() sounds great on paper, that’s until you realize in order to submit an order for picking, you’ll need other value objects such as Customer, Account, Warehouse, Picker, Robot, Supervisor, Audit information …. the list goes on and on. How are you going to inject these info into an Order? And do they really belong in an order? I certainly don’t want to see all of these info in my JSON when I retrieve a single order on the client side.

The moment you move behaviors close to a value object is also the moment a plain object is no longer a plain object. Furthermore, a behavior laden value object becomes hard to evolve, extend and modify. There’s no clear boundary of where data ends and behavior begins, you certainly cannot package them up as a library and give it to your clients, you’ll have to create a separate set of value objects for that and start a maintenance nightmare.

It's kinda sad that Java Code Geek rejected my comments (and many others') and we have to come to Hacker News to express our views.

Re: Your DI framework is killing your code

#52
post #6

Yet another time it comes up. But now, after functional programming being commonplace, we at least know the answer to the "why" question. Consider the "classical OOP" method signature: email.send() vs "the anemic way" emailSender.send(message: Email) If there is only one way to send email (SMTP), things works fine. But let's assume we have to implement another way (e.g. Mailgun API). In the "anemic" case everything i…

Excellent summary. What an oop language like Java really needs these days are immutable value classes.

did you read the blog post even ? He was calling for mutability in the classes and for the state to be closer to the data object itself.

Re: Your DI framework is killing your code

#53

"Almost certainly: if you’ve got value objects and noun-verbers, your design is rubbish." If the code is readable, understandable, testable, and it does the job - who are you to say it's rubbish?

I think the problem is that OO is a term that people don't understand anymore. The author is right about OO principles and the fact that most people don't follow the traditional usage. The thing is that good OO isn't actually good code. The world has moved away from strict OO because it's not very maintainable.

I've been seeing quite a lot of this kind of "OO reactionary backlash" recently, "... is an anti-pattern because OOP". Most of it already years old, but still something that feels like a little trend suddenly showing up in links left and right. Could be a sign of the last "pure OO" advocates starting to feel the pressure, or it's just me googling the wrong topics...

Re: Your DI framework is killing your code

#54

"One of the properties of good OO design is that code that operates on data is located close to the data." Says who? I say the point of good OO design is to have very clear focused responsibilities for classes, very clear layers of abstraction, and concretely declared dependencies. This way I know my business logic doesn't sprawl, is discoverable, can be replaced modularly, and tested extensively and throughly. This…

Sorry to nitpick: the point of OO is exactly what the original rant was advertising: compile your domain representation into furry little blackboxes that live inside the computer and interact with each other. Your point (and the HN hivemind consensus, because even the FP purists will agree) is that OO tools are better used in ways that do not follow the OO design principle.

Re: Your DI framework is killing your code

#55
For me anemic model is much more natural and easy to use. Object-Oriented Programming is not a good approach to a general architecture. It has its place in some layers, e.g. GUI API usually can be successfully modeled with OOP, but otherwise just use modular procedural approach and use object-oriented constructs very conservatively, unless it fits naturally. That's the best approach for me and it works flawlessly. Of course Functional Programming, Logic Programming has its place too, thanks to modern languages like Scala, where you don't have to choose the only one paradigm.

Re: Your DI framework is killing your code

#56
post #6

Yet another time it comes up. But now, after functional programming being commonplace, we at least know the answer to the "why" question. Consider the "classical OOP" method signature: email.send() vs "the anemic way" emailSender.send(message: Email) If there is only one way to send email (SMTP), things works fine. But let's assume we have to implement another way (e.g. Mailgun API). In the "anemic" case everything i…

> The "anemic way" had won because it is much more reusable and maintains API stability. Incidentally, this approach have smoothed the transition to functional languages — "NounVerber" objects became modules (collections of functions), and value objects became immutable data types.

I agree. By the way, you can do that even in imperative languages. I do it all the time in Python or Go.

Re: Your DI framework is killing your code

#57
This seems to be a complaint that some code doesn't correspond to the author's notions of "good" OO code, without a clear picture of what "good" OO code is except for a few vague references to fidelity to the domain without much discussion about what good domain modeling is.

For me, one of the clearest ways of analyzing a system in domain terms and working with it with business users to is with technology neutral specs in something like a Yourdon-style DFD, with a supporting data model and process descriptions.

It then becomes clear what the relevant nouns are in the domain: they fall in two basic groups:

(1) entities that correspond to named data items shown in flows or stores on the DFD (which will also, of course, be represented in the data model), and

(2) entities that correspond to named boxes and bubbles on the DFD, particularly processes, stores, and external interfaces.

A system whose implementation maps closely to this kind of requirements specification is a lot like an anemic data model system, with most of the classes being either immutable data objects or process objects (the latter of which may have "NounVerber" names if that convention is used), but that's because the processor is a real noun in the domain -- in a non-automated implementation of the system, its a role that a human actor would take on in executing the business process.

You do end up with state stored in (or stored externally and managed by) objects with methods which mutate state, but these tend to be the processor objects and the stores, not the data objects that are transferred along flows.

It seems to me that the "rich domain model" approach is mostly a failure of domain modeling that apply ideas from OO's origin in simulation modeling without recognizing that, in most other domains, the analogy to simulation modeling only works if you recognize that applications tend to be "simulations" of an idealized process executed by idealized technology-neutral actors acting on abstract data constructs, and that those idealized actors -- the processors -- are key elements of the domain model. Rich domain modeling ignores those and attributes their behavior somewhat arbitrarily to data objects, which end up giving data objects multiple, tangentially-related responsibilities (and provides lots of rooms for debating where certain responsibilities belong.)

Re: Your DI framework is killing your code

#58
post #46

I wonder if the author has ever worked on any relatively large projects. This has to be the worst way you can write your code. I know I wouldn't like working on anything written in that way. That's how you end up with 10,000 line files.

The anaemic way would turn that 10,000 line file into something closer to 10,000 one-line files. To me, that is the very definition of spaghetti code.

My biggest problem with the enterprise Java way of doing things is the fact that you have to open 18 files just to figure out how the hell one small bit of functionality works.

Re: Your DI framework is killing your code

#59
post #18

"One of the properties of good OO design is that code that operates on data is located close to the data." Says who? I say the point of good OO design is to have very clear focused responsibilities for classes, very clear layers of abstraction, and concretely declared dependencies. This way I know my business logic doesn't sprawl, is discoverable, can be replaced modularly, and tested extensively and throughly. This…

Well, encapsulation was one of the three legs of the OO stool, especially at a time when languages like C/C++ offered no protection against reading/writing memory anywhere in a program's data or code segments. Encapsulation back then literally meant keeping the representation of the data close to the code, i.e. in the same class that implemented the interface on the data or a closely-related specialty class. So I wou…

OO concepts live on whenever we are talking about interfaces, contracts and the like. The failed experiment is "true" object oriented domain modeling, the idea that software representations of real entities (an order, a dog, a car) should include code beyond maybe some basic constraint checking. Other than that, thehe OO tools are still powerful and some form of encapsulation is essential for any data structure that is more complicated than a pain array or a one-way linked list. But these structures are not representations of real objects, they are actual data objects. A hashmap isn't a representation of a hashmap, it is the real thing (even if it maps representations of dogs to representations of cars).
Post reply on HN