def __get__(self, instance, owner): """ Returns value from the translation field for the current language, or value for some another language according to fallback languages, or the custom fallback value, or field's default value. """ if instance is None: return self default = NONE undefined = self.fallback_undefined if undefined is NONE: default = self.field.get_default() undefined = default langs = resolution_order(get_language(), self.fallback_languages) for lang in langs: loc_field_name = build_localized_fieldname(self.field.name, lang) val = getattr(instance, loc_field_name, None) if self.meaningful_value(val, undefined): return val if mt_settings.ENABLE_FALLBACKS and self.fallback_value is not NONE: return self.fallback_value else: if default is NONE: default = self.field.get_default() # Some fields like FileField behave strange, as their get_default() doesn't return # instance of attr_class, but rather None or ''. # Normally this case is handled in the descriptor, but since we have overridden it, we # must mock it up. if (isinstance(self.field, fields.files.FileField) and not isinstance(default, self.field.attr_class)): return self.field.attr_class(instance, self.field, default) return default
def coalesce_translations(self, field): """ Coalesce all translations of a given field according to the current language and fallback resolution order, and annotate the current QuerySet with it through a `field_translations` key. """ # Languages the translation has to be searched in, in relevant # order langs = resolution_order(get_language(), {'defaut': AVAILABLE_LANGUAGES}) # Build the list of translated fields names in relevant order fields = [build_localized_fieldname(field, lang) for lang in langs] # If there is only one relevant field, no coalescing is needed if len(fields) == 1: annotation = F(fields[0]) else: # Get the underlying model field type FieldType = self.model._meta.get_field(field).__class__ # Annotate needs to know which type of field it has to output, # because translated fields type differs from usual Django # fields (e.g. TranslatedCharField differs from CharField) annotation = Coalesce(*fields, output_field=FieldType()) return self.annotate(**{field + '_translations': annotation})
def __get__(self, instance, owner): """ Returns value from the translation field for the current language, or value for some another language according to fallback languages, or the custom fallback value, or field's default value. """ if instance is None: return self default = NONE undefined = self.fallback_undefined if undefined is NONE: default = self.field.get_default() undefined = default langs = resolution_order(get_language(), self.fallback_languages) for lang in langs: loc_field_name = build_localized_fieldname(self.field.name, lang) val = getattr(instance, loc_field_name, None) if val is not None and val != undefined: return val if mt_settings.ENABLE_FALLBACKS and self.fallback_value is not NONE: return self.fallback_value else: if default is NONE: default = self.field.get_default() return default
def __get__(self, instance, owner): if instance is None: return self langs = resolution_order(get_language(), self.fallback_languages) for lang in langs: loc_field_name = build_localized_fieldname(self.field_name, lang) # Localized field name with '_id' loc_attname = instance._meta.get_field(loc_field_name).get_attname() val = getattr(instance, loc_attname, None) if val is not None: return val return None
def __get__(self, instance, owner): if instance is None: return self langs = resolution_order(get_language(), self.fallback_languages) for lang in langs: loc_field_name = build_localized_fieldname(self.field.name, lang) val = getattr(instance, loc_field_name, None) # Here we check only for None and '', because e.g. 0 should not fall back. if val is not None and val != '': return val if self.fallback_value is None or not mt_settings.ENABLE_FALLBACKS: return self.field.get_default() else: return self.fallback_value
def append_fallback(model, fields): """ If translated field is encountered, add also all its fallback fields. Returns tuple: (set_of_new_fields_to_use, set_of_translated_field_names) """ fields = set(fields) trans = set() from modeltranslation.translator import translator opts = translator.get_options_for_model(model) for key, _ in opts.fields.items(): if key in fields: langs = resolution_order(get_language(), getattr(model, key).fallback_languages) fields = fields.union(build_localized_fieldname(key, lang) for lang in langs) fields.remove(key) trans.add(key) return fields, trans
def __get__(self, instance, owner): if not instance: raise ValueError( "Translation field '%s' can only be accessed via an instance " "not via a class." % self.field.name) langs = resolution_order(get_language(), self.fallback_languages) for lang in langs: loc_field_name = build_localized_fieldname(self.field.name, lang) val = getattr(instance, loc_field_name, None) # Here we check only for None and '', because e.g. 0 should not fall back. if val is not None and val != '': return val if self.fallback_value is None: return self.field.get_default() else: return self.fallback_value
def __get__(self, instance, owner): """ Returns value from the translation field for the current language, or value for some another language according to fallback languages, or the custom fallback value, or field's default value. """ if instance is None: return self from modeltranslation.translator import translator current_language = get_language() default = NONE undefined = self.fallback_undefined if undefined is NONE: default = self.field.get_default() undefined = default langs = resolution_order(current_language, self.fallback_languages) for lang in langs: loc_field_name = build_localized_fieldname(self.field.name, lang) val = getattr(instance, loc_field_name, None) if self.meaningful_value(val, undefined): if lang != current_language and self.field.get_internal_type() in ["TextField", "CharField"]: opts = translator.get_options_for_model(self.field.model) if hasattr(opts, "fallback_prepend") and self.field.name in opts.fallback_prepend: val = "{}{}".format(opts.fallback_prepend[self.field.name], val) return val if mt_settings.ENABLE_FALLBACKS and self.fallback_value is not NONE: return self.fallback_value else: if default is NONE: default = self.field.get_default() # Some fields like FileField behave strange, as their # get_default() doesn't return instance of attr_class, but rather # None or ''. Normally this case is handled in the descriptor, but # since we have overridden it, we must mock it up. if (isinstance(self.field, fields.files.FileField) and not isinstance(default, self.field.attr_class)): return self.field.attr_class(instance, self.field, default) return default
def iter_i18n_fields_sql(model, field_name): table = model._meta.db_table for lang in resolution_order(get_language()): yield "NULLIF(`%(table)s`.`%(field_name)s_%(lang)s`, '')" % locals()