Exemple #1
0
def test_pathlib(temp_folder):
    subfolder = Path("subfolder")
    assert runez.to_path(subfolder) is subfolder
    assert not subfolder.is_dir()
    runez.ensure_folder(subfolder)
    assert subfolder.is_dir()

    with pytest.raises(Exception):
        runez.to_path("foo bar", no_spaces=Exception)

    with runez.CurrentFolder(subfolder, anchor=True):
        path = Path("foo")
        assert runez.short(path) == "foo"
        assert runez.short(path.absolute()) == "foo"

        assert runez.resolved_path(path)
        assert runez.parent_folder(path) == os.path.join(temp_folder, "subfolder")
        assert runez.touch(path) == 1
        assert runez.copy(path, Path("bar")) == 1
        assert runez.copy(Path("bar"), Path("baz")) == 1

        foo_json = Path("foo.json")
        runez.write(path, '{"a": "b"}')
        runez.symlink(path, foo_json)
        assert runez.read_json(foo_json) == {"a": "b"}
        assert list(runez.readlines(foo_json)) == ['{"a": "b"}']

        assert runez.basename(foo_json.absolute()) == "foo"
Exemple #2
0
def setup_audit_log(cfg=CFG):
    """Setup audit.log log file handler"""
    if runez.DRYRUN:
        if not runez.log.console_handler or runez.log.spec.console_level > logging.INFO:
            runez.log.setup(console_level=logging.INFO)

        return

    if not runez.log.file_handler:
        if runez.color.is_coloring():
            runez.log.progress.start(message_color=runez.dim,
                                     spinner_color=runez.bold)

        log_path = cfg.meta.full_path("audit.log")
        runez.log.trace("Logging to %s", log_path)
        runez.ensure_folder(cfg.meta.path)
        runez.log.setup(
            file_format=
            "%(asctime)s %(timezone)s [%(process)s] %(context)s%(levelname)s - %(message)s",
            file_level=logging.DEBUG,
            file_location=log_path,
            greetings=":: {argv}",
            rotate="size:500k",
            rotate_count=1,
        )
Exemple #3
0
    def finalize(self):
        """Run sanity check and/or symlinks, and return a report"""
        with runez.Anchored(self.folder, CFG.base.path):
            runez.ensure_folder(CFG.base.path, clean=True, logger=False)
            dist_folder = runez.resolved_path(self.dist)
            exes = PACKAGER.package(self.pspec, CFG.base.path, dist_folder,
                                    self.requirements, self.compile)
            if exes:
                report = PrettyTable(
                    ["Packaged executable", self.sanity_check],
                    border=self.border)
                report.header.style = "bold"
                if not self.sanity_check:
                    report.header[1].shown = False

                for exe in exes:
                    exe_info = self.validate_sanity_check(
                        exe, self.sanity_check)
                    report.add_row(runez.quoted(exe), exe_info)
                    if self.symlink and exe:
                        self.symlink.apply(exe)

                if not self.compile and not runez.DRYRUN:
                    clean_compiled_artifacts(dist_folder)

                return report
Exemple #4
0
    def effective_package(self, template):
        """
        :param str template: Template describing how to name delivered files, example: {meta}/{name}-{version}
        """
        folder = os.path.join(
            self.dist_folder,
            template.format(name=self.name, version=self.version))
        runez.delete(folder, logger=None)
        runez.ensure_folder(folder, folder=True, logger=None)
        vrun(self.name, "virtualenv", folder)

        bin_folder = os.path.join(folder, "bin")
        pip = os.path.join(bin_folder, "pip")
        spec = self.source_folder if self.source_folder else "%s==%s" % (
            self.name, self.version)
        runez.run(pip, "install", "-i", system.SETTINGS.index, "-f",
                  self.build_folder, spec)

        if self.relocatable:
            python = system.target_python(package_name=self.name).executable
            vrun(self.name, "virtualenv", "--relocatable",
                 "--python=%s" % python, folder)

        self.packaged.append(folder)
        self.executables = [
            os.path.join(bin_folder, name) for name in self.entry_points
        ]
Exemple #5
0
    def pex_build(self, name, destination):
        """
        Run pex build

        :param str name: Name of entry point
        :param str destination: Path to file where to produce pex
        :return str: None if successful, error message otherwise
        """
        runez.ensure_folder(self.build_folder, folder=True)
        runez.delete(destination)

        args = ["--cache-dir", self.build_folder, "--repo", self.build_folder]
        args.extend([
            "-c%s" % name,
            "-o%s" % destination,
            "%s==%s" % (self.name, self.version)
        ])

        python = system.target_python(package_name=self.name)
        shebang = python.shebang(
            universal=system.is_universal(self.build_folder))
        if shebang:
            args.append("--python-shebang")
            args.append(shebang)

        vrun(self.name,
             self.specced_command(),
             *args,
             path_env=C_COMPILATION_HELP)
Exemple #6
0
    def package(self):
        """Package pypi module with 'self.name'"""
        if not self.version and not self.source_folder:
            return runez.abort(
                "Need either source_folder or version in order to package",
                fatal=(True, []))

        if not self.version:
            setup_py = os.path.join(self.source_folder, "setup.py")
            if not os.path.isfile(setup_py):
                return runez.abort("No setup.py in %s",
                                   short(self.source_folder),
                                   fatal=(True, []))
            self.version = system.run_python(setup_py,
                                             "--version",
                                             dryrun=False,
                                             fatal=False,
                                             package_name=self.name)
            if not self.version:
                return runez.abort("Could not determine version from %s",
                                   short(setup_py),
                                   fatal=(True, []))

        self.pip_wheel()

        self.refresh_entry_points()
        runez.ensure_folder(self.dist_folder, folder=True)
        template = "{name}" if self.source_folder else "{name}-{version}"
        self.packaged = []
        self.effective_package(template)
Exemple #7
0
def test_base(cli, monkeypatch):
    monkeypatch.setenv("__PYVENV_LAUNCHER__", "foo")
    folder = os.getcwd()
    cli.expect_success("-n base", folder)
    cli.expect_success("-n base audit", dot_meta("audit.log", parent=folder))
    cli.expect_success("-n base cache", dot_meta(".cache", parent=folder))
    cli.expect_success("-n base meta", dot_meta(parent=folder))
    cli.expect_failure("-n base foo", "Unknown base folder reference")

    cli.run("-n base bootstrap-own-wrapper")
    assert cli.succeeded
    assert "Would wrap pickley" in cli.logged

    monkeypatch.setenv("PICKLEY_ROOT", "temp-base")
    with pytest.raises(SystemExit):  # Env var points to a non-existing folder
        find_base()

    runez.ensure_folder("temp-base")
    assert find_base() == runez.resolved_path("temp-base")

    assert sys.prefix in get_program_path("foo/bar.py")

    monkeypatch.delenv("PICKLEY_ROOT")
    monkeypatch.setattr(PickleyConfig, "program_path",
                        "/foo/.venv/bin/pickley")
    assert find_base() == "/foo/.venv/root"

    monkeypatch.setattr(PickleyConfig, "program_path",
                        dot_meta("pickley-0.0.0/bin/pickley", parent="foo"))
    assert find_base() == "foo"

    monkeypatch.setattr(PickleyConfig, "program_path", "foo/bar")
    assert find_base() == "foo"
Exemple #8
0
def clean_folder(folder):
    """Clean contents of 'folder', if any"""
    if os.path.isdir(folder):
        for fname in os.listdir(folder):
            runez.delete(os.path.join(folder, fname))

    else:
        runez.ensure_folder(folder, folder=True)
Exemple #9
0
def git_clone(pspec):
    basename = runez.basename(pspec.original)
    pspec.folder = pspec.cfg.cache.full_path("checkout", basename)
    runez.ensure_folder(pspec.folder, clean=True, dryrun=False)
    logger = LOG.info if runez.DRYRUN else runez.UNSET
    runez.run("git",
              "clone",
              pspec.original,
              pspec.folder,
              dryrun=False,
              logger=logger)
Exemple #10
0
    def pip_wheel(self):
        """
        Run pip wheel

        :return str: None if successful, error message otherwise
        """
        runez.ensure_folder(self.build_folder, folder=True)
        return vrun(
            self.name, "pip", "wheel", "-i", system.SETTINGS.index,
            "--cache-dir", self.build_folder, "--wheel-dir", self.build_folder,
            self.source_folder if self.source_folder else "%s==%s" %
            (self.name, self.version))
Exemple #11
0
    def package(pspec, build_folder, dist_folder, requirements, run_compile_all):
        runez.ensure_folder(dist_folder, clean=True, logger=False)
        venv = PythonVenv(pspec, folder=dist_folder)
        venv.pip_install(*requirements)
        if run_compile_all:
            venv.run_python("-mcompileall", dist_folder)

        contents = PackageContents(venv, pspec)
        if contents.entry_points:
            result = []
            for name in contents.entry_points:
                result.append(venv.bin_path(name))

            return result
Exemple #12
0
def test_locations(temp_log):
    runez.log.setup(locations=None)
    assert runez.log.file_handler is None

    # Verify that a non-writeable folder is not used
    runez.ensure_folder("foo/bar", logger=None)
    os.chmod("foo/bar", 0o400)
    runez.log.setup(locations=["foo/bar"])
    os.chmod("foo/bar", 0o700)
    assert runez.log.file_handler is None

    runez.log.setup(locations=["{dev}/test-location.log"])
    assert runez.log.file_handler

    runez.log.setup(locations=["{project}/.venv/test-location.log"])
    assert runez.log.file_handler
Exemple #13
0
def my_group(debug):
    # By default, --config value is NOT exposed, the global runez.config.CONFIG is altered
    runez.system.AbortException = SystemExit
    runez.log.setup(
        debug=debug,
        console_format="%(levelname)s %(message)s",
        console_level=logging.INFO,
        locations=None,
        greetings=":: {argv}",
    )
    config = runez.config.CONFIG
    cd = config.get("g.cd")
    if cd:
        logging.info("Changed folder to %s" % runez.short(cd))
        runez.ensure_folder(cd)
        os.chdir(cd)

    assert len(config.providers) == 1
    assert "--config: " in config.overview()
    assert config.provider_by_name("--config") is not None
Exemple #14
0
    def package(pspec, build_folder, dist_folder, requirements, run_compile_all):
        runez.ensure_folder(build_folder, clean=True)
        if pspec.python.major < 3:  # pragma: no cover
            abort("Packaging with pex is not supported any more with python2")

        pex_root = os.path.join(build_folder, "pex-root")
        tmp = os.path.join(build_folder, "pex-tmp")
        wheels = os.path.join(build_folder, "wheels")
        runez.ensure_folder(tmp, logger=False)
        runez.ensure_folder(wheels, logger=False)
        pex_venv = PythonVenv(pspec, folder=os.path.join(build_folder, "pex-venv"))
        pex_venv.pip_install("pex==2.1.75", *requirements)
        pex_venv.pip_wheel("--cache-dir", wheels, "--wheel-dir", wheels, *requirements)
        contents = PackageContents(pex_venv, pspec)
        if contents.entry_points:
            wheel_path = pspec.find_wheel(wheels)
            result = []
            for name in contents.entry_points:
                target = os.path.join(dist_folder, name)
                runez.delete(target)
                pex_venv.run_python(
                    "-mpex", "-o%s" % target, "--pex-root", pex_root, "--tmpdir", tmp,
                    "--no-index", "--find-links", wheels,  # resolver options
                    None if run_compile_all else "--no-compile",  # output options
                    "-c%s" % name,  # entry point options
                    "--python-shebang", "/usr/bin/env python%s" % pspec.python.major,
                    wheel_path,
                )
                result.append(target)

            return result
Exemple #15
0
def test_file_operations(temp_folder):
    runez.symlink("foo", "dangling-symlink", must_exist=False)
    runez.move("dangling-symlink", "dangling-symlink2")
    assert os.path.islink("dangling-symlink2")

    runez.write("README.md", "hello")
    runez.copy("README.md", "sample1/README.md")
    runez.copy("sample1", "sample2")
    runez.move("sample1/README.md", "sample1/foo")

    # overwrite=None "merges" dir contents
    runez.copy("sample1", "sample2", overwrite=None)
    assert dir_contents("sample2") == {"README.md": ["hello"], "foo": ["hello"]}

    # overwrite=True replaces dir
    runez.copy("sample1", "sample2", overwrite=True)
    assert dir_contents("sample2") == {"foo": ["hello"]}

    # overwrite=None, source is a dir, existing destination file gets replaced by source directory
    runez.copy("sample1", "sample2/foo", overwrite=None)
    assert dir_contents("sample2") == {"foo": {"foo": ["hello"]}}

    with runez.CaptureOutput(dryrun=True) as logged:
        assert runez.ensure_folder("some-folder", fatal=False) == 1
        assert "Would create" in logged.pop()

        assert runez.touch("some-file", logger=logging.debug) == 1
        assert "Would touch some-file" in logged.pop()

        assert runez.copy("some-file", "bar") == 1
        assert "Would copy some-file -> bar" in logged.pop()

        assert runez.move("some-file", "bar") == 1
        assert "Would move some-file -> bar" in logged.pop()

        assert runez.symlink("some-file", "bar") == 1
        assert "Would symlink some-file <- bar" in logged.pop()

        assert runez.delete(temp_folder) == 1
        assert "Would delete" in logged.pop()

        assert runez.copy("some-folder/bar", "some-folder", fatal=False) == -1
        assert "source contained in destination" in logged.pop()

        assert runez.move("some-folder/bar/baz", "some-folder", fatal=False) == -1
        assert "source contained in destination" in logged.pop()

        assert runez.symlink("some-folder/bar/baz", "some-folder", fatal=False) == -1
        assert "source contained in destination" in logged.pop()
Exemple #16
0
    def __init__(self, pspec=None, folder=None, python=None, index=None, cfg=None, create=True):
        """
        Args:
            pspec (pickley.PackageSpec | None): Package spec to install
            folder (str | None): Target folder (default: pspec.install_path)
            python (pickley.env.PythonInstallation): Python to use (default: pspec.python)
            index (str | None): Optional custom pypi index to use (default: pspec.index)
            cfg (pickley.PickleyConfig | None): Config to use
            create (bool): Create venv if True
        """
        if folder is None and pspec:
            folder = pspec.install_path

        if not python and pspec:
            python = pspec.python

        if not index and pspec:
            index = pspec.index

        self.folder = folder
        self.index = index
        self.py_path = os.path.join(folder, "bin", "python3")
        self.pip_path = os.path.join(folder, "bin", "pip3")
        if create and folder:
            cfg = cfg or pspec.cfg
            python = python or cfg.find_python(pspec=pspec)
            runez.ensure_folder(folder, clean=True, logger=False)
            if python.version > "3.7":
                runez.run(python.executable, "-mvenv", folder)

            else:
                import virtualenv.__main__

                runez.run(sys.executable, virtualenv.__main__.__file__, "-p", python.executable, folder)

            self.run_pip("install", "-U", "pip")
Exemple #17
0
def test_current_folder(temp_folder):
    sample = os.path.join(temp_folder, "sample")
    assert os.getcwd() == temp_folder
    assert runez.ensure_folder("sample") == 1

    with runez.CurrentFolder("sample", anchor=False):
        cwd = os.getcwd()
        assert cwd == sample
        assert runez.short(os.path.join(cwd, "some-file")) == os.path.join(
            "sample", "some-file")

    with runez.CurrentFolder("sample", anchor=True):
        cwd = os.getcwd()
        sample = os.path.join(temp_folder, "sample")
        assert cwd == sample
        assert runez.short(os.path.join(cwd, "some-file")) == "some-file"

    assert os.getcwd() == temp_folder
Exemple #18
0
def test_bogus_install(cli):
    cli.expect_success("settings -d", "base: %s" % short(cli.context))
    cli.expect_success("check", "No packages installed")
    cli.expect_success("list", "No packages installed")

    cli.expect_failure("-b foo/bar settings",
                       "Can't use foo/bar as base: folder does not exist")

    cli.expect_failure("--dryrun check -- -bogus",
                       "not a valid pypi package name")
    cli.expect_failure("--dryrun check this-package-does-not-exist",
                       "can't determine latest version")

    cli.expect_failure("--dryrun --delivery foo install tox",
                       "invalid choice: foo")

    cli.expect_failure("--dryrun uninstall --force /dev/null",
                       "is not a valid pypi package name")
    cli.expect_success(
        "--dryrun uninstall --force -- this-package-does-not-exist ",
        "Nothing to uninstall")

    runez.touch("foo")
    assert os.path.exists("foo")
    cli.expect_failure("uninstall foo", "foo was not installed with pickley")
    cli.expect_success("uninstall foo --force", "Uninstalled foo")
    assert not os.path.exists("foo")
    assert runez.ensure_folder("foo", folder=True) == 1
    cli.expect_failure("uninstall foo --force",
                       "Can't automatically uninstall")

    cli.expect_failure("auto-upgrade foo", "not currently installed")

    cli.expect_failure("package foo/bar", "Folder", "does not exist")
    cli.expect_failure(["package", cli.context], "No setup.py")
    runez.touch(os.path.join(cli.context, "setup.py"))
    cli.expect_failure(["package", cli.context],
                       "Could not determine package name")

    cli.expect_success("check", "No packages installed")
    cli.expect_success("list", "No packages installed")
    cli.expect_success("settings -d", "base: %s" % short(cli.context))
Exemple #19
0
def test_install(cli):
    tox = system.SETTINGS.base.full_path("tox")
    p = PACKAGERS.resolved("tox")
    p.refresh_desired()
    tox_version = p.desired.version
    assert not os.path.exists(tox)
    assert runez.first_line(tox) is None

    cli.expect_success("--dryrun -b{base} --delivery wrap install tox",
                       "Would wrap",
                       "Would install tox",
                       base=cli.context)
    cli.expect_success("--dryrun -b{base} --delivery symlink install tox",
                       "Would symlink",
                       "Would install tox",
                       base=cli.context)
    cli.expect_failure("--dryrun -b{base} --delivery foo install tox",
                       "invalid choice: foo",
                       base=cli.context)

    cli.expect_success("--dryrun uninstall /dev/null --force",
                       "Nothing to uninstall")

    runez.touch("foo")
    assert os.path.exists("foo")
    cli.expect_failure("uninstall foo", "foo was not installed with pickley")
    cli.expect_success("uninstall foo --force", "Uninstalled foo")

    assert not os.path.exists("foo")
    assert runez.ensure_folder("foo", folder=True) == 1
    cli.expect_failure("uninstall foo --force",
                       "Can't automatically uninstall")

    cli.expect_failure("-b{base} check tox foo/bar",
                       "is not installed",
                       "can't determine latest version",
                       base=cli.context)
    cli.expect_failure("-b{base} install six",
                       "'six' is not a CLI",
                       base=cli.context)

    # Install tox, but add a few files + a bogus previous entry point to test cleanup
    wep1 = system.SETTINGS.base.full_path("tox-old-entrypoint1")
    tep10 = system.SETTINGS.meta.full_path("tox", "tox-old-entrypoint1-1.0")
    tep11 = system.SETTINGS.meta.full_path("tox", "tox-old-entrypoint1-1.1")
    t00 = system.SETTINGS.meta.full_path("tox", "tox-0.0.0")
    tfoo = system.SETTINGS.meta.full_path("tox", "tox-foo")
    runez.touch(wep1)
    runez.touch(tep10)
    runez.touch(tep11)
    runez.touch(t00)
    runez.touch(tfoo)
    eppath = system.SETTINGS.meta.full_path("tox", ".entry-points.json")
    runez.write(eppath, '["tox-old-entrypoint1", "tox-old-entrypoint2"]\n')
    cli.expect_success("-b{base} --delivery wrap install tox",
                       "Installed tox",
                       base=cli.context)

    # Old entry point removed immediately
    assert not os.path.exists(wep1)

    # Only 1 cleaned up immediately (latest + 1 kept)
    assert not os.path.exists(tep10)
    assert os.path.exists(tep11)
    assert not os.path.exists(t00)
    assert os.path.exists(tfoo)

    assert runez.is_executable(tox)
    output = run_program(tox, "--version")
    assert "tox" in output
    assert tox_version in output

    cli.expect_success("-b{base} auto-upgrade tox",
                       "Skipping auto-upgrade",
                       base=cli.context)
    runez.delete(system.SETTINGS.meta.full_path("tox", ".ping"))
    cli.expect_success("-b{base} auto-upgrade tox",
                       "already installed",
                       base=cli.context)

    version = output.partition(" ")[0]
    cli.expect_success("copy .pickley/tox/tox-%s tox-copy" % version, "Copied")
    cli.expect_success("move tox-copy tox-relocated", "Moved")

    # Verify that older versions and removed entry-points do get cleaned up
    runez.save_json({"install_timeout": 0}, "custom-timeout.json")
    cli.expect_success("-b{base} -ccustom-timeout.json install tox",
                       "already installed",
                       base=cli.context)

    # All cleaned up when enough time went by
    assert not os.path.exists(tep10)
    assert not os.path.exists(tep11)
    assert not os.path.exists(t00)
    assert not os.path.exists(tfoo)

    cli.expect_success("-b{base} check",
                       "tox",
                       "is installed",
                       base=cli.context)
    cli.expect_success(
        "-b{base} check --verbose",
        "tox",
        "is installed (as %s wrap, channel: " % system.VENV_PACKAGER,
        base=cli.context,
    )

    p = PACKAGERS.get(system.VENV_PACKAGER)("tox")
    p.refresh_latest()
    p.latest.version = "10000.0"
    p.latest.save()
    cli.expect_failure("-b{base} check",
                       "tox",
                       "can be upgraded to 10000.0",
                       base=cli.context)

    cli.expect_success("-b{base} -ppex install twine",
                       "Installed twine",
                       base=cli.context)

    cli.expect_success("-b{base} list", "tox", "twine", base=cli.context)
    cli.expect_success("-b{base} list --verbose",
                       "tox",
                       "twine",
                       base=cli.context)

    tmp = os.path.realpath(cli.context)
    assert find_uninstaller(os.path.join(tmp, "tox"))
    assert find_uninstaller(os.path.join(tmp, "twine"))

    cli.expect_success("-b{base} uninstall twine",
                       "Uninstalled twine",
                       base=cli.context)

    runez.delete(p.current._path)
    runez.touch(p.current._path)
    cli.expect_failure("-b{base} check",
                       "tox",
                       "Couldn't read",
                       "is not installed",
                       base=cli.context)

    cli.expect_success("-b{base} uninstall tox",
                       "Uninstalled tox",
                       "entry points",
                       base=cli.context)
Exemple #20
0
def test_bootstrap(cli, monkeypatch):
    with patch("pickley.bstrap.which", side_effect=mocked_which):
        with patch("pickley.bstrap.os.path.expanduser",
                   side_effect=mocked_expanduser):
            runez.write(
                ".local/bin/pickley",
                "#!/bin/sh\necho 0.1")  # Pretend we have an old pickley
            runez.make_executable(".local/bin/pickley")

            with patch("pickley.bstrap.get_python_version",
                       return_value=(3, 6)):  # urllib fails
                monkeypatch.setenv("__PYVENV_LAUNCHER__", "oh apple, why?"
                                   )  # macos oddity env var, should be removed
                cli.run("-n", main=bstrap.main)
                assert cli.succeeded
                assert "__PYVENV_LAUNCHER__" not in os.environ
                assert "Replacing older pickley 0.1" in cli.logged
                assert "Would run: python virtualenv.pyz" in cli.logged
                assert "Would run: .local/bin/.pickley/pickley/pickley-" in cli.logged

            # Simulate multiple base candidates given
            cli.run("-n", "-b", "~/.local/bin:foo/bar", main=bstrap.main)
            assert cli.failed
            assert "not suitable: ~/.local/bin, foo/bar" in cli.logged

            # Simulate seeding
            cli.run("0.1",
                    "-b",
                    "~/.local/bin",
                    "-m",
                    "my-mirror",
                    "-c",
                    '{"pyenv":"~/.pyenv"}',
                    main=bstrap.main)
            assert cli.succeeded
            assert "Seeding .local/bin/.pickley/config.json with {'pyenv': '~/.pyenv'}" in cli.logged
            assert "Seeding .config/pip/pip.conf with my-mirror" in cli.logged
            assert "pickley version 0.1 is already installed" in cli.logged
            assert list(runez.readlines(".config/pip/pip.conf")) == [
                "[global]", "index-url = my-mirror"
            ]
            assert list(
                runez.readlines(".local/bin/.pickley/config.json")) == [
                    "{", '  "pyenv": "~/.pyenv"', "}"
                ]

            monkeypatch.setenv("PATH", "foo/bar:%s" % os.environ["PATH"])
            runez.ensure_folder("foo/bar", logger=None)
            cli.run("-n", "-b", "~/.local/bin:foo/bar", main=bstrap.main)
            assert cli.succeeded
            assert "base: foo/bar" in cli.logged

            with patch("pickley.bstrap.which", return_value=None):
                with patch("pickley.bstrap.is_executable", return_value=False):
                    # Simulate no python 3
                    cli.run("-n", main=bstrap.main)
                    assert cli.failed
                    assert "Could not find python3 on this machine" in cli.logged

            with patch("pickley.bstrap.get_python_version",
                       return_value=(3, 9)):  # urllib fails
                cli.run("-n", main=bstrap.main)
                assert cli.succeeded
                assert " -mvenv " in cli.logged
Exemple #21
0
def test_paths(temp_folder):
    assert runez.resolved_path(None) is None
    assert runez.resolved_path("some-file") == os.path.join(temp_folder, "some-file")
    assert runez.resolved_path("some-file", base="bar") == os.path.join(temp_folder, "bar", "some-file")

    assert runez.short(None) is None
    assert runez.short("") == ""
    assert runez.short(temp_folder) == temp_folder

    assert runez.short(temp_folder + "/some-file") == "some-file"
    assert runez.short(temp_folder + "/some-file") == "some-file"

    assert runez.parent_folder(None) is None
    assert runez.parent_folder(temp_folder + "/some-file") == temp_folder

    assert runez.represented_args(["ls", temp_folder + "/some-file bar", "-a"]) == 'ls "some-file bar" -a'

    # Don't crash for no-ops
    assert runez.ensure_folder(None) == 0
    assert runez.ensure_folder("") == 0
    assert runez.copy(None, None) == 0
    assert runez.move(None, None) == 0
    assert runez.symlink(None, None) == 0
    assert runez.copy("some-file", "some-file") == 0
    assert runez.move("some-file", "some-file") == 0
    assert runez.symlink("some-file", "some-file") == 0

    assert runez.ensure_folder("some-folder") == 0  # 'some-folder' would be in temp_folder, which already exists

    with runez.CaptureOutput(dryrun=True) as logged:
        assert runez.ensure_folder("some-folder", folder=True, fatal=False) == 1
        assert "Would create" in logged.pop()

        assert runez.touch("some-file", logger=logging.debug) == 1
        assert "Would touch some-file" in logged.pop()

        assert runez.copy("some-file", "bar") == 1
        assert "Would copy some-file -> bar" in logged.pop()

        assert runez.move("some-file", "bar") == 1
        assert "Would move some-file -> bar" in logged.pop()

        assert runez.symlink("some-file", "bar") == 1
        assert "Would symlink some-file <- bar" in logged.pop()

        assert runez.delete(temp_folder) == 1
        assert "Would delete" in logged.pop()

        assert runez.copy("some-folder/bar/baz", "some-folder", fatal=False) == -1
        assert "source contained in destination" in logged.pop()

        assert runez.move("some-folder/bar/baz", "some-folder", fatal=False) == -1
        assert "source contained in destination" in logged.pop()

        assert runez.symlink("some-folder/bar/baz", "some-folder", fatal=False) == -1
        assert "source contained in destination" in logged.pop()

    with runez.CaptureOutput():
        assert runez.touch("sample") == 1
        assert "Can't create folder" in runez.verify_abort(runez.ensure_folder, "sample", folder=True)
        custom = runez.verify_abort(runez.ensure_folder, "sample", folder=True, fatal=SystemExit, expected_exception=SystemExit)
        assert "Can't create folder" in custom
        with pytest.raises(AssertionError):
            assert runez.verify_abort(runez.ensure_folder, None)

        assert runez.delete("sample") == 1
        assert runez.ensure_folder("sample", folder=True) == 1
        assert os.getcwd() == temp_folder

    with runez.CurrentFolder("sample", anchor=False):
        cwd = os.getcwd()
        sample = os.path.join(temp_folder, "sample")
        assert cwd == sample
        assert runez.short(os.path.join(cwd, "some-file")) == "sample/some-file"

    with runez.CurrentFolder("sample", anchor=True):
        cwd = os.getcwd()
        sample = os.path.join(temp_folder, "sample")
        assert cwd == sample
        assert runez.short(os.path.join(cwd, "some-file")) == "some-file"

    assert os.getcwd() == temp_folder

    assert runez.delete("sample") == 1

    with runez.CaptureOutput() as logged:
        sample = os.path.join(os.path.dirname(__file__), "sample.txt")
        content = runez.get_lines(sample)

        assert runez.write("sample", "".join(content), fatal=False, logger=logging.debug) == 1
        assert runez.get_lines("sample") == content
        assert "Writing 13 bytes" in logged.pop()

        assert runez.first_line("sample") == "Fred"
        assert runez.is_younger("sample", age=10)
        assert not runez.is_younger("sample", age=-1)

        assert runez.copy("bar", "baz", fatal=False) == -1
        assert "does not exist" in logged.pop()
        assert runez.move("bar", "baz", fatal=False) == -1
        assert "does not exist" in logged.pop()
        assert runez.symlink("bar", "baz", fatal=False) == -1
        assert "does not exist" in logged.pop()

        # Creating dangling symlinks is possible
        assert runez.symlink("bar", "baz", fatal=False, must_exist=False) == 1
        assert "Symlink bar <- baz" in logged.pop()
        assert os.path.islink("baz")
        assert not os.path.exists("baz")

        assert runez.copy("sample", "x/y/sample") == 1
        assert runez.symlink("sample", "x/y/sample3", fatal=False) == 1

        assert os.path.exists("sample")
        assert runez.move("sample", "x/y/sample2") == 1
        assert not os.path.exists("sample")

        assert runez.copy("x/y", "x/z") == 1
        assert os.path.exists("x/z/sample")
        assert os.path.exists("x/z/sample2")
        assert os.path.exists("x/z/sample3")
        assert os.path.islink("x/z/sample3")

    assert runez.touch(None) == 0
    assert not runez.is_younger(None, 1)
    assert not runez.is_younger("/dev/null/not-there", 1)
    assert runez.first_line("/dev/null/not-there") is None

    assert runez.get_lines(None) is None
Exemple #22
0
def test_versions(_, __, temp_base):
    p = PACKAGERS.get("pex")("foo")
    p.pip_wheel = lambda *_: None

    assert p.specced_command() == "pex"
    p.implementation_version = "1.4.5"
    assert p.specced_command() == "pex==1.4.5"
    p.refresh_desired()
    assert p.desired.representation(
        verbose=True
    ) == "foo: can't determine latest version from pypi (channel: latest, source: pypi)"

    with patch("pickley.package.latest_pypi_version",
               return_value="error: test failed"):
        p.refresh_desired()
        assert p.desired.representation() == "foo: test failed"

    system.SETTINGS.cli.contents["channel"] = "stable"
    p.refresh_desired()
    assert p.desired.representation() == "foo: can't determine stable version"

    p.version = None
    assert "can't determine stable version" in verify_abort(p.install)

    # Without a build folder
    assert p.get_entry_points() is None

    # With an empty build fodler
    runez.ensure_folder(p.build_folder, folder=True)
    assert p.get_entry_points() is None

    # With a bogus wheel
    with runez.CaptureOutput() as logged:
        p.version = "0.0.0"
        whl = os.path.join(p.build_folder, "foo-0.0.0-py2.py3-none-any.whl")
        runez.touch(whl)
        assert p.get_entry_points() is None
        assert "Can't read wheel" in logged
        runez.delete(whl)

        p.refresh_desired()
        assert p.desired.channel == "adhoc"
        assert p.desired.source == "cli"
        assert p.desired.version == "0.0.0"
        assert not p.desired.problem
        p.version = None
        p.refresh_desired()
        assert p.desired.problem

    # Ambiguous package() call
    assert "Need either source_folder or version in order to package" in verify_abort(
        p.package)

    # Package bogus folder without a setup.py
    p.source_folder = temp_base
    assert "No setup.py" in verify_abort(p.package)

    # Package with a bogus setup.py
    setup_py = os.path.join(temp_base, "setup.py")
    runez.touch(setup_py)
    assert "Could not determine version" in verify_abort(p.package)

    # Provide a minimal setup.py
    runez.write(
        setup_py,
        "from setuptools import setup\nsetup(name='foo', version='0.0.0')\n")

    # Package project without entry points
    p.get_entry_points = lambda *_: None
    assert "is not a CLI" in verify_abort(p.required_entry_points)
Exemple #23
0
def test_edge_cases(temp_cfg, logged):
    runez.touch("dummy.whl")
    runez.ensure_folder(".", clean=True)
    assert "Cleaned 1 file from" in logged.pop()
    assert not os.path.exists("dummy.whl")
Exemple #24
0
def test_ensure_folder(temp_folder, logged):
    assert runez.ensure_folder(None) == 0
    assert runez.ensure_folder("") == 0
    assert runez.ensure_folder(".") == 0
    assert not logged

    assert runez.ensure_folder(".", clean=True) == 0
    assert not logged

    assert runez.touch("some-file", logger=None) == 1
    with pytest.raises(Exception):
        runez.ensure_folder("some-file")
    assert "Can't create folder" in logged.pop()

    assert runez.ensure_folder("some-dir", dryrun=True) == 1
    assert "Would create some-dir" in logged.pop()
    assert runez.ensure_folder("some-dir") == 1
    assert "Created folder some-dir" in logged.pop()

    assert runez.ensure_folder("some-dir") == 0
    assert not logged

    assert runez.touch("some-dir/a/b") == 1
    assert "Created folder" not in logged
    assert "Touched some-dir/a/b" in logged.pop()
    assert runez.ensure_folder("some-dir", clean=True, dryrun=True) == 1
    assert "Would clean 1 file from some-dir" in logged.pop()

    assert runez.touch("some-dir/b", logger=False) == 1
    assert not logged

    assert runez.ensure_folder("some-dir", clean=True) == 2
    assert "Cleaned 2 files from some-dir" in logged
Exemple #25
0
def test_file_inspection(temp_folder, logged):
    assert runez.touch("sample") == 1
    assert runez.delete("sample") == 1
    assert "Deleted sample" in logged.pop()

    assert runez.ensure_folder("sample") == 1
    assert runez.delete("sample") == 1
    assert "Deleted sample" in logged.pop()

    sample = runez.DEV.tests_path("sample.txt")
    assert len(list(runez.readlines(sample))) == 4
    assert len(list(runez.readlines(sample, first=1))) == 1
    assert not logged

    cc = "%s\n" % "\n".join(runez.readlines(sample))
    assert runez.write("sample", cc, fatal=False, logger=logging.debug) == 1
    cc2 = "%s\n" % "\n".join(runez.readlines("sample"))
    assert cc2 == cc
    assert "bytes to sample" in logged.pop()  # Wrote 13 bytes on linux... but 14 on windows...

    assert list(runez.readlines("sample", first=2)) == ["", "Fred"]
    assert runez.file.is_younger("sample", age=10)
    assert not runez.file.is_younger("sample", age=-1)

    # Verify that readlines() can ignore encoding errors
    with io.open("not-a-text-file", "wb") as fh:
        fh.write(b"\x89 hello\nworld")

    assert list(runez.readlines("not-a-text-file", first=1)) == [" hello"]
    assert not logged

    assert runez.copy("bar", "baz", fatal=False) == -1
    assert "does not exist" in logged.pop()
    assert runez.move("bar", "baz", fatal=False) == -1
    assert "does not exist" in logged.pop()
    assert runez.symlink("bar", "baz", fatal=False) == -1
    assert "does not exist" in logged.pop()

    # Creating dangling symlinks is possible
    assert runez.symlink("s/bar", "s/baz", fatal=False, must_exist=False) == 1
    assert "Symlink s/bar <- s/baz" in logged.pop()
    assert os.path.islink("s/baz")
    assert not os.path.exists("s/baz")
    runez.touch("s/bar")
    assert os.path.exists("s/baz")

    assert runez.copy("sample", "x/y/sample") == 1
    assert runez.symlink("sample", "x/y/sample3", fatal=False) == 1

    assert os.path.exists("sample")
    assert runez.move("sample", "x/y/sample2") == 1
    assert not os.path.exists("sample")

    assert runez.copy("x/y", "x/z1") == 1
    assert os.path.exists("x/z1/sample")
    assert os.path.exists("x/z1/sample2")
    assert os.path.exists("x/z1/sample3")
    assert os.path.islink("x/z1/sample3")

    assert runez.copy("x/y", "x/z2", ignore={"sample2"}) == 1
    assert os.path.exists("x/z2/sample")
    assert not os.path.exists("x/z2/sample2")
    assert os.path.exists("x/z2/sample3")
    assert os.path.islink("x/z2/sample3")

    def should_ignore(src, dest):
        if src == "x/y" and "sample3" in dest:
            return {"sample3"}

    assert runez.copy("x/y", "x/z3", ignore=should_ignore) == 1
    assert os.path.exists("x/z3/sample")
    assert os.path.exists("x/z3/sample2")
    assert not os.path.exists("x/z3/sample3")

    assert runez.copy("x/y", "x/z2") == 1
    assert os.path.exists("x/z2/sample2")

    # Copy a folder over an existing file
    runez.touch("x2")
    assert not os.path.exists("x2/z2/sample2")
    assert runez.copy("x", "x2") == 1
    assert os.path.exists("x2/z2/sample2")