Is having only one class in a package a code smell? - java

Is it a bad practice to have a package with only one class in it? Would it make more sense just to move the single class to a util package that would contain other random useful classes?

Is it a bad practice to have a package with only one class in it?
Not necessarily. It could be a sign of somebody getting obsessed with classifying things. On the other hand, it could just be a logical consequence of a sensible general classification scheme applied in an unusual case.
An example of the latter might be where you have a general API, and multiple implementations of that API, where each of the implementations consists of multiple classes. But one of those implementations (lets call it the Null implementation) consists of just one class.
The real test is whether the package structure is serving its purpose(s):
Is it making it easier to find library classes?
Do the packages organize the application classes along the lines of the application's logical module structure?
Does the structure allow you to effectively make use of "package private" visibility?
Would it make more sense just to move the single class to a util package that would contain other random useful classes?
Not necessarily. If the class is just another "randomly useful" leaf class, then there is a good case for moving it. On the other hand, if it has a specific function and is not intended to be used generally, then it may be better to leave it where it is.
It is best not to get too obsessed with creating elegant package hierarchies, or with rejigging them when they turn out to be not as elegant (or useful) as you first thought. There are usually more important things to do, like implementing functionality, writing tests, writing documentation and so on.

No
Package is used to put similar classes together,
In your system if there is no similar class then obviously you can put it .

Is it a bad practice to have a package with only one class in it?
Not necessarily. Packages are using to group together logically related entities. It doesn't prevent you from having just one such entity in a package.
Would it make more sense just to move the single class to a util package that would contain other random useful classes?
Not to me, for two reasons:
Util has a specific meaning. Moving an arbitrary entity to util for reasons of loneliness would be a borderline case of util-abuse.
This is premature organization. With Java the IDE support is rich enough to reorganize easily and effectively using a few clicks. Wait a while to see how your project evolves and then take a call.

There are different stategies for static util classes. I use this one :
if your util class is generic (String utils, DB utils, etc.), I put it in a "util" package, that is used in all the application.
if the util class is specific to a domain, I call it "DomainHelper" by convention, and put it in the domain package, at the same level as domain classes.

Yes, it's a definite code smell.
This doesn't mean it's necessarily wrong, but there should be a really good reason for a lone class in a package.
Most instances of a package with a single class that I've seen have been erroneous.
Packages should implement features. It's rare that a feature is implemented using only a single class.

Its not 'bad' to have a single class in a package, Create a new package to group more than one related classes and in case if you expect more related classes to your present single logically unrelated class in future to avoid refactoring. Moving all the random utility type classes to a single package is a common practice seen in many places.Its a matter of choice really.

I guess it depends. It is quite rare in to have a package with one class in it because in addition to the answers listed above, packages also serve the purpose of creating a layered system. A package with only one class in it indicates that the decomposition of the system has not surfaced some objects in the system. So, yes, I would take a closer look at this package and question what the purpose is.
It is better not to stick random stuff in an Util package precisely because of the reason mentioned above. You should ask yourself whether you would think to look in Util for your class in the future before putting it there. When Util grows large it starts to get difficult finding the Utility one is looking for.

Related

Should I avoid commonly used class names?

Some class names are so "generic" that they are often found in several different packages, including in libraries and application code. Some examples:
Comment
Component
Factory
Location
Region
In my IDE, attempting to auto-complete the import for a class like one of these summons several competing suggestions.
When naming classes, is it a good idea to avoid class names already used elsewhere?
For some of these examples, I would imagine that using such class name is discouraged because it is simply not meaningful enough (e.g. Factory), but I am wondering whether it is discouraged to use a class name because it is used (frequently) elsewhere.
You should use class names where they make the most sense for you. None of the names above that you've proposed are off limits, and there's no reason why you can't use them (assuming a language that supports namespaces and can avoid naming conflicts in this way).
However, you may consider drilling down to class names that are more specific and precise, which will better describe the meaning of the objects in your code. For example:
Instead of Comment: LineComment or BreakComment could easily be class names in a compiler project where you would like to create semantic blocks for comments.
Instead of Component: ListComponent, CalendarComponent, or ViewComponent make particular sense when implementing a UI library where you have class-based components.
Instead of Factory: PizzaFactory makes more sense if you're trying to make pizzas!
Instead of Location: GeographicLocation or SemanticLocation makes more sense when implementing a directions based navigation app, and you're trying to distinguish between '45 deg N, 77 deg W' and 'next to the pizza place'.
Region: CodeRegion could be used in a compiler, and GeographicRegion could be used in a Maps app.
If you're afraid to be specific, namespaces and packages help. However, there is nothing discouraging you from using the same name for a class as another package where it makes sense. The class names specifically aren't copyrighted, and most IDEs now are smart enough to make distinctions between what packages you're referring to when using autocompletion.
For the most part, specificity is helpful in assisting other developers to read your code, which every developer can appreciate!
Comment, Region, and Location seem fine. Personally, so subjectively, Component and Factory are definitely too common to use but objectively I can't think of any conventional reason not to use them as names. I'd definitely try and couple those names with their respective usage, for example; TaskFactory, WidgetComponent, ButtonFactory, etc.
Depends if we are talking about business or technical part.
In technical part: using common names is actually a way to let others know about the patterns used, Factory is a good example - when you see a class named like SomethingFactory, you can expect a Factory Pattern. It goes further to frameworks, libraries etc. - SomethingAutoConfiguration with Spring-Boot, SomethingEntity with JPA, I think with frontend frameworks (React, Angular) Component is a really common word. So ye, by all means, use them, as long as you use them correctly.
In business part: simple, if those words describe your business domain, then by all means use them. Don't try to invent some fancy names (or thesaurus!) just because the words seem common, it's your business domain - it's sacred.

What is the idiomatic way to package these classes in Java

I'm writing a library which has like 25 classes. 4-5 of them are meant to be a public api. The other classes are package private at the moment. My problem is that I want to arrange them to their own packages but this is not possible with the current setup because that way those classes won't be able to see each other.
So should I just leave them as-is without arrangement or make them all public so I can rearrange them? The latter I think is not a good solution because a lot of classes are not meant to be used by the end user but I don't like them just dumped into a root package as it will only grow in size.
Is there an idiomatic way in java to solve this problem?
Example:
I have a class named HexagonalGridBuilder. It is public and part of the api. Same stands for HexagonOrientation which is an enum and holds the value of (FLAT_TOP and POINTY_TOP) and HexagonalGridLayout which is an enum as well and holds the values for the types of hexagonal grids like RECTANGULAR and TRIANGULAR. The end user can use those enums to parametrize the HexagonalGridBuilder object which reuturns a HexagonalGrid which is an interface.
All of the implementation classes are package private like HexagonalGridImpl or TriangularGridLayoutStrategy. I can't move these classes into different packages without making them all public because of this packaging problem I described.
Aside for waiting for Java Project jigsaw there are several work arounds to your solution:
Keep the code as is with package-private classes, users won't see these so only you will be bothered by lots of classes in the package.
You can make packages with names like my.package.internal but have the classes public so they could be usable by others, but hopefully the name "internal" tells them not to.
Use something like OSGI which can enforce public vs private API and not let others ourside your jar directly access classes you don't want them to. However, this will only be enforced if your users are also using OSGI.

Why is it not recommended to store constants in a separate class?

It's been told me (and I have seen this statement in a few other places) that it's not recommended to store your constants in a separate class in Java, in order to use them in the other classes. But I haven't seen anywhere WHY is it so. What is the reason I should not store them in their own interface/class?
I came from C to Java and in C i would just make a .h file where i defined constants with #define
Constants in a dedicated file are frowned upon for stylistic reasons. Having a class dedicated to constants can encourage developers to add increasing numbers of unrelated (undocumented?) constants to a file that slowly bloats out of control.
By contrast, having constants associated with the classes they are related to is a more scalable and readable design.
So you can be an engineer and measure constants and their locations as a technical choice. This is great and fine when you work on performance critical systems or on cool small snippets. Once your application tends to grow however, it becomes harder and harder to grasp the business requirements and end-user needs reflected in the code.
So instead of thinking about style -- separate class, properties file or nested inside a class -- I tend to follow domain driven design -- if the set of constants exclusively belong to a specific class (entity), nest the constants; if the concept touches more than one of the entities in your domain model, feel free to make it a separate entity.
And please do remember, that since Java 5, you do have enums at your disposal.
A separate constants class is not object-oriented design. In OO, a class (or interface) represents a contract, and a class which only contains constants does not define any contract.
Another object-oriented consideration is that a separate constants class encourages misuse of inheritance. Inheritance is supposed to indicate that a class fully adheres to the contract defined by another class or interface. Inheritance should not be used just to share functionality or constants; that's what public methods and fields are for. Thus, this code is incorrect:
class SomeApplicationClass
implements ScrollPaneConstants // Incorrect, import ScrollPaneConstants instead
Issue is that they should be living outside of your source code entirely. You should be using something like Apache Commons Config, or at least loading from a .properties file.
I will also note that I'm interpreting "single" with respect to a reasonable scope. For instance, there should not be one Config file for all Java developers used stored on Google's servers with a request form for modifying. There probably should not be done for your entire code base; however, per UOR or package is a reasonable scope, and is the one I use in practice.

Bad practice to have two classes of the same name in different packages?

We have split our application so that package A handles data from one external source and package B from another. In both cases we need to create a domain object and have a "Transformer" to do this.
So I have com.foo.bar.a.ThingTransformer and com.foo.bar.b.ThingTransformer
I suspect that this is poor practice, but want to see what the good people of SO think.
I wouldn't go as far as saying that it's always a bad practice, but it's somewhat of a code smell.
If both classes do different things, then why don't they have different names?
if both classes do the same thing, then why are there two classes?
From a practical standpoint it can become very annoying if those two classes ever need to be referenced in the same class: you'll have to use the FQN for one of those (it would probably be best to use it for both in this case, for clarity). If those two classes are in sufficiently distinct parts of the code that they won't be referenced from the same code, then the practical problem is not so bad.
Not really poor practice, as in many domains have similar terminology, so you will end-up having same names. On the other hand if both are in same domain, but simply different implementations, you can (somehow) indicate the implementation specifics in the name.
The very ugly thing would be if you have to use both in same source file, in this case you have to use fully qualified name for at least one.
Examples:
java.util.List
java.awt.List
indicate implementation in the name:
java.util.ArrayList
java.util.LinkedList
It's fine. This is precisely why, by design, different packages have different namespaces.
Nothing wrong with that, since it's very unlikely you'll use both classes together in the same code. Duplicating the a/b distinction from the package in all class names would be worse.
You have to decide if this is more helpful or more confusing. You can get the same problem with using similar names in the same package where the difference is not clear.
An example of more-confusing-than-helpful is something like
com.sun.corba.se.internal.Interceptors.PIORB extends
com.sun.corba.se.internal.POA.POAORB which extends
com.sun.corba.se.internal.iiop.ORB which extends
com.sun.corba.se.impl.orb.ORBImpl which extends
com.sun.corba.se.spi.orb.ORB which extends
com.sun.corba.se.org.omg.CORBA.ORB which extends
org.omg.CORBA_2_3.ORB which extends
org.omg.CORBA.ORB

Where to put potentially re-useable helper functions?

This is language agnostic, but I'm working with Java currently.
I have a class Odp that does stuff. It has two private helper methods, one of which determines the max value in an int[][], and the other returns the occurrences of a character in a String.
These aren't directly related to the task at hand, and seem like they could be reused in future projects. Where is the best place to put this code?
Make it public -- bad, because Odp's functionality is not directly related, and these private methods are an implementation detail that don't need to be in the public interface.
Move them to a different class -- but what would this class be called? MiscFunctionsWithNoOtherHome? There's no unifying theme to them.
Leave it private and copy/paste into other classes if necessary -- BAD
What else could I do?
Here's one solution:
Move the method that determines te max value in a two-dimensional int array to a public class called IntUtils and put the class to a util package.
Put the method that returns the occurrences of a character in a String to a puclic class called StringUtils and put the class to a util package.
There's nothing particularly bad about writing static helper classes in Java. But make sure that you don't reinvent the wheel; the methods that you just described might already be in some OS library, like Jakarta Commons.
Wait until you need it!
Your classes wil be better for it, as you have no idea for now how your exact future needs will be.
When you are ready, in Eclipse "Extract Method".
EDIT: I have found that test driven development give code that is easier to reuse because you think of the API up front.
A lot of people create a Utility class with a lot of such methods declared as static. Some people don't like this approach but I think it strikes a balance between design, code reuse, and practicality.
If it were me, I'd either:
create one or more Helper classes that contained the methods as static publics, naming them as precisely as possible, or
if these methods are all going to be used by classes of basically the same type, I'd create an abstract base class that includes these as protected methods.
Most of the time I end up going with 1, although the helper methods I write are usually a little more specific than the ones you've mentioned, so it's easier to come up with a class name.
I not know what the other languages do but I have the voice of experience in Java on this: Just move to the end-brace of your class and write what you need ( or nested class if you prefer as that is accepted canonical convention in Java )
Move the file scope class ( default access class right there in the file ) to it's own compilation unit ( public class in it's own file ) when the compiler moans about it.
See other's comments about nested classes of same name if differing classes have the same functionality in nested class of same name. What will happen on larger code bases is the two will diverge over time and create maintainability issues that yield to Java's Name of class as type of class typing convention that forces you to resolve the issue somehow.
What else could I do?
Be careful not to yield to beginner impulses on this. Your 1-2 punch nails it, resist temptation.
In my experience, most large projects will have some files for "general" functions, which are usually all sorts of helper functions like this one which don't have any builtin language library.
In your case, I'd create a new folder (new package for Java) called "General", then create a file to group together functions (for Java, this will just be a class with lots of static members).
For example, in your case, I'd have something like: General/ArrayUtils.java, and in that I'd throw your function and any other function you need.
Don't worry that for now this is making a new class (and package) for only one function. Like you said in the question, this will be something you'll use for the next project, and the next. Over time, this "General" package will start to grow all sorts of really great helper classes, like MathUtils, StringUtils, etc. which you can easily copy to every project you work on.
You should avoid helper classes if you can, since it creates redundant dependencies. Instead, if the classes using the helper methods are of the same type (as kbrasee wrote), create an abstract superclass containing the methods.
If you do choose to make a separate class do consider making it package local, or at least the methods, since it may not make sense for smaller projects. If your helper methods are something you will use between projects, then a library-like approach is the nicest to code in, as mentioned by Edan Maor.
You could make a separate project called utils or something, where you add the classes needed, and attach them as a library to the project you are working on. Then you can easily make inter-project library updates/fixes by one modification. You could make a package for these tools, even though they may not be that unified (java.util anyone?).
Option 2 is probably your best bet in Java, despite being unsatisfying. Java is unsatisfying, so no surprise there.
Another option might be to use the C Preprocessor as a part of your build process. You could put some private static functions into file with no class, and then include that file somewhere inside a class you want to use it in. This may have an effect on the size of your class files if you go overboard with it, of course.

Categories