Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed layers #245

Open
OliverLSanz opened this issue Dec 6, 2024 · 2 comments
Open

Closed layers #245

OliverLSanz opened this issue Dec 6, 2024 · 2 comments

Comments

@OliverLSanz
Copy link

OliverLSanz commented Dec 6, 2024

First, thank you to the mantainers of this module, seems to be doing just what I need.

Here goes my question: I have this situation

graph TD
    C[Module A] --> | A requests data from B | B[Module B]
    B[Module B] --> |B requests data from C to fullfill A's request| A[Module C]
Loading

Module A uses module B, that in turn uses module C. But I want to keep A and C as decoupled as possible. I don't want any type defined by C to be present in A's code (caused by B directly forwarding C's response to A).

That's because I don't want a requirement change in A triggering a change in C's code. Responding to changes in A's requirements is B responsibility.

Is this something that can be enforced by import-linter? seems like a dumb question since it has nothing to do with imports, hit me with a newspaper

@seddonym
Copy link
Owner

seddonym commented Dec 6, 2024

Hi Oliver, thanks for the question.

I would describe this as you want Module B to be a 'closed' layer. Import Linter doesn't currently support this but it's something I think would belong in the library at some point. The syntax might be something like this:

[importlinter:contract:my-layers-contract]
name = My layers contract
type = layers
layers =
    a
    b
    -------
    c

In other words, imports can't pass below that line unless they go via b.

In the meantime there are a few options. You could look at a forbidden import contract between a and c, with allow_indirect_imports = True.

You could write a custom contract type to have finer-grained control over the check.

Or, if you're prepared to rearchitect things a little, you could use the ports and adapters pattern so that a interacts with an abstraction defined by b, which c could then implement via inversion of control (see this blog post). If you did that then you could use a layers contract to check the modules a and c both depend on b, and not the other way around.

@seddonym seddonym changed the title Question: Independence by type checking? Closed layers Dec 6, 2024
@OliverLSanz
Copy link
Author

Thank you for the detailed response! Would be a neat addition to the library. I'll check out the resources you recommended in the meantime :-)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants