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

WIP: collections as dicts #419

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

Conversation

chaselgrove
Copy link
Contributor

Why is this refactoring not working? Does it have something to do with attrs?

@kyleam
Copy link
Contributor

kyleam commented May 21, 2019

Why is this refactoring not working?

I didn't try anything with your example, so I don't know how exactly that fails but...

Does it have something to do with attrs?

... if it does have something to do with attrs, it's something more particular to how we use it, because this seems to work as expected:

import attr


@attr.s
class A(object):
    _a = attr.ib(default=attr.Factory(list))

    @property
    def a(self):
        return self._a

    @a.setter
    def a(self, value):
        self._a = value


x = A([0, 1])
print(x.a)
x.a = [0, 2]
print(x.a)
[0, 1]
[0, 2]

@chaselgrove
Copy link
Contributor Author

Thanks, @kyleam. The test suite fails on a number of tests, but not in ways that were obvious as to the root cause.

@yarikoptic, can you shed light on this? Or suggest how I can create getters and setters for DebianDistribution.packages?

@yarikoptic
Copy link
Member

Even without looking into failures: well, we do quite in a few places rely on exploring all those attr's attributes for the classes. E.g. git grep __attrs_attrs__ to see at least some of those spots. Here you are renaming packages into _packages, so saving into the spec would save it as _packages. And loading existing specs with packages would fail too.

This example doesn't show though the purpose of making packages into a property. Do you need to react on get or set for it, and how? Depending on your goal, see into using attr's functionality such as
Validators or Converters

@yarikoptic
Copy link
Member

ah, doh -- re "purpose" the title said it ;-) So, you would like to convert them to be a dict instead of a list... we discussed it a bit during the last call. Do I remember correctly that the main goal is to make lookups (for diff and otherwise) more efficient so we don't need to iterate?

I guess the best would be to define a custom class to be used here instead of list (atm via TypedList) which would provide necessary abstraction and which we would "manually" handle upon saving/loading into a spec file (to store it there as a list). I would have probably subclassed dict so we could react while loading/saving to store it as a list of values. But I am not sure what other parts might rely on those to be just a list so iteration through it should then be done through values not keys... Since some other classes would still be regular lists, I would have probably created some adapter for now like dictlist_values_iterator which would do the right job depending on what it is to iterate over. Eventually we could get rid of it whenever all classes would converge if we see it as a way to go forward.

@chaselgrove
Copy link
Contributor Author

chaselgrove commented May 23, 2019

@kyleam it looks like attrs uses the declaration of packages (via TypedList, which isn't a class but a function that returns an attr.ib()) to require it to be present at instantiation, so my attempt hid packages from attrs and it choked on DebianDistribution.init(). And also where we do introspection via __attrs_attrs__.

@yarikoptic my main purpose here was to express an idea by refactoring DebianDistribution -- I wanted to change its internals without affecting its behavior, but attrs limits our options here. We also run into problems because at some point(s?) we redefine packages completely. This is the reason we had to resort to working with __attrs_attrs__ in at least one case.

I'm rethinking my strategy and I suspect it might be better if the first step is not working on DebianDistribution's internals but rather on its interface, and to try to be stricter about how we can interact with it. This should also keep us from doing things that require crazy workarounds in other areas.

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.

3 participants