• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

pantsbuild / pants / 25259185675

02 May 2026 06:47PM UTC coverage: 92.141% (-0.8%) from 92.955%
25259185675

push

github

web-flow
Fix the dynamic UI. (#23306)

In #23114 we upgraded to indicatif 0.18.4,
which included a fix to respect TERM, and 
display nothing if it's unset.

Since we did not pass TERM through pantsd, the
dynamic ui is now not shown. 

This change fixes that, and also pass NO_COLOR
through, since indicatif inspects it too.

88773 of 96345 relevant lines covered (92.14%)

3.83 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

68.57
/src/python/pants/util/osutil.py
1
# Copyright 2015 Pants project contributors (see CONTRIBUTORS.md).
2
# Licensed under the Apache License, Version 2.0 (see LICENSE).
3

4
from __future__ import annotations
11✔
5

6
import errno
11✔
7
import getpass
11✔
8
import logging
11✔
9
import os
11✔
10
import platform
11✔
11
import posix
11✔
12
from functools import reduce
11✔
13

14
logger = logging.getLogger(__name__)
11✔
15

16

17
def _compute_cpu_count() -> int:
11✔
18
    # We use `sched_getaffinity()` to get the number of cores available to the process, rather than
19
    # the raw number of cores. This sometimes helps for containers to accurately report their # of
20
    # cores, rather than the host's.
21
    sched_getaffinity = getattr(os, "sched_getaffinity", None)
11✔
22
    if sched_getaffinity:
11✔
23
        return len(sched_getaffinity(0))
10✔
24
    cpu_count = os.cpu_count()
1✔
25
    if cpu_count:
1✔
26
        return cpu_count
1✔
27
    return 2
×
28

29

30
CPU_COUNT = _compute_cpu_count()
11✔
31

32

33
OS_ALIASES = {
11✔
34
    "macos": {"macos", "darwin", "macosx", "mac os x", "mac"},
35
    "linux": {"linux", "linux2"},
36
}
37

38
ARCH_ALIASES = {
11✔
39
    "x86_64": {"x86_64", "x86-64", "amd64"},
40
    "arm64": {"arm64", "aarch64"},
41
}
42

43
Pid = int
11✔
44

45

46
def get_arch_name(uname_result: posix.uname_result | None = None) -> str:
11✔
47
    """
48
    :API: public
49
    """
50
    if uname_result is None:
11✔
51
        uname_result = os.uname()
11✔
52
    return uname_result.machine.lower()
11✔
53

54

55
def get_os_name(uname_result: posix.uname_result | None = None) -> str:
11✔
56
    """
57
    :API: public
58
    """
59
    if uname_result is None:
11✔
60
        uname_result = os.uname()
11✔
61
    return uname_result.sysname.lower()
11✔
62

63

64
def normalize_arch_name(arch_name: str) -> str:
11✔
65
    """
66
    :API: public
67
    """
68
    return _normalize(arch_name, ARCH_ALIASES, "architecture")
11✔
69

70

71
def normalize_os_name(os_name: str) -> str:
11✔
72
    """
73
    :API: public
74
    """
75
    return _normalize(os_name, OS_ALIASES, "operating system")
11✔
76

77

78
def _normalize(name: str, aliases: dict[str, set[str]], warning_hint: str) -> str:
11✔
79
    for proper_name, alias_set in aliases.items():
11✔
80
        if name in alias_set:
11✔
81
            return proper_name
11✔
82
    else:
83
        logger.warning(
1✔
84
            "Unknown {hint} name: {bad}, known names are: {known}".format(
85
                hint=warning_hint, bad=name, known=", ".join(sorted(_values(aliases)))
86
            )
87
        )
88
        return name
1✔
89

90

91
def get_normalized_os_name() -> str:
11✔
92
    return normalize_os_name(get_os_name())
11✔
93

94

95
def get_normalized_arch_name() -> str:
11✔
96
    return normalize_arch_name(get_arch_name())
11✔
97

98

99
def macos_major_version() -> None | int:
11✔
100
    if not hasattr(platform, "mac_ver"):
×
101
        return None
×
102

103
    version = platform.mac_ver()[0]
×
104
    if not version:
×
105
        return None
×
106

107
    return int(version.split(".", 1)[0])
×
108

109

110
def is_macos_big_sur() -> bool:
11✔
111
    return macos_major_version() == 11
×
112

113

114
def getuser() -> str:
11✔
115
    try:
×
116
        return getpass.getuser()
×
117
    except KeyError:
×
118
        # Work when running with a uid not associated with a user,
119
        # e.g., in a docker container with a host uid.
120
        return str(os.getuid())
×
121

122

123
def _values(aliases: dict[str, set[str]]) -> set[str]:
11✔
124
    return reduce(set.union, aliases.values())
1✔
125

126

127
# From kill(2) on OSX 10.13:
128
#     [EINVAL]           Sig is not a valid, supported signal number.
129
#
130
#     [EPERM]            The sending process is not the super-user and its effective user id does not match the effective user-id of the receiving process.  When signaling a process group, this error is returned if
131
#                        any members of the group could not be signaled.
132
#
133
#     [ESRCH]            No process or process group can be found corresponding to that specified by pid.
134
#
135
#     [ESRCH]            The process id was given as 0, but the sending process does not have a process group.
136
def safe_kill(pid: Pid, signum: int) -> None:
11✔
137
    """Kill a process with the specified signal, catching nonfatal errors."""
138
    assert isinstance(pid, Pid)
×
139
    assert isinstance(signum, int)
×
140
    try:
×
141
        os.kill(pid, signum)
×
142
    except OSError as e:
×
143
        if e.errno in [errno.ESRCH, errno.EPERM]:
×
144
            pass
×
145
        elif e.errno == errno.EINVAL:
×
146
            raise ValueError(f"Invalid signal number {signum}: {e}", e)
×
147
        else:
148
            raise
×
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc