[KCP] SystemChangeNotifications: Current state and some code
Roel Wuyts
wuyts at iam.unibe.ch
Tue Jul 15 08:04:02 UTC 2003
It has gotten a lot better in the meantime :-)
There is not a lot of comments in the code yet (but quite a lot of unit
tests), so I will add some things in this mail for you pleasure. The
code can be downloaded at this URL:
http://www.iam.unibe.ch/~wuyts/SystemChangeNotification10.zip (20 kb).
It is for 3.5 only. I can almost guarantee you that it will not work in
3.6 (depending on how far you updated in the update stream). It
contains two changesets: first install SystemChangeNotification.10.cs,
then install NotificationHooks.10.cs. Run the unit tests
(SystemChangeTest and SystemChangeNotifierTest) after installing both
changesets: they should all run green.
This mails discusses the current state, and is actually quite long (not
that long either, but still). So I divided it in the following
'sections', since not everybody will want to read everything (but you
are welcome to :-) ):
Information about the core classes,
Comments on the current implementation, and
What next.
Information about the core classes
------------------------------------------------
There are four classes to have a look at: two containing SUnit tests
(SystemChangeTest and SystemChangeNotifierTest), and two core ones that
implement most of the code (SystemChangeNotifier and SystemEvent):
(1) SystemChangeTest: unit tests for testing the hooks in the system
and that show exactly what event is captured when changing something in
the system. For example, in the test for adding a class, the test
registers to get all system notifications, creates a subclass of a
class, and tests that the captured event contains all the necessary
information. Note that the test is clean: it does not modify your
current changeset and removes everything that you need to add. See the
#setup and #tearDown methods.
(2) SystemChangeNotifierTest: unit test for testing the basic workings
of the propagation system itself.
(3) SystemChangeNotifier: central class that gets notified of changes
to the system by the system (for example, when a class is added, it
will send a message to the SystemChangeNotifier that tells it what
happened), and that then updates its dependents. This is the class that
clients will use to register for system events; see the methods in the
'public' protocol. It is now possible to (a) get all events for a
certain kind of change (all additions, all removals, all renames, ...)
or (b) to get all events for a certain kind of item (all kinds of
changes to classes, or to methods or to ...) or (c) get all events, or
(d) get only a specific change on a specific item (for example, only
class additions, or method removals, ...). You register with a name of
the method that is used to call you back.
(4) SystemEvent: root class of the events that implement most of the
functionality. An event contains an 'item' (for example, a compiled
method), an 'itemKind' (#methodKind in this case), and an 'environment'
(more about that later). It has a number of accessing methods to easily
access the class, method, category, ... for that event, so that clients
can quite easily interrogate the event for information. Note that not
all of these accessing methods make sense. For example, there is a
SuperclassChanged event, which you can ask for its method, etc. This
will just return nil. These accessing methods are there for you
convenience (since you have the item you typically have enough
information, but it is easy to be able to immidiately ask a
'addition-method' event its itemClass, returning the class of the
method. Subclasses of SystemEvent implement all the particular changes
to the system for which events exist, so you find classes
SystemAddedEvent, SystemRenamedEvent, ... some of these have some extra
state to remember specific information (for example, SystemRenamedEvent
has the old name of the event). Last but not least, the class side of
SystemEvent contains methods that you can ask for all the events that
are supported, all the items that are supported, etc. Most of these are
commented.
Comments on the current implementation
--------------------------------------------------------
(1) Haven't looked at 'safety': it is currently a synchronous event
system, where each client that receives an event can block everything
by putting a 'self halt' etc. I first wanted something to play with
before having a look at what to do there (see the interesting
discussion by some people a while ago).
(2) Of course, it is not complete yet. It handles all class changes I
can think of (class addition, removal, renaming, recategorization,
superchanged, change of comment), addition of methods, and 'do its'
trapping. For this it provides the system hooks, unit tests
(3) All tests completely unhook all clients in every tearDown, not just
the test. So if you use it already in your tools, running the tests
will unhook your tools. This made it safer for me, and I was not sure
on how to unhook properly (send a mail about that and got a reply from
John Sarkela, so I'll have a look at that).
(4) Implemented for Squeak 3.5, since I need to be sure of certain
changes to methods that are being moved around (and where I have to put
hooks) before moving to 3.6.
(5) Can be severely optimised. Not that it is too slow currently, but
it can be made quite faster. Following the XP adagios (a bit) I wait
for performance to become a problem though, or until I am sure that the
code is nearly frozen.
What Next?
---------------
- Look at the unregistration (see point (3) above).
- Look at safety
- Add all the events for methods, then for instance variables, class
variables, and finally pool variables (I do this in parallel with the
rest, though).
- Incorporate more feedback from users
- Start rewriting ChangeSet to become a client of this system (need to
write SUnit tests for the changeset first!)
PS: Yes, I will put these things as class comments in the following
version :-)
More information about the Squeak-dev
mailing list
|