Version: current

# Class Translatable

The Translatable decorator allows your DataObjects to have versions in different languages, defining which fields are can be translated. Translatable can be applied to any `DataObject` subclass, but is mostly used with `SiteTree`. Translatable is compatible with the `Versioned` extension. To avoid cluttering up the database-schema of the 99% of sites without multiple languages, the translation-feature is disabled by default.

Locales (e.g. 'en_US') are used in Translatable for identifying a record by language, see section "Locales and Language Tags".

## Configuration

### Through Object::add_extension()

Enabling Translatable through `Object::add_extension()` in your _config.php:

    Object::add_extension('MyClass', 'Translatable');

This is the recommended approach for enabling Translatable.

### Through $extensions

    class MyClass extends DataObject {
      static $extensions = array(
        "Translatable"
      );
    }

Make sure to rebuild the database through /dev/build after enabling translatable. Use the correct `Translatable::set_default_locale()` before building the database for the first time, as this locale will be written on all new records.

### "Default" locales

Important: If the "default language" of your site is not US-English (en_US), please ensure to set the appropriate default language for your content before building the database with Translatable enabled:

    Translatable::set_default_locale(<locale>); // e.g. 'de_DE' or 'fr_FR'

For the Translatable class, a "locale" consists of a language code plus a region code separated by an underscore, for example "de_AT" for German language ("de") in the region Austria ("AT"). See http://www.w3.org/International/articles/language-tags/ for a detailed description.

## Usage

Getting a translation for an existing instance:

    $translatedObj = Translatable::get_one_by_locale('MyObject', 'de_DE');

Getting a translation for an existing instance:

    $obj = DataObject::get_by_id('MyObject', 99); // original language
    $translatedObj = $obj->getTranslation('de_DE');

Getting translations through `Translatable::set_current_locale()`. This is not a recommended approach, but sometimes inavoidable (e.g. for `Versioned` methods).

    $origLocale = Translatable::get_current_locale();
    Translatable::set_current_locale('de_DE');
    $obj = Versioned::get_one_by_stage('MyObject', "ID = 99");
    Translatable::set_current_locale($origLocale);

Creating a translation:

    $obj = new MyObject();
    $translatedObj = $obj->createTranslation('de_DE');

## Usage for SiteTree

Translatable can be used for subclasses of `SiteTree` as well.

    Object::add_extension('SiteTree', 'Translatable');
    Object::add_extension('SiteConig', 'Translatable');

If a child page translation is requested without the parent page already having a translation in this language, the extension will recursively create translations up the tree. Caution: The "URLSegment" property is enforced to be unique across languages by auto-appending the language code at the end. You'll need to ensure that the appropriate "reading language" is set before showing links to other pages on a website through $_GET['locale']. Pages in different languages can have different publication states through the `Versioned` extension.

Note: You can't get Children() for a parent page in a different language through set_current_locale(). Get the translated parent first.

    // wrong
    Translatable::set_current_locale('de_DE');
    $englishParent->Children();
    // right
    $germanParent = $englishParent->getTranslation('de_DE');
    $germanParent->Children();

## Translation groups

Each translation can have one or more related pages in other languages. This relation is optional, meaning you can create translations which have no representation in the "default language". This means you can have a french translation with a german original, without either of them having a representation in the default english language tree. Caution: There is no versioning for translation groups, meaning associating an object with a group will affect both stage and live records.

SiteTree database table (abbreviated) ^ ID ^ URLSegment ^ Title ^ Locale ^

1 | about-us | About us | en_US
2 | ueber-uns | Über uns | de_DE
3 | contact | Contact | en_US

SiteTree_translationgroups database table ^ TranslationGroupID ^ OriginalID ^

99 | 1
99 | 2
199 | 3

## Character Sets

Caution: Does not apply any character-set conversion, it is assumed that all content is stored and represented in UTF-8 (Unicode). Please make sure your database and HTML-templates adjust to this.

## Permissions

Authors without administrative access need special permissions to edit locales other than the default locale.

- TRANSLATE_ALL: Translate into all locales
- Translate_<locale>: Translate a specific locale. Only available for all locales set in `Translatable::set_allowed_locales()`.

Note: If user-specific view permissions are required, please overload `SiteTree->canView()`.

## Uninstalling/Disabling

Disabling Translatable after creating translations will lead to all pages being shown in the default sitetree regardless of their language. It is advised to start with a new database after uninstalling Translatable, or manually filter out translated objects through their "Locale" property in the database.

  Extension
  DataObjectDecorator
  Translatable implements PermissionProvider

Package: sapphire\i18n
Author: Ingo Schommer <ingo (at) silverstripe (dot) com>
Author: Michael Gall <michael (at) wakeless (dot) net>
Author: Bernat Foj Capell <bernat@silverstripe.com>
See: http://doc.silverstripe.org/doku.php?id=multilingualcontent
Located at sapphire/core/model/Translatable.php

## Methods summary

`public static` | # `reset( )` Reset static configuration variables to their default values Reset static configuration variables to their default values
`public static string` | # `choose_site_locale( mixed $langsAvailable = array() )` Choose the language the site is currently on. Choose the language the site is currently on. If $_GET['locale'] is currently set, then that locale will be used. Otherwise the member preference (if logged in) or default locale will be used. #### Parameters $langsAvailable $langsAvailable array A numerical array of languages which are valid choices (optional) #### Returns `string` Selected language (also saved in $current_locale).
`public static string` | # `default_locale( )` Get the current reading language. This value has to be set before the schema is built with translatable enabled, any changes after this can cause unintended side-effects. Get the current reading language. This value has to be set before the schema is built with translatable enabled, any changes after this can cause unintended side-effects. #### Returns `string` string
`public static` | # `set_default_locale( mixed $locale )` Set default language. Please set this value before creating any database records (like pages), as this locale will be attached to all new records. Set default language. Please set this value before creating any database records (like pages), as this locale will be attached to all new records. #### Parameters $locale $locale String
`public static string` | # `get_current_locale( )` Get the current reading language. If its not chosen, call `Translatable::choose_site_locale()`. Get the current reading language. If its not chosen, call `Translatable::choose_site_locale()`. #### Returns `string` string
`public static` | # `set_current_locale( string $locale )` Set the reading language, either namespaced to 'site' (website content) or 'cms' (management backend). This value is used in `Translatable::augmentSQL()` to "auto-filter" all SELECT queries by this language. See `Translatable::disable_locale_filter()` on how to override this behaviour temporarily. Set the reading language, either namespaced to 'site' (website content) or 'cms' (management backend). This value is used in `Translatable::augmentSQL()` to "auto-filter" all SELECT queries by this language. See `Translatable::disable_locale_filter()` on how to override this behaviour temporarily. #### Parameters $locale string $lang New reading language.
`public static `DataObject`` | # `get_one_by_locale( string $class, string $locale, string $filter = '', boolean $cache = false, string $orderby = "" )` Get a singleton instance of a class in the given language. Get a singleton instance of a class in the given language. #### Parameters $class string $class The name of the class. $locale string $locale The name of the language. $filter string $filter A filter to be inserted into the WHERE clause. $cache boolean $cache Use caching (default: false) $orderby string $orderby A sort expression to be inserted into the ORDER BY clause. #### Returns ``DataObject`` DataObject
`public static mixed` | # `get_by_locale( string $class, string $locale, string $filter = '', string $sort = '', string $join = "", string $limit = "", string $containerClass = "DataObjectSet", string $having = "" )` Get all the instances of the given class translated to the given language Get all the instances of the given class translated to the given language #### Parameters $class string $class The name of the class $locale string $locale The name of the language $filter string $filter A filter to be inserted into the WHERE clause. $sort string $sort A sort expression to be inserted into the ORDER BY clause. $join string $join A single join clause. This can be used for filtering, only 1 instance of each DataObject will be returned. $limit string $limit A limit expression to be inserted into the LIMIT clause. $containerClass string $containerClass The container class to return the results in. $having string $having A filter to be inserted into the HAVING clause. #### Returns `mixed` The objects matching the conditions.
`public static boolean` | # `locale_filter_enabled( )` #### Returns `boolean` bool
`public static` | # `enable_locale_filter( )` Enables automatic filtering by locale. This is normally called after is has been disabled using `Translatable::disable_locale_filter()`. Enables automatic filtering by locale. This is normally called after is has been disabled using `Translatable::disable_locale_filter()`.
`public static` | # `disable_locale_filter( )` Disables automatic locale filtering in `Translatable::augmentSQL()`. This can be re-enabled using `Translatable::enable_locale_filter()`. Disables automatic locale filtering in `Translatable::augmentSQL()`. This can be re-enabled using `Translatable::enable_locale_filter()`.
`public array` | # `getTranslatedLocales( )` Gets all translations for this specific page. Doesn't include the language of the current record. Gets all translations for this specific page. Doesn't include the language of the current record. #### Returns `array` Numeric array of all locales, sorted alphabetically.
`public array` | # `getAllowedLocalesForMember( `Member` $member )` Gets all locales that a member can access as defined by `Translatable::$allowed_locales` and `Translatable::canTranslate()`. If `Translatable::$allowed_locales` is not set and the user has the `TRANSLATE_ALL` permission, the method will return all available locales in the system. Gets all locales that a member can access as defined by `Translatable::$allowed_locales` and `Translatable::canTranslate()`. If `Translatable::$allowed_locales` is not set and the user has the `TRANSLATE_ALL` permission, the method will return all available locales in the system. #### Parameters $member Member $member #### Returns `array` Map of locales
`public static array` | # `get_langs_by_id( string $class, integer $id )` Get a list of languages in which a given element has been translated. Get a list of languages in which a given element has been translated. #### Deprecated 2.4 Use `Translatable::getTranslations()` #### Parameters $class string $class Name of the class of the element $id int $id ID of the element #### Returns `array` List of languages
`public static` | # `enable( )` Enables the multilingual feature Enables the multilingual feature #### Deprecated 2.4 Use Object::add_extension('SiteTree', 'Translatable')
`public static` | # `disable( )` Disable the multilingual feature Disable the multilingual feature #### Deprecated 2.4 Use Object::remove_extension('SiteTree', 'Translatable')
`public static boolean` | # `is_enabled( )` Check whether multilingual support has been enabled Check whether multilingual support has been enabled #### Deprecated 2.4 Use Object::has_extension('SiteTree', 'Translatable') #### Returns `boolean` True if enabled
`public` | # `__construct( mixed $translatableFields = null )` Construct a new Translatable object. Construct a new Translatable object. #### Var array $translatableFields The different fields of the object that can be translated. This is currently not implemented, all fields are marked translatable (see `Translatable::setOwner()`). #### Overrides `Extension::__construct`
`public` | # `setOwner( `Object` $owner, string $ownerBaseClass = null )` Set the owner of this decorator. Set the owner of this decorator. #### Parameters $owner Object $owner The owner object, $ownerBaseClass string $ownerBaseClass The base class that the extension is applied to; this may be the class of owner, or it may be a parent. For example, if Versioned was applied to SiteTree, and then a Page object was instantiated, $owner would be a Page object, but $ownerBaseClass would be 'SiteTree'. #### Overrides `Extension::setOwner`
`public array` | # `extraStatics( )` Define extra database fields Define extra database fields Return a map where the keys are db, has_one, etc, and the values are additional fields/relations to be defined. #### Returns `array` Returns a map where the keys are db, has_one, etc, and the values are additional fields/relations to be defined. #### Overrides `DataObjectDecorator::extraStatics`
`public` | # `augmentSQL( `SQLQuery` & $query )` Changes any SELECT query thats not filtering on an ID to limit by the current language defined in `Translatable::get_current_locale()`. It falls back to "Locale='' OR Lang IS NULL" and assumes that this implies querying for the default language. Changes any SELECT query thats not filtering on an ID to limit by the current language defined in `Translatable::get_current_locale()`. It falls back to "Locale='' OR Lang IS NULL" and assumes that this implies querying for the default language. Use `Translatable::disable_locale_filter()` to temporarily disable this "auto-filtering". #### Parameters $query SQLQuery $query Query to augment. #### Overrides `DataObjectDecorator::augmentSQL`
`public` | # `augmentDatabase( )` Create <table>_translation database table to enable tracking of "translation groups" in which each related translation of an object acts as a sibling, rather than a parent->child relation. Create <table>_translation database table to enable tracking of "translation groups" in which each related translation of an object acts as a sibling, rather than a parent->child relation. #### Overrides `DataObjectDecorator::augmentDatabase`
`public` | # `requireDefaultRecords( )` #### Overrides `DataObjectDecorator::requireDefaultRecords`
`public` | # `addTranslationGroup( integer $originalID, boolean $overwrite = false )` Add a record to a "translation group", so its relationship to other translations based off the same object can be determined later on. See class header for further comments. Add a record to a "translation group", so its relationship to other translations based off the same object can be determined later on. See class header for further comments. #### Parameters $originalID int $originalID Either the primary key of the record this new translation is based on, or the primary key of this record, to create a new translation group $overwrite boolean $overwrite
`public integer` | # `getTranslationGroup( )` Gets the translation group for the current record. This ID might equal the record ID, but doesn't have to - it just points to one "original" record in the list. Gets the translation group for the current record. This ID might equal the record ID, but doesn't have to - it just points to one "original" record in the list. #### Returns `integer` Numeric ID of the translationgroup in the <classname>_translationgroup table
`public` | # `removeTranslationGroup( )` Removes a record from the translation group lookup table. Makes no assumptions on other records in the group - meaning if this happens to be the last record assigned to the group, this group ceases to exist. Removes a record from the translation group lookup table. Makes no assumptions on other records in the group - meaning if this happens to be the last record assigned to the group, this group ceases to exist.
`public boolean` | # `isVersionedTable( string $table )` Determine if a table needs Versioned support This is called at db/build time Determine if a table needs Versioned support This is called at db/build time #### Parameters $table string $table Table name #### Returns `boolean` boolean
`public` | # `contentcontrollerInit( mixed $controller )` Note: The bulk of logic is in ModelAsController->getNestedController() and ContentController->handleRequest() Note: The bulk of logic is in ModelAsController->getNestedController() and ContentController->handleRequest()
`public` | # `modelascontrollerInit( mixed $controller )`
`public` | # `initgetEditForm( mixed $controller )`
`public` | # `onBeforeWrite( )` Recursively creates translations for parent pages in this language if they aren't existing already. This is a necessity to make nested pages accessible in a translated CMS page tree. It would be more userfriendly to grey out untranslated pages, but this involves complicated special cases in AllChildrenIncludingDeleted(). Recursively creates translations for parent pages in this language if they aren't existing already. This is a necessity to make nested pages accessible in a translated CMS page tree. It would be more userfriendly to grey out untranslated pages, but this involves complicated special cases in AllChildrenIncludingDeleted(). SiteTree->onBeforeWrite() will ensure that each translation will get a unique URL across languages, by means of `SiteTree::get_by_link()` and Translatable->alternateGetByURL(). #### Overrides `DataObjectDecorator::onBeforeWrite`
`public` | # `onAfterWrite( )` #### Overrides `DataObjectDecorator::onAfterWrite`
`public` | # `onBeforeDelete( )` Remove the record from the translation group mapping. Remove the record from the translation group mapping. #### Overrides `DataObjectDecorator::onBeforeDelete`
`public `SiteTree`` | # `alternateGetByLink( string $URLSegment, integer|null $parentID )` Attempt to get the page for a link in the default language that has been translated. Attempt to get the page for a link in the default language that has been translated. #### Parameters $URLSegment string $URLSegment $parentID int|null $parentID #### Returns ``SiteTree`` SiteTree
`public` | # `updateCMSFields( `FieldSet` & $fields )` If the record is not shown in the default language, this method will try to autoselect a master language which is shown alongside the normal formfields as a readonly representation. This gives translators a powerful tool for their translation workflow without leaving the translated page interface. Translatable also adds a new tab "Translation" which shows existing translations, as well as a formaction to create new translations based on a dropdown with available languages. If the record is not shown in the default language, this method will try to autoselect a master language which is shown alongside the normal formfields as a readonly representation. This gives translators a powerful tool for their translation workflow without leaving the translated page interface. Translatable also adds a new tab "Translation" which shows existing translations, as well as a formaction to create new translations based on a dropdown with available languages. #### Parameters $fields FieldSet $fields FieldSet with a contained TabSet #### Overrides `DataObjectDecorator::updateCMSFields`
`public array` | # `getTranslatableFields( )` Get the names of all translatable fields on this class as a numeric array. Get the names of all translatable fields on this class as a numeric array. #### Returns `array` array
`public string` | # `baseTable( mixed $stage = null )` Return the base table - the class that directly extends DataObject. Return the base table - the class that directly extends DataObject. #### Returns `string` string
`public` | # `extendWithSuffix( mixed $table )`
`public `DataObjectSet`` | # `getTranslations( string $locale = null, string $stage = null )` Gets all related translations for the current object, excluding itself. See `Translatable::getTranslation()` to retrieve a single translated object. Gets all related translations for the current object, excluding itself. See `Translatable::getTranslation()` to retrieve a single translated object. Getter with $stage parameter is specific to `Versioned` extension, mostly used for `SiteTree` subclasses. #### Parameters $locale string $locale $stage string $stage #### Returns ``DataObjectSet`` DataObjectSet
`public `DataObject`` | # `getTranslation( String $locale, mixed $stage = null )` Gets an existing translation based on the language code. Use `Translatable::hasTranslation()` as a quicker alternative to check for an existing translation without getting the actual object. Gets an existing translation based on the language code. Use `Translatable::hasTranslation()` as a quicker alternative to check for an existing translation without getting the actual object. #### Parameters $locale String $locale $stage #### Returns ``DataObject`` Translated object
`public `DataObject`` | # `createTranslation( string $locale )` Creates a new translation for the owner object of this decorator. Checks `Translatable::getTranslation()` to return an existing translation instead of creating a duplicate. Writes the record to the database before returning it. Use this method if you want the "translation group" mechanism to work, meaning that an object knows which group of translations it belongs to. For "original records" which are not created through this method, the "translation group" is set in `Translatable::onAfterWrite()`. Creates a new translation for the owner object of this decorator. Checks `Translatable::getTranslation()` to return an existing translation instead of creating a duplicate. Writes the record to the database before returning it. Use this method if you want the "translation group" mechanism to work, meaning that an object knows which group of translations it belongs to. For "original records" which are not created through this method, the "translation group" is set in `Translatable::onAfterWrite()`. #### Parameters $locale string $locale #### Returns ``DataObject`` The translated object
`public boolean` | # `canTranslate( `DataObject`|integer $member = null, string $locale )` Caution: Does not consider the `Translatable::canEdit()` permissions. Caution: Does not consider the `Translatable::canEdit()` permissions. #### Parameters $member DataObject|int $member $locale string $locale #### Returns `boolean` boolean
`public boolean` | # `canEdit( mixed $member )` #### Returns `boolean` boolean #### Overrides `DataObjectDecorator::canEdit`
`public boolean` | # `hasTranslation( string $locale )` Returns TRUE if the current record has a translation in this language. Use `Translatable::getTranslation()` to get the actual translated record from the database. Returns TRUE if the current record has a translation in this language. Use `Translatable::getTranslation()` to get the actual translated record from the database. #### Parameters $locale string $locale #### Returns `boolean` boolean
`public` | # `AllChildrenIncludingDeleted( mixed $context = null )`
`public string` | # `MetaTags( mixed & $tags )` Returns <link rel="alternate"> markup for insertion into a HTML4/XHTML compliant <head> section, listing all available translations of a page. Returns <link rel="alternate"> markup for insertion into a HTML4/XHTML compliant <head> section, listing all available translations of a page. #### Returns `string` HTML #### See http://www.w3.org/TR/html4/struct/links.html#edef-LINK http://www.w3.org/International/articles/language-tags/
`public` | # `providePermissions( )` Return a map of permission codes to add to the dropdown shown in the Security section of the CMS. array( 'VIEW_SITE' => 'View the site', ); Return a map of permission codes to add to the dropdown shown in the Security section of the CMS. array( 'VIEW_SITE' => 'View the site', ); #### Implementation of `PermissionProvider::providePermissions()`
`public static array` | # `get_existing_content_languages( string $className = 'SiteTree', mixed $where = '' )` Get a list of languages with at least one element translated in (including the default language) Get a list of languages with at least one element translated in (including the default language) #### Parameters $className string $className Look for languages in elements of this class $where #### Returns `array` Map of languages in the form locale => langName
`public static string` | # `get_homepage_link_by_locale( mixed $locale )` Get the RelativeLink value for a home page in another locale. This is found by searching for the default home page in the default language, then returning the link to the translated version (if one exists). Get the RelativeLink value for a home page in another locale. This is found by searching for the default home page in the default language, then returning the link to the translated version (if one exists). #### Returns `string` string
`public static` | # `get_homepage_urlsegment_by_locale( mixed $locale )` #### Deprecated 2.4 Use `Translatable::get_homepage_link_by_locale()`
`public static` | # `set_allowed_locales( array $locales )` Define all locales which in which a new translation is allowed. Checked in `Translatable::canTranslate()`. Define all locales which in which a new translation is allowed. Checked in `Translatable::canTranslate()`. #### Parameters $locales array List of allowed locale codes (see `i18n::$all_locales`). Example: array('de_DE','ja_JP')
`public static array` | # `get_allowed_locales( )` Get all locales which are generally permitted to be translated. Use `Translatable::canTranslate()` to check if a specific member has permission to translate a record. Get all locales which are generally permitted to be translated. Use `Translatable::canTranslate()` to check if a specific member has permission to translate a record. #### Returns `array` array
`public static` | # `get_homepage_urlsegment_by_language( mixed $locale )` #### Deprecated 2.4 Use get_homepage_urlsegment_by_locale()
`public static` | # `is_default_lang( )` #### Deprecated 2.4 Use custom check: self::$default_locale == self::get_current_locale()
`public static` | # `set_default_lang( mixed $lang )` #### Deprecated 2.4 Use set_default_locale()
`public static` | # `get_default_lang( )` #### Deprecated 2.4 Use get_default_locale()
`public static` | # `current_lang( )` #### Deprecated 2.4 Use get_current_locale()
`public static` | # `set_reading_lang( mixed $lang )` #### Deprecated 2.4 Use set_current_locale()
`public static` | # `get_reading_lang( )` #### Deprecated 2.4 Use get_reading_locale()
`public static` | # `default_lang( )` #### Deprecated 2.4 Use default_locale()
`public static` | # `get_by_lang( mixed $class, mixed $lang, mixed $filter = '', mixed $sort = '', mixed $join = "", mixed $limit = "", mixed $containerClass = "DataObjectSet", mixed $having = "" )` #### Deprecated 2.4 Use get_by_locale()
`public static` | # `get_one_by_lang( mixed $class, mixed $lang, mixed $filter = '', mixed $cache = false, mixed $orderby = "" )` #### Deprecated 2.4 Use get_one_by_locale()
`public boolean` | # `isTranslation( )` Determines if the record has a locale, and if this locale is different from the "default locale" set in `Translatable::default_locale()`. Does not look at translation groups to see if the record is based on another record. Determines if the record has a locale, and if this locale is different from the "default locale" set in `Translatable::default_locale()`. Does not look at translation groups to see if the record is based on another record. #### Deprecated 2.4 #### Returns `boolean` boolean
`public static` | # `choose_site_lang( mixed $langsAvail = null )` #### Deprecated 2.4 Use choose_site_locale()
`public` | # `getTranslatedLangs( )` #### Deprecated 2.4 Use getTranslatedLocales()
`public` | # `cacheKeyComponent( )` Return a piece of text to keep DataObject cache keys appropriately specific Return a piece of text to keep DataObject cache keys appropriately specific
`public boolean` | # `augmentValidURLSegment( )` Extends the SiteTree::validURLSegment() method, to do checks appropriate to Translatable Extends the SiteTree::validURLSegment() method, to do checks appropriate to Translatable #### Returns `boolean` bool

### Methods inherited from DataObjectDecorator

`augmentWrite()`, `can()`, `canCreate()`, `canDelete()`, `flushCache()`, `load_extra_statics()`, `onAfterDelete()`, `populateDefaults()`, `updateCMSActions()`, `updateFieldLabels()`, `updateFrontEndFields()`, `updateSummaryFields()`

### Methods inherited from Extension

`clearOwner()`, `getOwner()`, `get_classname_without_arguments()`

### Magic methods summary

## Properties summary

`protected static string` | $default_locale | # The 'default' language. The 'default' language.
`protected static string` | $current_locale | # The language in which we are reading dataobjects. The language in which we are reading dataobjects.
`protected static mixed` | $tableList | # A cached list of existing tables A cached list of existing tables
`protected array` | $translatableFields | # An array of fields that can be translated. An array of fields that can be translated.
`protected array` | $original_values | # A map of the field values of the original (untranslated) DataObject record A map of the field values of the original (untranslated) DataObject record
`protected static boolean` | $locale_filter_enabled | # If this is set to TRUE then `Translatable::augmentSQL()` will automatically add a filter clause to limit queries to the current `Translatable::get_current_locale()`. This camn be disabled using `Translatable::disable_locale_filter()` If this is set to TRUE then `Translatable::augmentSQL()` will automatically add a filter clause to limit queries to the current `Translatable::get_current_locale()`. This camn be disabled using `Translatable::disable_locale_filter()`
`protected static array` | $allowed_locales | # All locales in which a translation can be created. This limits the choice in the CMS language dropdown in the "Translation" tab, as well as the language dropdown above the CMS tree. If not set, it will default to showing all common locales. All locales in which a translation can be created. This limits the choice in the CMS language dropdown in the "Translation" tab, as well as the language dropdown above the CMS tree. If not set, it will default to showing all common locales.

### Properties inherited from DataObjectDecorator

`$decoratable_statics`

### Properties inherited from Extension

`$allowed_actions`, `$class`, `$owner`, `$ownerBaseClass`

[Raise a SilverStripe Framework issue/bug](https://github.com/silverstripe/silverstripe-framework/issues/new)
- [Raise a SilverStripe CMS issue/bug](https://github.com/silverstripe/silverstripe-cms/issues/new)
- Please use the Silverstripe Forums to ask development related questions. -