Hi,
Hi Jerry,
I seem to have some sort of corruption in one of my Magma databases.
Incidentally, corruption can occur if, on a particular system, the Squeak call to StandardFileStream>>#flush does not guarantee, upon return, bits were indeed flushed to the platter and the system experiences a hard power-off.
If this happens and happened to cause a corruption, the easiest remedy is to restore from last full backup, then roll-forward to the second before the power-out.
But the type of corruption you have seems to be related to the various history of instance migrations of STBUser, not a power-outage.
I'm running a Seaside application with Magma 0.41gamma1 and
I hope you meant 42, not 41.
I have 2 test images and 2 databases. Both images can access one of the databases with no problems. Trying to access the other database from either image results in a error. So I assume that there is something wrong with the "bad" database and not a problem with my images.
Please clarify whether you are connecting with brand new MagmaSession instances in each case, as opposed to an old session.
The error occurs during initial startup, beginning with:
BTW, the stack-trace attachment is always helpful.
Index: 1 Version: 4 ivar count: 5 Index: 2 Version: 5 ivar count: 6 Index: 3 Version: 2 ivar count: 9 Index: 4 Version: 1 ivar count: 10 Index: 5 Version: 3 ivar count: 11
Hm, that shouldn't happen.
The instance variable counts look right, but the version numbers appear
Would you clarify what you mean by, "The instance variable counts look right"?
to be wrong. Also, the inImageSerializer believes that we are on version 3:
def := (MaObjectSerializer allInstances first classIdManager inImageDefinition: STBUser). def version -> 3 def namedInstSize -> 11 (which is the correct number)
Great information, thanks!
So it appears that there are too many versions in Magmas' class definition collection for my class, and those versions are out of order.
You absolutely don't have "too many", your image may run with any "version" you want. Magma simply maps the instance-variables by name. There is no inherent requirement for Magma to be running at any particular version in the image, but obviously an image running with fewer inst-vars may truncate data from buffers committed by images running with more. Magma issues a warning in that case.
Somehow I always manage to make interesting errors!
How did you stumble into this thicket?
Also: after re-arranging those class definitions and closing the Magma session, closing my image without saving, and restarting the image, my application opened with no problems. So I guess my changes to the Magma class definitions were persisted. However, that does leave me with version 4 and 5 definitions; while the in-image version of STBUser is 3. I'm sure I could go in and remove those definitions, and close the session and everything will be OK.
Please don't remove any of the definitions. If you still have an instances of that version in the repository the session will blow up when trying to materialize them.
So my questions are:
Any idea how this could have possibly happened?
No, but if you are running a repository with buffers with five different versions of the same class, it is necessary to understand the details of how Magma handles all scenarios. It is worth documenting somewhere your process for evolving legacy instances from 5 to 11 inst-vars. Having 5 versions of the same class of instances in the database is common during development, but rarer in production. Production systems ensure instance migrations are handled deliberately and with some care.
How can I fix it permanently, preferably through a code patch and not manual "live" tinkering?
Option 1: The quickest and easiest fix was at the top of the e-mail; restore from backup and roll forward to just before the commit that caused the corruption (You can use the MagmaBufferBrowser to determine the commitNumber of the mis-ordered OC, then look at the time-stamp. You can roll-forward to just before that.
Option 2: What matters is that STBUser buffers in the repository all point consistently to the correct class version. Write a script using MagmaFileTraverser to interrogate all of the Fixed buffers ("type = 3") where classId=126, check that their versions all are correct and consistent with their number of instVars of the Buffer (#objectInstSize).
If they are all consistent, then connect a fresh MagmaSession to the database and commit your change to the mis-ordered OC. Stop and dispose of all other running sessions, replace them with fresh ones.
Is there any way to make sure it does not happen again?
Consider committing a change to all of the classDefinitionsById to a Dictionary of *SortedCollections* instead of OrderedCollection. The sortBlock would be:
[ : a : b | a version < b version ]
- Chris