cmlenz@410: # -*- coding: utf-8 -*- cmlenz@410: # cmlenz@410: # Copyright (C) 2005-2007 Christopher Lenz cmlenz@410: # Copyright (C) 2007 Edgewall Software cmlenz@410: # All rights reserved. cmlenz@410: # cmlenz@410: # This software is licensed as described in the file COPYING, which cmlenz@410: # you should have received as part of this distribution. The terms cmlenz@410: # are also available at http://bitten.edgewall.org/wiki/License. cmlenz@410: cmlenz@410: import shutil cmlenz@410: import tempfile cmlenz@410: import unittest cmlenz@410: cmlenz@439: from trac.core import TracError cmlenz@410: from trac.db import DatabaseManager cmlenz@410: from trac.perm import PermissionCache, PermissionSystem cmlenz@410: from trac.test import EnvironmentStub, Mock cmlenz@439: from trac.util.html import Markup cmlenz@410: from trac.web.href import Href cmlenz@439: from bitten.main import BuildSystem cmlenz@439: from bitten.model import Build, BuildConfig, BuildStep, TargetPlatform, schema cmlenz@439: from bitten.web_ui import BuildConfigController, SourceFileLinkFormatter cmlenz@410: cmlenz@410: cmlenz@410: class BuildConfigControllerTestCase(unittest.TestCase): cmlenz@410: cmlenz@410: def setUp(self): cmlenz@458: self.env = EnvironmentStub(enable=['trac.*', 'bitten.*']) cmlenz@410: self.env.path = tempfile.mkdtemp() cmlenz@410: cmlenz@410: # Create tables cmlenz@410: db = self.env.get_db_cnx() cmlenz@410: cursor = db.cursor() cmlenz@410: connector, _ = DatabaseManager(self.env)._get_connector() cmlenz@410: for table in schema: cmlenz@410: for stmt in connector.to_sql(table): cmlenz@410: cursor.execute(stmt) cmlenz@410: cmlenz@410: # Set up permissions cmlenz@410: self.env.config.set('trac', 'permission_store', cmlenz@410: 'DefaultPermissionStore') cmlenz@410: cmlenz@410: # Hook up a dummy repository cmlenz@410: self.repos = Mock( cmlenz@410: get_node=lambda path, rev=None: Mock(get_history=lambda: [], cmlenz@410: isdir=True), cmlenz@410: normalize_path=lambda path: path, cmlenz@410: sync=lambda: None cmlenz@410: ) cmlenz@410: self.env.get_repository = lambda authname=None: self.repos cmlenz@410: cmlenz@410: def tearDown(self): cmlenz@410: shutil.rmtree(self.env.path) cmlenz@410: cmlenz@410: def test_overview(self): cmlenz@410: PermissionSystem(self.env).grant_permission('joe', 'BUILD_VIEW') cmlenz@410: req = Mock(method='GET', base_path='', cgi_location='', cmlenz@410: path_info='/build', href=Href('/trac'), args={}, chrome={}, wbell@503: perm=PermissionCache(self.env, 'joe')) cmlenz@410: cmlenz@410: module = BuildConfigController(self.env) cmlenz@410: assert module.match_request(req) wbell@503: _, data, _ = module.process_request(req) cmlenz@410: wbell@503: self.assertEqual('overview', data['page_mode']) cmlenz@410: cmlenz@410: def test_view_config(self): cmlenz@410: config = BuildConfig(self.env, name='test', path='trunk') cmlenz@410: config.insert() cmlenz@410: platform = TargetPlatform(self.env, config='test', name='any') cmlenz@410: platform.insert() cmlenz@410: cmlenz@410: PermissionSystem(self.env).grant_permission('joe', 'BUILD_VIEW') cmlenz@410: req = Mock(method='GET', base_path='', cgi_location='', cmlenz@410: path_info='/build/test', href=Href('/trac'), args={}, wbell@503: chrome={}, authname='joe', cmlenz@410: perm=PermissionCache(self.env, 'joe')) cmlenz@410: cmlenz@410: root = Mock(get_entries=lambda: ['foo'], cmlenz@410: get_history=lambda: [('trunk', rev, 'edit') for rev in cmlenz@410: range(123, 111, -1)]) cmlenz@410: self.repos = Mock(get_node=lambda path, rev=None: root, cmlenz@410: sync=lambda: None, normalize_path=lambda path: path) cmlenz@410: cmlenz@410: module = BuildConfigController(self.env) cmlenz@410: assert module.match_request(req) wbell@503: _, data, _ = module.process_request(req) cmlenz@410: wbell@503: self.assertEqual('view_config', data['page_mode']) wbell@503: assert not 'next' in req.chrome['links'] cmlenz@410: cmlenz@410: def test_view_config_paging(self): cmlenz@410: config = BuildConfig(self.env, name='test', path='trunk') cmlenz@410: config.insert() cmlenz@410: platform = TargetPlatform(self.env, config='test', name='any') cmlenz@410: platform.insert() cmlenz@410: cmlenz@410: PermissionSystem(self.env).grant_permission('joe', 'BUILD_VIEW') cmlenz@410: req = Mock(method='GET', base_path='', cgi_location='', cmlenz@410: path_info='/build/test', href=Href('/trac'), args={}, wbell@503: chrome={}, authname='joe', cmlenz@410: perm=PermissionCache(self.env, 'joe')) cmlenz@410: cmlenz@410: root = Mock(get_entries=lambda: ['foo'], cmlenz@410: get_history=lambda: [('trunk', rev, 'edit') for rev in cmlenz@410: range(123, 110, -1)]) cmlenz@410: self.repos = Mock(get_node=lambda path, rev=None: root, cmlenz@410: sync=lambda: None, normalize_path=lambda path: path) cmlenz@410: cmlenz@410: module = BuildConfigController(self.env) cmlenz@410: assert module.match_request(req) wbell@503: _, data, _ = module.process_request(req) cmlenz@410: wbell@503: if req.chrome: cmlenz@410: self.assertEqual('/trac/build/test?page=2', cmlenz@410: req.chrome['links']['next'][0]['href']) cmlenz@410: cmlenz@410: cmlenz@439: class SourceFileLinkFormatterTestCase(unittest.TestCase): cmlenz@439: cmlenz@439: def setUp(self): cmlenz@458: self.env = EnvironmentStub(enable=['trac.*', 'bitten.*']) cmlenz@439: cmlenz@439: # Create tables cmlenz@439: db = self.env.get_db_cnx() cmlenz@439: cursor = db.cursor() cmlenz@439: connector, _ = DatabaseManager(self.env)._get_connector() cmlenz@439: for table in schema: cmlenz@439: for stmt in connector.to_sql(table): cmlenz@439: cursor.execute(stmt) cmlenz@439: cmlenz@439: # Hook up a dummy repository cmlenz@439: self.repos = Mock( cmlenz@439: get_node=lambda path, rev=None: Mock(get_history=lambda: [], cmlenz@439: isdir=True), cmlenz@439: normalize_path=lambda path: path, cmlenz@439: sync=lambda: None cmlenz@439: ) cmlenz@439: self.env.get_repository = lambda authname=None: self.repos cmlenz@439: cmlenz@439: def tearDown(self): cmlenz@439: pass cmlenz@439: cmlenz@439: def test_format_simple_link_in_repos(self): cmlenz@439: BuildConfig(self.env, name='test', path='trunk').insert() cmlenz@439: build = Build(self.env, config='test', platform=1, rev=123, rev_time=42, cmlenz@439: status=Build.SUCCESS, slave='hal') cmlenz@439: build.insert() cmlenz@439: step = BuildStep(self.env, build=build.id, name='foo', cmlenz@439: status=BuildStep.SUCCESS) cmlenz@439: step.insert() cmlenz@439: cmlenz@439: self.repos.get_node = lambda path, rev: (path, rev) cmlenz@439: cmlenz@439: req = Mock(method='GET', href=Href('/trac'), authname='hal') cmlenz@439: comp = SourceFileLinkFormatter(self.env) cmlenz@439: formatter = comp.get_formatter(req, build) cmlenz@439: cmlenz@440: output = formatter(step, None, None, u'error in foo/bar.c: bad') cmlenz@439: self.assertEqual(Markup, type(output)) cmlenz@439: self.assertEqual('error in ' cmlenz@440: 'foo/bar.c: bad', output) cmlenz@439: cmlenz@439: def test_format_simple_link_not_in_repos(self): cmlenz@439: BuildConfig(self.env, name='test', path='trunk').insert() cmlenz@439: build = Build(self.env, config='test', platform=1, rev=123, rev_time=42, cmlenz@439: status=Build.SUCCESS, slave='hal') cmlenz@439: build.insert() cmlenz@439: step = BuildStep(self.env, build=build.id, name='foo', cmlenz@439: status=BuildStep.SUCCESS) cmlenz@439: step.insert() cmlenz@439: cmlenz@439: def _raise(): cmlenz@439: raise TracError('No such node') cmlenz@439: self.repos.get_node = lambda path, rev: _raise() cmlenz@439: cmlenz@439: req = Mock(method='GET', href=Href('/trac'), authname='hal') cmlenz@439: comp = SourceFileLinkFormatter(self.env) cmlenz@439: formatter = comp.get_formatter(req, build) cmlenz@439: cmlenz@440: output = formatter(step, None, None, u'error in foo/bar.c: bad') cmlenz@439: self.assertEqual(Markup, type(output)) cmlenz@440: self.assertEqual('error in foo/bar.c: bad', output) cmlenz@439: cmlenz@439: def test_format_link_in_repos_with_line(self): cmlenz@439: BuildConfig(self.env, name='test', path='trunk').insert() cmlenz@439: build = Build(self.env, config='test', platform=1, rev=123, rev_time=42, cmlenz@439: status=Build.SUCCESS, slave='hal') cmlenz@439: build.insert() cmlenz@439: step = BuildStep(self.env, build=build.id, name='foo', cmlenz@439: status=BuildStep.SUCCESS) cmlenz@439: step.insert() cmlenz@439: cmlenz@439: self.repos.get_node = lambda path, rev: (path, rev) cmlenz@439: cmlenz@439: req = Mock(method='GET', href=Href('/trac'), authname='hal') cmlenz@439: comp = SourceFileLinkFormatter(self.env) cmlenz@439: formatter = comp.get_formatter(req, build) cmlenz@439: cmlenz@440: output = formatter(step, None, None, u'error in foo/bar.c:123: bad') cmlenz@439: self.assertEqual(Markup, type(output)) cmlenz@439: self.assertEqual('error in ' cmlenz@440: 'foo/bar.c:123: bad', output) cmlenz@439: cmlenz@439: def test_format_link_not_in_repos_with_line(self): cmlenz@439: BuildConfig(self.env, name='test', path='trunk').insert() cmlenz@439: build = Build(self.env, config='test', platform=1, rev=123, rev_time=42, cmlenz@439: status=Build.SUCCESS, slave='hal') cmlenz@439: build.insert() cmlenz@439: step = BuildStep(self.env, build=build.id, name='foo', cmlenz@439: status=BuildStep.SUCCESS) cmlenz@439: step.insert() cmlenz@439: cmlenz@439: def _raise(): cmlenz@439: raise TracError('No such node') cmlenz@439: self.repos.get_node = lambda path, rev: _raise() cmlenz@439: cmlenz@439: req = Mock(method='GET', href=Href('/trac'), authname='hal') cmlenz@439: comp = SourceFileLinkFormatter(self.env) cmlenz@439: formatter = comp.get_formatter(req, build) cmlenz@439: cmlenz@440: output = formatter(step, None, None, u'error in foo/bar.c:123: bad') cmlenz@439: self.assertEqual(Markup, type(output)) cmlenz@440: self.assertEqual('error in foo/bar.c:123: bad', output) cmlenz@439: cmlenz@439: cmlenz@410: def suite(): cmlenz@439: suite = unittest.TestSuite() cmlenz@439: suite.addTest(unittest.makeSuite(BuildConfigControllerTestCase, 'test')) cmlenz@439: suite.addTest(unittest.makeSuite(SourceFileLinkFormatterTestCase, 'test')) cmlenz@439: return suite cmlenz@410: cmlenz@410: if __name__ == '__main__': cmlenz@410: unittest.main(defaultTest='suite')