blob: f065eb20aca521db2d6d5a148f9977484035f965 [file] [log] [blame]
#!/usr/bin/python
# Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file
# for details. All rights reserved. Use of this source code is governed by a
# BSD-style license that can be found in the LICENSE file.
"""Tests for dartgenerator."""
import logging.config
import os.path
import re
import shutil
import tempfile
import unittest
import dartgenerator
import database
import idlnode
import idlparser
class DartGeneratorTestCase(unittest.TestCase):
def _InDatabase(self, interface_name):
return os.path.exists(os.path.join(self._database_dir,
'%s.idl' % interface_name))
def _FilePathForDartInterface(self, interface_name):
return os.path.join(self._generator._output_dir, 'src', 'interface',
'%s.dart' % interface_name)
def _InOutput(self, interface_name):
return os.path.exists(
self._FilePathForDartInterface(interface_name))
def _ReadOutputFile(self, interface_name):
self.assertTrue(self._InOutput(interface_name))
file_path = self._FilePathForDartInterface(interface_name)
f = open(file_path, 'r')
content = f.read()
f.close()
return content, file_path
def _AssertOutputSansHeaderEquals(self, interface_name, expected_content):
full_actual_content, file_path = self._ReadOutputFile(interface_name)
# Remove file header comments in // or multiline /* ... */ syntax.
header_re = re.compile(r'^(\s*(//.*|/\*([^*]|\*[^/])*\*/)\s*)*')
actual_content = header_re.sub('', full_actual_content)
if expected_content != actual_content:
msg = """
FILE: %s
EXPECTED:
%s
ACTUAL:
%s
""" % (file_path, expected_content, actual_content)
self.fail(msg)
def _AssertOutputContains(self, interface_name, expected_content):
actual_content, file_path = self._ReadOutputFile(interface_name)
if expected_content not in actual_content:
msg = """
STRING: %s
Was found not in output file: %s
FILE CONTENT:
%s
""" % (expected_content, file_path, actual_content)
self.fail(msg)
def _AssertOutputDoesNotContain(self, interface_name, expected_content):
actual_content, file_path = self._ReadOutputFile(interface_name)
if expected_content in actual_content:
msg = """
STRING: %s
Was found in output file: %s
FILE CONTENT:
%s
""" % (expected_content, file_path, actual_content)
self.fail(msg)
def setUp(self):
self._working_dir = tempfile.mkdtemp()
self._output_dir = os.path.join(self._working_dir, 'output')
self._database_dir = os.path.join(self._working_dir, 'database')
self._auxiliary_dir = os.path.join(self._working_dir, 'auxiliary')
self.assertFalse(os.path.exists(self._database_dir))
# Create database and add one interface.
db = database.Database(self._database_dir)
os.mkdir(self._auxiliary_dir)
self.assertTrue(os.path.exists(self._database_dir))
content = """
module shapes {
@A1 @A2
interface Shape {
@A1 @A2 getter attribute int attr;
@A1 setter attribute int attr;
@A3 boolean op();
const long CONSTANT = 1;
getter attribute DOMString strAttr;
Shape create();
boolean compare(Shape s);
Rectangle createRectangle();
void addLine(lines::Line line);
void someDartType(File file);
void someUnidentifiedType(UnidentifiableType t);
};
};
module rectangles {
@A3
interface Rectangle : @A3 shapes::Shape {
void someTemplatedType(List<Shape> list);
};
};
module lines {
@A1
interface Line : shapes::Shape {
};
};
"""
parser = idlparser.IDLParser(idlparser.FREMONTCUT_SYNTAX)
ast = parser.parse(content)
idl_file = idlnode.IDLFile(ast)
for interface in idl_file.interfaces:
db.AddInterface(interface)
db.Save()
self.assertTrue(self._InDatabase('Shape'))
self.assertTrue(self._InDatabase('Rectangle'))
self.assertTrue(self._InDatabase('Line'))
self._database = database.Database(self._database_dir)
self._generator = dartgenerator.DartGenerator(self._auxiliary_dir,
'../templates',
'test')
def tearDown(self):
shutil.rmtree(self._database_dir)
shutil.rmtree(self._auxiliary_dir)
def testBasicGeneration(self):
# Generate all interfaces:
self._database.Load()
self._generator.Generate(self._database, self._output_dir)
self._generator.Flush()
self.assertTrue(self._InOutput('Shape'))
self.assertTrue(self._InOutput('Rectangle'))
self.assertTrue(self._InOutput('Line'))
def testFilterByAnnotations(self):
self._database.Load()
self._generator.FilterInterfaces(self._database, ['A1', 'A2'], ['A3'])
self._generator.Generate(self._database, self._output_dir)
self._generator.Flush()
# Only interfaces with (@A1 and @A2) or @A3 should be generated:
self.assertTrue(self._InOutput('Shape'))
self.assertTrue(self._InOutput('Rectangle'))
self.assertFalse(self._InOutput('Line'))
# Only members with (@A1 and @A2) or @A3 should be generated:
# TODO(sra): make th
self._AssertOutputSansHeaderEquals('Shape', """interface Shape {
final int attr;
bool op();
}
""")
self._AssertOutputContains('Rectangle',
'interface Rectangle extends shapes::Shape')
def testTypeRenames(self):
self._database.Load()
# Translate 'Shape' to spanish:
self._generator.RenameTypes(self._database, {'Shape': 'Forma'}, False)
self._generator.Generate(self._database, self._output_dir)
self._generator.Flush()
# Validate that all references to Shape have been converted:
self._AssertOutputContains('Forma',
'interface Forma')
self._AssertOutputContains('Forma', 'Forma create();')
self._AssertOutputContains('Forma',
'bool compare(Forma s);')
self._AssertOutputContains('Rectangle',
'interface Rectangle extends Forma')
def testQualifiedDartTypes(self):
self._database.Load()
self._generator.FilterMembersWithUnidentifiedTypes(self._database)
self._generator.Generate(self._database, self._output_dir)
self._generator.Flush()
# Verify primitive conversions are working:
self._AssertOutputContains('Shape',
'static const int CONSTANT = 1')
self._AssertOutputContains('Shape',
'final String strAttr;')
# Verify interface names are converted:
self._AssertOutputContains('Shape',
'interface Shape {')
self._AssertOutputContains('Shape',
' Shape create();')
# TODO(sra): Why is this broken? Output contains qualified type.
#self._AssertOutputContains('Shape',
# 'void addLine(Line line);')
self._AssertOutputContains('Shape',
'Rectangle createRectangle();')
# TODO(sra): Why is this broken? Output contains qualified type.
#self._AssertOutputContains('Rectangle',
# 'interface Rectangle extends Shape')
# Verify dart names are preserved:
# TODO(vsm): Re-enable when package / namespaces are enabled.
# self._AssertOutputContains('shapes', 'Shape',
# 'void someDartType(File file);')
# Verify that unidentified types are not removed:
self._AssertOutputDoesNotContain('Shape',
'someUnidentifiedType')
# Verify template conversion:
# TODO(vsm): Re-enable when core collections are supported.
# self._AssertOutputContains('rectangles', 'Rectangle',
# 'void someTemplatedType(List<Shape> list)')
if __name__ == '__main__':
logging.config.fileConfig('logging.conf')
if __name__ == '__main__':
unittest.main()