Not sure if said it clearly, so I would like to do it again. In lots of times developer would like to use same module for 2 things (for example using helper library for your library) and then having macro which creates module or function (overriding
defp) are hard to use in some cases.
Here think how developer could create a helper library which adds some extra functions to your generated:
MyApp.MyModule.Router - except extra options (like
use MyLib.Module, use_modules: [MySecondLib.MyModule] or
use MyLib.Module do … end) I don’t see any way to do it for specific module.
Finally as said I prefer:
defmodule MyApp.MyModule.Router do
which allows to easily add extra functionality related to your library.
Think that for example
HTTPoison is really good, but for example any helper
GitHub library which uses
HTTPoison is much better as we do not need to worry about changes in
GitHub API - just update helper library. Now if you are adding some functions to module then in lots of times somebody would like to write helper function, for example:
defmodule MyApp.Repo do
use Ecto.Repo, adapter: Ecto.Adapters.Postgres, otp_app: :my_app
def soft_delete(entry) do
# use delete function from Ecto.Repo and handle stale error
In your case I would need to create 2nd module for helper functions and I would need to ASSUME that it would always have same name (even after library update). Assuming too much things is one of the worst practices I ever made and seen.
would accidentally throw compile time errors!
After that think about non-compile time errors, for example calling function dynamically using
apply/3. In lots of cases it would be a really big trouble.
So it’s not like creating module is bad practice directly, because in some edge-cases it’s really useful, but it’s not perfect in all use cases as it could later force developer to use true bad practices (like said assuming module name).
It’s also hard to maintain code which requires some assumption for 3rd-party developer. Think that your team joins somebody and would like to introduce American spelling instead of English spelling (or just something like that). This could be reasonable (for your team) change and none of tests would give any error, so other developers could not even notice such breaking backwards compatibility.
From your side such naming change could not be seen like that as you could (again!) assume that you are only one who is using generated code in such module, but again here comes helper library topic.