who 명령의 날짜 및 시간 출력을 일관되게 표시합니다.

who 명령의 날짜 및 시간 출력을 일관되게 표시합니다.

다른 Linux 서버에서 SSH를 통해 Debian 12 서버에 연결하고 다음을 실행하면WHO명령을 실행하면 다음이 표시됩니다.

test-user    pts/1        2024-01-24 11:13 (xx.xx.xx.xx)

그러나 Windows 터미널을 통해 또는 타사 애플리케이션을 사용하여 Windows 11 시스템에서 동일한 사용자를 사용하고 실행 중인 동일한 Debian 12 서버에 연결하는 경우WHO명령을 실행하면 날짜/시간 형식이 다르게 표시됩니다.

test-user    pts/0        Jan 24 11:15 (xx.xx.xx.xx)

나는 이 노선을 달리고 있다/etc/구성 파일로그인할 때마다 사용자의 IP 주소를 확인하지만 출력이 다르고 이러한 공백이 결과를 변경하기 때문에 작동하지 않습니다.

myip=$(who -m | awk '{print substr($5, 2, length($5) - 2)}')

날짜/시간 출력을 제어하는 ​​방법이 있나요?WHO주문하다? 이 동작의 원인은 무엇입니까?

고쳐 쓰다

다음에서 로캘 명령을 실행합니다.

리눅스에서:

$locale

LANG=en_US.UTF-8
LANGUAGE=
LC_CTYPE="en_US.UTF-8"
LC_NUMERIC="en_US.UTF-8"
LC_TIME="en_US.UTF-8"
LC_COLLATE="en_US.UTF-8"
LC_MONETARY="en_US.UTF-8"
LC_MESSAGES="en_US.UTF-8"
LC_PAPER="en_US.UTF-8"
LC_NAME="en_US.UTF-8"
LC_ADDRESS="en_US.UTF-8"
LC_TELEPHONE="en_US.UTF-8"
LC_MEASUREMENT="en_US.UTF-8"
LC_IDENTIFICATION="en_US.UTF-8"
LC_ALL=

윈도우 11부터 시작

$locale

LANG=
LANGUAGE=
LC_CTYPE="POSIX"
LC_NUMERIC="POSIX"
LC_TIME="POSIX"
LC_COLLATE="POSIX"
LC_MONETARY="POSIX"
LC_MESSAGES="POSIX"
LC_PAPER="POSIX"
LC_NAME="POSIX"
LC_ADDRESS="POSIX"
LC_TELEPHONE="POSIX"
LC_MEASUREMENT="POSIX"
LC_IDENTIFICATION="POSIX"
LC_ALL=

내가 연결한 Linux 서버에서는 이런 일이 발생하지 않는 것 같습니다. 이는 다르며 아래 솔루션에 설명되어 있습니다.

아래 설명을 바탕으로 근본 원인을 이해했을 때 이러한 제안을 사용하기로 결정했고 모두 내 사용 사례에 적합했습니다.

답변1

당신이 보면GNU 구현을 위한 소스 코드who, 바라보다:

  if (hard_locale (LC_TIME))
    {
      time_format = "%Y-%m-%d %H:%M";
      time_format_width = 4 + 1 + 2 + 1 + 2 + 1 + 2 + 1 + 2;
    }
  else
    {
      time_format = "%b %e %H:%M";
      time_format_width = 3 + 1 + 2 + 1 + 2 + 1 + 2;
    }

이것hard_locale()gnulib 선언다음과 같이 설명하세요.

 /* Return true if the specified CATEGORY of the current locale is hard, i.e.
   different from the C or POSIX locale that has a fixed behavior.
   CATEGORY must be one of the LC_* values, but not LC_ALL.  */
 extern bool hard_locale (int category);

그래서,

  • C/POSIX 로케일에서는 다음을 얻습니다.<EnglishMonthNameAbbreviation> <SpacePaddedDayOfTheMonth> <ZeroPaddedHour>:<ZeroPaddedMinute>
  • 기타 로케일: 표준 ISO8601 스타일 YYYY-MM-DD HH:MM 날짜.

LC_TIME 범주의 로케일은 env 변수에 의해 결정됩니다 LC_ALL. 이 변수가 설정되지 않았거나 둘 다 설정되지 않은 경우에는 이 변수가 결정됩니다 LC_TIME. 그렇거나 시스템에 설치된 로케일에 대한 문자열이 없거나 세 가지 변수가 모두 설정되지 않은 경우 C/POSIX 로케일을 얻게 됩니다.LC_ALLLANGCPOSIX

이 명령은 서버에 변수를 전달할 수 있으며 많은 Unix 계열 시스템에서 기본적으로 그렇게 합니다 ssh. 또한 많은 Unix 계열 시스템에서 다음과 같이 구성됩니다.LANGLC_*sshd수용하다기본적으로 이러한 변수 LANGLC_*변수가 있습니다. 그러나 Microsoft Windows는 Unix와 같은 시스템이 아닙니다. 사용 중인 클라이언트가 이러한 변수를 전달 하더라도 ssh서버에서 지원하는 로케일 이름을 포함하는 일부 변수가 환경에 존재할 가능성은 거의 없습니다 LANG.LC_*

이것은 CWindows에서 ing할 때 -like 날짜 형식을 얻지만 ssh, 다른 Unix 계열 시스템에서 sshing할 때는 ISO8601 스타일 날짜 형식을 얻는 이유를 설명합니다.

일관된 형식을 얻으려면 C다음을 실행하여 로캘을 강제로 적용 할 수 있습니다 who.

LC_ALL=C who -m

()하지만 여기서는 tty 로그인 위치 정보가 포함된 행의 첫 번째 항목과 마지막 항목 사이의 부분을 추출하려는 것으로 보입니다 . 다음과 같이 할 수 있습니다.

who -m | perl -ne 'print $1 if /\((.*)\)/'

tty에 의해 생성되고 이러한 환경 변수가 (예: 또는 에 sshd의해) 지워지지 않았다고 가정하는 경우 다음을 수행 하여 변수에서 SSH 클라이언트의 IP 주소를 추출할 수 있습니다 .sudosu -SSH_CLIENT

ipaddress="${SSH_CLIENT%% *}"

답변2

위의 제안을 사용하여 문제를 해결했습니다.

myip=$(echo $SSH_CONNECTION | awk '{print $1}')

두 번째 접근 방식도 효과가 있는 것 같습니다.

myip=$(echo $SSH_CLIENT | awk '{print $1}')

모두 감사합니다!

관련 정보