text: from pathlib import Path
  
  from tsrc.file_system import Copy
  from tsrc.git import get_current_branch, run_git, run_git_captured
  from tsrc.manifest import Manifest, load_manifest
  from tsrc.test.helpers.git_server import GitServer
  
  
  def read_remote_manifest(workspace_path: Path, git_server: GitServer) -> Manifest:
      run_git(workspace_path, "clone", git_server.manifest_url)
      manifest_yml = workspace_path / "manifest/manifest.yml"
      manifest = load_manifest(manifest_yml)
      return manifest
  
  
  def test_add_repo_can_clone(workspace_path: Path, git_server: GitServer) -> None:
      """Check that repo added to the GitServer can be cloned,
      typically, they should be bare but not empty!
  
      """
      foobar_url = git_server.add_repo("foo/bar")
      run_git(workspace_path, "clone", foobar_url)
      assert (workspace_path / "bar").exists()
  
  
  def test_can_set_remote_head(tmp_path: Path, git_server: GitServer) -> None:
      git_server.add_repo("foo")
      git_server.manifest.change_branch("main")
      git_server.manifest.set_head("main")
  
      run_git(tmp_path, "clone", git_server.manifest_url, "manifest")
  
      assert get_current_branch(tmp_path / "manifest") == "main"
  
  
  def test_can_add_copies(workspace_path: Path, git_server: GitServer) -> None:
      git_server.add_repo("foo")
      git_server.manifest.set_file_copy("foo", "foo.txt", "top.txt")
      manifest = read_remote_manifest(workspace_path, git_server)
      assert manifest.file_system_operations == [Copy("foo", "foo.txt", "top.txt")]
  
  
  def test_add_repo_updates_manifest(workspace_path: Path, git_server: GitServer) -> None:
      git_server.add_repo("foo/bar")
      git_server.add_repo("spam/eggs")
      manifest = read_remote_manifest(workspace_path, git_server)
      repos = manifest.get_repos()
      assert len(repos) == 2
      for repo in repos:
          clone_url = repo.clone_url
          _, out = run_git_captured(workspace_path, "ls-remote", clone_url)
          assert "refs/heads/master" in out
  
  
  def test_multiple_manifest_branches(
      workspace_path: Path, git_server: GitServer
  ) -> None:
      git_server.add_repo("foo")
      git_server.manifest.change_branch("devel")
      git_server.add_repo("bar")
  
      run_git(workspace_path, "clone", git_server.manifest_url)
      manifest_yml = workspace_path / "manifest/manifest.yml"
      manifest = load_manifest(manifest_yml)
      assert len(manifest.get_repos()) == 1
  
      run_git(workspace_path / "manifest", "reset", "--hard", "origin/devel")
      manifest = load_manifest(manifest_yml)
      assert len(manifest.get_repos()) == 2
  
  
  def test_push_to_other_branch(workspace_path: Path, git_server: GitServer) -> None:
      foo_url = git_server.add_repo("foo")
      git_server.push_file("foo", "devel.txt", contents="this is devel\n", branch="devel")
      run_git(workspace_path, "clone", foo_url, "--branch", "devel")
      foo_path = workspace_path / "foo"
      assert (foo_path / "devel.txt").read_text() == "this is devel\n"
  
  
  def test_tag(workspace_path: Path, git_server: GitServer) -> None:
      foo_url = git_server.add_repo("foo")
      git_server.tag("foo", "v0.1", branch="master")
      _, out = run_git_captured(workspace_path, "ls-remote", foo_url)
      assert "refs/tags/v0.1" in out
  
  
  def test_get_sha1(workspace_path: Path, git_server: GitServer) -> None:
      git_server.add_repo("foo")
      actual = git_server.get_sha1("foo")
      assert type(actual) == str
  
  
  def test_default_branch_devel(workspace_path: Path, git_server: GitServer) -> None:
      foo_url = git_server.add_repo("foo", default_branch="devel")
      run_git(workspace_path, "clone", foo_url)
      foo_path = workspace_path / "foo"
      cloned_branch = get_current_branch(foo_path)
      assert cloned_branch == "devel"
  
      manifest = read_remote_manifest(workspace_path, git_server)
      foo_config = manifest.get_repo("foo")
      assert foo_config.branch == "devel"
  
  
  def test_create_submodule(workspace_path: Path, git_server: GitServer) -> None:
      top_url = git_server.add_repo("top")
      sub_url = git_server.add_repo("sub", add_to_manifest=False)
      git_server.add_submodule("top", url=sub_url, path=Path("sub"))
  
      run_git(workspace_path, "clone", top_url, "--recurse-submodules")
  
      top_path = workspace_path / "top"
      sub_readme = top_path / "sub" / "README"
      assert sub_readme.exists()
  
  
  def test_update_submodule(workspace_path: Path, git_server: GitServer) -> None:
      top_url = git_server.add_repo("top")
      sub_url = git_server.add_repo("sub", add_to_manifest=False)
      git_server.add_submodule("top", url=sub_url, path=Path("sub"))
  
      run_git(workspace_path, "clone", top_url, "--recurse-submodules")
  
      git_server.push_file("sub", "new.txt")
      git_server.update_submodule("top", "sub")
  
      top_path = workspace_path / "top"
      run_git(top_path, "fetch")
      run_git(top_path, "reset", "--hard", "origin/master")
      run_git(top_path, "submodule", "update", "--init", "--recursive")
  
      new_sub = top_path / "sub" / "new.txt"
      assert new_sub.exists()
  