[squeak-dev] The Trunk: UpdateStream-fbs.3.mcz

commits at source.squeak.org commits at source.squeak.org
Fri Dec 6 20:57:04 UTC 2013


Frank Shearar uploaded a new version of UpdateStream to project The Trunk:
http://source.squeak.org/trunk/UpdateStream-fbs.3.mcz

==================== Summary ====================

Name: UpdateStream-fbs.3
Author: fbs
Time: 6 December 2013, 8:56:59.9 pm
UUID: 2d0c0933-b30f-da40-a681-f45f01308218
Ancestors: UpdateStream-nice.2

FilePackage has a bunch of logic around handling update streams' changesets. This logic now belongs in UpdateStream.

=============== Diff against UpdateStream-nice.2 ===============

Item was added:
+ ----- Method: FilePackage class>>conflictsWithUpdatedMethods: (in category '*UpdateStream-instance creation') -----
+ conflictsWithUpdatedMethods: fullName
+ 	| conflicts changeList |
+ 	conflicts := (self fromFileNamed: fullName) conflictsWithUpdatedMethods.
+ 	conflicts isEmpty ifTrue: [^ self].
+ 	changeList := ChangeList new.
+ 	changeList
+ 		changes: conflicts
+ 		file: (FileDirectory default readOnlyFileNamed: fullName) close.
+ 	ChangeList 
+ 		open: changeList
+ 		name: 'Conflicts for ', (FileDirectory localNameFor: fullName)
+ 		multiSelect: true.!

Item was added:
+ ----- Method: FilePackage class>>fileReaderServicesForFile:suffix: (in category '*UpdateStream-reader service') -----
+ fileReaderServicesForFile: fullName suffix: suffix
+ 
+ 	^(suffix = 'st') | (suffix = 'cs') | (suffix = '*')
+ 		ifTrue: [self services]
+ 		ifFalse: [#()]!

Item was added:
+ ----- Method: FilePackage class>>serviceConflictsWithUpdatedMethods (in category '*UpdateStream-reader service') -----
+ serviceConflictsWithUpdatedMethods
+ 	^ SimpleServiceEntry 
+ 		provider: self 
+ 		label: 'conflicts with updated methods'
+ 		selector: #conflictsWithUpdatedMethods:
+ 		description: 'check for conflicts with more recently updated methods in the image, showing the conflicts in a transcript window'
+ 		buttonLabel: 'conflicts'!

Item was added:
+ ----- Method: FilePackage class>>services (in category '*UpdateStream-reader service') -----
+ services
+ 	^ Array with: self serviceConflictsWithUpdatedMethods!

Item was added:
+ ----- Method: FilePackage>>checkForMoreRecentUpdateThanChangeSet:pseudoClass:selector: (in category '*UpdateStream-conflict checker') -----
+ checkForMoreRecentUpdateThanChangeSet: updateNumberChangeSet pseudoClass: pseudoClass selector: selector
+ 	"Returns the source code for a conflict if a conflict is found, otherwise returns nil."
+ 
+ 	| classOrMeta allChangeSets moreRecentChangeSets conflictingChangeSets changeRecordSource classAndMethodPrintString |
+ 
+ 	classAndMethodPrintString := pseudoClass name, (pseudoClass hasMetaclass ifTrue: [' class'] ifFalse: ['']), '>>', selector asString.
+ 
+ 	changeRecordSource := pseudoClass sourceCode at: selector.
+ 	changeRecordSource isText
+ 		ifTrue: [changeRecordSource := Text
+ 					fromString: 'method: ', classAndMethodPrintString, ' was removed']
+ 		ifFalse: [changeRecordSource stamp isEmptyOrNil ifTrue:
+ 					[self notify: 'Warning: ', classAndMethodPrintString, ' in ', self packageName, ' has no timestamp/initials!!']].
+ 
+ 	pseudoClass exists ifFalse:
+ 		[(self classes at: pseudoClass name) hasDefinition
+ 			ifTrue: [^ nil  "a method was added for a newly defined class; not a conflict"]
+ 			ifFalse: [self class logCr; log: 'CONFLICT found for ', classAndMethodPrintString, '... class ', pseudoClass name asString, ' does not exist in the image and is not defined in the file'.
+ 					^ changeRecordSource]].
+ 
+ 	classOrMeta := pseudoClass realClass.
+ 
+ 	"Only printout the replacing methods here, but we still check for removed methods too in the rest of this method."
+ 	(self class verboseConflicts and: [classOrMeta includesSelector: selector])
+ 		ifTrue: [self class logCr; log: '...checking ', classOrMeta asString, '>>', selector asString].
+ 
+ 	allChangeSets := ChangesOrganizer allChangeSets.
+ 	moreRecentChangeSets := allChangeSets
+ 				copyFrom: (allChangeSets indexOf: updateNumberChangeSet)
+ 				to: (allChangeSets size).
+ 	conflictingChangeSets := (moreRecentChangeSets select:
+ 		[:cs | (cs atSelector: selector class: classOrMeta) ~~ #none]).
+ 	conflictingChangeSets isEmpty ifTrue: [^ nil].
+ 
+ 	self class logCr; log: 'CONFLICT found for ', classAndMethodPrintString,
+ 				(' with newer changeset' asPluralBasedOn: conflictingChangeSets).
+ 	conflictingChangeSets do: [:cs | self class log: ' ', cs name].
+ 	^ changeRecordSource
+ !

Item was added:
+ ----- Method: FilePackage>>conflictsWithUpdatedMethods (in category '*UpdateStream-conflict checker') -----
+ conflictsWithUpdatedMethods
+ 	"Check this package for conflicts with methods in the image which are in newer updates."
+ 
+ 	| localFileName stream updateNumberString updateNumber imageUpdateNumber updateNumberChangeSet conflicts fileStream |
+ 
+ 	localFileName := FileDirectory localNameFor: fullName.
+ 	stream := ReadStream on: sourceSystem.
+ 	stream upToAll: 'latest update: #'.
+ 	updateNumberString := stream upTo: $].
+ 	stream close.
+ 	
+ 	fileStream := FileStream readOnlyFileNamed: fullName.
+ 	(fileStream contentsOfEntireFile includes: Character linefeed)
+ 		ifTrue: [self notifyWithLabel:  'The changeset file ', localFileName, ' contains linefeeds.  Proceed if...
+ you know that this is okay (e.g. the file contains raw binary data).'].
+ 	fileStream close.
+ 
+ 	updateNumberString isEmpty ifFalse:		"remove prepended junk, if any"
+ 		[updateNumberString := (updateNumberString findTokens: Character space) last].
+ 	updateNumberString asInteger ifNil:
+ 		[(self confirm: 'Error: ', localFileName, ' has no valid Latest Update number in its header.
+ Do you want to enter an update number for this file?')
+ 			ifFalse: [^ self]
+ 			ifTrue: [updateNumberString := UIManager default
+ 						request: 'Please enter the estimated update number (e.g. 4332).']].
+ 	updateNumberString asInteger ifNil: [self inform: 'Conflict check cancelled.'. ^ self].
+ 	updateNumber := updateNumberString asInteger.
+ 
+ 	imageUpdateNumber := SystemVersion current highestUpdate.
+ 	updateNumber > imageUpdateNumber ifTrue:
+ 		[(self confirm: 'Warning: The update number for this file (#', updateNumberString, ')
+ is greater than the highest update number for this image (#', imageUpdateNumber asString, ').
+ This probably means you need to update your image.
+ Should we proceed anyway as if the file update number is #', imageUpdateNumber asString, '?')
+ 			ifTrue:
+ 				[updateNumber := imageUpdateNumber.
+ 				updateNumberString := imageUpdateNumber asString]
+ 			ifFalse: [^ self]].
+ 
+ 	updateNumberChangeSet := self findUpdateChangeSetMatching: updateNumber.
+ 	updateNumberChangeSet ifNil: [^ self].
+ 
+ 	Smalltalk isMorphic ifTrue: [self currentWorld findATranscript: self currentEvent].
+ 	self class logCr; logCr; log: 'Checking ', localFileName, ' (#', updateNumberString, ') for method conflicts with changesets after ', updateNumberChangeSet name, ' ...'.
+ 
+ 	conflicts := OrderedCollection new.
+ 	self classes do: [:pseudoClass |
+ 		(Array with: pseudoClass with: pseudoClass metaClass) do: [:classOrMeta |
+ 			classOrMeta selectorsDo: [:selector | | conflict |
+ 				conflict := self
+ 							checkForMoreRecentUpdateThanChangeSet: updateNumberChangeSet
+ 							pseudoClass: classOrMeta
+ 							selector: selector.
+ 				conflict ifNotNil: [conflicts add: conflict].
+ 			].
+ 		].
+ 	].
+ 	self class logCr; log: conflicts size asString, (' conflict' asPluralBasedOn: conflicts), ' found.'; logCr.
+ 	self class closeLog.
+ 	^ conflicts!

Item was added:
+ ----- Method: FilePackage>>findUpdateChangeSetMatching: (in category '*UpdateStream-conflict checker') -----
+ findUpdateChangeSetMatching: updateNumber
+ 	"Find update-changeset beginning with updateNumber, or reasonably close."
+ 	"This is to account for the fact that many changeset files are output from final releases, but may be tested for conflicts in a following alpha image, which will often not include that particular update-changeset from the final release but will contain ones near it.  For example, if the file updateNumber is 5180 (from 3.5 final), but the image has no update-changeset beginning with 5180 because it's a 3.6alpha image (which starts at 5181), it will try up to 5190 and down to 5170 for a close match."
+ 	| updateNumberChangeSet updateNumberToTry |
+ 
+ 	updateNumberToTry := updateNumber.
+ 	updateNumberChangeSet := nil.
+ 	[updateNumberChangeSet isNil and: [updateNumberToTry notNil]] whileTrue:
+ 		[updateNumberChangeSet := ChangesOrganizer allChangeSets
+ 			detect: [:cs | (cs name beginsWith: updateNumberToTry asString)
+ 							and: [(cs name at: (updateNumberToTry asString size + 1)) isDigit not]]
+ 			ifNone: [nil].
+ 		updateNumberToTry >= updateNumber ifTrue:
+ 			[updateNumberToTry < (updateNumber + 10)
+ 				ifTrue: [updateNumberToTry := updateNumberToTry + 1]
+ 				ifFalse: [updateNumberToTry := updateNumber]].
+ 		updateNumberToTry <= updateNumber ifTrue:
+ 			[updateNumberToTry > (updateNumber - 10)
+ 				ifTrue: [updateNumberToTry := updateNumberToTry - 1]
+ 				ifFalse: [updateNumberToTry := nil  "we're done trying"]].
+ 		].
+ 
+ 	updateNumberChangeSet ifNil:
+ 		[(self confirm: 'Warning: No changeset beginning with ',
+ updateNumber asString, ' (within +/- 10) was found in the image.
+ You must have changesets going back this far in your image
+ in order to accurately check for conflicts.
+ Proceed anyway?')
+ 			ifTrue: [updateNumberChangeSet := ChangesOrganizer allChangeSets first]].
+ 
+ 	^ updateNumberChangeSet!



More information about the Squeak-dev mailing list