michael@0: # This Source Code Form is subject to the terms of the Mozilla Public michael@0: # License, v. 2.0. If a copy of the MPL was not distributed with this michael@0: # file, You can obtain one at http://mozilla.org/MPL/2.0/. michael@0: michael@0: import os.path michael@0: import shutil michael@0: import zipfile michael@0: from StringIO import StringIO michael@0: import simplejson as json michael@0: import unittest michael@0: import cuddlefish michael@0: from cuddlefish import packaging, manifest michael@0: michael@0: def up(path, generations=1): michael@0: for i in range(generations): michael@0: path = os.path.dirname(path) michael@0: return path michael@0: michael@0: ROOT = up(os.path.abspath(__file__), 4) michael@0: def get_linker_files_dir(name): michael@0: return os.path.join(up(os.path.abspath(__file__)), "linker-files", name) michael@0: michael@0: class Basic(unittest.TestCase): michael@0: def get_pkg(self, name): michael@0: d = get_linker_files_dir(name) michael@0: return packaging.get_config_in_dir(d) michael@0: michael@0: def test_deps(self): michael@0: target_cfg = self.get_pkg("one") michael@0: pkg_cfg = packaging.build_config(ROOT, target_cfg) michael@0: deps = packaging.get_deps_for_targets(pkg_cfg, ["one"]) michael@0: self.failUnlessEqual(deps, ["one"]) michael@0: deps = packaging.get_deps_for_targets(pkg_cfg, michael@0: [target_cfg.name, "addon-sdk"]) michael@0: self.failUnlessEqual(deps, ["addon-sdk", "one"]) michael@0: michael@0: def test_manifest(self): michael@0: target_cfg = self.get_pkg("one") michael@0: pkg_cfg = packaging.build_config(ROOT, target_cfg) michael@0: deps = packaging.get_deps_for_targets(pkg_cfg, michael@0: [target_cfg.name, "addon-sdk"]) michael@0: self.failUnlessEqual(deps, ["addon-sdk", "one"]) michael@0: # target_cfg.dependencies is not provided, so we'll search through michael@0: # all known packages (everything in 'deps'). michael@0: m = manifest.build_manifest(target_cfg, pkg_cfg, deps, scan_tests=False) michael@0: m = m.get_harness_options_manifest(False) michael@0: michael@0: def assertReqIs(modname, reqname, path): michael@0: reqs = m["one/%s" % modname]["requirements"] michael@0: self.failUnlessEqual(reqs[reqname], path) michael@0: assertReqIs("main", "sdk/panel", "sdk/panel") michael@0: assertReqIs("main", "two.js", "one/two") michael@0: assertReqIs("main", "./two", "one/two") michael@0: assertReqIs("main", "sdk/tabs.js", "sdk/tabs") michael@0: assertReqIs("main", "./subdir/three", "one/subdir/three") michael@0: assertReqIs("two", "main", "one/main") michael@0: assertReqIs("subdir/three", "../main", "one/main") michael@0: michael@0: target_cfg.dependencies = [] michael@0: # now, because .dependencies *is* provided, we won't search 'deps', michael@0: # so we'll get a link error michael@0: self.assertRaises(manifest.ModuleNotFoundError, michael@0: manifest.build_manifest, michael@0: target_cfg, pkg_cfg, deps, scan_tests=False) michael@0: michael@0: def test_main_in_deps(self): michael@0: target_cfg = self.get_pkg("three") michael@0: package_path = [get_linker_files_dir("three-deps")] michael@0: pkg_cfg = packaging.build_config(ROOT, target_cfg, michael@0: packagepath=package_path) michael@0: deps = packaging.get_deps_for_targets(pkg_cfg, michael@0: [target_cfg.name, "addon-sdk"]) michael@0: self.failUnlessEqual(deps, ["addon-sdk", "three"]) michael@0: m = manifest.build_manifest(target_cfg, pkg_cfg, deps, scan_tests=False) michael@0: m = m.get_harness_options_manifest(False) michael@0: def assertReqIs(modname, reqname, path): michael@0: reqs = m["three/%s" % modname]["requirements"] michael@0: self.failUnlessEqual(reqs[reqname], path) michael@0: assertReqIs("main", "three-a", "three-a/main") michael@0: assertReqIs("main", "three-b", "three-b/main") michael@0: assertReqIs("main", "three-c", "three-c/main") michael@0: michael@0: def test_relative_main_in_top(self): michael@0: target_cfg = self.get_pkg("five") michael@0: package_path = [] michael@0: pkg_cfg = packaging.build_config(ROOT, target_cfg, michael@0: packagepath=package_path) michael@0: deps = packaging.get_deps_for_targets(pkg_cfg, michael@0: [target_cfg.name, "addon-sdk"]) michael@0: self.failUnlessEqual(deps, ["addon-sdk", "five"]) michael@0: # all we care about is that this next call doesn't raise an exception michael@0: m = manifest.build_manifest(target_cfg, pkg_cfg, deps, scan_tests=False) michael@0: m = m.get_harness_options_manifest(False) michael@0: reqs = m["five/main"]["requirements"] michael@0: self.failUnlessEqual(reqs, {}); michael@0: michael@0: def test_unreachable_relative_main_in_top(self): michael@0: target_cfg = self.get_pkg("six") michael@0: package_path = [] michael@0: pkg_cfg = packaging.build_config(ROOT, target_cfg, michael@0: packagepath=package_path) michael@0: deps = packaging.get_deps_for_targets(pkg_cfg, michael@0: [target_cfg.name, "addon-sdk"]) michael@0: self.failUnlessEqual(deps, ["addon-sdk", "six"]) michael@0: self.assertRaises(manifest.UnreachablePrefixError, michael@0: manifest.build_manifest, michael@0: target_cfg, pkg_cfg, deps, scan_tests=False) michael@0: michael@0: def test_unreachable_in_deps(self): michael@0: target_cfg = self.get_pkg("four") michael@0: package_path = [get_linker_files_dir("four-deps")] michael@0: pkg_cfg = packaging.build_config(ROOT, target_cfg, michael@0: packagepath=package_path) michael@0: deps = packaging.get_deps_for_targets(pkg_cfg, michael@0: [target_cfg.name, "addon-sdk"]) michael@0: self.failUnlessEqual(deps, ["addon-sdk", "four"]) michael@0: self.assertRaises(manifest.UnreachablePrefixError, michael@0: manifest.build_manifest, michael@0: target_cfg, pkg_cfg, deps, scan_tests=False) michael@0: michael@0: class Contents(unittest.TestCase): michael@0: michael@0: def run_in_subdir(self, dirname, f, *args, **kwargs): michael@0: top = os.path.abspath(os.getcwd()) michael@0: basedir = os.path.abspath(os.path.join(".test_tmp",self.id(),dirname)) michael@0: if os.path.isdir(basedir): michael@0: assert basedir.startswith(top) michael@0: shutil.rmtree(basedir) michael@0: os.makedirs(basedir) michael@0: try: michael@0: os.chdir(basedir) michael@0: return f(basedir, *args, **kwargs) michael@0: finally: michael@0: os.chdir(top) michael@0: michael@0: def assertIn(self, what, inside_what): michael@0: self.failUnless(what in inside_what, inside_what) michael@0: michael@0: def test_jetpackID(self): michael@0: # this uses "id": "jid7", to which a @jetpack should be appended michael@0: seven = get_linker_files_dir("seven") michael@0: def _test(basedir): michael@0: stdout = StringIO() michael@0: shutil.copytree(seven, "seven") michael@0: os.chdir("seven") michael@0: try: michael@0: # regrettably, run() always finishes with sys.exit() michael@0: cuddlefish.run(["xpi", "--no-strip-xpi"], michael@0: stdout=stdout) michael@0: except SystemExit, e: michael@0: self.failUnlessEqual(e.args[0], 0) michael@0: zf = zipfile.ZipFile("seven.xpi", "r") michael@0: hopts = json.loads(zf.read("harness-options.json")) michael@0: self.failUnlessEqual(hopts["jetpackID"], "jid7@jetpack") michael@0: self.run_in_subdir("x", _test) michael@0: michael@0: def test_jetpackID_suffix(self): michael@0: # this uses "id": "jid1@jetpack", so no suffix should be appended michael@0: one = get_linker_files_dir("one") michael@0: def _test(basedir): michael@0: stdout = StringIO() michael@0: shutil.copytree(one, "one") michael@0: os.chdir("one") michael@0: try: michael@0: # regrettably, run() always finishes with sys.exit() michael@0: cuddlefish.run(["xpi", "--no-strip-xpi"], michael@0: stdout=stdout) michael@0: except SystemExit, e: michael@0: self.failUnlessEqual(e.args[0], 0) michael@0: zf = zipfile.ZipFile("one.xpi", "r") michael@0: hopts = json.loads(zf.read("harness-options.json")) michael@0: self.failUnlessEqual(hopts["jetpackID"], "jid1@jetpack") michael@0: self.run_in_subdir("x", _test) michael@0: michael@0: def test_strip_default(self): michael@0: seven = get_linker_files_dir("seven") michael@0: # now run 'cfx xpi' in that directory, except put the generated .xpi michael@0: # elsewhere michael@0: def _test(basedir): michael@0: stdout = StringIO() michael@0: shutil.copytree(seven, "seven") michael@0: os.chdir("seven") michael@0: try: michael@0: # regrettably, run() always finishes with sys.exit() michael@0: cuddlefish.run(["xpi"], # --strip-xpi is now the default michael@0: stdout=stdout) michael@0: except SystemExit, e: michael@0: self.failUnlessEqual(e.args[0], 0) michael@0: zf = zipfile.ZipFile("seven.xpi", "r") michael@0: names = zf.namelist() michael@0: # problem found in bug 664840 was that an addon michael@0: # without an explicit tests/ directory would copy all files from michael@0: # the package into a bogus JID-PKGNAME-tests/ directory, so check michael@0: # for that michael@0: testfiles = [fn for fn in names if "seven/tests" in fn] michael@0: self.failUnlessEqual([], testfiles) michael@0: # another problem was that data files were being stripped from michael@0: # the XPI. Note that data/ is only supposed to be included if a michael@0: # module that actually gets used does a require("self") . michael@0: self.assertIn("resources/seven/data/text.data", michael@0: names) michael@0: self.failIf("seven/lib/unused.js" michael@0: in names, names) michael@0: self.run_in_subdir("x", _test) michael@0: michael@0: def test_no_strip(self): michael@0: seven = get_linker_files_dir("seven") michael@0: def _test(basedir): michael@0: stdout = StringIO() michael@0: shutil.copytree(seven, "seven") michael@0: os.chdir("seven") michael@0: try: michael@0: # regrettably, run() always finishes with sys.exit() michael@0: cuddlefish.run(["xpi", "--no-strip-xpi"], michael@0: stdout=stdout) michael@0: except SystemExit, e: michael@0: self.failUnlessEqual(e.args[0], 0) michael@0: zf = zipfile.ZipFile("seven.xpi", "r") michael@0: names = zf.namelist() michael@0: self.assertIn("resources/addon-sdk/lib/sdk/loader/cuddlefish.js", names) michael@0: testfiles = [fn for fn in names if "seven/tests" in fn] michael@0: self.failUnlessEqual([], testfiles) michael@0: self.assertIn("resources/seven/data/text.data", michael@0: names) michael@0: self.failUnless("resources/seven/lib/unused.js" michael@0: in names, names) michael@0: self.run_in_subdir("x", _test) michael@0: michael@0: michael@0: if __name__ == '__main__': michael@0: unittest.main()