195640e3a20adea634b4df4ccf8c93f411184c438joi@chromium.org#!/usr/bin/env python
295640e3a20adea634b4df4ccf8c93f411184c438joi@chromium.org# Copyright (c) 2012 The Chromium Authors. All rights reserved.
301b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org# Use of this source code is governed by a BSD-style license that can be
401b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org# found in the LICENSE file.
501b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
601b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org'''The <output> and <file> elements.
701b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org'''
801b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
9cb65c63c5c7dc388c3de73705581179f8042e7ddjoi@chromium.orgimport os
10cb65c63c5c7dc388c3de73705581179f8042e7ddjoi@chromium.org
1101b3bc768461bd303bff39f8cd1663682254e407joi@chromium.orgimport grit.format.rc_header
1201b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
1301b3bc768461bd303bff39f8cd1663682254e407joi@chromium.orgfrom grit import xtb_reader
14b9161407f737461b5db16a29782f8a31d19e602dbenrg@chromium.orgfrom grit.node import base
1501b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
1601b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
1701b3bc768461bd303bff39f8cd1663682254e407joi@chromium.orgclass FileNode(base.Node):
1801b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  '''A <file> element.'''
1901b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
2001b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def __init__(self):
21b9161407f737461b5db16a29782f8a31d19e602dbenrg@chromium.org    super(FileNode, self).__init__()
2201b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    self.re = None
2301b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    self.should_load_ = True
2401b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
2501b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def IsTranslation(self):
2601b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    return True
2701b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
2801b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def GetLang(self):
2901b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    return self.attrs['lang']
3001b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
3101b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def DisableLoading(self):
3201b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    self.should_load_ = False
3301b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
3401b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def MandatoryAttributes(self):
3501b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    return ['path', 'lang']
3601b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
37ccda47032903a6550dac2921f88c51b4da55aa36benrg@chromium.org  def RunPostSubstitutionGatherer(self, debug=False):
38ccda47032903a6550dac2921f88c51b4da55aa36benrg@chromium.org    if not self.should_load_:
3901b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org      return
4001b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
4101b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    root = self.GetRoot()
42ca6c225d0059dd17b476c934e744a3c4f60e2df2joi@chromium.org    defs = getattr(root, 'defines', {})
43ca6c225d0059dd17b476c934e744a3c4f60e2df2joi@chromium.org    target_platform = getattr(root, 'target_platform', '')
4401b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
45ec8016c73b3b945b6284746230913d88653f35e7benrg@chromium.org    xtb_file = open(self.ToRealPath(self.GetInputPath()))
4601b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    try:
4701b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org      lang = xtb_reader.Parse(xtb_file,
4801b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org                              self.UberClique().GenerateXtbParserCallback(
49ca6c225d0059dd17b476c934e744a3c4f60e2df2joi@chromium.org                                  self.attrs['lang'], debug=debug),
50ca6c225d0059dd17b476c934e744a3c4f60e2df2joi@chromium.org                              defs=defs,
51ca6c225d0059dd17b476c934e744a3c4f60e2df2joi@chromium.org                              target_platform=target_platform)
5201b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    except:
53ec8016c73b3b945b6284746230913d88653f35e7benrg@chromium.org      print "Exception during parsing of %s" % self.GetInputPath()
5401b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org      raise
55d769b0cb7974d27fc2e1feda9a2523e0da4a10b9tony@chromium.org    # Translation console uses non-standard language codes 'iw' and 'no' for
56d769b0cb7974d27fc2e1feda9a2523e0da4a10b9tony@chromium.org    # Hebrew and Norwegian Bokmal instead of 'he' and 'nb' used in Chrome.
57d769b0cb7974d27fc2e1feda9a2523e0da4a10b9tony@chromium.org    # Note that some Chrome's .grd still use 'no' instead of 'nb', but 'nb' is
58d769b0cb7974d27fc2e1feda9a2523e0da4a10b9tony@chromium.org    # always used for generated .pak files.
59d769b0cb7974d27fc2e1feda9a2523e0da4a10b9tony@chromium.org    ALTERNATIVE_LANG_CODE_MAP = { 'he': 'iw', 'nb': 'no' }
6001b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    assert (lang == self.attrs['lang'] or
61d769b0cb7974d27fc2e1feda9a2523e0da4a10b9tony@chromium.org            lang == ALTERNATIVE_LANG_CODE_MAP[self.attrs['lang']]), (
62d769b0cb7974d27fc2e1feda9a2523e0da4a10b9tony@chromium.org            'The XTB file you reference must contain messages in the language '
63d769b0cb7974d27fc2e1feda9a2523e0da4a10b9tony@chromium.org            'specified\nby the \'lang\' attribute.')
6401b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
65ec8016c73b3b945b6284746230913d88653f35e7benrg@chromium.org  def GetInputPath(self):
66cb65c63c5c7dc388c3de73705581179f8042e7ddjoi@chromium.org    return os.path.expandvars(self.attrs['path'])
6701b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
6801b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
6901b3bc768461bd303bff39f8cd1663682254e407joi@chromium.orgclass OutputNode(base.Node):
7001b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  '''An <output> element.'''
7101b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
7201b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def MandatoryAttributes(self):
7301b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    return ['filename', 'type']
7401b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
7501b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def DefaultAttributes(self):
76ec8016c73b3b945b6284746230913d88653f35e7benrg@chromium.org    return {
77ec8016c73b3b945b6284746230913d88653f35e7benrg@chromium.org      'lang' : '', # empty lang indicates all languages
78ec8016c73b3b945b6284746230913d88653f35e7benrg@chromium.org      'language_section' : 'neutral', # defines a language neutral section
79ec8016c73b3b945b6284746230913d88653f35e7benrg@chromium.org      'context' : '',
80ec8016c73b3b945b6284746230913d88653f35e7benrg@chromium.org    }
8101b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
8201b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def GetType(self):
83ccda47032903a6550dac2921f88c51b4da55aa36benrg@chromium.org    return self.attrs['type']
8401b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
8501b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def GetLanguage(self):
8601b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    '''Returns the language ID, default 'en'.'''
8701b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    return self.attrs['lang']
8801b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
89ec8016c73b3b945b6284746230913d88653f35e7benrg@chromium.org  def GetContext(self):
90ec8016c73b3b945b6284746230913d88653f35e7benrg@chromium.org    return self.attrs['context']
91ec8016c73b3b945b6284746230913d88653f35e7benrg@chromium.org
9201b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def GetFilename(self):
9301b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    return self.attrs['filename']
9401b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
9501b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def GetOutputFilename(self):
96cb65c63c5c7dc388c3de73705581179f8042e7ddjoi@chromium.org    path = None
9701b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    if hasattr(self, 'output_filename'):
98cb65c63c5c7dc388c3de73705581179f8042e7ddjoi@chromium.org      path = self.output_filename
9901b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    else:
100cb65c63c5c7dc388c3de73705581179f8042e7ddjoi@chromium.org      path = self.attrs['filename']
101cb65c63c5c7dc388c3de73705581179f8042e7ddjoi@chromium.org    return os.path.expandvars(path)
10201b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
10301b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def _IsValidChild(self, child):
10401b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    return isinstance(child, EmitNode)
10501b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
10601b3bc768461bd303bff39f8cd1663682254e407joi@chromium.orgclass EmitNode(base.ContentNode):
10701b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  ''' An <emit> element.'''
10801b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
10901b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def DefaultAttributes(self):
11001b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    return { 'emit_type' : 'prepend'}
11101b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
11201b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org  def GetEmitType(self):
11301b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    '''Returns the emit_type for this node. Default is 'append'.'''
11401b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org    return self.attrs['emit_type']
11501b3bc768461bd303bff39f8cd1663682254e407joi@chromium.org
116