Пример #1
0
    def test_scmHgRequestId(self) -> None:
        if not is_hg_installed():
            self.skipTest("Hg not installed")
        self.skipIfNoHgRequestIdSupport()

        root = self.mkdtemp()

        # In this test, the repo does not necessarily need fsmonitor enabled,
        # since watchman calls HGREQUESTID=... hg status and that would also
        # have request_id logged without fsmonitor.
        env = os.environ.copy()
        env["HGPLAIN"] = "1"
        env["WATCHMAN_SOCK"] = (WatchmanInstance.getSharedInstance().
                                getSockPath().legacy_sockpath())
        subprocess.call(["hg", "init"], env=env, cwd=root)
        subprocess.call(
            [
                "hg",
                "commit",
                "-mempty",
                "-utest",
                "-d0 0",
                "--config=ui.allowemptycommit=1",
            ],
            env=env,
            cwd=root,
        )
        commit_hash = subprocess.check_output(["hg", "log", "-r.", "-T{node}"],
                                              env=env,
                                              cwd=root).decode("utf-8")

        # Must watch the directory after it's an HG repo to perform scm-aware
        # queries.
        self.watchmanCommand("watch", root)
        request_id = "4c05a798ea1acc7c97b75e61fec5f640d90f8209"

        params = {
            "fields": ["name"],
            "request_id": request_id,
            "since": {
                "scm": {
                    "mergebase-with": commit_hash
                }
            },
        }
        self.watchmanCommand("query", root, params)

        blackbox_path = os.path.join(root, ".hg", "blackbox.log")

        def try_read_blackbox():
            try:
                with open(blackbox_path) as f:
                    return f.read()
            except IOError:
                return ""

        self.assertWaitFor(
            lambda: request_id in try_read_blackbox(),
            message="request_id passed to and logged by hg",
        )
Пример #2
0
 def test_sock_name(self) -> None:
     resp = self.watchmanCommand("get-sockname")
     self.assertEqual(
         resp["sockname"],
         WatchmanInstance.getSharedInstance().getSockPath().legacy_sockpath(
         ),
     )
Пример #3
0
    def test_cppclient(self) -> None:
        env = os.environ.copy()
        env["WATCHMAN_SOCK"] = (WatchmanInstance.getSharedInstance().
                                getSockPath().legacy_sockpath())
        proc = subprocess.Popen(
            TEST_BINARY,
            env=env,
            stdout=subprocess.PIPE,
            stderr=subprocess.PIPE,
            cwd=self.tmpDir,
        )
        (stdout, stderr) = proc.communicate()
        status = proc.poll()

        if status == -signal.SIGINT:
            Interrupt.setInterrupted()
            self.fail("Interrupted by SIGINT")
            return

        if status != 0:
            self.fail("Exit status %d\n%s\n%s\n" %
                      (status, stdout.decode("utf-8"), stderr.decode("utf-8")))
            return

        self.assertTrue(True, TEST_BINARY)
Пример #4
0
    def runWatchTests(self, config, expect) -> None:
        with WatchmanInstance.Instance(config=config) as inst:
            inst.start()
            client = self.getClient(inst)

            for filetype, name, expect_pass in expect:
                for watch_type in ["watch", "watch-project"]:
                    # encode the test criteria in the dirname so that we can
                    # figure out which test scenario failed more easily
                    d = self.mkdtemp(suffix="-%s-%s-%s-%s" %
                                     (filetype, name, expect_pass, watch_type))
                    if filetype == "directory":
                        os.mkdir(os.path.join(d, name))
                    elif filetype == "file":
                        self.touchRelative(d, name)

                    assert_functions = {
                        (True, "watch"):
                        self.assertWatchSucceeds,
                        (True, "watch-project"):
                        self.assertWatchProjectSucceeds,
                        (False, "watch"):
                        self.assertWatchIsRestricted,
                        (False, "watch-project"):
                        self.assertWatchProjectIsRestricted,
                    }
                    assert_function = assert_functions[(expect_pass,
                                                        watch_type)]
                    assert_function(inst, client, d)
Пример #5
0
 def test_failing_to_start_when_nice(self) -> None:
     inst = WatchmanInstance.Instance()
     stdout, stderr = inst.commandViaCLI(["version"], prefix=["nice"])
     print("stdout", stdout.decode(errors="replace"))
     print("stderr", stderr.decode(errors="replace"))
     stderr = stderr.decode("ascii")
     self.assertEqual(b"", stdout)
     self.assertRegex(stderr, "refusing to start")
Пример #6
0
 def _new_instance(self, config, expect_success: bool = True):
     if expect_success:
         start_timeout = 20
     else:
         # If the instance is going to fail anyway then there's no point
         # waiting so long
         start_timeout = 5
     return WatchmanInstance.InstanceWithStateDir(
         config=config, start_timeout=start_timeout)
Пример #7
0
    def test_spawner(self) -> None:
        config = {"spawn_watchman_service": SITE_SPAWN}

        inst = WatchmanInstance.Instance(config=config)
        stdout, stderr = inst.commandViaCLI(["version"])

        parsed = json.loads(stdout.decode("ascii"))
        self.assertTrue("version" in parsed)

        # Shut down that process, as we have no automatic way to deal with it
        inst.commandViaCLI(["--no-spawn", "--no-local", "shutdown-server"])
Пример #8
0
    def runProjectTests(self,
                        config,
                        expect,
                        touch_watchmanconfig: bool = False) -> None:
        with WatchmanInstance.Instance(config=config) as inst:
            inst.start()
            client = self.getClient(inst)

            for touch, expect_watch, expect_rel, expect_pass in expect:
                # encode the test criteria in the dirname so that we can
                # figure out which test scenario failed more easily

                suffix = "-%s-%s-%s-%s" % (touch, expect_watch, expect_rel,
                                           expect_pass)
                suffix = suffix.replace("/", "Z")
                d = self.mkdtemp(suffix=suffix)

                dir_to_watch = os.path.join(d, "a", "b", "c")
                os.makedirs(dir_to_watch, 0o777)
                dir_to_watch = norm_absolute_path(dir_to_watch)
                self.touchRelative(d, touch)
                if touch_watchmanconfig:
                    make_empty_watchmanconfig(d)

                if expect_watch:
                    expect_watch = os.path.join(d, expect_watch)
                else:
                    expect_watch = d

                if expect_pass:
                    res = client.query("watch-project", dir_to_watch)

                    self.assertEqual(
                        norm_absolute_path(os.path.join(d, expect_watch)),
                        norm_absolute_path(res["watch"]),
                    )
                    if not expect_rel:
                        self.assertEqual(None, res.get("relative_path"))
                    else:
                        self.assertEqual(
                            norm_relative_path(expect_rel),
                            norm_relative_path(res.get("relative_path")),
                        )
                else:
                    with self.assertRaises(pywatchman.WatchmanError) as ctx:
                        client.query("watch-project", dir_to_watch)
                    self.assertIn(
                        ("None of the files listed in global config " +
                         "root_files are present in path `" + dir_to_watch +
                         "` or any of its parent directories.  " +
                         "root_files is defined by the"),
                        str(ctx.exception),
                    )
Пример #9
0
    def test_bulkstat_off(self) -> None:
        config = {"_use_bulkstat": False}
        with WatchmanInstance.Instance(config=config) as inst:
            inst.start()
            self.getClient(inst, replace_cached=True)

            root = self.mkdtemp()
            # pyre-fixme[16]: `TestBulkStat` has no attribute `client`.
            self.client.query("watch", root)

            self.touchRelative(root, "foo")
            self.touchRelative(root, "bar")
            self.assertFileList(root, ["foo", "bar"])
Пример #10
0
    def test_no_site_spawner(self) -> None:
        """With a site spawner configured to otherwise fail, pass
        `--no-site-spawner` and ensure that a failure didn't occur."""
        config = {"spawn_watchman_service": SITE_SPAWN_FAIL}

        inst = WatchmanInstance.Instance(config=config)
        stdout, stderr = inst.commandViaCLI(["version", "--no-site-spawner"])

        print(stdout, stderr.decode("ascii"))
        parsed = json.loads(stdout.decode("ascii"))
        self.assertTrue("version" in parsed)

        inst.commandViaCLI(["--no-spawn", "--no-local", "shutdown-server"])
Пример #11
0
    def test_failingSpawner(self) -> None:
        config = {"spawn_watchman_service": SITE_SPAWN_FAIL}

        inst = WatchmanInstance.Instance(config=config)
        stdout, stderr = inst.commandViaCLI(["version"])
        sys.stdout.buffer.write(b"stdout:\n")
        sys.stdout.buffer.write(stdout)
        sys.stdout.buffer.write(b"stderr:\n")
        sys.stdout.buffer.write(stderr)
        stderr = stderr.decode("ascii")
        self.assertEqual(b"", stdout)
        self.assertRegex(stderr, "failed to start\n")
        self.assertRegex(stderr, "site_spawn_fail.py: exited with status 1")
Пример #12
0
    def test_shutdown_and_restart(self) -> None:
        def populate(repo: hgrepo.HgRepository) -> None:
            repo.write_file("hello", "hola\n")
            repo.commit("initial commit.")

        root = self.makeEdenMount(populate)

        inst = WatchmanInstance.Instance()
        _, stderr = inst.commandViaCLI(["watch", root])
        self.assertEqual(stderr, b"")
        _, stderr = inst.commandViaCLI(["shutdown-server"])
        self.assertEqual(stderr, b"")
        _, stderr = inst.commandViaCLI(["get-sockname"])
        self.assertEqual(stderr, b"")
Пример #13
0
def is_hg_installed() -> bool:
    with open(os.devnull, "wb") as devnull:
        try:
            env = os.environ.copy()
            env["HGPLAIN"] = "1"
            env["WATCHMAN_SOCK"] = (WatchmanInstance.getSharedInstance().
                                    getSockPath().legacy_sockpath())

            exit_code = subprocess.call(["hg", "--version"],
                                        stdout=devnull,
                                        stderr=devnull,
                                        env=env)
            return exit_code == 0
        except OSError as e:
            if e.errno == errno.ENOENT:
                return False
            raise
Пример #14
0
    def test_failing_to_start_when_nice_foreground(self) -> None:
        inst = WatchmanInstance.Instance()
        stdout, stderr = inst.commandViaCLI(["--foreground", "version"],
                                            prefix=["nice"])
        print("stdout", stdout)
        print("stderr", stderr)

        output = stderr.decode("ascii")
        try:
            output += inst.getServerLogContents()
        except IOError:
            # on macos, we may not have gotten as far
            # as creating the log file when the error
            # triggers, so we're fine with passing
            # on io errors here
            pass
        self.assertRegex(output, "refusing to start")
Пример #15
0
    def runTest(self) -> None:
        env = os.environ.copy()
        env["WATCHMAN_SOCK"] = (WatchmanInstance.getSharedInstance().
                                getSockPath().legacy_sockpath())
        env["TMPDIR"] = self.tempdir

        # build the node module with yarn
        node_dir = os.path.join(env["TMPDIR"], "fb-watchman")
        shutil.copytree(os.path.join(WATCHMAN_SRC_DIR, "node"), node_dir)

        install_args = [yarn_bin, "install"]
        if "YARN_OFFLINE" in env:
            install_args.append("--offline")

        bser_dir = os.path.join(node_dir, "bser")
        subprocess.check_call(install_args, cwd=bser_dir, env=env)

        env["TMP"] = env["TMPDIR"]
        env["TEMP"] = env["TMPDIR"]
        env["IN_PYTHON_HARNESS"] = "1"
        env["NODE_PATH"] = "%s:%s" % (node_dir, env["TMPDIR"])
        proc = subprocess.Popen(
            # pyre-fixme[16]: `NodeTestCase` has no attribute `getCommandArgs`.
            self.getCommandArgs(),
            env=env,
            stdout=subprocess.PIPE,
            stderr=subprocess.PIPE,
        )
        (stdout, stderr) = proc.communicate()
        status = proc.poll()

        if status == -signal.SIGINT:
            Interrupt.setInterrupted()
            self.fail("Interrupted by SIGINT")
            return

        if status != 0:
            self.fail("Exit status %d\n%s\n%s\n" %
                      (status, stdout.decode("utf-8"), stderr.decode("utf-8")))
            return
        self.assertTrue(True, self.getCommandArgs())
Пример #16
0
    def test_Illegal(self) -> None:
        config = {
            "illegal_fstypes": [
                # This should include any/all fs types. If this test fails on
                # your platform, look in /tmp/watchman-test.log for a line like:
                # "path /var/tmp/a3osdzvzqnco0sok is on filesystem type zfs"
                # then add the type name to this list, in sorted order
                "NTFS",
                "apfs",
                "btrfs",
                "cifs",
                "ext2",
                "ext3",
                "ext4",
                "fuse",
                "hfs",
                "msdos",
                "nfs",
                "smb",
                "tmpfs",
                "ufs",
                "unknown",
                "xfs",
                "zfs",
            ],
            "illegal_fstypes_advice":
            "just cos",
        }

        with WatchmanInstance.Instance(config=config) as inst:
            inst.start()
            client = self.getClient(inst)

            d = self.mkdtemp()
            with self.assertRaises(pywatchman.WatchmanError) as ctx:
                client.query("watch", d)
            self.assertIn(
                ("filesystem and is disallowed by global config" +
                 " illegal_fstypes: just cos"),
                str(ctx.exception),
            )
Пример #17
0
    def skipIfNoHgRequestIdSupport(self) -> None:
        root = self.mkdtemp()
        request_id = "bf8a47014bd1b66103a8ab0aece4be7ada871660"

        env = os.environ.copy()
        env["HGPLAIN"] = "1"
        env["HGREQUESTID"] = request_id
        env["WATCHMAN_SOCK"] = (WatchmanInstance.getSharedInstance().
                                getSockPath().legacy_sockpath())

        subprocess.call(["hg", "init"], env=env, cwd=root)
        subprocess.call(["hg", "log"], env=env, cwd=root)

        try:
            with open(os.path.join(root, ".hg/blackbox.log")) as f:
                if request_id in f.read():
                    return
        except IOError:
            pass

        self.skipTest("HGREQUESTID is not supported")
Пример #18
0
    def spawnWatchmanWait(self, cmdArgs):
        wait_script = os.environ.get("WATCHMAN_WAIT_PATH")
        if wait_script:
            args = [wait_script]
        else:
            args = [
                sys.executable,
                os.path.join(os.environ["WATCHMAN_PYTHON_BIN"],
                             "watchman-wait"),
            ]
        args.extend(cmdArgs)

        env = os.environ.copy()
        sock_path = WatchmanInstance.getSharedInstance().getSockPath()
        env["WATCHMAN_SOCK"] = sock_path.legacy_sockpath()
        pywatchman_path = env.get("PYWATCHMAN_PATH")
        if pywatchman_path:
            env["PYTHONPATH"] = pywatchman_path
        return subprocess.Popen(args,
                                env=env,
                                stdin=None,
                                stdout=subprocess.PIPE,
                                stderr=subprocess.PIPE)
Пример #19
0
 def getSockPath(self):
     return WatchmanInstance.getSharedInstance().getSockPath()