2013-09-22 6 views
5

내가 최대 INFO 레벨 이상 사용하는 모든 SSH/Paramiko 관련 출력 로그인 할 수 원단을 설정 한 :패브릭 로그 형식은 날짜와 시간을 표시

logging.basicConfig() 
logging.getLogger('ssh.transport').setLevel(logging.INFO) 

이이처럼 보이는 로그 결과를 :

[host1] Executing task 'task1' 
[host1] Run: ls 
... 

ssh.transport 로거의 포맷터를 변경하여 각 줄에도 날짜와 시간이 인쇄되도록 할 수 있습니까?

답변

4

alecxe said으로 포맷은 패브릭 1.x에 하드 코드되어 있습니다 (내가 게시 할 때 사용 가능한 유일한 버전 임).이 문제를 해결할 수있는 a rejected pull request이있었습니다.

대신에 해결 방법이 필요합니다. 이것은 제가 작성한 다소 해로운 해결책이지만 Fabric의 문서화되지 않은 부분에 의존합니다. 이는 Fabric이 이후 버전에서 중단 될 수 있음을 의미합니다.

from fabric.io import OutputLooper 
from datetime import datetime 

def newFlush(self, text): 
    stamp = datetime.now().strftime("%a %b %d %H:%M:%S - ") 
    print(stamp + text) 

OutputLooper._flush = newFlush 

이 시점부터 원격 시스템의 모든 출력에는 타임 스탬프가 적용됩니다.

예를 들어,이 코드없이 sudo('echo "test"')의 출력은 다음과 같습니다

[InteractSL-DT1.usma.ibm.com] sudo: echo "test" 
[InteractSL-DT1.usma.ibm.com] out: test 
[InteractSL-DT1.usma.ibm.com] out: 

'test' 

하지만 지금은 얻을 것이다 것을 추가 한 후 :

[InteractSL-DT1.usma.ibm.com] sudo: echo "test" 
Fri Jan 02 12:54:49 - [InteractSL-DT1.usma.ibm.com] out: 
Fri Jan 02 12:54:49 - test 

Fri Jan 02 12:54:49 - [InteractSL-DT1.usma.ibm.com] out: 
Fri Jan 02 12:54:49 - 

'test' 

당신이 기본으로 주위를 재생할 수 있습니다 그것을 정리하는 아이디어. 출력 시작 부분의 sudo 행은 fabric.operations._run_command에서 900 행 주위에 있습니다. 수정할 수있는 간단한 방법이 확실하지 않습니다.

3

지금은 불가능합니다. 형식은 하드 코딩되어 있습니다 (source 참조).

참고로 정확히 너를 묻는 proposal이 있습니다.


당신은 내부 asctime와 형식을 로깅을 설정할 수 있지만,이 직물 출력 만 paramiko들에 영향을 미치지 않습니다 :

import logging 
FORMAT = "%(asctime)s %(name)s %(message)s" 
logging.basicConfig(format=FORMAT, level=logging.INFO) 

예를 출력 :

[host] Executing task 'restart' 
[host] sudo: ls 
2013-09-23 02:36:54,800 paramiko.transport Connected (version 2.0, client OpenSSH_5.3) 
2013-09-23 02:36:55,728 paramiko.transport Authentication (password) successful! 
2013-09-23 02:36:55,889 paramiko.transport Secsh channel 1 opened. 
... 

희망하는 데 도움이 .

0

도 역시 _flush()을 대체 할 방법을 찾지 못했습니다. 나는 일반적으로 제 3자를 제외하고 어떤 수업에서든 개인적인 방법을 대체하는 것은 위험한 습관이라고 생각합니다. 다음은 Fabric _flush() 메서드를 꾸미고 원시 Python time.asctime 메서드를 사용하여 타임 스탬프의 형식을 지정하는 솔루션입니다.

> fab uptime -H 10.0.1.3,10.0.1.2 
[10.0.1.3] Executing task 'uptime' 
[10.0.1.3] run: uptime 
[Thu Dec 15 19:34:35 2016] [10.0.1.3] out: 19:34:35 up 69 days, 4:22, 1 user, load average: 0.05, 0.03, 0.05 
[Thu Dec 15 19:34:35 2016] [10.0.1.3] out: 

[10.0.1.2] Executing task 'uptime' 
[10.0.1.2] run: uptime 
[Thu Dec 15 19:34:35 2016] [10.0.1.2] out: 19:34:35 up 70 days, 1:12, 1 user, load average: 0.00, 0.01, 0.05 
[Thu Dec 15 19:34:35 2016] [10.0.1.2] out: 


Done. 
Disconnecting from [email protected] done. 
Disconnecting from [email protected] done. 
:

def time_decorator(msg): 
    """ 
    Decorates `msg` with current timestamp 
    Args: 
     msg(str): The log message from fabric 
    Returns: 
     str: Original message prepended with current date time 
    """ 
    if "\n" not in msg and msg.strip(): 
     return "[%s] %s" % (time.asctime(), msg) 

    return msg 


# Compose original method inside of decorator 
_original_flush = OutputLooper._flush 
OutputLooper._flush = lambda self, msg: { 
    _original_flush(self, time_decorator(msg)) 
} 


@task 
def uptime(): 
    run('uptime') 

테스트 그것을, 당신의 출력은 같은 유사합니다

관련 문제