patternphpModerate
Multi-language website management
Viewed 0 times
managementwebsitemultilanguage
Problem
I have just started to use PHP OOP and I would like to write a class to make a multi-language website. I started from this but I wanted to use OOP so I came up with this:
Language.php
```
UserLng = $userLanguage;
}
public function userLanguage(){
switch($this->UserLng){
/*
------------------
Language: English
------------------
*/
case "en":
$lang['PAGE_TITLE'] = 'My website page title';
$lang['HEADER_TITLE'] = 'My website header title';
$lang['SITE_NAME'] = 'My Website';
$lang['SLOGAN'] = 'My slogan here';
$lang['HEADING'] = 'Heading';
// Menu
$lang['MENU_LOGIN'] = 'Login';
$lang['MENU_SIGNUP'] = 'Sign up';
$lang['MENU_FIND_RIDE'] = 'Find Ride';
$lang['MENU_ADD_RIDE'] = 'Add Ride';
$lang['MENU_LOGOUT'] = 'Logout';
return $lang;
break;
/*
------------------
Language: Italian
------------------
*/
case "it":
$lang['PAGE_TITLE'] = 'Il titolo della mia pagina';
$lang['HEADER_TITLE'] = 'Il mio titolo';
$lang['SITE_NAME'] = 'Il nome del mio sito';
$lang['SLOGAN'] = 'Uno slogan';
$lang['HEADING'] = 'Heading';
// Menu
$lang['MENU_LOGIN'] = 'Entra';
$lang['MENU_SIGNUP'] = 'Registrati';
$lang['MENU_FIND_RIDE'] = 'Trova gruppi';
$lang['MENU_ADD_RIDE'] = 'Aggiungi gruppo';
$lang['MENU_LOGOUT'] = 'Esci';
return $lang;
break;
/*
------------------
Default Language
------------------
*/
d
Language.php
```
UserLng = $userLanguage;
}
public function userLanguage(){
switch($this->UserLng){
/*
------------------
Language: English
------------------
*/
case "en":
$lang['PAGE_TITLE'] = 'My website page title';
$lang['HEADER_TITLE'] = 'My website header title';
$lang['SITE_NAME'] = 'My Website';
$lang['SLOGAN'] = 'My slogan here';
$lang['HEADING'] = 'Heading';
// Menu
$lang['MENU_LOGIN'] = 'Login';
$lang['MENU_SIGNUP'] = 'Sign up';
$lang['MENU_FIND_RIDE'] = 'Find Ride';
$lang['MENU_ADD_RIDE'] = 'Add Ride';
$lang['MENU_LOGOUT'] = 'Logout';
return $lang;
break;
/*
------------------
Language: Italian
------------------
*/
case "it":
$lang['PAGE_TITLE'] = 'Il titolo della mia pagina';
$lang['HEADER_TITLE'] = 'Il mio titolo';
$lang['SITE_NAME'] = 'Il nome del mio sito';
$lang['SLOGAN'] = 'Uno slogan';
$lang['HEADING'] = 'Heading';
// Menu
$lang['MENU_LOGIN'] = 'Entra';
$lang['MENU_SIGNUP'] = 'Registrati';
$lang['MENU_FIND_RIDE'] = 'Trova gruppi';
$lang['MENU_ADD_RIDE'] = 'Aggiungi gruppo';
$lang['MENU_LOGOUT'] = 'Esci';
return $lang;
break;
/*
------------------
Default Language
------------------
*/
d
Solution
You've made a good start, but the switch statement in
A class called
Is it maintainable?
Not really, no. At the moment you have two languages, which I assume you know. However, should you ever want to translate it into another language (perhaps using another Charset, you're going to run into issues of space in the file, saving the file correctly, and merging in translations provided by other people for your site.
As to whether to use databases, abstract classes et cetera: You may want to, though there are other solutions.
Solution 1: Simple Configuration File
You can simply use:
Solution 2: Abstract class
As your array is basically acting as getter methods, an abstract Language class should have all the language components you need in it, like so:
Though the interface is small, implementing it may produce a big file, though it would arguably be clearer than the array style:
Alternative
Alternatively, you could combine these styles and have a singleton Language with getter methods accessing that array, i.e.:
Which will provide the benefits of both. Personally though, unless you're planning on adding more languages in the very near future, I believe solution #2 would suit you best.
userLanguage() just doesn't feel right from an Object orientated perspective:A class called
Language should represent a single language which is generic enough to fit all cases: however at the moment, whatever language it represents, it has the definitions of all of them just jammed into that one method.Is it maintainable?
Not really, no. At the moment you have two languages, which I assume you know. However, should you ever want to translate it into another language (perhaps using another Charset, you're going to run into issues of space in the file, saving the file correctly, and merging in translations provided by other people for your site.
As to whether to use databases, abstract classes et cetera: You may want to, though there are other solutions.
Solution 1: Simple Configuration File
parse_ini_file() is a very powerful little tool that does exactly what you expect. Using a simple file like this which we'll call en.ini:PAGE_TITLE = My website page title
HEADER_TITLE = My website header title
SITE_NAME = My Website
SLOGAN = My slogan here
HEADING = Heading
MENU_LOGIN = Login
MENU_SIGNUP = Sign up
MENU_FIND_RIDE = Find Ride
MENU_ADD_RIDE = Add Ride
MENU_LOGOUT = LogoutYou can simply use:
parse_ini_file('en.ini') to return an array exactly as in your switch statement, which will be much easier for other (non-programmers) to read and write for you. And if you were to then continue naming the files with this style, you could reduce userLanguage() to something like:public function userLanguage()
{
$file = '/path/to/language/config/' . $this->UserLng . '.ini';
if(!file_exists($file))
{
//Handle Error
}
return parse_ini_file($file);
}Solution 2: Abstract class
As your array is basically acting as getter methods, an abstract Language class should have all the language components you need in it, like so:
interface Language
{
public function getPageTitle();
public function getHeaderTitle();
public function getSiteName();
public function getSlogan();
public function getHeading();
public function getMenuLogin();
public function getMenuSignup();
public function getMenuFindRide();
public function getMenuAddRide();
public function getMenuLogout();
}Though the interface is small, implementing it may produce a big file, though it would arguably be clearer than the array style:
class English implements Language
{
public function getHeaderTitle()
{
return 'My website header title';
}
public function getHeading()
{
return 'Heading';
}
// etc...
}Alternative
Alternatively, you could combine these styles and have a singleton Language with getter methods accessing that array, i.e.:
class Language
{
private $languageArray;
private $userLanguage;
public function __construct($language)
{
$this->userLanguage = $language;
$this->languageArray = self::userLanguage();
}
private static function userLanguage()
{
$file = '/path/to/language/config/' . $this->userLanguage . '.ini';
if(!file_exists($file))
{
//Handle Error
}
return parse_ini_file($file);
}
public function getPageTitle()
{
return $this->languageArray['PAGE_TITLE'];
}
public function getHeaderTitle()
{
return $this->languageArray['HEADER_TITLE'];
}
//etc...
}Which will provide the benefits of both. Personally though, unless you're planning on adding more languages in the very near future, I believe solution #2 would suit you best.
Code Snippets
PAGE_TITLE = My website page title
HEADER_TITLE = My website header title
SITE_NAME = My Website
SLOGAN = My slogan here
HEADING = Heading
MENU_LOGIN = Login
MENU_SIGNUP = Sign up
MENU_FIND_RIDE = Find Ride
MENU_ADD_RIDE = Add Ride
MENU_LOGOUT = Logoutpublic function userLanguage()
{
$file = '/path/to/language/config/' . $this->UserLng . '.ini';
if(!file_exists($file))
{
//Handle Error
}
return parse_ini_file($file);
}interface Language
{
public function getPageTitle();
public function getHeaderTitle();
public function getSiteName();
public function getSlogan();
public function getHeading();
public function getMenuLogin();
public function getMenuSignup();
public function getMenuFindRide();
public function getMenuAddRide();
public function getMenuLogout();
}class English implements Language
{
public function getHeaderTitle()
{
return 'My website header title';
}
public function getHeading()
{
return 'Heading';
}
// etc...
}class Language
{
private $languageArray;
private $userLanguage;
public function __construct($language)
{
$this->userLanguage = $language;
$this->languageArray = self::userLanguage();
}
private static function userLanguage()
{
$file = '/path/to/language/config/' . $this->userLanguage . '.ini';
if(!file_exists($file))
{
//Handle Error
}
return parse_ini_file($file);
}
public function getPageTitle()
{
return $this->languageArray['PAGE_TITLE'];
}
public function getHeaderTitle()
{
return $this->languageArray['HEADER_TITLE'];
}
//etc...
}Context
StackExchange Code Review Q#39787, answer score: 10
Revisions (0)
No revisions yet.