Browse Source

Fix class copy process that shared slots.

They should have been copied instead.

Also add #slots and make #instanceVariableNames only return ivar names
(though no visible change atm, as only slots are ivars,
but there can be different return values in the future).
Herby Vojčík 4 years ago
parent
commit
a2e891d56a
5 changed files with 101 additions and 17 deletions
  1. 3 0
      lang/API-CHANGES.txt
  2. 30 7
      lang/src/Kernel-Classes.js
  3. 6 2
      lang/src/Kernel-Classes.st
  4. 58 7
      lang/src/Kernel-Tests.js
  5. 4 1
      lang/src/Kernel-Tests.st

+ 3 - 0
lang/API-CHANGES.txt

@@ -2,7 +2,10 @@
 
 * Deprecate ClassBuilder >> addSubclass:named:instanceVariableNames:package:.
 * Deprecate ... >> migrateClassNamed:superclass:instanceVariableNames:package:.
+* Behavior >> instanceVariableNames aimed at only that. No visible change atm.
 
++ Behavior >>
+  + slots
 + ClassBuilder >>
   + addSubclass:named:slots:package:
   + migrateClassNamed:superclass:slots:package:

+ 30 - 7
lang/src/Kernel-Classes.js

@@ -405,15 +405,20 @@ selector: "instanceVariableNames",
 protocol: "accessing",
 //>>excludeStart("ide", pragmas.excludeIdeData);
 args: [],
-source: "instanceVariableNames\x0a\x09^ slots",
+source: "instanceVariableNames\x0a\x09^ slots select: #isString",
 referencedClasses: [],
 //>>excludeEnd("ide");
 pragmas: [],
-messageSends: []
+messageSends: ["select:"]
 }, function ($methodClass){ return function (){
 var self=this,$self=this;
-return $self.slots;
-
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+return $core.withContext(function($ctx1) {
+//>>excludeEnd("ctx");
+return $recv($self.slots)._select_("isString");
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+}, function($ctx1) {$ctx1.fill(self,"instanceVariableNames",{})});
+//>>excludeEnd("ctx");
 }; }),
 $globals.Behavior);
 
@@ -621,6 +626,24 @@ return $recv($self._javaScriptConstructor())._prototype();
 }; }),
 $globals.Behavior);
 
+$core.addMethod(
+$core.method({
+selector: "slots",
+protocol: "accessing",
+//>>excludeStart("ide", pragmas.excludeIdeData);
+args: [],
+source: "slots\x0a\x09^ slots",
+referencedClasses: [],
+//>>excludeEnd("ide");
+pragmas: [],
+messageSends: []
+}, function ($methodClass){ return function (){
+var self=this,$self=this;
+return $self.slots;
+
+}; }),
+$globals.Behavior);
+
 $core.addMethod(
 $core.method({
 selector: "subclasses",
@@ -1668,11 +1691,11 @@ selector: "copyClass:named:",
 protocol: "copying",
 //>>excludeStart("ide", pragmas.excludeIdeData);
 args: ["aClass", "className"],
-source: "copyClass: aClass named: className\x0a\x09| newClass |\x0a\x0a\x09newClass := self\x0a\x09\x09addSubclassOf: aClass superclass\x0a\x09\x09named: className\x0a\x09\x09slots: aClass instanceVariableNames\x0a\x09\x09package: aClass package name.\x0a\x0a\x09self copyClass: aClass to: newClass.\x0a\x09\x0a\x09SystemAnnouncer current\x0a\x09\x09announce: (ClassAdded new\x0a\x09\x09\x09theClass: newClass;\x0a\x09\x09\x09yourself).\x0a\x09\x0a\x09^ newClass",
+source: "copyClass: aClass named: className\x0a\x09| newClass |\x0a\x0a\x09newClass := self\x0a\x09\x09addSubclassOf: aClass superclass\x0a\x09\x09named: className\x0a\x09\x09slots: aClass slots copy\x0a\x09\x09package: aClass package name.\x0a\x0a\x09self copyClass: aClass to: newClass.\x0a\x09\x0a\x09SystemAnnouncer current\x0a\x09\x09announce: (ClassAdded new\x0a\x09\x09\x09theClass: newClass;\x0a\x09\x09\x09yourself).\x0a\x09\x0a\x09^ newClass",
 referencedClasses: ["SystemAnnouncer", "ClassAdded"],
 //>>excludeEnd("ide");
 pragmas: [],
-messageSends: ["addSubclassOf:named:slots:package:", "superclass", "instanceVariableNames", "name", "package", "copyClass:to:", "announce:", "current", "theClass:", "new", "yourself"]
+messageSends: ["addSubclassOf:named:slots:package:", "superclass", "copy", "slots", "name", "package", "copyClass:to:", "announce:", "current", "theClass:", "new", "yourself"]
 }, function ($methodClass){ return function (aClass,className){
 var self=this,$self=this;
 var newClass;
@@ -1680,7 +1703,7 @@ var newClass;
 return $core.withContext(function($ctx1) {
 //>>excludeEnd("ctx");
 var $1,$2;
-newClass=$self._addSubclassOf_named_slots_package_($recv(aClass)._superclass(),className,$recv(aClass)._instanceVariableNames(),$recv($recv(aClass)._package())._name());
+newClass=$self._addSubclassOf_named_slots_package_($recv(aClass)._superclass(),className,$recv($recv(aClass)._slots())._copy(),$recv($recv(aClass)._package())._name());
 $self._copyClass_to_(aClass,newClass);
 $1=$recv($globals.SystemAnnouncer)._current();
 $2=$recv($globals.ClassAdded)._new();

+ 6 - 2
lang/src/Kernel-Classes.st

@@ -67,7 +67,7 @@ beJavaScriptSubclassOf: aJavaScriptFunction
 !
 
 instanceVariableNames
-	^ slots
+	^ slots select: #isString
 !
 
 javaScriptConstructor
@@ -106,6 +106,10 @@ prototype
 	^ self javaScriptConstructor prototype
 !
 
+slots
+	^ slots
+!
+
 subclasses
 	self subclassResponsibility
 !
@@ -494,7 +498,7 @@ copyClass: aClass named: className
 	newClass := self
 		addSubclassOf: aClass superclass
 		named: className
-		slots: aClass instanceVariableNames
+		slots: aClass slots copy
 		package: aClass package name.
 
 	self copyClass: aClass to: newClass.

+ 58 - 7
lang/src/Kernel-Tests.js

@@ -16602,11 +16602,11 @@ selector: "assert:isClassCopyOf:",
 protocol: "running",
 //>>excludeStart("ide", pragmas.excludeIdeData);
 args: ["aClass", "anotherClass"],
-source: "assert: aClass isClassCopyOf: anotherClass\x0a\x09self assert: aClass superclass == anotherClass superclass.\x0a\x09self assert: aClass instanceVariableNames == anotherClass instanceVariableNames.\x0a\x09self assert: aClass package == anotherClass package.\x0a\x09self assert: (aClass package classes includes: aClass).\x0a\x09self assert: aClass methodDictionary keys equals: anotherClass methodDictionary keys",
+source: "assert: aClass isClassCopyOf: anotherClass\x0a\x09self assert: aClass superclass == anotherClass superclass.\x0a\x09self deny: aClass slots == anotherClass slots.\x0a\x09self assert: aClass slots equals: anotherClass slots.\x0a\x09self deny: aClass class slots == anotherClass class slots.\x0a\x09self assert: aClass class slots equals: anotherClass class slots.\x0a\x09self assert: aClass package == anotherClass package.\x0a\x09self assert: (aClass package classes includes: aClass).\x0a\x09self assert: aClass methodDictionary keys equals: anotherClass methodDictionary keys",
 referencedClasses: [],
 //>>excludeEnd("ide");
 pragmas: [],
-messageSends: ["assert:", "==", "superclass", "instanceVariableNames", "package", "includes:", "classes", "assert:equals:", "keys", "methodDictionary"]
+messageSends: ["assert:", "==", "superclass", "deny:", "slots", "assert:equals:", "class", "package", "includes:", "classes", "keys", "methodDictionary"]
 }, function ($methodClass){ return function (aClass,anotherClass){
 var self=this,$self=this;
 //>>excludeStart("ctx", pragmas.excludeDebugContexts);
@@ -16625,17 +16625,68 @@ return $core.withContext(function($ctx1) {
 ,$ctx1.sendIdx["assert:"]=1
 //>>excludeEnd("ctx");
 ][0];
-[$self._assert_([$recv([$recv(aClass)._instanceVariableNames()
+[$self._deny_([$recv([$recv(aClass)._slots()
 //>>excludeStart("ctx", pragmas.excludeDebugContexts);
-,$ctx1.sendIdx["instanceVariableNames"]=1
+,$ctx1.sendIdx["slots"]=1
 //>>excludeEnd("ctx");
-][0]).__eq_eq($recv(anotherClass)._instanceVariableNames())
+][0]).__eq_eq([$recv(anotherClass)._slots()
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+,$ctx1.sendIdx["slots"]=2
+//>>excludeEnd("ctx");
+][0])
 //>>excludeStart("ctx", pragmas.excludeDebugContexts);
 ,$ctx1.sendIdx["=="]=2
 //>>excludeEnd("ctx");
 ][0])
 //>>excludeStart("ctx", pragmas.excludeDebugContexts);
-,$ctx1.sendIdx["assert:"]=2
+,$ctx1.sendIdx["deny:"]=1
+//>>excludeEnd("ctx");
+][0];
+[$self._assert_equals_([$recv(aClass)._slots()
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+,$ctx1.sendIdx["slots"]=3
+//>>excludeEnd("ctx");
+][0],[$recv(anotherClass)._slots()
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+,$ctx1.sendIdx["slots"]=4
+//>>excludeEnd("ctx");
+][0])
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+,$ctx1.sendIdx["assert:equals:"]=1
+//>>excludeEnd("ctx");
+][0];
+$self._deny_([$recv([$recv([$recv(aClass)._class()
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+,$ctx1.sendIdx["class"]=1
+//>>excludeEnd("ctx");
+][0])._slots()
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+,$ctx1.sendIdx["slots"]=5
+//>>excludeEnd("ctx");
+][0]).__eq_eq([$recv([$recv(anotherClass)._class()
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+,$ctx1.sendIdx["class"]=2
+//>>excludeEnd("ctx");
+][0])._slots()
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+,$ctx1.sendIdx["slots"]=6
+//>>excludeEnd("ctx");
+][0])
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+,$ctx1.sendIdx["=="]=3
+//>>excludeEnd("ctx");
+][0]);
+[$self._assert_equals_([$recv([$recv(aClass)._class()
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+,$ctx1.sendIdx["class"]=3
+//>>excludeEnd("ctx");
+][0])._slots()
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+,$ctx1.sendIdx["slots"]=7
+//>>excludeEnd("ctx");
+][0],$recv($recv(anotherClass)._class())._slots())
+//>>excludeStart("ctx", pragmas.excludeDebugContexts);
+,$ctx1.sendIdx["assert:equals:"]=2
 //>>excludeEnd("ctx");
 ][0];
 [$self._assert_($recv([$recv(aClass)._package()
@@ -16648,7 +16699,7 @@ return $core.withContext(function($ctx1) {
 //>>excludeEnd("ctx");
 ][0]))
 //>>excludeStart("ctx", pragmas.excludeDebugContexts);
-,$ctx1.sendIdx["assert:"]=3
+,$ctx1.sendIdx["assert:"]=2
 //>>excludeEnd("ctx");
 ][0];
 $self._assert_($recv($recv($recv(aClass)._package())._classes())._includes_(aClass));

+ 4 - 1
lang/src/Kernel-Tests.st

@@ -3050,7 +3050,10 @@ is: anObject javaScriptInstanceOf: aJavaScriptClass
 
 assert: aClass isClassCopyOf: anotherClass
 	self assert: aClass superclass == anotherClass superclass.
-	self assert: aClass instanceVariableNames == anotherClass instanceVariableNames.
+	self deny: aClass slots == anotherClass slots.
+	self assert: aClass slots equals: anotherClass slots.
+	self deny: aClass class slots == anotherClass class slots.
+	self assert: aClass class slots equals: anotherClass class slots.
 	self assert: aClass package == anotherClass package.
 	self assert: (aClass package classes includes: aClass).
 	self assert: aClass methodDictionary keys equals: anotherClass methodDictionary keys