1# coding=utf8 2from __future__ import unicode_literals 3from __future__ import absolute_import 4 5import fluent.syntax.ast as FTL 6 7from .errors import SkipTransform 8from .transforms import evaluate 9from .util import get_message, get_transform 10 11 12def merge_resource(ctx, reference, current, transforms, in_changeset): 13 """Transform legacy translations into FTL. 14 15 Use the `reference` FTL AST as a template. For each en-US string in the 16 reference, first check for an existing translation in the current FTL 17 `localization` and use it if it's present; then if the string has 18 a transform defined in the migration specification and if it's in the 19 currently processed changeset, evaluate the transform. 20 """ 21 22 def merge_body(body): 23 return [ 24 entry 25 for entry in map(merge_entry, body) 26 if entry is not None 27 ] 28 29 def merge_entry(entry): 30 # All standalone comments will be merged. 31 if isinstance(entry, FTL.BaseComment): 32 return entry 33 34 # Ignore Junk 35 if isinstance(entry, FTL.Junk): 36 return None 37 38 ident = entry.id.name 39 40 # If the message is present in the existing localization, we add it to 41 # the resulting resource. This ensures consecutive merges don't remove 42 # translations but rather create supersets of them. 43 existing = get_message(current.body, ident) 44 if existing is not None: 45 return existing 46 47 transform = get_transform(transforms, ident) 48 49 # Make sure this message is supposed to be migrated as part of the 50 # current changeset. 51 if transform is not None and in_changeset(ident): 52 if transform.comment is None: 53 transform.comment = entry.comment 54 try: 55 return evaluate(ctx, transform) 56 except SkipTransform: 57 return None 58 59 body = merge_body(reference.body) 60 return FTL.Resource(body) 61