Symfony4 MongoDB inject repository - mongodb

I try to injcect doctrine mongo repository to controller.
In services.yaml file I added entry:
App\Account\Repository\MongoAccountRepository:
factory: ["#doctrine_mongodb", getRepository]
arguments:
- App\Account\Domain\Entity\Account
In my code I want to use repositories hidden behind the interface AccountRepository
class MongoAccountRepository extends DocumentRepository implements AccountRepository {}
When I try to inject repository to controller constructor
class DefaultController extends Controller
{
private $accountRepository;
public function __construct(AccountRepository $accountRepository) {
$this->accountRepository = $accountRepository;
}
I get following error:
Argument 1 passed to App\Account\UserInterface\DefaultController::__construct() must implement interface App\Account\Domain\Repository\AccountRepository, instance of Doctrine\ODM\MongoDB\DocumentRepository given
Has someone similar problem?

For all my cases, the following solution works:
mongo_account_repository:
class: Doctrine\ODM\MongoDB\Repository\DocumentRepository
factory: ['#doctrine_mongodb.odm.default_document_manager', getRepository]
arguments:
- App\Infrastructure\Repository\MongoDB\Document\Keyword

Related

EclipseContext get beans of type

I have classes:
#Creatable
#Singleton
public class Sample1 implements ISample {
}
#Creatable
#Singleton
public class Sample2 implements ISample {
}
How can i get all beans of type ISample from EclipseContext?
The Eclipse context does not support anything like this. All you can do is look for objects with a specific name (or specific class which is just converted to a name).
Additionally objects declared using #Creatable are not even created and added to the context until something actually uses them.

Symfony2 get public services in controller

Much ink has flowed about Sf2 controller/container. I face with follow situation:
app/console container:debug security
...
> 4
[container] Information for service security.token_storage
Service Id security.token_interface
Class Symfony\Component\Security\Core\Authentication\Token ...
...
Public yes
LoginBundle\DefaultController.php
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
class DefaultController extends Controller
{
public function indexAction()
{
dump(Controller::get('security.token_storage'));
...
works OK, obviously.
LoginBundle\UserUtilsController
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
class UserUtilsController extends Controller
{
public function getRoleById()
{
dump(Controller::get('security.token_storage'));
...
throw: Error: Call to a member function get() on a non-object
In Sf2 Book - Service container I found:
In this example, the controller extends Symfony's base Controller, which gives you access to the service container itself. You can then use the get method to locate and retrieve the my_mailer service from the service container.
The misunderstanding is:
- Both controllers extends basic controller which itself extends ContainerAware which implements ContainerAwareInterface which set container.
- Both controllers access same public service container.
So, why the second controller it doesn't work?
I know that the question is old but I don't want to inject a controller as service and I think it is redundant and wrong to redeclare a public service in services.yml
Thank you in advance.
I found the answer myself and I want to share for every one is in same situation...
The UserUtilsController doesn't work because it's not working in this manner. The Symfony architecture is interesting if you get to know it.
LoginBundle\Controller\UserUtilsController
// For this job we don't need to extends any class..
class UserUtilsController
{
// but we need a property for injecting the service in it
private $token;
// Now let's inject service into our property $token
public function __construct($token)
{
$this->token = $token;
}
// It's not done but let pretend it is and let's use it
public function getRoleById()
{
...
return $this->token->getToken()->getRoles();
...
services.yml
#here it's the magic
services:
# this is a new services container
user.loggeduser_utils:
# this is my class (second class)
class: LoginBundle\Controller\UserUtilsController
# this is how I feed my _construct argument
arguments: ["#security.token_storage"]
So I just inject an existing service in my new class.
Now, to use this we must to call in first class:
LoginBundle\Controller\DefaultController.php
class DefaultController extends Controller
{
public function indexAction()
{
// because my class is now a service container we call in this way
$userRoleId = $this->get('user.loggeduser_utils');
...
This solution above is almost trivial simple AFTER understanding the Sf2 DI model.

Is it possible to annotate class constructor in Kotlin

Clarification
This questions was asked before kotlin hit version 1.0. Language syntax in example is obsolete now, please follow official docs.
I'm playing with kotlin and spring DI.
I want to use constructor-based dependency injection, so I need to annotate the constructor.
I tried following approach:
Configuration
Import(javaClass<DataSourceConfig>())
public open class AppConfig(dataSource: DataSource) {
private val dataSource: DataSource
Autowired {
this.dataSource = dataSource
}
}
Configuration
public open class DataSourceConfig {
Bean
public open fun dataSource(): DataSource {
// source omitted
}
}
But it doesn't work. Is it even possible to annotate constructor in kotlin?
P.S. I'm using Kotlin M10.1 and Spring 4.1.4
UPDATE:
Annotating constructor is possible in kotlin. The problem was that it's not allowed to use constructor-based DI for #Configuration
Hrm, I think the syntax has changed radically since this question was posted. The current way (according to the docs) is to add the keyword constructor between your class name and arguments and annotate that, i.e.
public class AppConfig #Configuration constructor(dataSource: DataSource) {
//...
}
Try to write:
Configuration
public open class AppConfig [Import(javaClass<DataSourceConfig>())] (dataSource: DataSource) {
//...
}
This syntax works for me:
Configuration
Import(javaClass<DataSourceConfig>())
public open class AppConfig {
private val dataSource: DataSource
Autowired constructor(dataSource: DataSource){
this.dataSource = dataSource
}
}

In asp.net mvc 2 : how to access http post data inside constructor of any controller

My controller has abstract base controller. I want to access the form post data inside abstract base class constructor. How can we do that ?
public abstract class AppController : Controller
{
public AppController()
{
// request post data required here
}
}
public class ProductController : AppController
{
public ProductController() { }
}
Purpose : Updating second dropdown on change of first dropdown. Both are on MASTER page.
Code given above is one of the 2 options to pass data to master page:
Add using ViewData in ALL the action methods.
Do it in only one place using abstract base controller - add the required data using ViewData inside its constructor and make our main controller class implement this abstract base controller class. So that we don't have to add the viewdata for master page in all action methods.
I don't know what is your final goal with this but this is something which is not recommended to be done in MVC. The Request object is not yet initialized in the constructor of the controller. You could try to use the native HttpContext object:
string foo = System.Web.HttpContext.Current.Request["foo"];
but that's something extremely bad and I would never recommend you doing this as now your controller is coupled to the static native HttpContext instance without any chance of unit testing it.
Instead of using the constructor you could override the Initialize method of your controller where you will have access to the request context and you could read posted data:
protected override void Initialize(System.Web.Routing.RequestContext requestContext)
{
base.Initialize(requestContext);
string foo = requestContext.HttpContext.Request["foo"];
}

How to test annotation object in the class that implement AbstractModule

I got a question regarding binding and annotation.
I have the following class:
public class MailFacadeImpl implements MailFacade {
private final PersonDao personDao;
#Inject
public MailFacadeImpl(#Mail PersonDao personDao) {
super();
this.personDao = personDao;
}
The PersonDao is annotated with a custom annotation.
I would like to be able to test this annotation inside the class that implement AbstractModule.
here is a piece of code:
bind(new TypeLiteral<SecurityRulesFactory<Person>>(){}).toProvider(FactoryProvider.newFactory(
new TypeLiteral<SecurityRulesFactory<Person>>(){}, new TypeLiteral<MailSecurityRulesCrdb>(){}));
I would like to have somthing similar to :
if(PersonDAO is annotated with(Mail.class) ){
bind(new TypeLiteral<SecurityRulesFactory<Person>>(){}).toProvider(FactoryProvider.newFactory(
new TypeLiteral<SecurityRulesFactory<Person>>(){}, new TypeLiteral<MailSecurityRulesCrdb>(){}));
}
Do you think it's possible?
thx for your help :-)
Have a nice friday!
It's not clear why you want your module to do this test. Instead, your module can specify how to get or create an instance of PersonDao for injection points annotated with Mail:
bind(PersonDao.class).annotatedWith(Mail.class).to(EmailAwarePersonDao.class);
Note that your PersonDao.class.isAnnotationPresent(Mail.class) won't help here, since the PersonDao class itself isn't annotated with Mail; the parameter to the MailFacadeImpl constructor has that annotation. There are ways to test for that, but if you are trying to do that from a Guice module, you're probably doing something wrong.