2010-07-21 6 views
17

Ich versuche, ein Mock-Objekt in PHPUnit zu konfigurieren Werte für verschiedene Eigenschaften zurückPHPUnit - Erstellen von Mock-Objekte als Stubs Objekte zu handeln

Beispiel (die die __get Funktion zugegriffen verwenden):

class OriginalObject { 
public function __get($name){ 
switch($name) 
case "ParameterA": 
    return "ValueA"; 
case "ParameterB": 
    return "ValueB"; 
} 
} 

ich versuche, dies mit zu verspotten:

$mockObject = $this->getMock("OrigionalObject"); 

$mockObject ->expects($this->once()) 
    ->method('__get') 
    ->with($this->equalTo('ParameterA')) 
    ->will($this->returnValue("ValueA")); 

$mockObject ->expects($this->once()) 
    ->method('__get') 
    ->with($this->equalTo('ParameterB')) 
    ->will($this->returnValue("ValueB")); 

aber nicht schrecklich :-(

+1

Sind die Fehler ("ursprüngliche" anstelle von "Original", fehlt Schließung Anführungszeichen bei ValueA und ValueB) in der Mock Code-Teil Ihres tatsächlichen Codes oder Übertragungsfehler? – Phil

+1

LOL Danke Phil (zum Hinweis auf meine Legasthenie) Die Tippfehler (jetzt geändert) sind nur in der Beispielcode - klar dies ist nicht der eigentliche Code ausgeführt wird – Tim

Antwort

9

Ich habe spöttisch noch nicht versucht __get, aber vielleicht wird diese Arbeit:

// getMock() is deprecated 
// $mockObject = $this->getMock("OrigionalObject"); 
$mockObject = $this->createMock("OrigionalObject"); 

$mockObject->expects($this->at(0)) 
    ->method('__get') 
    ->with($this->equalTo('ParameterA')) 
    ->will($this->returnValue('ValueA')); 

$mockObject->expects($this->at(1)) 
    ->method('__get') 
    ->with($this->equalTo('ParameterB')) 
    ->will($this->returnValue('ValueB')); 

Ich habe schon $ this-> bei() in einem Test verwendet und es funktioniert (aber nicht eine optimale Lösung) . Ich habe es von dieser Lauffläche:

How can I get PHPUnit MockObjects to return different values based on a parameter?

+0

hey koen $ this-> at() funktioniert für mich - Danke dir ;-) Warum denkst du nicht, dass dies eine optimale Lösung ist? – Tim

+1

Es ist nicht wirklich skalierbar und der Test ist schwer zu lesen. Ein Rückruf kann leichter zu lesen sein, wenn Sie ihm einen guten Namen geben. Aber in erster Linie würde ich versuchen, das __get umzuformen. – koen

+0

auch, testen Sie Staat (die einige als schlechte Praxis betrachten) und noch mehr, privaten Staat (die viele als eine schlechte Praxis betrachten). Natürlich gibt es schlaue Leute, die darin kein Problem sehen und vielleicht einer von ihnen sind. – koen

4

Dies sollte funktionieren:

class Test extends \PHPUnit_Framework_TestCase { 
... 
    function testSomething() { 
     $mockObject = $this->getMock("OrigionalObject"); 

     $mockObject 
       ->expects($this->any()) 
       ->method('__get') 
       ->will($this->returnCallback('myMockGetter')); 
     ... 
    } 
... 
} 

function myMockGetter($classPropertyName) { 
    switch($classPropertyName) { 
     case 'ParameterA': 
      return 'ValueA'; 

     case 'ParameterB': 
      return 'ValueB'; 
    } 
} 
... ... 
+0

Ich denke meine Lösung ist optimaler als Koen, aber er macht einige wichtige Punkte in seinen Kommentaren. Ich denke, eine mögliche Lösung wäre, eine Testklasse zu erstellen und kein Mock-Objekt zu verwenden. Dies wird oft für Dinge wie HTTP-Adapter verwendet. –

Verwandte Themen