2010-08-26 15 views
9

Używam mockito i próbuję wykpić obiekt scala.Szyderczy obiekt scala

object Sample { } 
//test 
class SomeTest extends Specification with ScalaTest with Mockito { 
    "mocking should succeed" in { 
     val mockedSample = mock[Sample] 
    } 
} 

Daje mi to dwa błędy kompilacji.

error: Not found type Sample 
error: could not find implicit value for parameter m: 
scala.reflect.ClassManifest[<error>] 

Po zmianie próbki z obiektu na klasę działa. Czy można symulować obiekty scala za pomocą mockito? Jeśli tak, to w jaki sposób?

Odpowiedz

10

Jak napisano, twój Sample jest czysty singleton. Jego typ jest własny i jest tylko jeden element tego typu, kropka. Scala object s może rozszerzyć kolejną klasę (być może abstrakcyjną, jeśli dostarcza niezbędne definicje, aby była konkretna) i cechy. Dzięki temu uzyskujemy tożsamość typu obejmującą tych przodków.

Nie wiem, co naprawdę robi Mockito, ale według mnie to, o co prosisz, jest ściśle sprzeczne z tym, czym jest Scala object.

+3

Zdecydowanie się zgadzam tutaj. Być może uda ci się spróbować sfingować [Sample.type], ale wątpię, by zadziałało w praktyce. Zaleciłbym, aby Sample rozszerzyć pewną cechę interfejsu i wyśmiać ją w ten sposób. Największym problemem jest to, że jeśli chcesz wstrzyknąć swoją próbkę w miejsce próbki pojedynczej, musisz zrobić fajną, złą, zabawną magię odbijającą. Jeśli jesteś zainteresowany, możemy to opublikować. – jsuereth

+0

Kiedyś patrzyłem na kod źródłowy Mockito, aby odpowiedzieć na pokrewne pytanie (które z jakiegoś powodu nie mogę teraz znaleźć) i wydaje mi się, że widziałem jeden z "symulowanych" generatorów, który po prostu zwraca określoną wartość, a nie próbuje generować naprzemiennie/warianty. –

+0

Czy jest jakiś sposób na zrobienie tego z Powermock lub podobnym? Jeśli mam metodę (skutecznie globalną) na obiekcie towarzyszącym, wydaje się rozsądne, aby chcieć wyśmiać jego zachowanie; z pewnością jest to powszechny wzór w rubinowym świecie. – Korny

6

Pamiętaj, że może mock Metody danego object jeśli podniesie je do funkcji.

case class Person(name: String) 
object Person { 
    def listToJson(lp: List[Person]) = "some actual implementation" 
} 

class ClassUnderTest(listToJson: (List[Person]) => String = Person.listToJson(_)) { 
    def testIt(lp: List[Person]) = listToJson(lp) 
} 

import org.specs._ 
import org.specs.mock.Mockito 
import org.mockito.Matchers._ 

class ASpec extends Specification with Mockito { 
    "a thing" should { 
    "do whatever" in { 
     val m = mock[(List[Person]) => String] 
     val subject = new ClassUnderTest(m) 
     m(Nil) returns "mocked!" 
     subject.testIt(Nil) must_== "mocked! (this will fail on purpose)" 
    } 
    } 
} 

Tutaj nie kpię z obiektu Osoba, ale metoda na nim (prawdopodobnie tam, gdzie OP miał zamiar).

Wynik badania pokazuje szyderczy działa:

[info] == ASpec == 
[error] x a thing should 
[error] x do whatever 
[error]  'mocked![]' is not equal to 'mocked![ (this will fail on purpose)]' (ASpec.scala:21) 
[info] == ASpec == 

Tymczasem korzystanie produkcyjno-czas ClassUnderTest jest po prostu new ClassUnderTest powodu funkcja wstrzykiwany jest domyślnym argumentem.

9

Niedawno wydałem ScalaMock, bibliotekę szyderczą dla Scali, która może, między innymi, udawać pojedyncze obiekty (i towarzyszące).

+4

Na stronie pod warunkiem, że wsparcie dla pojedynczych i towarzyszących obiektów jest zadeklarowane w sekcji zatytułowanej "Plany na przyszłość". Czy framework obsługuje obecnie te funkcje? – Zotov

+2

@Zotov, wygląda na to, że obsługa kpiących obiektów jest dostępna tylko w ScalaMock2 przy użyciu wtyczki kompilatora 2.9, jak wyjaśniono w tym [tutorialu] (http://paulbutcher.com/2011/11/06/scalamock- krok po kroku/). ScalaMock3 nie wymaga wtyczki kompilatora, ponieważ bazuje na Scali 2.10 makr zamiast tego, ale nie obsługuje jeszcze wszystkich funkcji ScalaMock2, jak wspomniano w tym [blogu] (http://paulbutcher.com/2012/06/04/scalamock-3-0-preview-release /). Przedmioty szarpiące nie są więc obsługiwane w 2.10): O ile wiem, wciąż wydaje się, że jest to obecny stan projektu. –

+0

Ta biblioteka nadal nie działa całkiem dobrze – danielrvt

Powiązane problemy