dimanche 22 novembre 2020

Python: Better design to have a python object with intellisense get all available property

My main goal is to have a python object available for users, imported from the library, that can access all its properties using dot operations (that works with intellisense/auto complete -- very important). See sample code below.

Is there a better way to design this library? As you can see, there could be multiple classes, which are fairly similar. How could I pass the "parent" value without __init__, since I want to just access the values/property using all dot operation, without () in it. Basically I just want users to do something like Sample.parentA.john and not Sample().parentA().john or something

This could be fairly messy especially when it gets very nested. I tried reading/creating a table and access the members of the dictionary using dot operation (kinda from dot access dictionary, but the problem is, the object wont really autofill or cant use intellisense, so users will still need to know the structure or available properties, so it does not really work for my need.

It might also be cleaner having the whole data implemented in XML structure, and somehow have a code generate and object that can have intellisense detect available properties, but I cant seem to make it work with intellisense as well. Kinda like the dot operation using dictionary above.

In short, I want a python object that supports intellisense/autofill to help users get the available properties (which could be nested). And at the end, I really need just a string representation of all the options the user selected. Options meaning Sample.parentA.steve.joe user really selected options parentA, steve, and joe. And ofcourse, some options are only available, depending on what 'parent' option was selected.

mylibrary.py:

class GrandchildSarah():
    name = "ParentA_ChildSteve_GrandchildSarah"


class GrandchildJoeA():
    name = "ParentA_ChildSteve_GrandchildJoe"


class GrandchildJoeB():
    name = "ParentB_ChildSteve_GrandchildJoe"


class ChildSteveA():
    name = "ParentA_ChildSteve"
    sarah = GrandchildSarah
    joe = GrandchildJoeA


class ChildSteveB():
    name = "ParentB_ChildSteve"
    joe = GrandchildJoeB


class ChildJohn():
    name = "ParentA_ChildJohn"


class ParentA():
    name = "ParentA"
    john = ChildJohn
    steve = ChildSteveA


class ParentB():
    name = "ParentB"
    steve = ChildSteveB


class Sample():
    parentA = ParentA
    parentB = ParentB


def check(exp, obj):
    if isinstance(obj, str):
        print(f"expected: {exp} actual: {obj}")

    elif isinstance(obj, type):
        print(f"expected: {exp} actual: {obj.name}")

    else:
        print(f"expected: {exp} actual: {obj}")

main.py:

from mylibrary import Sample, check

a = Sample.parentA                    # can be completed using auto complete
check("ParentA", a)

a = Sample.parentA.john               # can be completed using auto complete
check("ParentA_ChildJohn", a)

a = Sample.parentA.steve              # can be completed using auto complete
check("ParentA_ChildSteve", a)

a = Sample.parentA.steve.sarah        # can be completed using auto complete
check("ParentA_ChildSteve_GrandchildSarah", a)

a = Sample.parentA.steve.joe          # can be completed using auto complete
check("ParentA_ChildSteve_GrandchildJoe", a)

a = Sample.parentB                    # can be completed using auto complete
check("ParentB", a)

a = Sample.parentB.steve              # can be completed using auto complete
check("ParentB_ChildSteve", a)

a = Sample.parentB.steve.joe          # can be completed using auto complete
check("ParentB_ChildSteve_GrandchildJoe", a)

Aucun commentaire:

Enregistrer un commentaire