[Bf-committers] Blender Python changes
Kai Kostack
kaikostack at gmx.net
Wed Oct 26 13:23:27 CEST 2016
Thank you for the explanation. It makes more sense to me now and I see the
advantages of the changes. However, I still think that the average use case
would be unlinking without the hassle to handle all references manually for a
'simple' script. I would consider writing simple scripts even a general user
requirement and not so much something exclusively reserved for die-hard
add-on development.
By the way, I realized the ramifications of the changes just in the last two
days, otherwise I would have voiced up earlier.
-- Kai
> Gesendet: Mittwoch, 26. Oktober 2016 um 10:29 Uhr
> Von: "Bastien Montagne" <montagne29 at wanadoo.fr>
> An: bf-committers at blender.org
> Betreff: Re: [Bf-committers] Blender Python changes
> To keeps things short: remove() behavior was previously utterly
> inconsistent, a few types (Scene, at least, iirc) were also doing an
> implicit unlink, while most types would not work and error if datablock
> was still in use. So you had to use an horrible hack (user_clear()) to
> set ID's usercount to zero before calling remove() (or ensure you
> removed things in a specific order such that all users got removed
> before you removed some data), also usercount was not handled correctly
> in many corner cases, etc.
>
> In a word: it could quickly turn into nightmare to clean up some data -
> and it was *very* easy to make Blender crash in the process.
>
> This has been fixed in 2.78, you now can just directly use remove()
> (with do_unlink option) to get rid of some data-block, without having to
> care about clearing its usages first, nor its usercount, nor anything
> else. And remove() behavior has been unified, my decision to keep unlink
> optional and off by default was for two reasons:
> - Unlink did not happen at all in most cases (that was the main reason).
> - And when it comes to handling *a lot* of data-blocks (thousands of
> them), skipping unlink can be a huge time saver, it avoids several loops
> over the whole Main database of data-blocks for each removed one.
>
> So yes, this is API breakage (in some limited cases, again, iirc only
> bpy.data.scenes.remove() was implicitly unlinking before) - but there
> was no other solution, and this area really needed to be cleaned up, one
> way or the other some default remove() behavior would have changed. By
> the way, Py API is not really part of the 'we do not break anything in
> 2.7x series' stance, this goes mostly for the .blend file compatibility.
> Py API stance has always been 'we *try* not to break anything, unless it
> is really necessary'. Blender is not a library, but an end-user
> application, and its API has to reflect changes to its internal
> behavior, even when things exposed to end user through the UI look the same.
>
> Now, maybe I should have rather enabled do_unlink by default, this could
> have been less disruptive… But would have been much, much nicer to have
> that kind of topic raised *before* we release. Because now we for sure
> cannot do anything about it, which is rather frustrating for everybody.
>
> Regards,
> Bastien
>
> Le 26/10/2016 à 09:18, Kai Kostack a écrit :
>> Dear Blender devs,
>>
>> I'd like to provide some feedback about a recent change in BPY... OK, and
> share
>> some frustration about it. ;)
>>
>> Just until recently you could unlink a lot of datablock types via their
>> corresponding remove() methods without any problems. Now with Blender 2.78
>> someone has decided to change some of these methods in a way that they throw
> an
>> exception when there are still other users left on a default unlink attempt:
>> "RuntimeError: Error: Text 'export.txt' must have zero users to be removed,
>> found 1 (try with do_unlink=True parameter)"
>>
>> I thought, "Okaaay, just another parameter to add, no problem." - Why that
>> would be necessary, since you could have checked for other users anyway
> before
>> unlinking, was beyond me. - But then I realized that there are 27 datablock
>> types that use an updated remove() method while others remained unchanged. I
>> have like 100 scripts for Blender 2.76 at my disposal and ca. 30 of them have
>> at least one ".remove(" in the code. "Wow, that's a lot of scripts that might
>> have been broken by now", I thought. Note that you can't easily go over them
>> and add the parameter because not all remove methods of Blender would accept
> it
>> (not to mention general Python list removes). So I had to look up each and
>> every line with 'remove' in the API if they were changed or not. That was
> fun.
>>
>> While the scripts will (probably) all work by now again, I got first
> complains
>> that some of my Add-ons wouldn't work with 2.77 builds anymore. Great. To
> make
>> a long story short, I have decided to implement BOTH ways of calling remove
> via
>> try & except now, just to make sure the code will work in both versions, 2.77
>> and 2.78.
>>
>> I remember a statement along the lines that breaking things will be postponed
>> until 2.8 and that 2.7x should be kept in a working state. - This is not a
> call
>> to change it back, I just want to give you a glimpse of what seemingly
> appears
>> to be a clever and small change in design can mean to users, and that they
>> eventually have to include more and more workarounds and hacks just to
>> circumvent your 'clever design' to make things just work. Sometimes less is
>> more.
>>
>> With respect,
>>
>> -- Kai
>> _______________________________________________
>> Bf-committers mailing list
>> Bf-committers at blender.org
>> https://lists.blender.org/mailman/listinfo/bf-committers
>>
>
> _______________________________________________
> Bf-committers mailing list
> Bf-committers at blender.org
> https://lists.blender.org/mailman/listinfo/bf-committers[https://lists.blender.o
> rg/mailman/listinfo/bf-committers]
More information about the Bf-committers
mailing list