Francois Gouget : testbot/lib: Make Collections try harder to return existing Item objects to avoid inconsistencies.
julliard at winehq.org
Tue May 6 12:32:38 CDT 2014
Author: Francois Gouget <fgouget at codeweavers.com>
Date: Tue May 6 12:40:27 2014 +0200
testbot/lib: Make Collections try harder to return existing Item objects to avoid inconsistencies.
Assume we have the following code:
1: my $Jobs = CreateJobs();
2: my $VM1 = $Jobs->GetItem(100)->Steps->GetItem(1)->Tasks->GetItem(1)->VM;
3: my $VM2 = $Jobs->GetItem(101)->Steps->GetItem(1)->Tasks->GetItem(1)->VM;
4: my $VM2b = $Jobs->GetItem(101)->Steps->GetItem(1)->Tasks->GetItem(1)->VM;
5: print $VM1->Name, " is ", $VM1->Status, "\n"; # Prints 'buildvm is idle'
6: print $VM2->Name, " is ", $VM2->Status, "\n"; # Prints 'buildvm is idle'
9: print $VM1->Name, " is ", $VM1->Status, "\n"; # Prints 'buildvm is running'
10: print $VM2->Name, " is ", $VM2->Status, "\n"; # Prints 'buildvm is idle' !!!
11: print $VM2b->Name, " is ", $VM2b->Status, "\n"; # Prints 'buildvm is running'
The problem is that although $VM1, $VM2 and $VM2b refer to the same
VM (buildvm), they are all separate objects. Then $VM2->Status gets
loaded from the database for the print statement on line 6, and is
then never refreshed; hence the out-of-date value printed on line
10. In contrast $VM2b->Status is loaded from database for the print
statement on line 11 and thus shows the up-to-date value that was
saved on line 8. This is very confusing.
This patch associates a scope to each Collection and ensures that
there is no duplicate Item objects within that scope. Further, any
object created from a Collection inherits its scope. So in the example
above, because all objects can ultimately be traced back to the $Jobs
collection, $VM1, $VM2 and $VM2b all point to the same object which
avoids any inconsistency.
It's also possible to ensure that two Collections share the same scope
by passing the reference collection as a parameter. For instance, in
the above sample code, CreateVMs($Jobs)->GetItem('buildvm') will
As before, creating a new Collection normally, CreateVMs() for
instance, ensures gets a new, empty, scope and thus reload the objects
from the database. This ensures the new objects will reflect changes
made to the database by other processes. This is also why having a
global persistent cache would not work.
testbot/bin/WineSendLog.pl | 2 +-
testbot/lib/ObjectModel/Collection.pm | 199 +++++++++++++++++++++++----
testbot/lib/ObjectModel/DBIBackEnd.pm | 10 +-
testbot/lib/ObjectModel/Item.pm | 27 +++-
testbot/lib/WineTestBot/Branches.pm | 6 +-
testbot/lib/WineTestBot/CGI/Sessions.pm | 5 +-
testbot/lib/WineTestBot/Jobs.pm | 6 +-
testbot/lib/WineTestBot/Patches.pm | 5 +-
testbot/lib/WineTestBot/PendingPatchSets.pm | 5 +-
testbot/lib/WineTestBot/PendingPatches.pm | 6 +-
testbot/lib/WineTestBot/Roles.pm | 5 +-
testbot/lib/WineTestBot/Steps.pm | 7 +-
testbot/lib/WineTestBot/StepsTasks.pm | 6 +-
testbot/lib/WineTestBot/Tasks.pm | 7 +-
testbot/lib/WineTestBot/UserRoles.pm | 7 +-
testbot/lib/WineTestBot/Users.pm | 6 +-
testbot/lib/WineTestBot/VMs.pm | 6 +-
testbot/web/JobDetails.pl | 2 +-
18 files changed, 250 insertions(+), 67 deletions(-)
More information about the wine-cvs