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

Dependency chain paths #59

Draft
wants to merge 1 commit into
base: main
Choose a base branch
from
Draft

Conversation

davidbrochart
Copy link
Contributor

@davidbrochart davidbrochart commented Mar 1, 2023

It would be nice to be able to retrieve the hierarchical path of a dependency, something like this (sorry for the hacky PR, just meant to illustrate):

import in_n_out as ino

class T0:
    def __init__(self, t1):
        self.t1 = t1

class T1:
    def __init__(self, t2):
        self.t2 = t2

class T2:
    def __init__(self, t3, t5):
        self.t3 = t3
        self.t5 = t5

class T3:
    def __init__(self, t4):
        self.t4 = t4

class T4:
    pass

class T5:
    pass

@ino.inject
def f0(t1: T1):
    return T0(t1)

@ino.register_provider
@ino.inject
def t1_provider(t2: T2) -> T1:
    return T1(t2)

@ino.register_provider
@ino.inject
def t2_provider(t3: T3, t5: T5) -> T2:
    return T2(t3, t5)

@ino.register_provider
@ino.inject
def t3_provider(t4: T4) -> T3:
    return T3(t4)

@ino.register_provider
def t4_provider() -> T4:
    return T4()

@ino.register_provider
def t5_provider() -> T5:
    return T5()

t0 = f0()

def get_path(v):
    l = v._path
    if not l:
        return l
    path = [l[1]]
    while True:
        l = l[0]
        if not l:
            break
        path.insert(0, l[1])
    return path

print(get_path(t0))
[]
print(get_path(t0.t1))
['t1']
print(get_path(t0.t1.t2))
['t1', 't2']
print(get_path(t0.t1.t2.t3))
['t1', 't2', 't3']
print(get_path(t0.t1.t2.t5))
['t1', 't2', 't5']
print(get_path(t0.t1.t2.t3.t4))
['t1', 't2', 't3', 't4']

@davidbrochart davidbrochart marked this pull request as draft March 1, 2023 22:46
@tlambert03
Copy link
Member

oh yeah, that's a very nifty idea. Would be very useful for debugging! we'll probably need to find somewhere else to store _path (rather than on the result object)... but i'm generally supportive of the idea

@tlambert03
Copy link
Member

curious what made you think of this? ... would it be for debugging (and therefore something that could be turned off by default), or do you have a use case where you'd actually like to do something differently with the result depending on who provided it?

@davidbrochart
Copy link
Contributor Author

davidbrochart commented Mar 2, 2023

My use case is for configuration. I'd like to use in-n-out as a plugin system, where plugins add themselves as resources and can be required by other plugins. This builds up a hierarchical tree of objects, where the top-level object is an application that can be launched at the CLI. And I'd like to be able to pass configuration to a particular plugin, e.g.:

my_app --set path.to.my.plugin.attribute=my_value

I think the configuration system doesn't have its place in in-n-out core, but the possibility to get the path of a plugin is general enough to build this kind of systems, and it makes sense to have it in in-n-out.
Maybe the path could be stored on the result object itself, with the possibility to give it a different name than _path? And of course that would be an opt-in feature, so that by default there is no risk to pollute the namespace of the object with this attribute.

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

Successfully merging this pull request may close these issues.

2 participants