How to get translated(to chosen language) url from named route? (or how to switch language and make Redirect::route(...) to localized link)
I use:
php Laravel 4 (L4) mcamara/laravel-localization (LaravelLocalization)
It is simple :) just use
$lang = App:getLocale(); // two letters lang eg. 'en', 'pl'...
return Redirect::to( LaravelLocalization::getURLFromRouteNameTranslated($lang,
'routes.site.dashboard') );
Caution! We assume that routes english translations for key 'site.dashboard' are in file app/lang/en/routes.php
If you have route with parameters for instance: 'companies.edit' => 'companies/{company}/edit' in routes.php file
then you can use:
$lang = App:getLocale(); // two letters lang eg. 'en', 'pl'...
Redirect::to(LaravelLocalization::getURLFromRouteNameTranslated($lang,
'routes.companies.edit', ['company' => $company->id]) );
That's all :)
Related
I'm translating my site into different languages. By the default, the language will be English, which I'm using the following route to return the "welcome" view:
Route::get('welcome', function ()
{
return view('welcome');
});
For my other languages, I'm using this other route:
Route::get('welcome/{locale}', function ($locale)
{
App::setLocale($locale);
return view('welcome');
});
Is there any way I can combine those two routes into one? For example, if the route is "welcome" or "welcome/en", return the "welcome" view in English, the default language.
However, if the route is "welcome/fr", the "welcome" view should be returned in French.
I'm going to have hundreds of routes so I would love being able to combine my routes.
The default language for your application is stored in the config/app.php configuration file. You may modify this value to suit the needs of your application. You may also change the active language at runtime using the setLocale method on the App facade:
Route::get('welcome/{locale}', function ($locale) {
if (! in_array($locale, ['en', 'es', 'fr'])) {
abort(400);
}
App::setLocale($locale);
//
});
You may configure a "fallback language", which will be used when the active language does not contain a given translation string. Like the default language, the fallback language is also configured in the config/app.php configuration file:
'fallback_locale' => 'en',
Occasionally you may need to specify a route parameter, but make the presence of that route parameter optional. You may do so by placing a ? mark after the parameter name. Make sure to give the route's corresponding variable a default value:
Route::get('welcome/{locale?}', function ($locale = null) {
//
});
How can I have localization based on the subdomain?
www.example.com ==> locale = default local = en
ar.example.com ==> local = ar
After researching online, I am not sure if it should be a middleware or in the routes file.
I think you can do something like:
Route::group(['domain' => '{lang}.myapp.com'], function()
{
Route::get('/', function($lang)
{
App::setLocale($lang);
});
});
Or use the App::setLocale in your controller.
The group allows you to use a wildcard, ar.example.com en.example.com or it.example.com all will be catch by the group. Inside de group you can define all the routes you need and pass the $lang
Maybe you can add a middleware to limit the language, maybe a middleware that check if the language exists.
My code in laravel to handle multiple language is:
$languages = array('it-IT','en-GB','fr-FR');
$lingua = Request::segment(1);
if(in_array($lingua, $languages)){
\App::setLocale($lingua);
}else{
$lingua = 'it-IT';
}
Route::group(array('prefix' => $lingua), function()
{
Route::get('/', array('as' => 'home', 'uses' => 'ItemController#menu'));
Route::get('/{idcampo}','ItemController#show');
});
How can i:
1)Make the page start always with it-IT as default. (i need it because I use $lingua to fetch from a database) so i can't have that null. Should I use a redirect::to / to /it-IT?
2) change url and language(app:locale) on he fly with a link in the upper section of every pages. withouth returning to the home.
3) to link pages I learn to use:
URL::route('home')
but how to do it when the link change with the entry of a database (for example my link is {{ URL::to($lingua. '/'. $campo[1].'/') }}) I need to use
URL::action('ItemController#show', ($lingua. '/'. $campo[1].'/'))
EDIT:
OK at the top of my pages there is a link to change language on the fly.
Italian //
English //
French
I create a controller clled LanguageController
<?php
class LanguageController extends BaseController {
public function select($lingua)
{
// Store the current language in the session
Session::put('lingua', $lingua);
return Redirect::back(); // redirect to the same page, nothing changes, just the language
}
}
I create a route:
Route::get('lingua/{lingua}', 'LanguageController#select');
Route::get('/', array('as' => 'home', 'uses' => 'ItemController#menu'));
Route::get('/mondo/','ItemController#mondo');
Route::get('/{idcampo}','ItemController#show');
I have my ItemController#menu
public function menu()
{ $linguadefault='it-IT';
$lingua = Session::get('lingua',$linguadefault);
$data = DB::table('campo')->lists('id');
return View::make('index')->with('campo',$data)->with('lingua',$lingua);
}
1) I don't understand why i need to route at lingua/{lingua} if i never route there but i use a url:action to a controller directly.
2) now i need to add
$linguadefault='it-IT';
$lingua = Session::get('lingua',$linguadefault);
at the beginning of every function to have a lingua variable in my page right?
3) now my language seems stucked to french and i can't change it anymore.
I would not use the language in the URL all the time, you can just switch languages when you need and persist it:
1) Use Session to persist the language chosen:
// Set the default language to the current user language
// If user is not logged, defaults to Italian
$linguaDefault = Auth::check()
? Auth::user()->lingua
: 'it-IT';
/// If not stored in Session, current language will be the default one
\App::setLocale(Session::get('lingua', $linguaDefault));
To have the language always set in your application, you can put this code in your file
app/start/global.php
And you don't need to add this anywhere else. So it will use it in this order:
a) Language stored in Session (selected online)
b) Language user has in database
c) Italian
2) To change the language you create a route:
Route::get('lingua/{lang}', 'LanguageController#select');
Your links
URL::action('LanguageController#select', 'it-IT')
URL::action('LanguageController#select', 'en-GB')
URL::action('LanguageController#select', 'fr-FR');
And in your controller you just have to do:
public function select($lang)
{
// Store the current language in the session
Session::put('lingua', $lang);
return Redirect::back(); // redirect to the same page, nothing changes, just the language
}
3) This way you don't need your language in all your URLs, you don't have to deal with it in all your routes. If your user changes the language in database, you just:
$user->save();
Session::put('lingua', $user->lingua);
return Redirect::route('home'); // or anything else
I'm trying to set up sub-domain based routing in Laravel 4 and I've hit a bit of an annoyance...
My route group looks like this:
Route::group(array('domain' => '{company}.domain.com'), function() {
// ...
});
Which seems to work fine, however, I need to specify the company parameter for every route/url I generate. I.e:
{{ HTML::linkRoute('logout', 'Logout', ['company' => Input::get('company')]) }}
Is there any way to specify the company parameter as static/global, so it is automatically added to any links I specify, unless otherwise overwritten/removed?
Unfortunately, no (I haven't seen any evidence in the router or HTMLBuilder that you can). You could, however, make an HTML macro... Example:
HTML::macro('lr', function($link, $title) {
$company = !empty(Input::get('company')) ? Input::get('company') : "";
return HTML::linkRoute($link, $title, ['company' => $company]);
});
Then call it - instead of HTML::linkRoute, use HTML::lr('logout', 'Logout')
Just an idea.
I'm trying to implement a multilanguage laravel 4 website, with language code in the url ( mywebsite.com/en/home and mywebsite.com/de/home )
I've seen a couple of options like filtering all requests and checking if the first param is one of the language code.
I've also check on packagist but haven't find something that already do tee job.
Is there a better way to implement it?
Thank you
Finally, I've create a config variable in config/app.php
'available_language' => array('en', 'fr', 'es'),
In filters.php I detect the browser language:
Route::filter('detectLang', function($lang = "auto")
{
if($lang != "auto" && in_array($lang , Config::get('app.available_language')))
{
Config::set('app.locale', $lang);
}else{
$browser_lang = !empty($_SERVER['HTTP_ACCEPT_LANGUAGE']) ? strtok(strip_tags($_SERVER['HTTP_ACCEPT_LANGUAGE']), ',') : '';
$browser_lang = substr($browser_lang, 0,2);
$userLang = (in_array($browser_lang, Config::get('app.available_language'))) ? $browser_lang : Config::get('app.locale');
Config::set('app.locale', $userLang);
}
});
and then in routes.php I can either detect the language or force it:
Route::get('/', array(
'before' => 'detectLang()', // auto-detect language
function(){
...
})
);
or
Route::get('/', array(
'before' => 'detectLang("fr")', // force language to "fe"
function(){
...
})
);
You could set a language variable in the user session.
Then use a 'before' filter, and view that variable, and log the correct language file.
If there is no variable set - then use a default (perhaps based upon their IP location).