I get a 'parameter count mismatch' TargetParameterCountException when I want to test my Tenant repository:
The interface:
public interface ITenantRepository
{
IQueryable<Tenant> Get(Expression<Func<Tenant, bool>> filter = null,
Func<IQueryable<Tenant>, IOrderedQueryable<Tenant>> orderBy = null,
string includeProperties = null);
}
The test code:
var TenantRepository = new Mock<ITenantRepository>();
TenantRepository
.Setup(p => p.Get(It.IsAny<Expression<Func<Tenant, bool>>>(),
It.IsAny<Func<IQueryable<Tenant>,IOrderedQueryable<Tenant>>>() ,
It.IsAny<string>()))
.Returns(new Func<Expression<Func<Tenant, bool>>,
IQueryable<Tenant>>(expr => Tenants.Where(expr.Compile()).AsQueryable()));
Tenant TestTenant = TenantRepository.Object.Get(
t => t.TenantID == Tenant2.TenantID,
null,
null).FirstOrDefault();
The error occurs on the last line.
Found the solution for the correct parameters:
TenantRepository.Setup(p => p.Get(It.IsAny<Expression<Func<Tenant, bool>>>(),
It.IsAny<Func<IQueryable<Tenant>, IOrderedQueryable<Tenant>>>(),
It.IsAny<string>()))
.Returns(
(Expression<Func<Tenant, bool>> expr,
Func<IQueryable<Tenant>, IOrderedQueryable<Tenant>> orderBy,
string includeProperties) => Tenants.Where(expr.Compile()).AsQueryable());
I believe the problem resides in the return type of your mocked object: according to your interface, the method Get should return an IQueryable, but you are mocking it to return a Func<Expression<Func<Tenant, bool>>, IQueryable<Tenant>> instead.
Just keep in mind that returning a function is different from returning its result; in this case, you should create an expected IQueryable object and just tell Moq to return it. It doesn't make much sense to mock something using its expected behaviour - which looks like what you are trying to do here.
Related
please help on how to get reactor context value in Groovy test
private Mono<PersonDetail> getMemberDetailsWithName(String studNumber, PersonDetail detail) {
Set<StudError> errors = new HashSet<>();
return coreCustomerIndividualNameClient.getStudName(studNumber)
.map(nameResponse -> {
detail.setName(mapper.map(nameResponse));
return detail; })
.onErrorResume(e -> {
errors.addAll(e);
return Mono.just(detail);
})
.handle((studDetail, sink) -> {
StudContext studAggCtx = sink.currentContext().get(StudContext.CONTEXT_KEY);
studAggCtx.getErrors().addAll(errors);
sink.next(studDetail);
});
}
I am mocking,
.getStudName(studNumber) return Error.
I need to check whether the context got added with Error, how we can validate this in StepVerifier.create
the context created in the below way through reactor.util.context
.subscriberContext(Context.of(StudContext.CONTEXT_KEY,
new StudContext(headers, timeoutMillis, false)))
.collectList().block();
You can use the method expectAccessibleContext to gain access to the ContextExpectations methods. You can then use these methods to assert the state of the Context.
Example
Mono<Integer> mono = Mono.just(1)
.subscriberContext(Context.of("key", "value"));
StepVerifier.create(mono)
.expectAccessibleContext()
.contains("key", "value")
.then()
.expectNext(1)
.verifyComplete();
expectAccessibleContext docs
I'm trying to write white test to test my API with file uploads.
I'm following the docs about this using basic client request, not crawler.
The unit test is:
class RecordsControllerTest extends WebTestCase {
private $client;
public function __construct() {
parent::__construct();
$this->client = self::createClient();
$this->client->insulate();
}
public function testApiPostUpload($params){
$fileToUpload = realpath(__DIR__.'/../../resources/mpthreetest.mp3');
$file = new UploadedFile(
$fileToUpload,
'mpthreetest.mp3',
MimeTypeGuesser::getInstance()->guess($fileToUpload),
filesize($fileToUpload)
);
$this->client->request('POST', '/records/'.$params['createdRecordId'].'/upload', array(), array('file' => $file) );
$this->assertEquals(200, $this->client->getResponse()->getStatusCode());
}
}
When I execute the test I receive an error:
Exception: Serialization of 'Symfony\Component\HttpFoundation\File\UploadedFile' is not allowed
/path/to/project/vendor/symfony/symfony/src/Symfony/Bundle/FrameworkBundle/Client.php:165
/path/to/project/vendor/symfony/symfony/src/Symfony/Component/BrowserKit/Client.php:348
/path/to/project/vendor/symfony/symfony/src/Symfony/Bundle/FrameworkBundle/Client.php:143
/path/to/project/vendor/symfony/symfony/src/Symfony/Component/BrowserKit/Client.php:313
/path/to/project/src/Bundle/Tests/Functional/Controller/RecordsControllerTest.php:182
I have found this question for about the same error, but in this case the request is not sent to the controller and the problem is not the entity and implementing serialization.
Anyone who knows how to fix this?
Anyone who managed to make unit test for uploading file in symfony 2?
You could try to NOT insulate the requests passing false as argument to the insulate method so try this:
$this->client->insulate(false);
instead of this:
$this->client->insulate();
Hope this help
I was able to resolve it by setting the changeHistory parameter to false (7th and last parameter in the request method signature):
$crawler = $client->request($form->getMethod(), $form->getUri(), $values, $files, [], null, false);
This will prevent the serialize on following lines :
if ($this->followRedirects && $this->redirect) {
$this->redirects[serialize($this->history->current())] = true;
return $this->crawler = $this->followRedirect();
}
I have a method that validate an Object calling an external service:
public void Validate(IValidator<MyType> validator)
{
IMapper<MyType> mapper = new MyTypeMapper();
foreach (var element in this.Elements)
{
ValidationResult result = validator.Validate(myTypeInstance, mapper, new ValidationConfiguration());
if (result.IsValid)
// do something
else
// do something else
}
}
Now in my unit test I have a collection of elements. And I want that if an element have a given id number the Validate method should return another stub with validation messages:
// arrange
var myAggregate aggregate = ElementsNonValidated.Stub();
var mockedValidator = new Mock<IValidator<MyType>>();
mockedValidator.Setup(a => a.Validate(
It.Is<Mytype>(x => x.Id == Guid.Parse("3F2504E0-4F89-11D3-9A0C-0305E82C3301")),
new Mapper(),
new ValidationConfiguration()
)).Returns<ValidationResult>(x => x = new ValidationResult());
// act
myAggregate.Valida(mockedValidator.Object);
The problem is: When unit test starts and go forth till the real method validate still return result=null. Why? What's wrong with my mock?
The problem is here:
mockedValidator.Setup(a => a.Validate(
It.Is<Mytype>(x => x.Id == Guid.Parse("3F2504E0-4F89-11D3-9A0C-0305E82C3301")),
new Mapper(),
new ValidationConfiguration()
)).Returns<ValidationResult>(x => x = new ValidationResult());
You setup Validate to expect specific Mapper and ValidationResult instances, which of course do not match the instances used in your system under test. If you don't care what instance should be used for a parameter, use It.IsAny<>:
mockedValidator.Setup(a => a.Validate(
It.Is<Mytype>(x => x.Id == Guid.Parse("3F2504E0-4F89-11D3-9A0C-0305E82C3301")),
It.IsAny<Mapper>(),
It.IsAny<ValidationConfiguration>()
)).Returns<ValidationResult>(x => x = new ValidationResult());
This will return a new ValidationResult for any and every invocation to Validate where the object's Id is equal to that particular GUID.
The reason for the TargetParameterCountException is in your Returns statement, and is answered here.
I have two webservice calls. Webservice1 returns Promise[Option[Model]] and Webservice2 should take Model as a parameter and then return a Promise[Option[String]]. This is how I have structured my code:
def call1: Promise[Option[Model]] = for {
response1 <- callService1(requestHolderForService1)
} yield {
for {
response <- response1
} yield ParserForResponse(response)
}
After, this I want to chain my call to service 2 that takes the result from service 1 as a parameter:
def call2:Promise[Option[String]] = call1.flatMap{
optionModel => optionModel.flatMap{
model => callService2(requestHolderForService2(model)).map{
service2Option => service2Option.map{
service2Result => ResultParse(service2Result)
}
}
}
}
The problem is that my call1 returns a Promise[Option[Model]] whereas the return from call2 needs to be Promise[Option[String]]. The issue stems from the intermediate service call
callService2
which returns Promise[Option[JsValue]] and I am unable to figure out the transition from Promise[Option[Model]] -> Promise[Option[JsValue]] -> Promise[Option[String]]
Can somebody point out how I might be able to chain these two calls together using map or flatMap?
Thanks
The "normal" way would not to be working with the promises directly, but futures for those promises, which you can access from scala.concurrent.Promise.future
First you map the future, think of it as when the option arrives, do this transformation with it, then you need to handle the fact that the option may not exist, which also is a map, think of it as if there is a value to this tranformation on it.
so:
val future1: Future[Option[Model]] = (...).future
val future2: Future[Option[String]] = future1.map { maybeModel =>
maybeModel.map(model => model.toString) // or hovewer you make it a string
}
Which you then can use in your second web service call
I am trying to mock my repository's Get() method to return an object in order to fake an update on that object, but my setup is not working:
Here is my Test:
[Test]
public void TestUploadDealSummaryReportUploadedExistingUpdatesSuccessfully()
{
var dealSummary = new DealSummary {FileName = "Test"};
_mockRepository.Setup(r => r.Get(x => x.FileName == dealSummary.FileName))
.Returns(new DealSummary {FileName = "Test"}); //not working for some reason...
var reportUploader = new ReportUploader(_mockUnitOfWork.Object, _mockRepository.Object);
reportUploader.UploadDealSummaryReport(dealSummary, "", "");
_mockRepository.Verify(r => r.Update(dealSummary));
_mockUnitOfWork.Verify(uow => uow.Save());
}
Here is the method that is being tested:
public void UploadDealSummaryReport(DealSummary dealSummary, string uploadedBy, string comments)
{
dealSummary.UploadedBy = uploadedBy;
dealSummary.Comments = comments;
// method should be mocked to return a deal summary but returns null
var existingDealSummary = _repository.Get(x => x.FileName == dealSummary.FileName);
if (existingDealSummary == null)
_repository.Insert(dealSummary);
else
_repository.Update(dealSummary);
_unitOfWork.Save();
}
And here is the error that I get when I run my unit test:
Moq.MockException :
Expected invocation on the mock at least once, but was never performed: r => r.Update(.dealSummary)
No setups configured.
Performed invocations:
IRepository1.Get(x => (x.FileName == value(FRSDashboard.Lib.Concrete.ReportUploader+<>c__DisplayClass0).dealSummary.FileName))
IRepository1.Insert(FRSDashboard.Data.Entities.DealSummary)
at Moq.Mock.ThrowVerifyException(MethodCall expected, IEnumerable1 setups, IEnumerable1 actualCalls, Expression expression, Times times, Int32 callCount)
at Moq.Mock.VerifyCalls(Interceptor targetInterceptor, MethodCall expected, Expression expression, Times times)
at Moq.Mock.Verify(Mock mock, Expression1 expression, Times times, String failMessage)
at Moq.Mock1.Verify(Expression`1 expression)
at FRSDashboard.Test.FRSDashboard.Lib.ReportUploaderTest.TestUploadDealSummaryReportUploadedExistingUpdatesSuccessfully
Through debugging I have found that the x => x.FileName is returning null, but even if i compare it to null I still get a null instead of the Deal Summary I want returned. Any ideas?
I'm guessing your setup isn't matching the call you make because they're two different anonymous lambdas. You may needs something like
_mockRepository.Setup(r => r.Get(It.IsAny<**whatever your get lambda is defined as**>()).Returns(new DealSummary {FileName = "Test"});
You could verify by setting a breakpoint in the Get() method of your repository and seeing if it is hit. It shouldn't be.