ChangesBrowser.st
changeset 7953 23bd20d36582
parent 7783 a0c1578e65fb
child 8000 3412bd5bb2dc
equal deleted inserted replaced
7952:85a2949ad13a 7953:23bd20d36582
  1635         ] ifFalse:[
  1635         ] ifFalse:[
  1636             ^ 'Cannot compare this change (class not present)'.
  1636             ^ 'Cannot compare this change (class not present)'.
  1637         ].
  1637         ].
  1638     ].
  1638     ].
  1639 
  1639 
  1640     selector == #'category:' ifTrue:[
  1640     (#(#'category:' #'package:') includes:selector) ifTrue:[
  1641         receiver isMessage ifTrue:[
  1641         receiver isMessage ifTrue:[
  1642             receiver selector == #compiledMethodAt: ifTrue:[
  1642             receiver selector == #compiledMethodAt: ifTrue:[
  1643                 classGlobalNode := receiver receiver.
  1643                 classGlobalNode := receiver receiver.
  1644                 (classGlobalNode isMessage and:[classGlobalNode selector == #class]) ifTrue:[
  1644                 (classGlobalNode isMessage and:[classGlobalNode selector == #class]) ifTrue:[
  1645                     classGlobalNode := classGlobalNode receiver
  1645                     classGlobalNode := classGlobalNode receiver
  1646                 ].
  1646                 ].
  1647                 classGlobalNode isUndeclared ifTrue:[
  1647                 classGlobalNode isUndeclared ifTrue:[
  1648                     ^ 'Class does not exist.'.
  1648                     ^ 'Class does not exist.'.
  1649                 ].
  1649                 ].
  1650                 Error handle:[method := nil] do:[method := receiver evaluate].
  1650                 Error handle:[method := nil] do:[method := receiver evaluate].
  1651                 method isMethod ifTrue:[
  1651                 method isMethod ifFalse:[
       
  1652                     ^ 'There is no such method'.
       
  1653                 ].
       
  1654                 selector == #category: ifTrue:[
  1652                     method category = parseTree arg1 evaluate ifFalse:[
  1655                     method category = parseTree arg1 evaluate ifFalse:[
  1653                         ^ '(' , method class name , ' compiledMethodAt: ' , method selector storeString , ') category: ' , method category storeString.
  1656                         ^ '(' , method mclass name , ' compiledMethodAt: ' , method selector storeString , ') category: ' , method category storeString.
  1654                     ]
  1657                     ].
  1655                 ] ifFalse:[
  1658                 ] ifFalse:[
  1656                     ^ 'There is no such method'.
  1659                     method package = parseTree arg1 evaluate ifFalse:[
  1657                 ]
  1660                         ^ '(' , method mclass name , ' compiledMethodAt: ' , method selector storeString , ') package: ' , method package storeString.
       
  1661                     ].
       
  1662                 ].
       
  1663                 ^ nil
  1658             ]
  1664             ]
  1659         ]
  1665         ]
  1660     ].
  1666     ].
  1661 
  1667 
  1662     selector == #'instanceVariableNames:' ifTrue:[
  1668     selector == #'instanceVariableNames:' ifTrue:[
  1987     "
  1993     "
  1988      first look, if not already known
  1994      first look, if not already known
  1989     "
  1995     "
  1990     name := changeClassNames at:changeNr.
  1996     name := changeClassNames at:changeNr.
  1991     name notNil ifTrue:[
  1997     name notNil ifTrue:[
  1992 	name == #nil ifTrue:[^ nil].
  1998         name == #nil ifTrue:[^ nil].
  1993 	^ name
  1999         ^ name
  1994     ].
  2000     ].
  1995 
  2001 
  1996     prevMethodDefNr := changeNr.
  2002     prevMethodDefNr := changeNr.
  1997     [changeIsFollowupMethodChange at:prevMethodDefNr] whileTrue:[
  2003     [changeIsFollowupMethodChange at:prevMethodDefNr] whileTrue:[
  1998 	prevMethodDefNr := prevMethodDefNr - 1.
  2004         prevMethodDefNr := prevMethodDefNr - 1.
  1999     ].
  2005     ].
  2000 
  2006 
  2001     "
  2007     "
  2002      get the chunk
  2008      get the chunk
  2003     "
  2009     "
  2004     chunk := changeChunks at:prevMethodDefNr.
  2010     chunk := changeChunks at:prevMethodDefNr.
  2005     chunk isNil ifTrue:[^ nil].       "mhmh - empty"
  2011     chunk isNil ifTrue:[^ nil].       "mhmh - empty"
  2006 
  2012 
  2007     (chunk startsWith:'''---') ifTrue:[
  2013     (chunk startsWith:'''---') ifTrue:[
  2008 	words := chunk asCollectionOfWords.
  2014         words := chunk asCollectionOfWords.
  2009 	words size > 2 ifTrue:[
  2015         words size > 2 ifTrue:[
  2010 	    (words at:2) = 'checkin' ifTrue:[
  2016             (words at:2) = 'checkin' ifTrue:[
  2011 		name := words at:3.
  2017                 name := words at:3.
  2012 		^ name
  2018                 ^ name
  2013 	    ]
  2019             ]
  2014 	].
  2020         ].
  2015     ].
  2021     ].
  2016 
  2022 
  2017     "/ fix it - otherwise, it cannot be parsed
  2023     "/ fix it - otherwise, it cannot be parsed
  2018     (chunk endsWith:'primitiveDefinitions:') ifTrue:[
  2024     (chunk endsWith:'primitiveDefinitions:') ifTrue:[
  2019 	chunk := chunk , ''''''
  2025         chunk := chunk , ''''''
  2020     ].
  2026     ].
  2021     (chunk endsWith:'primitiveFunctions:') ifTrue:[
  2027     (chunk endsWith:'primitiveFunctions:') ifTrue:[
  2022 	chunk := chunk , ''''''
  2028         chunk := chunk , ''''''
  2023     ].
  2029     ].
  2024     (chunk endsWith:'primitiveVariables:') ifTrue:[
  2030     (chunk endsWith:'primitiveVariables:') ifTrue:[
  2025 	chunk := chunk , ''''''
  2031         chunk := chunk , ''''''
  2026     ].
  2032     ].
  2027 
  2033 
  2028     "
  2034     "
  2029      use parser to construct a parseTree
  2035      use parser to construct a parseTree
  2030     "
  2036     "
  2031     oldDollarSetting := Parser allowDollarInIdentifier.
  2037     oldDollarSetting := Parser allowDollarInIdentifier.
  2032     [
  2038     [
  2033 	Parser allowDollarInIdentifier:true.
  2039         Parser allowDollarInIdentifier:true.
  2034 "/        Class nameSpaceQuerySignal answer:(self nameSpaceForApply)
  2040 "/        Class nameSpaceQuerySignal answer:(self nameSpaceForApply)
  2035 "/        do:[
  2041 "/        do:[
  2036 	    aParseTree := Parser parseExpression:chunk.
  2042             aParseTree := Parser parseExpression:chunk.
  2037 "/        ].
  2043 "/        ].
  2038 
  2044 
  2039 	aParseTree == #Error ifTrue:[
  2045         aParseTree == #Error ifTrue:[
  2040 	    (chunk includesString:'comment') ifTrue:[
  2046             (chunk includesString:'comment') ifTrue:[
  2041 		"/ could be a comment ...
  2047                 "/ could be a comment ...
  2042 		aParseTree := Parser parseExpression:chunk , ''''.
  2048                 aParseTree := Parser parseExpression:chunk , ''''.
  2043 	    ]
  2049             ]
  2044 	].
  2050         ].
  2045     ] ensure:[
  2051     ] ensure:[
  2046 	Parser allowDollarInIdentifier:oldDollarSetting
  2052         Parser allowDollarInIdentifier:oldDollarSetting
  2047     ].
  2053     ].
  2048     (aParseTree isNil or:[aParseTree == #Error]) ifTrue:[
  2054     (aParseTree isNil or:[aParseTree == #Error]) ifTrue:[
  2049 	^ nil        "seems strange ... (could be a comment)"
  2055         ^ nil        "seems strange ... (could be a comment)"
  2050     ].
  2056     ].
  2051     aParseTree isMessage ifFalse:[
  2057     aParseTree isMessage ifFalse:[
  2052 	^ nil        "very strange ... (whats that ?)"
  2058         ^ nil        "very strange ... (whats that ?)"
  2053     ].
  2059     ].
  2054 
  2060 
  2055     "
  2061     "
  2056      ask parser for selector
  2062      ask parser for selector
  2057     "
  2063     "
  2081        #methodsFor                   "/ Dolphin support
  2087        #methodsFor                   "/ Dolphin support
  2082        #categoriesForClass           "/ Dolphin support
  2088        #categoriesForClass           "/ Dolphin support
  2083        #categoriesFor:               "/ Dolphin support
  2089        #categoriesFor:               "/ Dolphin support
  2084        #methods                      "/ STV support
  2090        #methods                      "/ STV support
  2085     ) includes:sel) ifTrue:[
  2091     ) includes:sel) ifTrue:[
  2086 	"
  2092         "
  2087 	 yes, the className is the receiver
  2093          yes, the className is the receiver
  2088 	"
  2094         "
  2089 	(recTree notNil and:[recTree ~~ #Error]) ifTrue:[
  2095         (recTree notNil and:[recTree ~~ #Error]) ifTrue:[
  2090 	    isMeta := false.
  2096             isMeta := false.
  2091 	    recTree isUnaryMessage ifTrue:[
  2097             recTree isUnaryMessage ifTrue:[
  2092 		(recTree selector ~~ #class) ifTrue:[^ nil].
  2098                 (recTree selector ~~ #class) ifTrue:[^ nil].
  2093 		"id class methodsFor:..."
  2099                 "id class methodsFor:..."
  2094 		recTree := recTree receiver.
  2100                 recTree := recTree receiver.
  2095 		isMeta := true.
  2101                 isMeta := true.
  2096 	    ].
  2102             ].
  2097 	    recTree isPrimary ifTrue:[
  2103             recTree isPrimary ifTrue:[
  2098 		name := recTree name.
  2104                 name := recTree name.
  2099 		isMeta ifTrue:[
  2105                 isMeta ifTrue:[
  2100 		    name := name , ' class'.
  2106                     name := name , ' class'.
  2101 		].
  2107                 ].
  2102 		^ name
  2108                 ^ name
  2103 	    ]
  2109             ]
  2104 	].
  2110         ].
  2105 	"more strange things"
  2111         "more strange things"
  2106 	^ nil
  2112         ^ nil
  2107     ].
  2113     ].
  2108 
  2114 
  2109     "
  2115     "
  2110      is it a change in a class-description ?
  2116      is it a change in a class-description ?
  2111     "
  2117     "
  2112 
  2118 
  2113     (('subclass:*' match:sel)
  2119     (('subclass:*' match:sel)
  2114     or:[('variable*ubclass:*' match:sel)]) ifTrue:[
  2120     or:[('variable*ubclass:*' match:sel)]) ifTrue:[
  2115 	"/ must parse the full changes text, to get
  2121         "/ must parse the full changes text, to get
  2116 	"/ privacy information.
  2122         "/ privacy information.
  2117 
  2123 
  2118 	changeStream := self streamForChange:changeNr.
  2124         changeStream := self streamForChange:changeNr.
  2119 	changeStream notNil ifTrue:[
  2125         changeStream notNil ifTrue:[
  2120 	    chunk := changeStream nextChunk.
  2126             chunk := changeStream nextChunk.
  2121 	    changeStream close.
  2127             changeStream close.
  2122 	    fullParseTree := Parser parseExpression:chunk.
  2128             fullParseTree := Parser parseExpression:chunk.
  2123 	    (fullParseTree isNil or:[fullParseTree == #Error]) ifTrue:[
  2129             (fullParseTree isNil or:[fullParseTree == #Error]) ifTrue:[
  2124 		fullParseTree := nil
  2130                 fullParseTree := nil
  2125 	    ] ifFalse:[
  2131             ] ifFalse:[
  2126 		fullParseTree isMessage ifFalse:[
  2132                 fullParseTree isMessage ifFalse:[
  2127 		    fullParseTree := nil
  2133                     fullParseTree := nil
  2128 		]
  2134                 ]
  2129 	    ].
  2135             ].
  2130 	    "/ actually, the nil case cannot happen
  2136             "/ actually, the nil case cannot happen
  2131 	    fullParseTree notNil ifTrue:[
  2137             fullParseTree notNil ifTrue:[
  2132 		aParseTree := fullParseTree.
  2138                 aParseTree := fullParseTree.
  2133 		sel := aParseTree selector.
  2139                 sel := aParseTree selector.
  2134 	    ].
  2140             ].
  2135 	].
  2141         ].
  2136 
  2142 
  2137 	arg1Tree := aParseTree arg1.
  2143         arg1Tree := aParseTree arg1.
  2138 	(arg1Tree notNil and:[arg1Tree isConstant]) ifTrue:[
  2144         (arg1Tree notNil and:[arg1Tree isConstant]) ifTrue:[
  2139 	    name := arg1Tree value asString.
  2145             name := arg1Tree value asString.
  2140 
  2146 
  2141 	    "/ is it a private-class ?
  2147             "/ is it a private-class ?
  2142 	    ('*privateIn:' match:sel) ifTrue:[
  2148             ('*privateIn:' match:sel) ifTrue:[
  2143 		ownerTree := aParseTree args last.
  2149                 ownerTree := aParseTree args last.
  2144 		ownerName := ownerTree name asString.
  2150                 ownerName := ownerTree name asString.
  2145 		name := ownerName , '::' , name
  2151                 name := ownerName , '::' , name
  2146 	    ].
  2152             ].
  2147 	    ^ name
  2153             ^ name
  2148 	].
  2154         ].
  2149 	"very strange"
  2155         "very strange"
  2150 	^ nil
  2156         ^ nil
  2151     ].
  2157     ].
  2152 
  2158 
  2153     "
  2159     "
  2154      is it a class remove ?
  2160      is it a class remove ?
  2155     "
  2161     "
  2156     (sel == #removeClass:) ifTrue:[
  2162     (sel == #removeClass:) ifTrue:[
  2157 	(recTree notNil
  2163         (recTree notNil
  2158 	and:[recTree ~~ #Error
  2164         and:[recTree ~~ #Error
  2159 	and:[recTree isPrimary
  2165         and:[recTree isPrimary
  2160 	and:[recTree name = 'Smalltalk']]]) ifTrue:[
  2166         and:[recTree name = 'Smalltalk']]]) ifTrue:[
  2161 	    arg1Tree := aParseTree arg1.
  2167             arg1Tree := aParseTree arg1.
  2162 	    (arg1Tree notNil and:[arg1Tree isPrimary]) ifTrue:[
  2168             (arg1Tree notNil and:[arg1Tree isPrimary]) ifTrue:[
  2163 		name := arg1Tree name.
  2169                 name := arg1Tree name.
  2164 		^ name
  2170                 ^ name
  2165 	    ].
  2171             ].
  2166 	]
  2172         ]
  2167     ].
  2173     ].
  2168 
  2174 
  2169     "
  2175     "
  2170      is it a method category change ?
  2176      is it a method category change ?
  2171     "
  2177     "
  2172     ((sel == #category:)
  2178     ((sel == #category:)
  2173     or:[sel == #privacy:]) ifTrue:[
  2179     or:[sel == #package:
  2174 	(recTree notNil
  2180     or:[sel == #privacy:]]) ifTrue:[
  2175 	and:[recTree ~~ #Error
  2181         (recTree notNil
  2176 	and:[recTree isMessage
  2182         and:[recTree ~~ #Error
  2177 	and:[recTree selector == #compiledMethodAt:]]]) ifTrue:[
  2183         and:[recTree isMessage
  2178 	    isMeta := false.
  2184         and:[recTree selector == #compiledMethodAt:]]]) ifTrue:[
  2179 	    recTree := recTree receiver.
  2185             isMeta := false.
  2180 	    recTree isUnaryMessage ifTrue:[
  2186             recTree := recTree receiver.
  2181 		(recTree selector ~~ #class) ifTrue:[^ nil].
  2187             recTree isUnaryMessage ifTrue:[
  2182 		"id class "
  2188                 (recTree selector ~~ #class) ifTrue:[^ nil].
  2183 		recTree := recTree receiver
  2189                 "id class "
  2184 	    ].
  2190                 recTree := recTree receiver
  2185 	    recTree isPrimary ifTrue:[
  2191             ].
  2186 		isMeta ifTrue:[
  2192             recTree isPrimary ifTrue:[
  2187 		    name := name , ' class'.
  2193                 isMeta ifTrue:[
  2188 		].
  2194                     name := name , ' class'.
  2189 		name := recTree name.
  2195                 ].
  2190 		^ name
  2196                 name := recTree name.
  2191 	    ]
  2197                 ^ name
  2192 	]
  2198             ]
       
  2199         ]
  2193     ].
  2200     ].
  2194     ^ nil
  2201     ^ nil
  2195 
  2202 
  2196     "Modified: / 13.2.2000 / 15:05:28 / cg"
  2203     "Modified: / 13.2.2000 / 15:05:28 / cg"
  2197 !
  2204 !
  2805     ^ aborted not
  2812     ^ aborted not
  2806 
  2813 
  2807     "Modified: / 20-11-2006 / 13:15:48 / cg"
  2814     "Modified: / 20-11-2006 / 13:15:48 / cg"
  2808 !
  2815 !
  2809 
  2816 
       
  2817 compareCategoryChange:parseTree
       
  2818     |receiverExpression method|
       
  2819 
       
  2820     receiverExpression := parseTree receiver.
       
  2821     receiverExpression isMessage ifTrue:[
       
  2822         receiverExpression selector == #compiledMethodAt: ifTrue:[
       
  2823             (receiverExpression receiver evaluate isBehavior
       
  2824              and:[(method := receiverExpression evaluate) isMethod]) ifTrue:[
       
  2825                 method category = parseTree arg1 evaluate ifTrue:[
       
  2826                     ^ true -> 'Change has no effect\\(same category)'.
       
  2827                 ] ifFalse:[
       
  2828                     ^ false -> 'Category is different (''' , method category , ''' vs. ''' , parseTree arg1 evaluate , ''')'.
       
  2829                 ]
       
  2830             ] ifFalse:[
       
  2831                 ^ nil -> 'There is no such method'.
       
  2832             ]
       
  2833         ]
       
  2834     ].
       
  2835     ^ nil -> 'Unhandled receiver'
       
  2836 !
       
  2837 
  2810 compareChange:changeNr
  2838 compareChange:changeNr
  2811     "compare a change with the current (in-image) version; show the result of the compare (as dialog)"
  2839     "compare a change with the current (in-image) version; show the result of the compare (as dialog)"
  2812 
  2840 
  2813     ^ self compareChange:changeNr showResult:true
  2841     ^ self compareChange:changeNr showResult:true
  2814 !
  2842 !
  2817     "compare a change with current version.
  2845     "compare a change with current version.
  2818      Return the result of the compare (same -> true, different -> false, uncomparable -> nil).
  2846      Return the result of the compare (same -> true, different -> false, uncomparable -> nil).
  2819      If doShowResult is true, the outcome is shown in a dialog/diffViewer."
  2847      If doShowResult is true, the outcome is shown in a dialog/diffViewer."
  2820 
  2848 
  2821     |aStream chunk sawExcla parseTree thisClass cat oldSource newSource
  2849     |aStream chunk sawExcla parseTree thisClass cat oldSource newSource
  2822      parser sel oldMethod outcome showDiff d t1 t2 selector isLoaded
  2850      parser sel oldMethod outcome showDiff d t1 t2 selector isLoaded beep superClass thisClassSym varsHere varsInChange addedVars removedVars
  2823      method beep superClass thisClassSym varsHere varsInChange addedVars removedVars
  2851      isSame ownerClass superClassHere superClassInChange sameAndOutcome |
  2824      isSame ownerClass superClassHere superClassInChange|
       
  2825 
  2852 
  2826     aStream := self streamForChange:changeNr.
  2853     aStream := self streamForChange:changeNr.
  2827     aStream isNil ifTrue:[^ nil].
  2854     aStream isNil ifTrue:[^ nil].
  2828 
  2855 
  2829     showDiff := false.
  2856     showDiff := false.
  2848         ].
  2875         ].
  2849         (parseTree notNil and:[parseTree ~~ #Error and:[ parseTree isMessage ]]) ifTrue:[
  2876         (parseTree notNil and:[parseTree ~~ #Error and:[ parseTree isMessage ]]) ifTrue:[
  2850             selector := parseTree selector.
  2877             selector := parseTree selector.
  2851 
  2878 
  2852             selector == #'removeSelector:' ifTrue:[
  2879             selector == #'removeSelector:' ifTrue:[
  2853                 thisClass := (parseTree receiver evaluate).
  2880                 sameAndOutcome := self compareRemoveSelectorChange:parseTree.
  2854                 thisClass isBehavior ifTrue:[
  2881                 isSame := sameAndOutcome key.
  2855                     (self checkClassIsLoaded:thisClass) ifTrue:[
  2882                 outcome := sameAndOutcome value.
  2856                         selector := (parseTree arg1 evaluate).
  2883             ].
  2857                         (thisClass includesSelector:selector) ifTrue:[
  2884             selector == #'package:' ifTrue:[
  2858                             outcome := 'Change removes the #' , selector , ' method from ' , thisClass name.
  2885                 sameAndOutcome := self comparePackageChange:parseTree.
  2859                             isSame := false.
  2886                 isSame := sameAndOutcome key.
  2860                         ] ifFalse:[
  2887                 outcome := sameAndOutcome value.
  2861                             outcome := 'Change has no effect\\(there is no method for #' , selector , ' in ' , thisClass name , ')'.
       
  2862                             isSame := true.
       
  2863                         ]
       
  2864                     ] ifFalse:[
       
  2865                         beep := true.
       
  2866                         outcome := 'Cannot compare this change (compare requires class to be loaded).'.
       
  2867                         isSame := nil.
       
  2868                     ]
       
  2869                 ] ifFalse:[
       
  2870                     outcome := 'Cannot compare this change (class not present)'.
       
  2871                     isSame := nil.
       
  2872                 ].
       
  2873             ].
  2888             ].
  2874             selector == #'category:' ifTrue:[
  2889             selector == #'category:' ifTrue:[
  2875                 parseTree receiver isMessage ifTrue:[
  2890                 sameAndOutcome := self compareCategoryChange:parseTree.
  2876                     parseTree receiver selector == #compiledMethodAt: ifTrue:[
  2891                 isSame := sameAndOutcome key.
  2877                         |receiver|
  2892                 outcome := sameAndOutcome value.
  2878                         receiver := parseTree receiver.
       
  2879                         (receiver receiver evaluate isBehavior
       
  2880                          and:[(method := receiver evaluate) isMethod]) ifTrue:[
       
  2881                             method category = parseTree arg1 evaluate ifTrue:[
       
  2882                                 outcome := 'Change has no effect\\(same category)'.
       
  2883                                 isSame := true.
       
  2884                             ] ifFalse:[
       
  2885                                 outcome := 'Category is different (''' , method category , ''' vs. ''' , parseTree arg1 evaluate , ''')'.
       
  2886                                 isSame := false.
       
  2887                             ]
       
  2888                         ] ifFalse:[
       
  2889                             beep := true.
       
  2890                             outcome := 'There is no such method'.
       
  2891                             isSame := nil.
       
  2892                         ]
       
  2893                     ]
       
  2894                 ]
       
  2895             ].
  2893             ].
  2896             selector == #'comment:' ifTrue:[
  2894             selector == #'comment:' ifTrue:[
  2897                 thisClass := (parseTree receiver evaluate).
  2895                 sameAndOutcome := self compareCommentChange:parseTree.
  2898                 thisClass isBehavior ifTrue:[
  2896                 isSame := sameAndOutcome key.
  2899                     (self checkClassIsLoaded:thisClass) ifTrue:[
  2897                 outcome := sameAndOutcome value.
  2900                         (thisClass comment = parseTree arg1 evaluate) ifTrue:[
       
  2901                             outcome := 'Change has no effect\\(same comment)'.
       
  2902                             isSame := true.
       
  2903                         ] ifFalse:[
       
  2904                             outcome := 'Comment is different'.
       
  2905                             isSame := false.
       
  2906                         ]
       
  2907                     ] ifFalse:[
       
  2908                         beep := true.
       
  2909                         outcome := 'Cannot compare this change (compare requires class to be loaded).'.
       
  2910                         isSame := nil.
       
  2911                     ]
       
  2912                 ] ifFalse:[
       
  2913                     outcome := 'Cannot compare this change (class not present)'.
       
  2914                     isSame := nil.
       
  2915                 ].
       
  2916             ].
  2898             ].
  2917 
  2899 
  2918             selector == #'instanceVariableNames:' ifTrue:[
  2900             selector == #'instanceVariableNames:' ifTrue:[
  2919                 parseTree receiver isMessage ifTrue:[
  2901                 sameAndOutcome := self compareInstanceVariableNamesChange:parseTree.
  2920                     parseTree receiver selector == #class ifTrue:[
  2902                 isSame := sameAndOutcome key.
  2921                         thisClass := (parseTree receiver evaluate).
  2903                 outcome := sameAndOutcome value.
  2922                         varsHere := thisClass instanceVariableString asCollectionOfWords.
       
  2923                         varsInChange := (parseTree arguments at:1) evaluate asCollectionOfWords.
       
  2924                         varsHere = varsInChange ifTrue:[
       
  2925                             outcome := 'Change has no effect\\(same definition)'.
       
  2926                             isSame := true.
       
  2927                         ] ifFalse:[
       
  2928                             outcome := 'Class-instanceVariable definition is different'.
       
  2929                             isSame := false.
       
  2930                         ].
       
  2931                     ].
       
  2932                 ]
       
  2933             ].
  2904             ].
  2934 
  2905 
  2935             (Class definitionSelectors includes:selector)
  2906             (Class definitionSelectors includes:selector)
  2936             "/ selector == #'subclass:instanceVariableNames:classVariableNames:poolDictionaries:category:'
  2907             "/ selector == #'subclass:instanceVariableNames:classVariableNames:poolDictionaries:category:'
  2937             ifTrue:[
  2908             ifTrue:[
  3179 
  3150 
  3180     "Created: / 24.11.1995 / 14:30:46 / cg"
  3151     "Created: / 24.11.1995 / 14:30:46 / cg"
  3181     "Modified: / 13.2.2000 / 15:04:39 / cg"
  3152     "Modified: / 13.2.2000 / 15:04:39 / cg"
  3182 !
  3153 !
  3183 
  3154 
       
  3155 compareCommentChange:parseTree
       
  3156     |thisClass|
       
  3157 
       
  3158     thisClass := (parseTree receiver evaluate).
       
  3159     thisClass isBehavior ifTrue:[
       
  3160         (self checkClassIsLoaded:thisClass) ifTrue:[
       
  3161             (thisClass comment = parseTree arg1 evaluate) ifTrue:[
       
  3162                 ^ true -> 'Change has no effect\\(same comment)'.
       
  3163             ] ifFalse:[
       
  3164                 ^ false -> 'Comment is different'.
       
  3165             ]
       
  3166         ] ifFalse:[
       
  3167             ^ nil -> 'Cannot compare this change (compare requires class to be loaded).'.
       
  3168         ]
       
  3169     ].
       
  3170     ^ nil -> 'Cannot compare this change (class not present)'.
       
  3171 !
       
  3172 
       
  3173 compareInstanceVariableNamesChange:parseTree
       
  3174     |receiverExpression thisClass varsHere varsInChange |
       
  3175 
       
  3176     receiverExpression := parseTree receiver.
       
  3177     receiverExpression isMessage ifTrue:[
       
  3178         receiverExpression selector == #class ifTrue:[
       
  3179             thisClass := (receiverExpression evaluate).
       
  3180             varsHere := thisClass instanceVariableString asCollectionOfWords.
       
  3181             varsInChange := (parseTree arguments at:1) evaluate asCollectionOfWords.
       
  3182             varsHere = varsInChange ifTrue:[
       
  3183                 ^ true -> 'Change has no effect\\(same definition)'.
       
  3184             ] ifFalse:[
       
  3185                 ^ false -> 'Class-instanceVariable definition is different'.
       
  3186             ].
       
  3187         ].
       
  3188     ].
       
  3189     ^ nil -> 'Unhandled receiver'
       
  3190 !
       
  3191 
       
  3192 comparePackageChange:parseTree
       
  3193     |receiverExpression method|
       
  3194 
       
  3195     receiverExpression := parseTree receiver.
       
  3196     receiverExpression isMessage ifTrue:[
       
  3197         receiverExpression selector == #compiledMethodAt: ifTrue:[
       
  3198             (receiverExpression receiver evaluate isBehavior
       
  3199              and:[(method := receiverExpression evaluate) isMethod]) ifTrue:[
       
  3200                 method package = parseTree arg1 evaluate ifTrue:[
       
  3201                     ^ true -> 'Change has no effect\\(same package)'.
       
  3202                 ] ifFalse:[
       
  3203                     ^ false -> 'Package is different (''' , method package , ''' vs. ''' , parseTree arg1 evaluate , ''')'.
       
  3204                 ]
       
  3205             ] ifFalse:[
       
  3206                 ^ nil -> 'There is no such method'.
       
  3207             ]
       
  3208         ]
       
  3209     ].
       
  3210     ^ nil -> 'Unhandled receiver'
       
  3211 !
       
  3212 
       
  3213 compareRemoveSelectorChange:parseTree
       
  3214     |thisClass selector|
       
  3215 
       
  3216     thisClass := (parseTree receiver evaluate).
       
  3217     thisClass isBehavior ifTrue:[
       
  3218         (self checkClassIsLoaded:thisClass) ifTrue:[
       
  3219             selector := (parseTree arg1 evaluate).
       
  3220             (thisClass includesSelector:selector) ifTrue:[
       
  3221                 ^ false -> 'Change removes the #' , selector , ' method from ' , thisClass name.
       
  3222             ] ifFalse:[
       
  3223                 ^ true -> 'Change has no effect\\(there is no method for #' , selector , ' in ' , thisClass name , ')'.
       
  3224             ]
       
  3225         ] ifFalse:[
       
  3226             ^ nil -> 'Cannot compare this change (compare requires class to be loaded).'.
       
  3227         ]
       
  3228     ].
       
  3229     ^ nil -> 'Cannot compare this change (class not present)'.
       
  3230 !
       
  3231 
  3184 compressForClass:aClassNameOrNil
  3232 compressForClass:aClassNameOrNil
  3185     "compress the change-set;
  3233     "compress the change-set;
  3186      this replaces multiple method-changes by the last (i.e. the most recent) change.
  3234      this replaces multiple method-changes by the last (i.e. the most recent) change.
  3187      If the class argument is nil, compress for all classes.
  3235      If the class argument is nil, compress for all classes.
  3188      otherwise, only changes for that class are compressed."
  3236      otherwise, only changes for that class are compressed."
  5938 ! !
  5986 ! !
  5939 
  5987 
  5940 !ChangesBrowser class methodsFor:'documentation'!
  5988 !ChangesBrowser class methodsFor:'documentation'!
  5941 
  5989 
  5942 version
  5990 version
  5943     ^ '$Header: /cvs/stx/stx/libtool/ChangesBrowser.st,v 1.372 2007-04-04 16:27:28 stefan Exp $'
  5991     ^ '$Header: /cvs/stx/stx/libtool/ChangesBrowser.st,v 1.373 2008-01-27 17:11:10 cg Exp $'
  5944 ! !
  5992 ! !