def test_gc_fixes_old_user_registrations(self): with self.run_in_subprocess("getpwnam") as (enter, preloads): enter() # Setup the system hook preloads["getpwnam"].side_effect = ( lambda name: self.make_pointer(Passwd(pw_dir=b"/foo"))) # Setup both databases db1 = os.path.join(self.temp_dir, "db1") db2 = os.path.join(self.temp_dir, "db2") db = Click.DB() db.add(db1) db.add(db2) # Prepare common manifest for the packages manifest = {"hooks": {"test-app": {"test": "foo"}}} # Setup versions 1.0 and 3.0 of package in db1 version1 = os.path.join(db1, "test-package", "1.0") with mkfile( os.path.join(version1, ".click", "info", "test-package.manifest")) as f: json.dump(manifest, f) version3 = os.path.join(db1, "test-package", "3.0") with mkfile( os.path.join(version3, ".click", "info", "test-package.manifest")) as f: json.dump(manifest, f) # Setup version 0.2 of package in db2 version2 = os.path.join(db2, "test-package", "2.0") with mkfile( os.path.join(version2, ".click", "info", "test-package.manifest")) as f: json.dump(manifest, f) # Setup the user registration for 2.0 in db2. registrationPath = os.path.join(db2, ".click", "users", "foo", "test-package") os.makedirs(os.path.dirname(registrationPath)) os.symlink(version2, registrationPath) # Run the garbage collection to update the registrations. db.gc() # Verify that the user still has a registration for the package, # and that it's now registered for version 3.0. self.assertTrue(os.path.lexists(registrationPath)) self.assertEqual(version3, os.readlink(registrationPath)) user_db = Click.User.for_user(db, "foo") try: version = user_db.get_version("test-package") self.assertEqual("3.0", version) except: self.fail("No user registration for 'test-package'")
def test_manifests_all(self): with open(os.path.join(self.temp_dir, "a.conf"), "w") as a: print("[Click Database]", file=a) print("root = %s" % os.path.join(self.temp_dir, "a"), file=a) with open(os.path.join(self.temp_dir, "b.conf"), "w") as b: print("[Click Database]", file=b) print("root = %s" % os.path.join(self.temp_dir, "b"), file=b) db = Click.DB() db.read(db_dir=self.temp_dir) self.assertEqual([], json_array_to_python( db.get_manifests(all_versions=True))) self.assertEqual([], json.loads( db.get_manifests_as_string(all_versions=True))) a_pkg1_manifest_path = os.path.join(self.temp_dir, "a", "pkg1", "1.0", ".click", "info", "pkg1.manifest") a_pkg1_manifest_obj = {"name": "pkg1", "version": "1.0"} with mkfile(a_pkg1_manifest_path) as a_pkg1_manifest: json.dump(a_pkg1_manifest_obj, a_pkg1_manifest) os.symlink("1.0", os.path.join(self.temp_dir, "a", "pkg1", "current")) b_pkg1_manifest_path = os.path.join(self.temp_dir, "b", "pkg1", "1.1", ".click", "info", "pkg1.manifest") b_pkg1_manifest_obj = {"name": "pkg1", "version": "1.1"} with mkfile(b_pkg1_manifest_path) as b_pkg1_manifest: json.dump(b_pkg1_manifest_obj, b_pkg1_manifest) os.symlink("1.1", os.path.join(self.temp_dir, "b", "pkg1", "current")) b_pkg2_manifest_path = os.path.join(self.temp_dir, "b", "pkg2", "0.1", ".click", "info", "pkg2.manifest") b_pkg2_manifest_obj = {"name": "pkg2", "version": "0.1"} with mkfile(b_pkg2_manifest_path) as b_pkg2_manifest: json.dump(b_pkg2_manifest_obj, b_pkg2_manifest) os.symlink("0.1", os.path.join(self.temp_dir, "b", "pkg2", "current")) a_pkg1_manifest_obj["_directory"] = os.path.join( self.temp_dir, "a", "pkg1", "1.0") a_pkg1_manifest_obj["_removable"] = 0 b_pkg1_manifest_obj["_directory"] = os.path.join( self.temp_dir, "b", "pkg1", "1.1") b_pkg1_manifest_obj["_removable"] = 1 b_pkg2_manifest_obj["_directory"] = os.path.join( self.temp_dir, "b", "pkg2", "0.1") b_pkg2_manifest_obj["_removable"] = 1 self.assertEqual( [b_pkg1_manifest_obj, b_pkg2_manifest_obj, a_pkg1_manifest_obj], json_array_to_python(db.get_manifests(all_versions=True))) self.assertEqual( [b_pkg1_manifest_obj, b_pkg2_manifest_obj, a_pkg1_manifest_obj], json.loads(db.get_manifests_as_string(all_versions=True)))
def test_build(self): self.use_temp_dir() scratch = os.path.join(self.temp_dir, "scratch") touch(os.path.join(scratch, "bin", "foo")) touch(os.path.join(scratch, ".git", "config")) touch(os.path.join(scratch, "foo.so")) touch(os.path.join(scratch, "build", "meep.goah")) with mkfile(os.path.join(scratch, "manifest.json")) as f: json.dump( { "name": "com.example.test", "version": "1.0", "maintainer": "Foo Bar <*****@*****.**>", "title": "test title", "architecture": "all", "framework": "ubuntu-sdk-13.10", }, f) # build() overrides this back to 0o644 os.fchmod(f.fileno(), 0o600) self.builder.add_file(scratch, "./") self.builder.add_ignore_pattern("build") path = os.path.join(self.temp_dir, "com.example.test_1.0.tar.gz") self.assertEqual(path, self.builder.build(self.temp_dir)) self.assertTrue(os.path.exists(path)) with tarfile.open(path, mode="r:gz") as tar: self.assertCountEqual( [".", "./bin", "./bin/foo", "./manifest.json"], tar.getnames()) self.assertTrue(tar.getmember("./bin/foo").isfile())
def test_manifest(self): manifest_path = os.path.join(self.temp_dir, "a", "1.0", ".click", "info", "a.manifest") manifest_obj = { "name": "a", "version": "1.0", "hooks": { "a-app": {} }, "_should_be_removed": "", } with mkfile(manifest_path) as manifest: json.dump(manifest_obj, manifest) del manifest_obj["_should_be_removed"] manifest_obj["_directory"] = os.path.join(self.temp_dir, "a", "1.0") self.assertEqual( manifest_obj, json_object_to_python(self.db.get_manifest("a", "1.0"))) self.assertRaisesDatabaseError(Click.DatabaseError.DOES_NOT_EXIST, self.db.get_manifest, "a", "1.1") self.assertEqual( manifest_obj, json.loads(self.db.get_manifest_as_string("a", "1.0"))) self.assertRaisesDatabaseError(Click.DatabaseError.DOES_NOT_EXIST, self.db.get_manifest_as_string, "a", "1.1")
def test_audit_matching_md5sums(self): with self.run_in_subprocess("click_get_frameworks_dir") as (enter, preloads): enter() data_path = os.path.join(self.temp_dir, "foo") with mkfile(data_path) as data: print("test", file=data) with open(data_path, "rb") as data: data_md5sum = hashlib.md5(data.read()).hexdigest() path = self.make_fake_package( control_fields={"Click-Version": "0.2"}, manifest={ "name": "test-package", "version": "1.0", "framework": "ubuntu-sdk-13.10", }, control_scripts={ "preinst": static_preinst, "md5sums": "%s foo" % data_md5sum, }, data_files={"foo": data_path}) self._setup_frameworks(preloads, frameworks=["ubuntu-sdk-13.10"]) with mock_quiet_subprocess_call(): installer = ClickInstaller(self.db) self.assertEqual(("test-package", "1.0"), installer.audit(path, slow=True))
def test_manifest_bad(self): manifest_path = os.path.join(self.temp_dir, "a", "1.0", ".click", "info", "a.manifest") with mkfile(manifest_path) as manifest: print("{bad syntax", file=manifest) self.assertRaisesDatabaseError(Click.DatabaseError.BAD_MANIFEST, self.db.get_manifest, "a", "1.0") self.assertRaisesDatabaseError(Click.DatabaseError.BAD_MANIFEST, self.db.get_manifest_as_string, "a", "1.0") manifest_path = os.path.join(self.temp_dir, "a", "1.1", ".click", "info", "a.manifest") with mkfile(manifest_path) as manifest: print("[0]", file=manifest) self.assertRaisesDatabaseError(Click.DatabaseError.BAD_MANIFEST, self.db.get_manifest, "a", "1.1") self.assertRaisesDatabaseError(Click.DatabaseError.BAD_MANIFEST, self.db.get_manifest_as_string, "a", "1.1")
def test_manifest_bad(self): with open(os.path.join(self.temp_dir, "a.conf"), "w") as a: print("[Click Database]", file=a) print("root = %s" % os.path.join(self.temp_dir, "a"), file=a) db = Click.DB() db.read(db_dir=self.temp_dir) manifest_path = os.path.join(self.temp_dir, "a", "pkg", "1.0", ".click", "info", "pkg.manifest") with mkfile(manifest_path) as manifest: print("{bad syntax", file=manifest) self.assertRaisesDatabaseError(Click.DatabaseError.BAD_MANIFEST, db.get_manifest, "pkg", "1.0") self.assertRaisesDatabaseError(Click.DatabaseError.BAD_MANIFEST, db.get_manifest_as_string, "pkg", "1.0") manifest_path = os.path.join(self.temp_dir, "a", "pkg", "1.1", ".click", "info", "pkg.manifest") with mkfile(manifest_path) as manifest: print("[0]", file=manifest) self.assertRaisesDatabaseError(Click.DatabaseError.BAD_MANIFEST, db.get_manifest, "pkg", "1.0") self.assertRaisesDatabaseError(Click.DatabaseError.BAD_MANIFEST, db.get_manifest_as_string, "pkg", "1.0")
def test_manifest_syntax_error(self): self.use_temp_dir() manifest_path = os.path.join(self.temp_dir, "manifest.json") with mkfile(manifest_path) as manifest: # The comma after the "name" entry is intentionally missing. print(dedent("""\ { "name": "com.example.test" "version": "1.0" }"""), file=manifest) self.assertRaises(ClickBuildError, self.builder.read_manifest, manifest_path)
def test_manifest(self): with open(os.path.join(self.temp_dir, "a.conf"), "w") as a: print("[Click Database]", file=a) print("root = %s" % os.path.join(self.temp_dir, "a"), file=a) with open(os.path.join(self.temp_dir, "b.conf"), "w") as b: print("[Click Database]", file=b) print("root = %s" % os.path.join(self.temp_dir, "b"), file=b) db = Click.DB() db.read(db_dir=self.temp_dir) self.assertRaisesDatabaseError(Click.DatabaseError.DOES_NOT_EXIST, db.get_manifest, "pkg", "1.0") self.assertRaisesDatabaseError(Click.DatabaseError.DOES_NOT_EXIST, db.get_manifest_as_string, "pkg", "1.0") a_manifest_path = os.path.join(self.temp_dir, "a", "pkg", "1.0", ".click", "info", "pkg.manifest") a_manifest_obj = {"name": "pkg", "version": "1.0"} with mkfile(a_manifest_path) as a_manifest: json.dump(a_manifest_obj, a_manifest) a_manifest_obj["_directory"] = os.path.join(self.temp_dir, "a", "pkg", "1.0") self.assertEqual(a_manifest_obj, json_object_to_python(db.get_manifest("pkg", "1.0"))) self.assertEqual(a_manifest_obj, json.loads(db.get_manifest_as_string("pkg", "1.0"))) self.assertRaisesDatabaseError(Click.DatabaseError.DOES_NOT_EXIST, db.get_manifest, "pkg", "1.1") self.assertRaisesDatabaseError(Click.DatabaseError.DOES_NOT_EXIST, db.get_manifest_as_string, "pkg", "1.1") b_manifest_path = os.path.join(self.temp_dir, "b", "pkg", "1.1", ".click", "info", "pkg.manifest") b_manifest_obj = {"name": "pkg", "version": "1.1"} with mkfile(b_manifest_path) as b_manifest: json.dump(b_manifest_obj, b_manifest) b_manifest_obj["_directory"] = os.path.join(self.temp_dir, "b", "pkg", "1.1") self.assertEqual(b_manifest_obj, json_object_to_python(db.get_manifest("pkg", "1.1"))) self.assertEqual(b_manifest_obj, json.loads(db.get_manifest_as_string("pkg", "1.1")))
def _setUpMultiDB(self): self.multi_db = Click.DB() self.multi_db.add(os.path.join(self.temp_dir, "custom")) self.multi_db.add(os.path.join(self.temp_dir, "click")) user_dbs = [ os.path.join( self.multi_db.get(i).props.root, ".click", "users", "user") for i in range(self.multi_db.props.size) ] a_1_0 = os.path.join(self.temp_dir, "custom", "a", "1.0") os.makedirs(a_1_0) with mkfile(os.path.join(a_1_0, ".click", "info", "a.manifest")) as m: json.dump({ "name": "a", "version": "1.0", "hooks": { "a-app": {} } }, m) b_2_0 = os.path.join(self.temp_dir, "custom", "b", "2.0") os.makedirs(b_2_0) with mkfile(os.path.join(b_2_0, ".click", "info", "b.manifest")) as m: json.dump({"name": "b", "version": "2.0"}, m) a_1_1 = os.path.join(self.temp_dir, "click", "a", "1.1") os.makedirs(a_1_1) with mkfile(os.path.join(a_1_1, ".click", "info", "a.manifest")) as m: json.dump({"name": "a", "version": "1.1"}, m) c_0_1 = os.path.join(self.temp_dir, "click", "c", "0.1") os.makedirs(c_0_1) with mkfile(os.path.join(c_0_1, ".click", "info", "c.manifest")) as m: json.dump({"name": "c", "version": "0.1"}, m) os.makedirs(user_dbs[0]) os.symlink(a_1_0, os.path.join(user_dbs[0], "a")) os.symlink(b_2_0, os.path.join(user_dbs[0], "b")) os.makedirs(user_dbs[1]) os.symlink(a_1_1, os.path.join(user_dbs[1], "a")) os.symlink(c_0_1, os.path.join(user_dbs[1], "c")) return user_dbs, Click.User.for_user(self.multi_db, "user")
def test_gc(self): with self.run_in_subprocess("click_find_on_path", "g_spawn_sync", "getpwnam") as (enter, preloads): enter() preloads["getpwnam"].side_effect = ( lambda name: self.make_pointer(Passwd(pw_uid=1, pw_gid=1))) os.environ["TEST_QUIET"] = "1" a_path = os.path.join(self.temp_dir, "a", "1.0") a_manifest_path = os.path.join(a_path, ".click", "info", "a.manifest") with mkfile(a_manifest_path) as manifest: json.dump({"hooks": {"a-app": {}}}, manifest) b_path = os.path.join(self.temp_dir, "b", "1.0") b_manifest_path = os.path.join(b_path, ".click", "info", "b.manifest") with mkfile(b_manifest_path) as manifest: json.dump({"hooks": {"b-app": {}}}, manifest) c_path = os.path.join(self.temp_dir, "c", "1.0") c_manifest_path = os.path.join(c_path, ".click", "info", "c.manifest") with mkfile(c_manifest_path) as manifest: json.dump({"hooks": {"c-app": {}}}, manifest) a_user_path = os.path.join(self.temp_dir, ".click", "users", "test-user", "a") os.makedirs(os.path.dirname(a_user_path)) os.symlink(a_path, a_user_path) b_gcinuse_path = os.path.join(self.temp_dir, ".click", "users", "@gcinuse", "b") os.makedirs(os.path.dirname(b_gcinuse_path)) os.symlink(b_path, b_gcinuse_path) preloads["g_spawn_sync"].side_effect = partial( self.g_spawn_sync_side_effect, {b"ubuntu-app-pid": 1 << 8}) preloads["click_find_on_path"].return_value = True self.db.gc() self.assertTrue(os.path.exists(a_path)) self.assertFalse(os.path.exists(b_gcinuse_path)) self.assertFalse(os.path.exists(b_path)) self.assertFalse(os.path.exists(c_path))
def test_any_app_running_no_hooks(self): with self.run_in_subprocess( "click_find_on_path", "g_spawn_sync", ) as (enter, preloads): enter() manifest_path = os.path.join(self.temp_dir, "a", "1.0", ".click", "info", "a.manifest") with mkfile(manifest_path) as manifest: json.dump({}, manifest) preloads["click_find_on_path"].side_effect = ( lambda command: command == b"ubuntu-app-pid") self.assertFalse(self.db.any_app_running("a", "1.0")) self.assertFalse(preloads["g_spawn_sync"].called)
def test_any_app_running_no_app_pid_command(self): with self.run_in_subprocess( "click_find_on_path", "g_spawn_sync", ) as (enter, preloads): enter() manifest_path = os.path.join(self.temp_dir, "a", "1.0", ".click", "info", "a.manifest") with mkfile(manifest_path) as manifest: json.dump({"hooks": {"a-app": {}}}, manifest) preloads["click_find_on_path"].return_value = False preloads["g_spawn_sync"].side_effect = partial( self.g_spawn_sync_side_effect, {b"ubuntu-app-pid": 0}) self.assertFalse(self.db.any_app_running("a", "1.0"))
def test_get_manifests(self): registry = Click.User.for_user(self.db, "user") a_manifest_path = os.path.join(self.temp_dir, "a", "1.0", ".click", "info", "a.manifest") a_manifest_obj = {"name": "a", "version": "1.0"} with mkfile(a_manifest_path) as a_manifest: json.dump(a_manifest_obj, a_manifest) registry.set_version("a", "1.0") b_manifest_path = os.path.join(self.temp_dir, "b", "2.0", ".click", "info", "b.manifest") b_manifest_obj = {"name": "b", "version": "2.0"} with mkfile(b_manifest_path) as b_manifest: json.dump(b_manifest_obj, b_manifest) registry.set_version("b", "2.0") a_manifest_obj["_directory"] = os.path.join(registry.get_overlay_db(), "a") a_manifest_obj["_removable"] = 1 b_manifest_obj["_directory"] = os.path.join(registry.get_overlay_db(), "b") b_manifest_obj["_removable"] = 1 self.assertEqual([a_manifest_obj, b_manifest_obj], json_array_to_python(registry.get_manifests())) self.assertEqual([a_manifest_obj, b_manifest_obj], json.loads(registry.get_manifests_as_string()))
def make_fake_package(self, control_fields=None, manifest=None, control_scripts=None, data_files=None): """Build a fake package with given contents.""" control_fields = {} if control_fields is None else control_fields control_scripts = {} if control_scripts is None else control_scripts data_files = {} if data_files is None else data_files data_dir = os.path.join(self.temp_dir, "fake-package") control_dir = os.path.join(self.temp_dir, "DEBIAN") with mkfile(os.path.join(control_dir, "control")) as control: for key, value in control_fields.items(): print('%s: %s' % (key.title(), value), file=control) print(file=control) if manifest is not None: with mkfile(os.path.join(control_dir, "manifest")) as f: json.dump(manifest, f) print(file=f) for name, contents in control_scripts.items(): with mkfile(os.path.join(control_dir, name)) as script: script.write(contents) Click.ensuredir(data_dir) for name, path in data_files.items(): Click.ensuredir(os.path.dirname(os.path.join(data_dir, name))) if path is None: touch(os.path.join(data_dir, name)) elif os.path.isdir(path): shutil.copytree(path, os.path.join(data_dir, name)) else: shutil.copy2(path, os.path.join(data_dir, name)) package_path = '%s.click' % data_dir ClickBuilder()._pack(self.temp_dir, control_dir, data_dir, package_path) return package_path
def test_get_manifest(self): registry = Click.User.for_user(self.db, "user") manifest_path = os.path.join(self.temp_dir, "a", "1.0", ".click", "info", "a.manifest") manifest_obj = {"name": "a", "version": "1.0"} with mkfile(manifest_path) as manifest: json.dump(manifest_obj, manifest) manifest_obj["_directory"] = os.path.join(registry.get_overlay_db(), "a") manifest_obj["_removable"] = 1 registry.set_version("a", "1.0") self.assertEqual(manifest_obj, json_object_to_python(registry.get_manifest("a"))) self.assertEqual(manifest_obj, json.loads(registry.get_manifest_as_string("a")))
def _make_scratch_dir(self, manifest_override={}): self.use_temp_dir() scratch = os.path.join(self.temp_dir, "scratch") manifest = { "name": "com.example.test", "version": "1.0", "maintainer": "Foo Bar <*****@*****.**>", "title": "test title", "architecture": "all", "framework": "ubuntu-sdk-13.10", } manifest.update(manifest_override) with mkfile(os.path.join(scratch, "manifest.json")) as f: json.dump(manifest, f) self.builder.add_file(scratch, "/") return scratch
def test_maybe_remove_running(self): with self.run_in_subprocess( "click_find_on_path", "g_spawn_sync", ) as (enter, preloads): enter() version_path = os.path.join(self.temp_dir, "a", "1.0") manifest_path = os.path.join(version_path, ".click", "info", "a.manifest") with mkfile(manifest_path) as manifest: json.dump({"hooks": {"a-app": {}}}, manifest) preloads["g_spawn_sync"].side_effect = partial( self.g_spawn_sync_side_effect, {b"ubuntu-app-pid": 0}) preloads["click_find_on_path"].return_value = True self.db.maybe_remove("a", "1.0") self.assertTrue(os.path.exists(version_path))
def test_gc_ignores_non_directory(self): with self.run_in_subprocess("getpwnam") as (enter, preloads): enter() preloads["getpwnam"].side_effect = ( lambda name: self.make_pointer(Passwd(pw_uid=1, pw_gid=1))) a_path = os.path.join(self.temp_dir, "a", "1.0") a_manifest_path = os.path.join(a_path, ".click", "info", "a.manifest") with mkfile(a_manifest_path) as manifest: json.dump({"hooks": {"a-app": {}}}, manifest) a_user_path = os.path.join(self.temp_dir, ".click", "users", "test-user", "a") os.makedirs(os.path.dirname(a_user_path)) os.symlink(a_path, a_user_path) touch(os.path.join(self.temp_dir, "file")) self.db.gc() self.assertTrue(os.path.exists(a_path))
def test_epochless_version(self): self.use_temp_dir() manifest_path = os.path.join(self.temp_dir, "manifest.json") for version, epochless_version in ( ("1.0", "1.0"), ("1:1.2.3", "1.2.3"), ): with mkfile(manifest_path) as manifest: print(dedent("""\ { "name": "com.example.test", "version": "%s", "maintainer": "Foo Bar <*****@*****.**>", "title": "test title", "framework": "ubuntu-sdk-13.10" }""") % version, file=manifest) self.builder.read_manifest(manifest_path) self.assertEqual(epochless_version, self.builder.epochless_version)
def test_read_manifest(self): self.use_temp_dir() manifest_path = os.path.join(self.temp_dir, "manifest.json") with mkfile(manifest_path) as manifest: print(dedent("""\ { "name": "com.example.test", "version": "1.0", "maintainer": "Foo Bar <*****@*****.**>", "title": "test title", "framework": "ubuntu-sdk-13.10" }"""), file=manifest) self.builder.read_manifest(manifest_path) self.assertEqual("com.example.test", self.builder.name) self.assertEqual("1.0", self.builder.version) self.assertEqual("Foo Bar <*****@*****.**>", self.builder.maintainer) self.assertEqual("test title", self.builder.title) self.assertEqual("all", self.builder.architecture)
def test_maybe_remove_not_running(self): with self.run_in_subprocess( "click_find_on_path", "g_spawn_sync", ) as (enter, preloads): enter() os.environ["TEST_QUIET"] = "1" version_path = os.path.join(self.temp_dir, "a", "1.0") manifest_path = os.path.join(version_path, ".click", "info", "a.manifest") with mkfile(manifest_path) as manifest: json.dump({"hooks": {"a-app": {}}}, manifest) current_path = os.path.join(self.temp_dir, "a", "current") os.symlink("1.0", current_path) preloads["g_spawn_sync"].side_effect = partial( self.g_spawn_sync_side_effect, {b"ubuntu-app-pid": 1 << 8}) preloads["click_find_on_path"].return_value = True self.db.maybe_remove("a", "1.0") self.assertFalse(os.path.exists(os.path.join(self.temp_dir, "a")))
def test_any_app_running_upstart_app_pid(self): with self.run_in_subprocess( "click_find_on_path", "g_spawn_sync", ) as (enter, preloads): enter() manifest_path = os.path.join(self.temp_dir, "a", "1.0", ".click", "info", "a.manifest") with mkfile(manifest_path) as manifest: json.dump({"hooks": {"a-app": {}}}, manifest) preloads["click_find_on_path"].side_effect = ( lambda command: command == b"upstart-app-pid") preloads["g_spawn_sync"].side_effect = partial( self.g_spawn_sync_side_effect, {b"upstart-app-pid": 0}) self.assertTrue(self.db.any_app_running("a", "1.0")) self.assertEqual([[b"upstart-app-pid", b"a_a-app_1.0"]], self.spawn_calls) preloads["g_spawn_sync"].side_effect = partial( self.g_spawn_sync_side_effect, {b"upstart-app-pid": 1 << 8}) self.assertFalse(self.db.any_app_running("a", "1.0"))
def test_build(self): self.use_temp_dir() scratch = os.path.join(self.temp_dir, "scratch") with mkfile(os.path.join(scratch, "bin", "foo")) as f: f.write("test /bin/foo\n") os.symlink("foo", os.path.join(scratch, "bin", "bar")) touch(os.path.join(scratch, ".git", "config")) with mkfile(os.path.join(scratch, "toplevel")) as f: f.write("test /toplevel\n") os.symlink("file-does-not-exist", os.path.join(scratch, "broken-symlink")) with mkfile(os.path.join(scratch, "manifest.json")) as f: json.dump( { "name": "com.example.test", "version": "1.0", "maintainer": "Foo Bar <*****@*****.**>", "title": "test title", "architecture": "all", "framework": "ubuntu-sdk-13.10", }, f) # build() overrides this back to 0o644 os.fchmod(f.fileno(), 0o600) self.builder.add_file(scratch, "/") path = os.path.join(self.temp_dir, "com.example.test_1.0_all.click") self.assertEqual(path, self.builder.build(self.temp_dir)) self.assertTrue(os.path.exists(path)) for key, value in ( ("Package", "com.example.test"), ("Version", "1.0"), ("Click-Version", "0.4"), ("Architecture", "all"), ("Maintainer", "Foo Bar <*****@*****.**>"), ("Description", "test title"), ): self.assertEqual(value, self.extract_field(path, key)) self.assertNotEqual("", self.extract_field(path, "Installed-Size")) control_path = os.path.join(self.temp_dir, "control") subprocess.check_call(["dpkg-deb", "-e", path, control_path]) manifest_path = os.path.join(control_path, "manifest") self.assertEqual(0o644, stat.S_IMODE(os.stat(manifest_path).st_mode)) with open(os.path.join(scratch, "manifest.json")) as source, \ open(manifest_path) as target: source_json = json.load(source) target_json = json.load(target) self.assertNotEqual("", target_json["installed-size"]) del target_json["installed-size"] self.assertEqual(source_json, target_json) with open(os.path.join(control_path, "md5sums")) as md5sums: self.assertRegex( md5sums.read(), r"^" r"eb774c3ead632b397d6450d1df25e001 bin/bar\n" r"eb774c3ead632b397d6450d1df25e001 bin/foo\n" r"49327ce6306df8a87522456b14a179e0 toplevel\n" r"$") with open(os.path.join(control_path, "preinst")) as preinst: self.assertEqual(static_preinst, preinst.read()) contents = subprocess.check_output(["dpkg-deb", "-c", path], universal_newlines=True) self.assertRegex(contents, r"^drwxr-xr-x root/root 0 .* \./\n") self.assertRegex( contents, "\nlrwxrwxrwx root/root 0 .* \./bin/bar -> foo\n") self.assertRegex(contents, "\n-rw-r--r-- root/root 14 .* \./bin/foo\n") self.assertRegex(contents, "\n-rw-r--r-- root/root 15 .* \./toplevel\n") extract_path = os.path.join(self.temp_dir, "extract") subprocess.check_call(["dpkg-deb", "-x", path, extract_path]) for rel_path in ( os.path.join("bin", "foo"), "toplevel", ): with open(os.path.join(scratch, rel_path)) as source, \ open(os.path.join(extract_path, rel_path)) as target: self.assertEqual(source.read(), target.read()) self.assertTrue( os.path.islink(os.path.join(extract_path, "bin", "bar"))) self.assertEqual("foo", os.readlink(os.path.join(extract_path, "bin", "bar")))