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

See if we can use Python properties to get/set DOT attributes #250

Open
3 tasks
peternowee opened this issue Dec 11, 2020 · 2 comments
Open
3 tasks

See if we can use Python properties to get/set DOT attributes #250

peternowee opened this issue Dec 11, 2020 · 2 comments

Comments

@peternowee
Copy link
Member

This is a reminder issue that during development of pydot 2.0.0 we should see if we can use Python property for getters/setters of DOT attributes. This was suggested by @johnyf in #151 (comment) and by @sandrotosi in #217 (comment) for example.

Some points of attention already:

  • Currently (pydot 1.4.2.dev0), we dynamically create getter/setter methods, also known as convenience methods, like Node.get_color(), Edge.set_label(), etc. These seem to be used a lot, so we will need to have a generous transition/deprecation period for those.
  • Currently (pydot 1.4.2.dev0), we have no clear way to prevent name clashes between pydot attributes and (custom) DOT attributes. For example, Node.set_name() and Graph.set_type() set pydot attributes, so getter/setter methods created for custom DOT attributes name and type would clash with those. Perhaps when introducing new getters/setters based on Python properties, we can somehow provide separate namespaces for them, at least for the (custom) DOT attributes over which we have no control. For example by prefixing getters/setters for (custom) DOT attributes with dot_: node.dot_color = 'blue' (DOT attribute used by Graphviz), node.dot_name = 'My Name', graph.dot_type = 'My Type' (custom DOT attributes). The main drawback of this of course the inconvenience of having to use the dot_-prefix all the time, so other suggestions are welcome.
  • There are over 200 DOT attributes for which we need to generate getters/setters. Even when using Python properties, it may be desirable to dynamically generate them instead of having a long source file with duplicate code to set up property for each DOT attribute individually. In PR Full pickle support #242, also targeted for pydot 2.0.0, I proposed changes to how the current getter/setter methods are dynamically created. We will have to see if the dynamic generation of Python properties can fit in there as well.
@ferdnyc
Copy link
Contributor

ferdnyc commented Feb 14, 2024

  • Perhaps when introducing new getters/setters based on Python properties, we can somehow provide separate namespaces for them, at least for the (custom) DOT attributes over which we have no control. For example by prefixing getters/setters for (custom) DOT attributes with dot_: node.dot_color = 'blue' (DOT attribute used by Graphviz), node.dot_name = 'My Name', graph.dot_type = 'My Type' (custom DOT attributes). The main drawback of this of course the inconvenience of having to use the dot_-prefix all the time, so other suggestions are welcome.

My suggestion, on this, would be to simply put all of the attributes inside a member object of the class. So, e.g.:

node = pydot.Node()
node.attrib.color = 'blue'
node.attrib.style = 'myclass'

At face value it doesn't seem much different than the dot_ prefixes, but there are several advantages:

  1. Dotted names are easier to type than underscore prefixes.

  2. Someone who's really averse to the extra typing can easily alias the attributes member object:

    node = pydot.Node()
    a = node.attrib
    a.color = 'blue'
    a.style = 'myclass'
  3. Similarly, it's far easier to script changes to member attributes than prefixed names.

    node = pydot.Node()
    attributes = {'color': 'blue', 'style': 'myclass'}
    for k, v in attributes.items():
        setattr(node.attrib, k, v)

@ferdnyc
Copy link
Contributor

ferdnyc commented Feb 14, 2024

Oh, and as an added bonus, if node.attrib implements the MutableMapping interface (basically, has implementations for the abstract __len__, __iter__, __getitem__, __setitem__, and __delitem__ methods, and is a subclass of collections.abc.MutableMapping), then it can also be used as a dictionary:

node = pydot.Node()
node.attrib["color"] = "blue"
attributes_dict = dict(node.attrib)
attribute_names = node.attrib.keys()

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

No branches or pull requests

2 participants