configurationengine/source/cone/public/tests/unittest_plugin_api.py
changeset 0 2e8eeb919028
child 3 e7e0ae78773e
equal deleted inserted replaced
-1:000000000000 0:2e8eeb919028
       
     1 #
       
     2 # Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
       
     3 # All rights reserved.
       
     4 # This component and the accompanying materials are made available
       
     5 # under the terms of "Eclipse Public License v1.0"
       
     6 # which accompanies this distribution, and is available
       
     7 # at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     8 #
       
     9 # Initial Contributors:
       
    10 # Nokia Corporation - initial contribution.
       
    11 #
       
    12 # Contributors:
       
    13 #
       
    14 # Description:
       
    15 #
       
    16 
       
    17 import unittest
       
    18 import os
       
    19 import logging
       
    20 import __init__
       
    21 from cone.public import *
       
    22 from cone.public import _plugin_reader
       
    23 ROOT_PATH = os.path.dirname(os.path.abspath(__file__))
       
    24 
       
    25 Tfd = _plugin_reader.TempVariableDefinition
       
    26 Tsfd = _plugin_reader.TempVariableSequenceDefinition
       
    27 Sro = _plugin_reader.SettingRefsOverride
       
    28 
       
    29 
       
    30 
       
    31 MULTI_IMPL_1 = """<?xml version="1.0" encoding="UTF-8"?>
       
    32 <common:container xmlns:common="http://www.symbianfoundation.org/xml/implml/1">
       
    33     <impl xmlns="http://www.test.com/xml/1">
       
    34         <elem x="1" y="2"/>
       
    35     </impl>
       
    36     
       
    37     <impl xmlns="http://www.test.com/xml/2">
       
    38         <dummy z="500"/>
       
    39         <elem x="10" y="20"/>
       
    40     </impl>
       
    41     
       
    42     <impl xmlns="http://www.test.com/xml/3">
       
    43         <elem x="100" y="200"/>
       
    44         <elem z="300"/>
       
    45     </impl>
       
    46 </common:container>
       
    47 """.encode('utf-8')
       
    48 
       
    49 MULTI_IMPL_2 = """<?xml version="1.0" encoding="UTF-8"?>
       
    50 <container xmlns="http://www.symbianfoundation.org/xml/implml/1"
       
    51     xmlns:ns0="http://www.test.com/xml/1" 
       
    52     xmlns:ns2="http://www.test.com/xml/2"
       
    53     xmlns:ns3="http://www.test.com/xml/3">
       
    54     
       
    55     <ns0:impl>
       
    56       <ns0:elem x="1" y="2"/>
       
    57     </ns0:impl>
       
    58 
       
    59     <ns2:impl>
       
    60       <ns2:dummy z="500"/>
       
    61       <ns2:elem x="10" y="20"/>
       
    62     </ns2:impl>
       
    63 
       
    64     <ns3:impl>
       
    65       <ns3:elem x="100" y="200"/>
       
    66       <ns3:elem z="300"/>
       
    67     </ns3:impl>
       
    68 </container>
       
    69 """.encode('utf-8')
       
    70 
       
    71 MULTI_IMPL_3 = """<?xml version="1.0" encoding="UTF-8"?>
       
    72 <container xmlns="http://www.symbianfoundation.org/xml/implml/1">
       
    73     <impl1:impl xmlns:impl1="http://www.test.com/xml/1">
       
    74         <impl1:elem x="1" y="2"/>
       
    75     </impl1:impl>
       
    76     
       
    77     <impl2:impl xmlns:impl2="http://www.test.com/xml/2">
       
    78         <impl2:elem x="1" y="2"/>
       
    79     </impl2:impl>
       
    80     
       
    81     <impl1:impl xmlns:impl1="http://www.test.com/xml/1">
       
    82         <impl1:elem a="1" b="2"/>
       
    83     </impl1:impl>
       
    84     
       
    85     <impl2:impl xmlns:impl2="http://www.test.com/xml/2">
       
    86         <impl2:elem a="1" b="2"/>
       
    87     </impl2:impl>
       
    88 </container>
       
    89 """.encode('utf-8')
       
    90 
       
    91 UNSUPPORTED_IMPL_1 = """<?xml version="1.0" encoding="UTF-8"?>
       
    92 <test_impl>
       
    93     <impl xmlns="http://www.test.com/xml/1">
       
    94         <elem x="1" y="2"/>
       
    95     </impl>
       
    96     
       
    97     <impl xmlns="http://www.test.com/xml/2">
       
    98         <dummy z="500"/>
       
    99         <elem x="10" y="20"/>
       
   100     </impl>
       
   101     
       
   102     <impl xmlns="http://www.test.com/xml/4">
       
   103         <elem x="1" y="2"/>
       
   104     </impl>
       
   105 </test_impl>
       
   106 """.encode('utf-8')
       
   107 
       
   108 UNSUPPORTED_IMPL_2 = """<?xml version="1.0" encoding="UTF-8"?>
       
   109 <test_impl xmlns="http://www.test.com/xml/6"
       
   110     xmlns:ns2="http://www.test.com/xml/2"
       
   111     xmlns:ns4="http://www.test.com/xml/4">
       
   112     
       
   113     <elem x="1" y="2"/>
       
   114 
       
   115     <ns2:dummy z="500"/>
       
   116     <ns2:elem x="10" y="20"/>
       
   117 
       
   118     <ns4:elem x="1" y="2"/>
       
   119 </test_impl>
       
   120 """.encode('utf-8')
       
   121 
       
   122 SINGLE_IMPL_1 = """<?xml version="1.0" encoding="UTF-8"?>
       
   123 <impl xmlns="http://www.test.com/xml/1">
       
   124     <elem x="1"/>
       
   125     <elem y="2"/>
       
   126     <elem z="3"/>
       
   127 </impl>
       
   128 """.encode('utf-8')
       
   129 
       
   130 SINGLE_IMPL_2 = """<?xml version="1.0" encoding="UTF-8"?>
       
   131 <joujou xmlns="http://www.test.com/xml/2"/>
       
   132 """.encode('utf-8')
       
   133 
       
   134 SINGLE_IMPL_3 = """<?xml version="1.0" encoding="UTF-8"?>
       
   135 <impl xmlns="http://www.test.com/xml/3">
       
   136     <elem x="1"/>
       
   137 </impl>
       
   138 """.encode('utf-8')
       
   139 
       
   140 IGNORED_NAMESPACE_IMPL_1 = """<?xml version="1.0" encoding="UTF-8"?>
       
   141 <common:container xmlns:common="http://www.symbianfoundation.org/xml/implml/1">
       
   142     <impl xmlns="http://www.test.com/xml/3">
       
   143         <elem x="1"/>
       
   144     </impl>
       
   145     
       
   146     <ignored xmlns:ignored="http://www.test.com/xml/ignored/3">
       
   147         <elem test="foo"/>
       
   148     </ignored>
       
   149 </common:container>
       
   150 """.encode('utf-8')
       
   151 
       
   152 IGNORED_NAMESPACE_IMPL_2 = """<?xml version="1.0" encoding="UTF-8"?>
       
   153 <impl xmlns="http://www.test.com/xml/3" xmlns:ignored="http://www.test.com/xml/ignored/3">
       
   154     <elem x="1"/>
       
   155     <ignored:some_elem/>
       
   156 </impl>
       
   157 """.encode('utf-8')
       
   158 
       
   159 NO_IMPL = """<?xml version="1.0" encoding="UTF-8"?>
       
   160 <impl>
       
   161 </impl>
       
   162 """.encode('utf-8')
       
   163 
       
   164 class Mock(object):
       
   165     pass
       
   166 
       
   167 class MockView(object):
       
   168     def __init__(self, feature_dict):
       
   169         self.feature_dict = feature_dict
       
   170     
       
   171     def get_feature(self, ref):
       
   172         feature = Mock()
       
   173         feature.get_value = lambda: self.feature_dict[ref]
       
   174         feature.get_original_value = lambda: self.feature_dict[ref]
       
   175         return feature
       
   176 
       
   177 class MockConfiguration(object):
       
   178     def __init__(self, resources, features={}):
       
   179         self.resources = resources
       
   180         self.features = features
       
   181     
       
   182     def get_resource(self, ref):
       
   183         res = Mock()
       
   184         res.read = lambda: self.resources[ref]
       
   185         res.close = lambda: None
       
   186         return res
       
   187     
       
   188     def get_layer(self):
       
   189         layer = Mock()
       
   190         layer.list_implml = lambda: self.resources.keys()
       
   191         return layer
       
   192     
       
   193     def get_doc(self, ref):
       
   194         return utils.etree.fromstring(self.get_resource(ref).read())
       
   195     
       
   196     def get_default_view(self):
       
   197         return MockView(self.features)
       
   198 
       
   199 class MockImpl(plugin.ImplBase):
       
   200     def __init__(self, data):
       
   201         self.data = data
       
   202         self.generate_invoked = False
       
   203     
       
   204     @classmethod
       
   205     def create(cls, resource_ref, configuration, data):
       
   206         impl = cls(data)
       
   207         plugin.ImplBase.__init__(impl, resource_ref, configuration)
       
   208         return impl
       
   209     
       
   210     def generate(self, context=None):
       
   211         if context and hasattr(context,'objects'):
       
   212             context.objects.append(self) 
       
   213         self.generate_invoked = True
       
   214     
       
   215     def __repr__(self):
       
   216         return "MockImpl(%r)" % self.data
       
   217     
       
   218     def __eq__(self, other):
       
   219         if type(self) == type(other):
       
   220             return self.data == other.data
       
   221         else:
       
   222             return False
       
   223     
       
   224     def __ne__(self, other):
       
   225         return not (self == other)
       
   226         
       
   227     def __lt__(self, other):
       
   228         if type(self) == type(other):
       
   229             return self.data < other.data
       
   230         else:
       
   231             return False
       
   232 
       
   233 class MockReaderBase(plugin.ReaderBase):
       
   234     @classmethod
       
   235     def read_impl(cls, resource_ref, configuration, root_elem):
       
   236         data = [cls.__name__, resource_ref]
       
   237         for elem in root_elem.findall('{%s}elem' % cls.NAMESPACE):
       
   238             data.append(elem.attrib)
       
   239         return MockImpl.create(resource_ref, configuration, data)
       
   240 
       
   241 class MockReader1(MockReaderBase):
       
   242     NAMESPACE = "http://www.test.com/xml/1"
       
   243     FILE_EXTENSIONS = ['mock1ml']
       
   244 class MockReader2(MockReaderBase):
       
   245     NAMESPACE = "http://www.test.com/xml/2"
       
   246     FILE_EXTENSIONS = ['mock2ml']
       
   247 class MockReader3(MockReaderBase):
       
   248     NAMESPACE = "http://www.test.com/xml/3"
       
   249     IGNORED_NAMESPACES = ["http://www.test.com/xml/ignored/3"]
       
   250     FILE_EXTENSIONS = ['mock3ml', 'test3ml']
       
   251 
       
   252 MOCK_READER_CLASSES = [MockReader1, MockReader2, MockReader3]
       
   253 
       
   254 mock_config = MockConfiguration({
       
   255     'layer1/implml/multi1.implml'           : MULTI_IMPL_1,
       
   256     'layer1/implml/multi2.implml'           : MULTI_IMPL_2,
       
   257     'layer1/implml/multi3.implml'           : MULTI_IMPL_3,
       
   258     'layer1/implml/unsupported1.implml'     : UNSUPPORTED_IMPL_1,
       
   259     'layer1/implml/unsupported2.implml'     : UNSUPPORTED_IMPL_2,
       
   260     'layer1/implml/single1.implml'          : SINGLE_IMPL_1,
       
   261     'layer1/implml/single2.implml'          : SINGLE_IMPL_2,
       
   262     'layer1/implml/single3.implml'          : SINGLE_IMPL_3,
       
   263     'layer1/implml/none.implml'             : NO_IMPL,
       
   264     'layer1/implml/broken.implml'           : 'Some invalid XML data...',
       
   265     'layer1/implml/single1.mock1ml'         : SINGLE_IMPL_1,
       
   266     'layer1/implml/single2.mock2ml'         : SINGLE_IMPL_2,
       
   267     'layer1/implml/single3.mock3ml'         : SINGLE_IMPL_3,
       
   268     'layer1/implml/single3.test3ml'         : SINGLE_IMPL_3,
       
   269     'layer1/implml/ignored_ns_1.mock3ml'    : IGNORED_NAMESPACE_IMPL_1,
       
   270     'layer1/implml/ignored_ns_2.mock3ml'    : IGNORED_NAMESPACE_IMPL_2,
       
   271     'layer1/implml/multi1.dummyml'          : MULTI_IMPL_1,
       
   272     'layer1/implml/dummy'                   : MULTI_IMPL_1,
       
   273 })
       
   274 
       
   275 class TestPluginImplBase(unittest.TestCase):
       
   276     def setUp(self):
       
   277         pass
       
   278 
       
   279     def test_implbase_add_tags(self):
       
   280         impl = plugin.ImplBase('test',None)
       
   281         impl.set_tags({'target': ['test', 'foo']})
       
   282         self.assertEquals(impl.get_tags()['target'],['test','foo'])
       
   283         #self.assertEquals(impl.has_tag({}, policy='OR'), True)
       
   284         self.assertEquals(impl.has_tag({'target': ['test']}, policy='OR'), True)
       
   285         self.assertEquals(impl.has_tag({'target': ['test']}, policy='AND'), True)
       
   286         self.assertEquals(impl.has_tag({'target': ['foo']}, policy='OR'), True)
       
   287         self.assertEquals(impl.has_tag({'target': ['foo']}, policy='AND'), True)
       
   288         self.assertEquals(impl.has_tag({'target': ['test','foo']}, policy='OR'), True)
       
   289         self.assertEquals(impl.has_tag({'target': ['test','foo']}, policy='AND'), True)
       
   290         self.assertEquals(impl.has_tag({'target': ['test2','foo']}, policy='OR'), True)
       
   291         self.assertEquals(impl.has_tag({'target': ['test2','foo']}, policy='AND'), False)
       
   292         self.assertEquals(impl.has_tag({'foo': ['foo']}, policy='OR'), False)
       
   293         self.assertEquals(impl.has_tag({'foo': ['foo']}, policy='AND'), False)
       
   294         self.assertEquals(impl.has_tag({'target': ['foo'], 'foo':['bar']}, policy='AND'), False)
       
   295         self.assertEquals(impl.has_tag({'target': ['foo'], 'foo':['bar']}, policy='OR'), True)
       
   296     
       
   297     def test_implbase_tags_with_refs(self):
       
   298         config = MockConfiguration({}, features = {
       
   299             'Foo.Bar'           : 'foobar',
       
   300             'Foo.Baz'           : 'foobaz',
       
   301             'Feature.TagName'   : 'tagname',
       
   302             'Feature.TagValue'  : 'tagvalue',
       
   303         })
       
   304         
       
   305         impl = plugin.ImplBase('test', config)
       
   306         impl.set_tags({
       
   307             'test'              : ['${Foo.Bar}', 'foo', 'bar', '${Foo.Bar} and ${Foo.Baz}'],
       
   308             '${Feature.TagName}': ['${Feature.TagValue}']})
       
   309         
       
   310         expected = {
       
   311             'test': ['foobar', 'foo', 'bar', 'foobar and foobaz'],
       
   312             'tagname': ['tagvalue'],
       
   313         }
       
   314         self.assertEquals(impl.get_tags(), expected)
       
   315     
       
   316     def test_has_ref(self):
       
   317         impl = plugin.ImplBase('test', None)
       
   318         self.assertEquals(impl.has_ref('Foo.Bar'), None)
       
   319         
       
   320         impl.get_refs = lambda: ['Foo.Bar', 'Xyz']
       
   321         
       
   322         # Test using different supported parameter types
       
   323         self.assertTrue(impl.has_ref('Foo.Bar'))
       
   324         self.assertTrue(impl.has_ref(['Foo.Bar']))
       
   325         self.assertTrue(impl.has_ref(('Foo.Bar',)))
       
   326         
       
   327         # Impl uses the exact given ref
       
   328         self.assertTrue(impl.has_ref('Foo.Bar'))
       
   329         self.assertTrue(impl.has_ref('Xyz'))
       
   330         
       
   331         # Impl uses the given ref's parent ref
       
   332         self.assertTrue(impl.has_ref('Foo.Bar.Baz'))
       
   333         self.assertTrue(impl.has_ref('Xyz.Zyx'))
       
   334         
       
   335         # Impl does not use the entire parent ref of 'Foo.Bar', only the
       
   336         # 'Bar' sub-ref
       
   337         self.assertFalse(impl.has_ref('Foo'))
       
   338         
       
   339         # Various refs almost matching a specified ref
       
   340         self.assertFalse(impl.has_ref('Fo'))
       
   341         self.assertFalse(impl.has_ref('Fog'))
       
   342         self.assertFalse(impl.has_ref('Food'))
       
   343         self.assertFalse(impl.has_ref('Foo.Ba'))
       
   344         self.assertFalse(impl.has_ref('Foo.Bag'))
       
   345         self.assertFalse(impl.has_ref('Foo.Bard'))
       
   346         
       
   347         # Various refs not at all in the impl's ref list
       
   348         self.assertFalse(impl.has_ref('Yay'))
       
   349         self.assertFalse(impl.has_ref(['Yay', 'Fhtagn']))
       
   350         
       
   351         # One of the refs in the given list matches
       
   352         self.assertTrue(impl.has_ref(['Yay', 'Fhtagn', 'Foo.Bar']))
       
   353         self.assertTrue(impl.has_ref(['Yay', 'Foo.Bar.Baz', 'Fhtagn']))
       
   354         self.assertTrue(impl.has_ref(['Yay', 'Xyz', 'Fhtagn']))
       
   355         
       
   356     def test_impl_container_eval_context_with_tags(self):
       
   357         container = plugin.ImplBase("norm", None)
       
   358         context = plugin.GenerationContext()
       
   359         self.assertTrue(container._eval_context(context))
       
   360         container.set_tags({'target':['rofs2','core']})
       
   361         context.tags = {'target': ['rofs2'], 'foobar': ['test']}
       
   362         self.assertTrue(container._eval_context(context))
       
   363         context.tags_policy = "AND"
       
   364         self.assertFalse(container._eval_context(context))
       
   365         container.set_tags({})
       
   366         self.assertFalse(container._eval_context(context))
       
   367         context.tags = {'target': ['rofs2']}
       
   368         self.assertFalse(container._eval_context(context))
       
   369         context.tags = {}
       
   370         self.assertTrue(container._eval_context(context))
       
   371 
       
   372 class TestPluginImplSet(unittest.TestCase):
       
   373     
       
   374     def test_add_implementation_and_list(self):
       
   375         container = plugin.ImplSet()
       
   376         imp1  = plugin.ImplBase("implml/test.content",None)
       
   377         imp2a = plugin.ImplBase("implml/copy.content",None)
       
   378         imp2b = plugin.ImplBase("implml/copy.content",None)
       
   379         container.add_implementation(imp1)
       
   380         container.add_implementation(imp2a)
       
   381         container.add_implementation(imp2b)
       
   382         self.assertEquals(sorted(container.list_implementation()),
       
   383                           sorted(['implml/test.content',
       
   384                                   'implml/copy.content']))
       
   385 
       
   386     def test_add_implementation_and_get_implementations_by_file(self):
       
   387         container = plugin.ImplSet()
       
   388         imp1  = plugin.ImplBase("implml/test.content",None)
       
   389         imp2a = plugin.ImplBase("implml/copy.content",None)
       
   390         imp2b = plugin.ImplBase("implml/copy.content",None)
       
   391         container.add_implementation(imp1)
       
   392         container.add_implementation(imp2a)
       
   393         container.add_implementation(imp2b)
       
   394         self.assertEquals(container.get_implementations_by_file("implml/test.content"), [imp1])
       
   395         self.assertEquals(sorted(container.get_implementations_by_file("implml/copy.content")),
       
   396                           sorted([imp2a, imp2b]))
       
   397 
       
   398     def test_add_implementation_and_remove_implementation(self):
       
   399         container = plugin.ImplSet()
       
   400         imp1  = plugin.ImplBase("implml/test.content",None)
       
   401         imp2a = plugin.ImplBase("implml/copy.content",None)
       
   402         imp2b = plugin.ImplBase("implml/copy.content",None)
       
   403         container.add_implementation(imp1)
       
   404         container.add_implementation(imp2a)
       
   405         container.add_implementation(imp2b)
       
   406         container.remove_implementation("implml/test.content")
       
   407         self.assertEquals(len(container.list_implementation()),1)
       
   408         self.assertEquals(container.list_implementation()[0],"implml/copy.content")
       
   409 
       
   410     def test_add_implementation_and_remove_all(self):
       
   411         container = plugin.ImplSet()
       
   412         imp1  = plugin.ImplBase("implml/test.content",None)
       
   413         imp2a = plugin.ImplBase("implml/copy.content",None)
       
   414         imp2b = plugin.ImplBase("implml/copy.content",None)
       
   415         imp3  = plugin.ImplBase("implml/foo.content",None)
       
   416         container.add_implementation(imp1)
       
   417         container.add_implementation(imp2a)
       
   418         container.add_implementation(imp2b)
       
   419         container.add_implementation(imp3)
       
   420         for implref in container.list_implementation():
       
   421             container.remove_implementation(implref)
       
   422         self.assertEquals(len(container.list_implementation()),0)
       
   423 
       
   424     def test_create_impl_set(self):
       
   425         plugin.create_impl_set('',None);
       
   426         pass
       
   427 
       
   428     def test_add_implementation_find_with_tags(self):
       
   429         class TestPlugin(plugin.ImplBase):
       
   430             pass
       
   431         container = plugin.ImplSet()
       
   432         imp1 = TestPlugin("implml/test.content",None)
       
   433         imp2 = TestPlugin("implml/copy.content",None)
       
   434         imp3 = TestPlugin("implml/foo.content",None)
       
   435         imp1.set_tags({'target': ['core','rofs2','rofs3']})
       
   436         imp2.set_tags({'target': ['rofs3','uda']})
       
   437         imp3.set_tags({'target': ['mmc','uda']})
       
   438         container.add_implementation(imp1)
       
   439         container.add_implementation(imp2)
       
   440         container.add_implementation(imp3)
       
   441         self.assertEquals(list(container.filter_implementations(tags={'target' : ['rofs3']})),
       
   442                           [imp1,imp2])
       
   443         self.assertEquals(list(container.filter_implementations(tags={'target' : ['uda']})),
       
   444                           [imp2,imp3])
       
   445         self.assertEquals(list(container.filter_implementations(tags={'target' : ['mmc','uda']}, policy='AND')),
       
   446                           [imp3])
       
   447         self.assertEquals(list(container.filter_implementations(tags={'target' : ['mmc','uda']}, policy='OR')),
       
   448                           [imp2, imp3])
       
   449         cont = container.filter_implementations(tags={'target' : ['core']}) | container.filter_implementations(tags={'target' : ['mmc']}) 
       
   450         self.assertEquals(len(cont),2)
       
   451         self.assertEquals(list(cont), [imp1,imp3])
       
   452 
       
   453         cont = container.filter_implementations(tags={'target' : ['rofs3']}) & container.filter_implementations(tags={'target' : ['uda']}) 
       
   454         self.assertEquals(len(cont),1)
       
   455         self.assertEquals(list(cont), [imp2])
       
   456     
       
   457     def test_pre_impl_filter(self):
       
   458         resources = [
       
   459             "foo.txt",
       
   460             ".hidden_file",
       
   461             ".test/test.txt",
       
   462             "layer1/implml/.hidden",
       
   463             "layer1/implml/test.crml",
       
   464             "layer1/implml/test3.gcfml",
       
   465             "layer1/implml/.svn/text-base/test.crml.svn-base",
       
   466             "layer1/implml/subdir/test5.crml",
       
   467             "layer1/implml/subdir/test6.ruleml",
       
   468             "layer1/implml/subdir/.scripts/test6_ruleml.py",
       
   469         ]
       
   470         
       
   471         expected = [
       
   472             "foo.txt",
       
   473             "layer1/implml/test.crml",
       
   474             "layer1/implml/test3.gcfml",
       
   475             "layer1/implml/subdir/test5.crml",
       
   476             "layer1/implml/subdir/test6.ruleml",
       
   477         ]
       
   478         
       
   479         self.assertEquals(expected, plugin.pre_filter_impls(resources))
       
   480         
       
   481         # Test with backslashes
       
   482         resources = map(lambda path: path.replace('/', '\\'), resources)
       
   483         expected = map(lambda path: path.replace('/', '\\'), expected)
       
   484         self.assertEquals(expected, plugin.pre_filter_impls(resources))
       
   485 
       
   486 
       
   487 class TestPluginImplSetCopy(unittest.TestCase):
       
   488     class TestImpl(plugin.ImplBase):
       
   489         pass # No default invocation phase specified, should be 'normal'
       
   490     class PreImpl(plugin.ImplBase):
       
   491         DEFAULT_INVOCATION_PHASE = 'pre'
       
   492     class NormalImpl(plugin.ImplBase):
       
   493         DEFAULT_INVOCATION_PHASE = 'normal'
       
   494     class PostImpl(plugin.ImplBase):
       
   495         DEFAULT_INVOCATION_PHASE = 'post'
       
   496 
       
   497     def setUp(self):
       
   498         plugin.ImplFactory.set_reader_classes_override(MOCK_READER_CLASSES)
       
   499     
       
   500     def tearDown(self):
       
   501         plugin.ImplFactory.set_reader_classes_override(None)
       
   502     
       
   503     def _get_impl_container(self):
       
   504         impl_files = ['layer1/implml/single1.implml',
       
   505                       'layer1/implml/single2.implml',
       
   506                       'layer1/implml/single3.implml',
       
   507                       'layer1/implml/multi1.implml',
       
   508                       'layer1/implml/multi2.implml']
       
   509         return plugin.create_impl_set(impl_files, mock_config)
       
   510     
       
   511 
       
   512     def test_get_test_impl_container(self):
       
   513         container = self._get_impl_container()
       
   514         # There are 5 ImplML files
       
   515         self.assertEquals(len(container.list_implementation()), 5)
       
   516         # ...but two of them contain 3 implementations each
       
   517         self.assertEquals(len(container), 5)
       
   518     
       
   519     def _get_phase_test_impl_container(self):
       
   520         return plugin.ImplSet([
       
   521             self.TestImpl('foo.test', None),
       
   522             self.NormalImpl('foo.norm', None),
       
   523             self.PreImpl('foo.pre', None),
       
   524             self.PostImpl('test.post', None),
       
   525             self.PostImpl('foo.post', None),
       
   526         ])
       
   527     
       
   528     def test_get_phase_test_impl_container(self):
       
   529         container = self._get_phase_test_impl_container()
       
   530         self.assertEquals(5, len(container))
       
   531         self.assertEquals(len(container.list_implementation()), 5)
       
   532         
       
   533         def check(filename, phase):
       
   534             impls = container.get_implementations_by_file(filename)
       
   535             self.assertEquals(1, len(impls))
       
   536             impl = impls[0]
       
   537             self.assertEquals(impl.ref, filename)
       
   538             self.assertEquals(impl.invocation_phase(), phase)
       
   539         check('foo.test', 'normal')
       
   540         check('foo.norm', 'normal')
       
   541         check('foo.pre', 'pre')
       
   542         check('test.post', 'post')
       
   543         check('foo.post', 'post')
       
   544         
       
   545         return container
       
   546     
       
   547     def test_create_impl_set(self):
       
   548         container = self._get_impl_container()
       
   549         # There are 5 ImplML files
       
   550         self.assertEquals(len(container.list_implementation()), 5)
       
   551         # ...but two of them contain 3 implementations each
       
   552         self.assertEquals(len(container), 5)
       
   553     
       
   554     def test_invocation_phases(self):
       
   555         container = self._get_phase_test_impl_container()
       
   556         phases = container.invocation_phases()
       
   557         self.assertEquals(phases,['pre','normal','post'])
       
   558  
       
   559     def test_copy(self):
       
   560         container = self._get_impl_container()
       
   561         newcontainer = container.copy()
       
   562         self.assertTrue(newcontainer is not container)
       
   563         self.assertEquals(len(newcontainer), 5)
       
   564 
       
   565     def test_execute_generate(self):
       
   566         container = self._get_impl_container()
       
   567         container.execute(container, 'generate')
       
   568         actual_impls = []
       
   569         for impl in container:
       
   570             if isinstance(impl, plugin.ImplContainer):
       
   571                 actual_impls += impl.get_all_implementations()
       
   572             else:
       
   573                 actual_impls.append(impl)
       
   574         for impl in actual_impls:
       
   575             self.assertTrue(impl.generate_invoked)
       
   576 
       
   577     def test_impl_container_generate(self):
       
   578         container = self._get_impl_container()
       
   579         context = plugin.GenerationContext()
       
   580         context.history = ""
       
   581         context.objects = []
       
   582         container.generate(context)
       
   583         self.assertEquals(len(context.objects), 9)
       
   584         actual_impls = []
       
   585         for impl in container:
       
   586             if isinstance(impl, plugin.ImplContainer):
       
   587                 actual_impls += impl.get_all_implementations()
       
   588             else:
       
   589                 actual_impls.append(impl)
       
   590         for impl in actual_impls:
       
   591             self.assertTrue(impl.generate_invoked)
       
   592 
       
   593     def test_filter_all(self):
       
   594         container = self._get_impl_container()
       
   595         impl_list = container.filter_implementations()
       
   596         self.assertEquals(len(impl_list), 5)
       
   597 
       
   598     def test_filter_for_pre_phase(self):
       
   599         container = self._get_phase_test_impl_container()
       
   600         impl_list = list(container.filter_implementations(phase='pre'))
       
   601         self.assertEquals(len(impl_list), 1)
       
   602         self.assertEquals(impl_list[0].invocation_phase(), 'pre')
       
   603         self.assertEquals(impl_list[0].ref, 'foo.pre')
       
   604 
       
   605     def test_filter_for_normal_phase(self):
       
   606         container = self._get_phase_test_impl_container()
       
   607         impl_list = list(container.filter_implementations(phase='normal'))
       
   608         self.assertEquals(len(impl_list), 2)
       
   609         self.assertEquals(impl_list[0].invocation_phase(), 'normal')
       
   610         self.assertEquals(impl_list[1].invocation_phase(), 'normal')
       
   611 
       
   612     def test_filter_for_post_phase(self):
       
   613         container = self._get_phase_test_impl_container()
       
   614         impl_list = list(container.filter_implementations(phase='post'))
       
   615         self.assertEquals(len(impl_list), 2)
       
   616         self.assertEquals(impl_list[0].invocation_phase(), 'post')
       
   617         self.assertEquals(impl_list[1].invocation_phase(), 'post')
       
   618 
       
   619 
       
   620 class TestPluginImplSettings(unittest.TestCase):
       
   621     class Test1Impl(plugin.ImplBase):
       
   622         IMPL_TYPE_ID = "test1"
       
   623     class Test2Impl(plugin.ImplBase):
       
   624         IMPL_TYPE_ID = "test2"
       
   625     class Test3Impl(plugin.ImplBase):
       
   626         IMPL_TYPE_ID = "test3"
       
   627 
       
   628     def test_plugin_settings(self):
       
   629         settings.SettingsFactory.cone_parser().read([os.path.join(ROOT_PATH,'test_defaults.cfg')])
       
   630         impl = TestPluginImplSettings.Test1Impl("",None)
       
   631         self.assertEquals(impl.output_root, 'output')
       
   632         self.assertEquals(impl.output_subdir, '')
       
   633         impl.output_subdir = 'foobar'
       
   634         self.assertEquals(impl.get_tags(), {})
       
   635         self.assertEquals(impl.output, 'output/foobar')
       
   636 
       
   637         impl = TestPluginImplSettings.Test2Impl("",None)
       
   638         self.assertEquals(impl.output_subdir, '')
       
   639 
       
   640 
       
   641 
       
   642 class TestReaders(unittest.TestCase):
       
   643     
       
   644     def setUp(self):
       
   645         plugin.ImplFactory.set_reader_classes_override(MOCK_READER_CLASSES)
       
   646     
       
   647     def tearDown(self):
       
   648         plugin.ImplFactory.set_reader_classes_override(None)
       
   649     
       
   650     def assert_namespace_list_equals(self, resource_ref, expected_namespaces):
       
   651         self.assertEquals(
       
   652             expected_namespaces,
       
   653             _plugin_reader.ImplReader._get_namespaces(mock_config.get_doc(resource_ref)))
       
   654     
       
   655     def test_get_needed_reader_classes(self):
       
   656         self.assert_namespace_list_equals('layer1/implml/none.implml', [])
       
   657         
       
   658         self.assert_namespace_list_equals('layer1/implml/single1.implml',
       
   659             ['http://www.test.com/xml/1'])
       
   660         
       
   661         self.assert_namespace_list_equals('layer1/implml/single2.implml',
       
   662             ['http://www.test.com/xml/2'])
       
   663         
       
   664         self.assert_namespace_list_equals('layer1/implml/multi1.implml',
       
   665             ['http://www.symbianfoundation.org/xml/implml/1', 
       
   666              'http://www.test.com/xml/1',
       
   667              'http://www.test.com/xml/2',
       
   668              'http://www.test.com/xml/3'])
       
   669         
       
   670         self.assert_namespace_list_equals('layer1/implml/multi2.implml',
       
   671             ['http://www.symbianfoundation.org/xml/implml/1', 
       
   672              'http://www.test.com/xml/1',
       
   673              'http://www.test.com/xml/2',
       
   674              'http://www.test.com/xml/3'])
       
   675         
       
   676         self.assert_namespace_list_equals('layer1/implml/multi3.implml',
       
   677             ['http://www.symbianfoundation.org/xml/implml/1', 
       
   678              'http://www.test.com/xml/1',
       
   679              'http://www.test.com/xml/2'])
       
   680         
       
   681         self.assert_namespace_list_equals('layer1/implml/unsupported1.implml',
       
   682             ['http://www.test.com/xml/1',
       
   683              'http://www.test.com/xml/2',
       
   684              'http://www.test.com/xml/4'])
       
   685         
       
   686         self.assert_namespace_list_equals('layer1/implml/unsupported2.implml',
       
   687             ['http://www.test.com/xml/6',
       
   688              'http://www.test.com/xml/2',
       
   689              'http://www.test.com/xml/4'])
       
   690     
       
   691     def assert_read_impls_equal(self, expected, resource_ref):
       
   692         actual = plugin.ImplFactory.get_impls_from_file(resource_ref, mock_config)
       
   693         if len(actual) == 1 and isinstance(actual[0], plugin.ImplContainer):
       
   694             actual = actual[0].get_all_implementations() 
       
   695         self.assertEquals(expected, actual)
       
   696         
       
   697 #        # Assert that the implementations have the correct impl indices set
       
   698 #        for i, impl in enumerate(actual):
       
   699 #            self.assertEquals(i, impl.index, "Impl %r does not have the expected index %r (is %r)" % (impl, i, impl.index))
       
   700         
       
   701     def test_get_impls_from_file(self):
       
   702         self.assert_read_impls_equal(
       
   703             [],
       
   704             'layer1/implml/none.implml')
       
   705         
       
   706         file = 'layer1/implml/single1.implml'
       
   707         self.assert_read_impls_equal(
       
   708             [MockImpl(['MockReader1', file, {'x': '1'}, {'y': '2'}, {'z': '3'}])],
       
   709             file)
       
   710         
       
   711         file = 'layer1/implml/single2.implml'
       
   712         self.assert_read_impls_equal(
       
   713             [MockImpl(['MockReader2', file])],
       
   714             file)
       
   715         
       
   716         file = 'layer1/implml/single3.implml'
       
   717         self.assert_read_impls_equal(
       
   718             [MockImpl(['MockReader3', file, {'x': '1'}])],
       
   719             file)
       
   720         
       
   721         file = 'layer1/implml/multi1.implml'
       
   722         self.assert_read_impls_equal(
       
   723             [MockImpl(['MockReader1', file, {'x': '1', 'y': '2'}]),
       
   724              MockImpl(['MockReader2', file, {'x': '10', 'y': '20'}]),
       
   725              MockImpl(['MockReader3', file, {'x': '100', 'y': '200'}, {'z': '300'}])],
       
   726             file)
       
   727         
       
   728         file = 'layer1/implml/multi2.implml'
       
   729         self.assert_read_impls_equal(
       
   730             [MockImpl(['MockReader1', file, {'x': '1', 'y': '2'}]),
       
   731              MockImpl(['MockReader2', file, {'x': '10', 'y': '20'}]),
       
   732              MockImpl(['MockReader3', file, {'x': '100', 'y': '200'}, {'z': '300'}])],
       
   733             file)
       
   734         
       
   735         file = 'layer1/implml/multi3.implml'
       
   736         self.assert_read_impls_equal(
       
   737             [MockImpl(['MockReader1', file, {'x': '1', 'y': '2'}]),
       
   738              MockImpl(['MockReader2', file, {'x': '1', 'y': '2'}]),
       
   739              MockImpl(['MockReader1', file, {'a': '1', 'b': '2'}]),
       
   740              MockImpl(['MockReader2', file, {'a': '1', 'b': '2'}]),],
       
   741             file)
       
   742         
       
   743         file = 'layer1/implml/ignored_ns_1.mock3ml'
       
   744         self.assert_read_impls_equal([MockImpl(['MockReader3', file, {'x': '1'}])], file)
       
   745         
       
   746         file = 'layer1/implml/ignored_ns_2.mock3ml'
       
   747         self.assert_read_impls_equal([MockImpl(['MockReader3', file, {'x': '1'}])], file)
       
   748         
       
   749         
       
   750         self.assert_read_impls_equal([], 'layer1/implml/unsupported1.implml')
       
   751         self.assert_read_impls_equal([], 'layer1/implml/unsupported2.implml')
       
   752         
       
   753         self.assert_read_impls_equal([], 'layer1/implml/broken.implml')
       
   754     
       
   755     def test_is_supported_impl_file(self):
       
   756         def check(filename, expected):
       
   757             self.assertEquals(expected, plugin.ImplFactory.is_supported_impl_file(filename))
       
   758         check('test.implml', True)
       
   759         check('layer/implml/test.implml', True)
       
   760         check('layer/implml/test.mock1ml', True)
       
   761         check('layer/implml/test.mock2ml', True)
       
   762         check('layer/implml/test.mock3ml', True)
       
   763         check('layer/implml/test.test3ml', True)
       
   764         check('layer/implml/test.dummyml', False)
       
   765         check('layer/implml/test.xml', False)
       
   766         check('layer/implml/test', False)
       
   767         check('layer/implml/test.IMPLML', True)
       
   768         check('layer/implml/test.ImplML', True)
       
   769         check('layer/implml/test.Mock1ML', True)
       
   770     
       
   771     def test_read_all_impls(self):
       
   772         actual = list(plugin.get_impl_set(mock_config))
       
   773         actual_impls = []
       
   774         for impl in actual:
       
   775             if isinstance(impl, plugin.ImplContainer):
       
   776                 actual_impls += impl.get_all_implementations()
       
   777             else:
       
   778                 actual_impls.append(impl)
       
   779         
       
   780         expected = [
       
   781             MockImpl(['MockReader1', 'layer1/implml/single1.implml', {'x': '1'}, {'y': '2'}, {'z': '3'}]),
       
   782             MockImpl(['MockReader2', 'layer1/implml/single2.implml']),
       
   783             MockImpl(['MockReader3', 'layer1/implml/single3.implml', {'x': '1'}]),
       
   784             
       
   785             MockImpl(['MockReader1', 'layer1/implml/single1.mock1ml', {'x': '1'}, {'y': '2'}, {'z': '3'}]),
       
   786             MockImpl(['MockReader2', 'layer1/implml/single2.mock2ml']),
       
   787             MockImpl(['MockReader3', 'layer1/implml/single3.mock3ml', {'x': '1'}]),
       
   788             
       
   789             MockImpl(['MockReader3', 'layer1/implml/single3.test3ml', {'x': '1'}]),
       
   790             
       
   791             MockImpl(['MockReader3', 'layer1/implml/ignored_ns_1.mock3ml', {'x': '1'}]),
       
   792             MockImpl(['MockReader3', 'layer1/implml/ignored_ns_2.mock3ml', {'x': '1'}]),
       
   793             
       
   794             MockImpl(['MockReader1','layer1/implml/multi1.implml', {'y': '2', 'x': '1'}]),  
       
   795             MockImpl(['MockReader2', 'layer1/implml/multi1.implml', {'y': '20', 'x': '10'}]),
       
   796             MockImpl(['MockReader3', 'layer1/implml/multi1.implml', {'y': '200', 'x': '100'}, {'z': '300'}]),
       
   797             
       
   798             MockImpl(['MockReader1', 'layer1/implml/multi2.implml', {'x': '1', 'y': '2'}]),
       
   799             MockImpl(['MockReader2', 'layer1/implml/multi2.implml', {'x': '10', 'y': '20'}]),
       
   800             MockImpl(['MockReader3', 'layer1/implml/multi2.implml', {'x': '100', 'y': '200'}, {'z': '300'}]),
       
   801             
       
   802             MockImpl(['MockReader1', 'layer1/implml/multi3.implml', {'x': '1', 'y': '2'}]),
       
   803             MockImpl(['MockReader2', 'layer1/implml/multi3.implml', {'x': '1', 'y': '2'}]),
       
   804             MockImpl(['MockReader1', 'layer1/implml/multi3.implml', {'a': '1', 'b': '2'}]),
       
   805             MockImpl(['MockReader2', 'layer1/implml/multi3.implml', {'a': '1', 'b': '2'}]),
       
   806         ]
       
   807         
       
   808         if sorted(expected) != sorted(actual_impls):
       
   809             print 50 * '-'
       
   810             for impl in sorted(expected): print impl
       
   811             print 50 * '-'
       
   812             for impl in sorted(actual_impls): print impl
       
   813             print 50 * '-'
       
   814             
       
   815         
       
   816         self.assertEquals(sorted(expected), sorted(actual_impls))
       
   817 
       
   818 
       
   819 class TestTempFeatureDefinition(unittest.TestCase):
       
   820     
       
   821     def setUp(self):
       
   822         plugin.ImplFactory.set_reader_classes_override(MOCK_READER_CLASSES)
       
   823     
       
   824     def tearDown(self):
       
   825         plugin.ImplFactory.set_reader_classes_override(None)
       
   826     
       
   827     def assert_contains_feature(self, config, ref, type, value):
       
   828         dview = config.get_default_view()
       
   829         feature = dview.get_feature(ref)
       
   830         self.assertEquals(type, feature.get_type())
       
   831         self.assertEquals(value, feature.get_value())
       
   832     
       
   833     def test_create_feature(self):
       
   834         config = api.Configuration("test.confml")
       
   835         def add_feature(setting_ref, value):
       
   836             config.add_feature(api.Feature(setting_ref), "ExistingFeature")
       
   837             config.add_data(api.Data(fqr="ExistingFeature." + setting_ref, value=value))
       
   838         add_feature('String', 'existing value')
       
   839         add_feature('Boolean', '0')
       
   840         add_feature('Boolean2', 'true')
       
   841         
       
   842         Tfd = _plugin_reader.TempVariableDefinition
       
   843         feadefs = [Tfd('TempFeature.String',    'string',   'testing'),
       
   844                    Tfd('TempFeature.Int',       'int',      '500'),
       
   845                    Tfd('TempFeature.Real',      'real',     '1.5'),
       
   846                    Tfd('TempFeature.Boolean',   'boolean',  'true'),
       
   847                    Tfd('TempFeature.String2',   'string',   'xyz ${ExistingFeature.String} zyx'),
       
   848                    Tfd('TempFeature.Boolean2',  'boolean',  '${ExistingFeature.Boolean}'),
       
   849                    Tfd('TempFeature.Boolean3',  'boolean',  '${ExistingFeature.Boolean2}')]
       
   850         for feadef in feadefs:
       
   851             feadef.create_feature(config)
       
   852         
       
   853         # This needs to be done or the default view won't be up-to-date
       
   854         config.recreate_default_view()
       
   855         
       
   856         self.assert_contains_feature(config, 'TempFeature.String', 'string', 'testing')
       
   857         self.assert_contains_feature(config, 'TempFeature.Int', 'int', 500)
       
   858         self.assert_contains_feature(config, 'TempFeature.Real', 'real', 1.5)
       
   859         self.assert_contains_feature(config, 'TempFeature.Boolean', 'boolean', True)
       
   860         self.assert_contains_feature(config, 'TempFeature.String2', 'string', 'xyz existing value zyx')
       
   861         self.assert_contains_feature(config, 'TempFeature.Boolean2', 'boolean', False)
       
   862         self.assert_contains_feature(config, 'TempFeature.Boolean3', 'boolean', True)
       
   863     
       
   864     def test_create_seq_feature(self):
       
   865         Tsfd = _plugin_reader.TempVariableSequenceDefinition
       
   866         feadef = Tsfd('TempFeature.Seq', [('String', 'string'),
       
   867                                           ('Int', 'int'),
       
   868                                           ('Real', 'real'),
       
   869                                           ('Boolean', 'boolean'),
       
   870                                           ('DefaultType', 'string')])
       
   871         config = api.Configuration("test.confml")
       
   872         feadef.create_feature(config)
       
   873         self.assert_contains_feature(config, 'TempFeature.Seq', 'sequence', [])
       
   874         self.assert_contains_feature(config, 'TempFeature.Seq.String', 'string', [])
       
   875         self.assert_contains_feature(config, 'TempFeature.Seq.Int', 'int', [])
       
   876         self.assert_contains_feature(config, 'TempFeature.Seq.Real', 'real', [])
       
   877         self.assert_contains_feature(config, 'TempFeature.Seq.Boolean', 'boolean', [])
       
   878         self.assert_contains_feature(config, 'TempFeature.Seq.DefaultType', 'string', [])
       
   879         
       
   880         fea = config.get_default_view().get_feature('TempFeature.Seq')
       
   881         fea.set_value([['test', '1', '2.0', 'true', 'foo']])
       
   882         self.assertEquals(fea.get_value(), [['test', '1', '2.0', 'true', 'foo']])
       
   883     
       
   884     def _create_mock_impl(self, temp_var_defs):
       
   885         impl = Mock()
       
   886         impl.ref = "test.implml"
       
   887         impl.get_temp_variable_definitions = lambda: temp_var_defs
       
   888         return impl
       
   889     
       
   890     def test_create_from_impl_container(self):
       
   891         impls = plugin.ImplSet()
       
   892         Tfd = _plugin_reader.TempVariableDefinition
       
   893         Tsfd = _plugin_reader.TempVariableSequenceDefinition
       
   894         
       
   895         feadefs = [Tfd('TempFeature.String',    'string',   'testing'),
       
   896                    Tfd('TempFeature.Int',       'int',      '500')]
       
   897         impls.add_implementation(self._create_mock_impl(feadefs))
       
   898         
       
   899         feadefs = [Tfd('TempFeature.Real',      'real',     '1.5'),
       
   900                    Tfd('TempFeature.Boolean',   'boolean',  'true')]
       
   901         impls.add_implementation(self._create_mock_impl(feadefs))
       
   902         
       
   903         feadefs = [Tsfd('TempFeature.Seq', [('String',  'string'),
       
   904                                             ('Int',     'int'),
       
   905                                             ('Real',    'real'),
       
   906                                             ('Boolean', 'boolean')])]
       
   907         impls.add_implementation(self._create_mock_impl(feadefs))
       
   908         
       
   909         config = api.Configuration("test.confml")
       
   910         impls.create_temp_features(config)
       
   911         
       
   912         self.assert_contains_feature(config, 'TempFeature.String', 'string', 'testing')
       
   913         self.assert_contains_feature(config, 'TempFeature.Int', 'int', 500)
       
   914         self.assert_contains_feature(config, 'TempFeature.Real', 'real', 1.5)
       
   915         self.assert_contains_feature(config, 'TempFeature.Boolean', 'boolean', True)
       
   916         self.assert_contains_feature(config, 'TempFeature.Seq', 'sequence', [])
       
   917         self.assert_contains_feature(config, 'TempFeature.Seq.String', 'string', [])
       
   918         self.assert_contains_feature(config, 'TempFeature.Seq.Int', 'int', [])
       
   919         self.assert_contains_feature(config, 'TempFeature.Seq.Real', 'real', [])
       
   920         self.assert_contains_feature(config, 'TempFeature.Seq.Boolean', 'boolean', [])
       
   921         
       
   922     
       
   923     def test_create_from_impl_container_with_duplicates(self):
       
   924         impls = plugin.ImplSet()
       
   925         
       
   926         Tfd = _plugin_reader.TempVariableDefinition
       
   927         feadefs = [Tfd('TempFeature.String',    'string',   'testing'),
       
   928                    Tfd('TempFeature.Int',       'int',      '500')]
       
   929         impls.add_implementation(self._create_mock_impl(feadefs))
       
   930         
       
   931         feadefs = [Tfd('TempFeature.Real',      'real',     '1.5'),
       
   932                    Tfd('TempFeature.Boolean',   'boolean',  'true'),
       
   933                    Tfd('TempFeature.Int',       'int',      '500')]
       
   934         impls.add_implementation(self._create_mock_impl(feadefs))
       
   935         
       
   936         config = api.Configuration("test.confml")
       
   937         self.assertRaises(exceptions.AlreadyExists, impls.create_temp_features, config)
       
   938     
       
   939     def test_create_from_impl_container_with_existing(self):
       
   940         impls = plugin.ImplSet()
       
   941         
       
   942         Tfd = _plugin_reader.TempVariableDefinition
       
   943         feadefs = [Tfd('TempFeature.String',    'string',   'testing'),
       
   944                    Tfd('TempFeature.Int',       'int',      '500')]
       
   945         impls.add_implementation(self._create_mock_impl(feadefs))
       
   946         
       
   947         feadefs = [Tfd('TempFeature.Real',      'real',     '1.5'),
       
   948                    Tfd('TempFeature.Boolean',   'boolean',  'true')]
       
   949         impls.add_implementation(self._create_mock_impl(feadefs))
       
   950         
       
   951         config = api.Configuration("test.confml")
       
   952         config.add_feature(api.Feature("Int"), "TempFeature")
       
   953         self.assertRaises(exceptions.AlreadyExists, impls.create_temp_features, config)
       
   954 
       
   955 class TestCommonImplmlDataReader(unittest.TestCase):
       
   956     
       
   957     def _read_data(self, xml_data):
       
   958         etree = utils.etree.fromstring(xml_data)
       
   959         return _plugin_reader.CommonImplmlDataReader.read_data(etree)
       
   960     
       
   961     def test_simple_all_tags(self):
       
   962         XML = """<test xmlns="http://www.symbianfoundation.org/xml/implml/1">
       
   963             <phase name="pre"/>
       
   964             <tag name="target" value="rofs3"/>
       
   965             <tempVariable ref="Temp.Feature" type="string" value="test"/>
       
   966             <tempVariableSequence ref="Temp.SeqFeature">
       
   967                 <tempVariable ref="Sub" type="int"/>
       
   968             </tempVariableSequence>
       
   969             <settingRefsOverride>
       
   970                 <settingRef value="Foo.Bar"/>
       
   971             </settingRefsOverride>
       
   972             <outputRootDir value="output_root"/>
       
   973             <outputSubDir value="output_sub"/>
       
   974         </test>"""
       
   975         actual = self._read_data(XML)
       
   976         
       
   977         expected = _plugin_reader.CommonImplmlData()
       
   978         expected.phase = 'pre'
       
   979         expected.tags = {'target': ['rofs3']}
       
   980         expected.tempvar_defs = [Tfd('Temp.Feature', 'string', 'test'),
       
   981                                       Tsfd('Temp.SeqFeature', [('Sub', 'int')])]
       
   982         expected.setting_refs_override = Sro(['Foo.Bar'])
       
   983         expected.output_root_dir = 'output_root'
       
   984         expected.output_sub_dir = 'output_sub'
       
   985         
       
   986         self.assertEquals(actual, expected)
       
   987     
       
   988     def test_invalid_phases(self):
       
   989         XML = """<test xmlns="http://www.symbianfoundation.org/xml/implml/1">
       
   990             <phase/>
       
   991         </test>"""
       
   992         self.assertRaises(exceptions.ParseError, self._read_data, XML)
       
   993         
       
   994         XML = """<test xmlns="http://www.symbianfoundation.org/xml/implml/1">
       
   995             <phase name="foo"/>
       
   996         </test>"""
       
   997         self.assertRaises(exceptions.ParseError, self._read_data, XML)
       
   998     
       
   999     def test_valid_phases(self):
       
  1000         def run_test(phase ):
       
  1001             xml_data = """<test xmlns="http://www.symbianfoundation.org/xml/implml/1">
       
  1002                 <phase name="%s"/>
       
  1003             </test>""" % phase
       
  1004             actual = self._read_data(xml_data)
       
  1005             expected = _plugin_reader.CommonImplmlData()
       
  1006             expected.phase = phase
       
  1007             self.assertEquals(actual, expected)
       
  1008         
       
  1009         run_test('pre')
       
  1010         run_test('normal')
       
  1011         run_test('post')
       
  1012     
       
  1013     def test_invalid_temp_features(self):
       
  1014         def run_test(element_xml_data):
       
  1015             xml_data = """<test xmlns="http://www.symbianfoundation.org/xml/implml/1">
       
  1016                 %s
       
  1017             </test>""" % element_xml_data
       
  1018             self.assertRaises(exceptions.ParseError, self._read_data, xml_data)
       
  1019         
       
  1020         run_test('<tempVariable/>')
       
  1021         run_test('<tempVariable ref="Foo.Bar" type="foo"/>')
       
  1022         run_test('<tempVariable ref="Foo.Bar" type="foo" value="x"/>')
       
  1023         
       
  1024         run_test('<tempVariableSequence/>')
       
  1025         run_test('<tempVariableSequence ref="Foo.Seq"/>')
       
  1026         run_test('<tempVariableSequence ref="Foo.Seq"><tempVariable/></tempVariableSequence>')
       
  1027         run_test('<tempVariableSequence ref="Foo.Seq"><tempVariable ref="SubFoo" type="foo"/></tempVariableSequence>')
       
  1028     
       
  1029     def test_valid_temp_feature_types(self):
       
  1030         def run_test(type):
       
  1031             # Test for simple features
       
  1032             xml_data = """<test xmlns="http://www.symbianfoundation.org/xml/implml/1">
       
  1033                 <tempVariable ref="Foo.Bar" type="%s"/>
       
  1034             </test>""" % type
       
  1035             actual = self._read_data(xml_data)
       
  1036             expected = _plugin_reader.CommonImplmlData()
       
  1037             expected.tempvar_defs = [Tfd('Foo.Bar', type, '')]
       
  1038             self.assertEquals(actual, expected)
       
  1039             
       
  1040             # Test for sequence features
       
  1041             xml_data = """<test xmlns="http://www.symbianfoundation.org/xml/implml/1">
       
  1042                     <tempVariableSequence ref="Foo.Bar">
       
  1043                         <tempVariable ref="Sub" type="%s"/>
       
  1044                     </tempVariableSequence>
       
  1045                 </test>""" % type
       
  1046             actual = self._read_data(xml_data)
       
  1047             expected = _plugin_reader.CommonImplmlData()
       
  1048             expected.tempvar_defs = [Tsfd('Foo.Bar', [('Sub', type)])]
       
  1049             self.assertEquals(actual, expected)
       
  1050         
       
  1051         run_test('string')
       
  1052         run_test('int')
       
  1053         run_test('real')
       
  1054         run_test('boolean')
       
  1055     
       
  1056     def test_setting_refs_override(self):
       
  1057         def check(xml, expected_refs):
       
  1058             xml = '<test xmlns="http://www.symbianfoundation.org/xml/implml/1">%s</test>' % xml
       
  1059             actual = self._read_data(xml)
       
  1060             expected = _plugin_reader.CommonImplmlData()
       
  1061             expected.setting_refs_override = Sro(expected_refs)
       
  1062             self.assertEquals(actual, expected)
       
  1063         
       
  1064         check('<settingRefsOverride/>', [])
       
  1065         check('<settingRefsOverride refsIrrelevant="false"/>', [])
       
  1066         check('<settingRefsOverride refsIrrelevant="true"/>', None)
       
  1067         check("""
       
  1068                 <settingRefsOverride>
       
  1069                     <settingRef value="Foo.Bar"/>
       
  1070                 </settingRefsOverride>
       
  1071             """,
       
  1072             ['Foo.Bar'])
       
  1073         check("""
       
  1074                 <settingRefsOverride>
       
  1075                     <settingRef value="Foo.Bar"/>
       
  1076                     <settingRef value="Foo.Baz"/>
       
  1077                     <settingRef value="Test.Setting"/>
       
  1078                 </settingRefsOverride>
       
  1079             """,
       
  1080             ['Foo.Bar', 'Foo.Baz', 'Test.Setting'])
       
  1081