override translation fallback symfony 2 - symfony

I have a symfony 2 project that supports 2 languages in both the backend and the front end. And I have enabled translation fallback in the configuration to allow the admin to view all the database records regardless of what language he chooses to use in the backend. However, for the front end of the website I wish to disable the fallback. How can I override the translation fallback from true to false in only the controllers I want?
I am using Gedmo translatable in my entities to translate specific columns.
Thank you.

The locale of the current user is stored in the request and is accessible via the request object like this:
use Symfony\Component\HttpFoundation\Request;
public function indexAction(Request $request)
{
$locale = $request->getLocale();
$request->setLocale('en_US');
}
More details here
I think this is what you are looking for.
Using this you can override locale settings.
If you want to set fallback locale you can do that also, using:
$translator->setFallbackLocale(array('en'));
More Details given here
Hope this will help you.

Well I found it http://blog.lazycloud.net/symfony2-doctrine2-extentions-translatable/
Apparently I should add to my entity a $locale attribute and set above it the annotation * #Gedmo\Locale . and then I can use that to override the default fallback of the entity by seting the locale to whatever language I wish then calling $em->refresh($entity)

Related

#Security annotation and user parameter

In a controller, I have an action meant to display a user. The argument is the user to be displayed and is automatically fetched through a parameter converter.
Now I want to secure this action (displaying a user profile) so that only users with the USER_VIEW permission (currently implemented as a custom Voter) have access.
Using an #Security annotation it would look like:
/**
* #Security("is_granted('USER_VIEW', user)")
*/
public function showAction(User $user) {...}
This doesn't work because the user variable in the expression refers to the authenticated user rather than the action argument.
The documentation mentions that, but this is rather unfortunate.
How can I fix this issue and get my $user argument passed to the security expression? I could rename it, but perhaps there's something better to do.
I was also wondering if this should be considered a bug in Symfony, since 'user' is a rather common word, perhaps it should be renamed to something more specific such as 'authenticated_user' or 'security_user' or something. The same goes for the other 3 variables that are passed to the expression by Symfony: 'token', 'request', 'roles'.
Thanks.

Doctrine2 , generate on a fly the value of a Entity's attribute that depends on symfony2 container

I have an API, with an API call GET /users which returns me a list of users that all have a avatar_url field
in database this field is just the image name, and in the controller i'm then putting the base URL of my static domain serving images. So that it's only one URL to change in my conf , so the code works in staging/production etc.
but things start to get tricky with GET /comments etc. that all have sub-resource users that needs to have the url, so it means that currently every single point using users needs to have this logic, which is not very DRY
I would like to have something like that
// in my entity
use JMS\Serializer\Annotation as Serializer;
/**
* #Serializer\VirtualProperty
* #Serializer\SerializedName("url")
*/
public function getUrl()
{
return $this->container->getParameter('IMG_URL').$this->imgName;
}
so that regardless on how deeply nested my entity is, I will be able to seralize it with the property.
It seems to me it is possible to achieve something like as there's a bundle
https://github.com/KnpLabs/DoctrineBehaviors
which seems to achieve something similar
Check this out. http://jmsyst.com/libs/serializer/master/handlers
From what I understand you could create your own handler for the url serializer. By having the handler as a service written by you, then you can inject anything you want in it.
More info can be found at Creating a JMS Serializer handler in symfony2

Automatic Localization in symfony2

Please look at the following code:
public function __construct($error_code)
{
$translator = new Translator('en');
$translator->addLoader('yaml', new YamlFileLoader());
$translator->addResource('yaml', dirname(__DIR__).'/Resources/translations/messages.en.yml', 'en');
$this->setErrorCode($translator->trans($error_code));
}
I am new to symfony. I have created a class MyProjectExceptions which extends Exception. Now when I have to throw a custom exception I call this class where I get the $error_code. Now this $error_code is a constant of another class which has its locale in MyBundle/Resources/transalations/messages.en.yml which will be used to throw as exception message.
Now my question are following:
How can I avoid addResource, so it can automatically add it based on Locale and find the string?
How to access serviceContainer in this class so that I can access session to set and get locales OR other services.
Can we set the default Loader as well.
In above code I am creating an instance of Translator class and manually passing 'en'. but it should pick default locale or user set locale.
I tried many solutions but not able to get the desired results.
Any help would be appreciated. Thanks in advance.
You need to register your class as Symfony service. Read the documentation: http://symfony.com/doc/current/book/service_container.html#creating-configuring-services-in-the-container
After that you can inject other services (like Translation) in your constructor. It will use all parameters that you have already set.
If you inject translator service it will pick the parameters that you have already set. For example, if you defined parameters for translator (including default locale) at config.yml, then you overrode this locale with parameter in route, you will get translator service set up with this locale. And it will automatically use resources that are lied in appropriate directories.

Symfony2 language switcher bundle default inclusion in base template

I'm searching for a solution how I can implement a bundle into my base-template so that it will be visible on every page of my project without including it into every single Template/Bundle.
Is this possible? It's a language switch and I thought about building a bundle for it, so that it can interact directly to set the locale for all links etc...
Edit: Maybe I need to set it up as a service??
My problem is; how to get the language Selector into the base Template without any route ?
So at least I figured out how to handle this. Maybe its not a beauty, but for now its working so that I can checkout a better solution
public function localize_route($locale = NULL) {
// Merge query parameters and route attributes
$attributes = array_merge($this->request->query->all(), $this->request->attributes->get('_route_params'));
// Set/override locale
$attributes['_locale'] = $locale ?: \Locale::getDefault();
return $this->router->generate($this->request->attributes->get('_route'), $attributes);
}
as it's described here http://blog.viison.com/post/15619033835/symfony2-twig-extension-switch-locale-current-route
So that it works

Create an Admin User with FosUserBundle

I try to create an Admin User with FOsUserBundle from command windows with the following command:
php app/console fos:user:create
In my project the Admin User extends other user with mandatory propriety. So, when I choose my username, mail and password, it tells me:
SQLSTATE[23000]: Integrity constraint violation: 1048 Column 'latitude' cannot be null
How can I set the value "latitude" in my AdminUser? I also use PUGXMultiUserBundle.
Only possibile way to reach that to me is
1 - override the cli command of FOSUserBundle placed into Command/CreateUserCommand.php
2 - override the user create method of FOSUserBundle placed into Util/UserManipulator.php
// Command/CreateUserCommand.php
protected function execute(InputInterface $input, OutputInterface $output)
{
$username = $input->getArgument('username');
$email = $input->getArgument('email');
$password = $input->getArgument('password');
$inactive = $input->getOption('inactive');
$superadmin = $input->getOption('super-admin');
$latitude = $input->getOption('latitude'); //this will be your own logic add
$manipulator = $this->getContainer()->get('fos_user.util.user_manipulator');
$manipulator->create($username, $password, $email, $latitude, !$inactive, $superadmin);
$output->writeln(sprintf('Created user <comment>%s</comment>', $username));
}
and
// Util/UserManipulator.php
public function create($username, $password, $email, $latitude, $active, $superadmin)
{
$user = $this->userManager->createUser();
$user->setUsername($username);
$user->setEmail($email);
$user->setPlainPassword($password);
$user->setEnabled((Boolean) $active);
$user->setSuperAdmin((Boolean) $superadmin);
$user->setLatitude($latitude);
$this->userManager->updateUser($user);
return $user;
}
Of course when I say override i mean ... override :P So you haven't to modify FOSUserBundle original files (you know, it's dangerous for many reasons) but make your own files by making your bundle extended by FOSUserBundle
Are you wondering how to make your bundle extended by FOSUserBundle?
Into your bundle "mainfile" - is the one you use to register your bundle - just add this lines
public function getParent()
{
return 'FOSUserBundle';
}
Then you simply recreate the tree structure where your ovverride files lives into original bundle, into your custom bundle's Resources/ directory (same position, same file name, same annotations if any) and .... the magic can start :) (this is valid only for views, please pay attention!)
What "override" means?
Override means that you take an existent function, "shadow" it by redefining elsewhere (declare a function with the same name, no matter how many parameters it accept, no matter the type of paramenters since php doesn't support method overloading [except if you do some "hack"]) and then you can use it instead of the original one. This is a common technique for add extra functionalities to a function or to change the function itself.
Say that we have two classes, A and B with B that is a child class of A. Say also that A have a method called myMethod().
In B we can do something like
public function myMethod() {
parent::myMethod();
//add extra functionalities here
}
in that way we're adding extra functionalities as we're calling the parent ("original") method and then execute some extra functionalities
Whereas if in B we make something like
public function myMethod() {
//some code here, but not calling parent method
}
we're redefining the behaviour of myMethod()
How Symfony2 let me override methods?
As I said previously in my answer, you have to make your bundle a child of the bundle that containts the function(s) you're trying to override (in that case FOSUserBundle). Once you did it, use the Resources directory of your bundle to accomplish what you need. reproduce the "tree-folder-structure" of the original bundle (ie.: same names of the folders) until you reach the class that contains the function you need to override.
Follow your real example: you need to override execute() function contained in Command/CreateUserCommand.php. You have to create, into your bundle folder that path:
PathTo/YourCostumBundle/Command/
and place inside the file CreateUserCommand.php with the content I show you above.
If you don't understand where I find that path, please take a look to FOSUserBundle code and it will be absolutely clear!
Why is dangerous to modify the FOSUserBundle code directly?
Well, there's a lot of answer an critic point that I can show you. Choosing the main (not ordered for importance):
What if you need to update FOSUserBundle? You'll use composer and lost every modify that you made to FOSUserBundle code
What if you have more than one bundle into your project that need to use FOSUserBundle? Maybe the custom behaviour makes sense for a bundle but not for the other one. Costumizing the behaviour at local bundle level helps you to keep FOSUserBundle logic intact
What if you're developing a bundle that you want to share with other user? You need to force them to "take" your own costumized FOSUserBundle version and warn them about updating it
Finally: I perfeclty know that your entity isn't into FOSUserBundle, but I can bet that they extend FOSUserBundle base user so what I told above is applicable to your case.
Hope it's less fuzzy now :)
Documentation: http://symfony.com/doc/current/cookbook/bundles/inheritance.html#overriding-controllers
I always follow the pattern I learned in the symfony documentation itself:
php bin/console fos:user:create usertest mail#domain.com password
and sometimes I need change the "roles" on the table "fos_user"
then
a:0:{}
to
a:1:{i:0;s:10:"ROLE_ADMIN";}
After creating a user with:
bash-5.1# bin/console fos:user:create admin admin#mydomain.com password123
Promote the user with the ROLE_ADMIN role:
bash-5.1# bin/console fos:user:promote
Please choose a username:admin
Please choose a role:ROLE_ADMIN
Role "ROLE_ADMIN" has been added to user "admin". This change will not
apply until the user logs out and back in again.

Resources