Tôi có thể thấy trong một tệp nhật ký tất cả các tác vụ dựa trên GUI ở định dạng dòng lệnh thay thế không?


9

Ví dụ: tôi thường mở mousepad (xfce tương đương với gedit) từ menu ứng dụng. Tuy nhiên, tôi biết rằng bạn cũng có thể làm điều này trong một thiết bị đầu cuối bằng cách gõ mousepad.

Theo ví dụ này, điều tôi muốn là bất cứ khi nào tôi mở mousepad thông qua GUI, một dòng mới được viết trong một tệp nhật ký có nội dung như thế Sep 5 15:35:11 lucho@lucho:~$ mousepad. Nói chung, điều tôi muốn là ghi nhật ký tất cả các hoạt động GUI có khả năng thực hiện thông qua dòng lệnh (như mở chương trình, thay đổi quyền, sửa đổi cài đặt hệ thống, v.v.) nhưng được viết bằng định dạng thực thi dòng lệnh thay thế . Tôi muốn điều này để cải thiện kiến ​​thức của tôi về cách sử dụng dòng lệnh (mà không cần thông qua các mantrang). Có nhiều điều tôi làm thông qua GUI mà tôi không thực hiện thông qua dòng lệnh (một số có khả năng tự động hóa thông qua tập lệnh hoặc qua phím tắt) và có tệp nhật ký này sẽ là một cách tốt để tìm hiểu chúng.

Tôi biết về sự tồn tại của tệp nhật ký hệ thống /var/lognhưng đó không phải là thứ tôi cần. Ứng dụng Trình quản lý nhật ký hoạt động từ kho lưu trữ Ubuntu không hiển thị định dạng dòng lệnh, theo như tôi biết. Tôi cần một cái gì đó như tệp .bash_history tồn tại trong thư mục nhà của tôi nhưng ghi lại các hoạt động dựa trên GUI của tôi.


bạn có thể sử dụng một công cụ như strace để xem lén một chương trình đang chạy và xem hệ thống gọi nó là gì, điều này sẽ tạo ra một lượng lớn dữ liệu mặc dù
Amias

Nếu bạn đang tìm kiếm một chương trình chỉ ghi nhật ký tên nhị phân của các chương trình mở trong GUI, tôi có thể thực hiện điều đó trong một tập lệnh. Nếu đó là những gì bạn muốn, hãy cho tôi biết. Sẽ tốt hơn nếu bạn làm rõ những yêu cầu của bạn thực sự là gì, vì vậy hãy chỉnh sửa câu hỏi của bạn. Ghi lại các hoạt động dựa trên GUI, chẳng hạn như nhấp vào nút hoặc mở tab mới trong trình duyệt không phải là thứ có thể dễ dàng ghi lại, vì những thứ này không được kết nối với các lệnh shell thực tế
Sergiy Kolodyazhnyy

@Serg Nhật ký mà bạn đề xuất sẽ chắc chắn là những gì tôi đang tìm kiếm. Một cái gì đó giống như nhật ký "Trình quản lý tác vụ" dựa trên tên CLI thay vì tên GLI, như câu trả lời hiện có cho thấy, có thể không trùng khớp. Chẳng hạn, nếu tôi mở "Hỗ trợ ngôn ngữ" trong Cài đặt, tôi muốn biết tương đương CLI của nó. V.v ...

@luchonacho OK, tôi sẽ bắt đầu viết hôm nay, sẽ đăng khi nó sẵn sàng. Nhân tiện, "Hỗ trợ ngôn ngữ" trong Cài đặt không có cli tương đương với chính nó. Một số điều, như menu bluetooth hoặc menu nền, thực hiện - bạn có thể chỉ định unity-control-center backgroundhoặc gnome-control-center background(tùy thuộc vào máy tính để bàn của bạn, Unity hoặc XFCE hoặc Gnome). Nhưng thế giới bên ngoài có lẽ sẽ chỉ nhìn thấygnome-control-center
Sergiy Kolodyazhnyy

Có rất nhiều, rất nhiều cách để tìm ra nhiệm vụ nào được thực hiện bởi các ứng dụng GUI và tìm hiểu xem cli của chúng là gì. Tôi có vẻ khá kém hiệu quả khi cố gắng ghi lại một cách mù quáng mọi thứ xảy ra bằng vũ lực, chắc chắn rằng bạn sẽ không bắt được tất cả. Tìm hiểu tốt hơn trong các trường hợp cụ thể, sử dụng các công cụ cụ thể.
Jacob Vlijm

Câu trả lời:


2

Giới thiệu

Mặc dù không thể ghi nhật ký tất cả các hành động GUI, nhưng những việc như ghi nhật ký lệnh tương ứng với các cửa sổ đang mở có thể được thực hiện. Dưới đây là kịch bản python đơn giản mà thực hiện công việc. Nó vẫn đang được phát triển, nhưng thực hiện 90% nhiệm vụ cần thiết.

Mã nguồn

#!/usr/bin/env python3
import gi
gi.require_version('Gtk', '3.0')
gi.require_version('Gdk', '3.0')
from gi.repository import Gdk,Gtk
import time
import os
import subprocess

def run_cmd(cmdlist):
    """ Reusable function for running external commands """
    new_env = dict(os.environ)
    new_env['LC_ALL'] = 'C'
    try:
        stdout = subprocess.check_output(cmdlist, env=new_env)
    except subprocess.CalledProcessError:
        pass
    else:
        if stdout:
            return stdout
def print_info(stack,event):
    base_xprop = ['xprop','-notype']
    for xid in stack:
        pid = None
        check_pid = run_cmd(base_xprop + [ '_NET_WM_PID', '-id',str(xid)])
        if check_pid:
            pid = check_pid.decode().split('=')[1].strip()
        with open('/proc/'+pid+'/cmdline') as fd:
            command = fd.read()
        print(time.strftime("%D %H:%M:%S" + " "*3) + event + pid + " " + command)

def main():
    sc = Gdk.Screen.get_default()
    old_stack = None

    while True:
        stack = [ win.get_xid() for win in sc.get_window_stack() ]
        if old_stack:
            # Difference between current and old stack will show new programs
            diff = set(stack) - set(old_stack)
            if diff:
                print_info(diff," 'New window open' ")
        else:
            print_info(stack," 'Script Started' ")

        old_stack = stack
        time.sleep(2)

if __name__ == '__main__': main()

Chạy thử nghiệm:

$ ./log_open_windows.py                                                                                                
01/25/17 15:33:13    'Script Started' 2915 nautilus-n
01/25/17 15:33:13    'Script Started' 3408 /opt/google/chrome/chrome
01/25/17 15:33:13    'Script Started' 12540 /usr/bin/python/usr/bin/x-terminal-emulator
01/25/17 15:33:13    'Script Started' 2454 compiz
01/25/17 15:33:13    'Script Started' 2454 compiz
01/25/17 15:33:13    'Script Started' 2454 compiz
01/25/17 15:33:13    'Script Started' 2454 compiz
01/25/17 15:33:13    'Script Started' 2454 compiz
01/25/17 15:33:21    'New window open' 15143 /usr/lib/firefox/firefox-new-window
01/25/17 15:33:27    'New window open' 15196 unity-control-center

Kịch bản hiển thị dấu thời gian, loại sự kiện, cửa sổ PID và lệnh tương ứng.

Cách sử dụng

Các quy tắc tiêu chuẩn của bất kỳ kịch bản áp dụng. Hãy chắc chắn rằng bạn lưu trữ tập lệnh trong ~/binthư mục. Nếu bạn không có ~/binthư mục, hãy tạo một thư mục. Lưu tập tin tập lệnh ở đó và đảm bảo nó được thực thi với chmod +x ~/bin/log_open_windows.py. Sau đó, bạn có thể chạy nó từ dòng lệnh bất cứ lúc nào bạn muốn bằng cách gọi ~/log_open_windows.pytrong dòng lệnh.


Cảm ơn. Trông đầy hứa hẹn! Hai câu hỏi. Làm thế nào để chạy nó? 10% còn thiếu là gì?

Tiện lợi! +1 từ tôi!
Fabby

@luchonacho Tôi đã thêm một đoạn về cách sử dụng. Tôi khuyên bạn nên sử dụng nó thủ công từ dòng lệnh như tôi đã mô tả. Bạn có thể làm cho nó khởi động tự động khi khởi động, nhưng tôi không khuyên bạn nên làm điều đó. 10% còn thiếu là một vài tính năng khác mà tôi muốn thêm, nhưng tôi không nghĩ mình sẽ thêm chúng. Nó hoạt động đủ tốt cho bây giờ. Nhưng có lẽ tôi sẽ thay đổi suy nghĩ của mình một lần nữa
Sergiy Kolodyazhnyy

Đây có lẽ là thứ gần nhất mà bạn có thể có được với những gì tôi đang tìm kiếm, biết rằng giải pháp hoàn hảo không tồn tại. Cảm ơn!

4

Đề xuất rằng tệp nhật ký loại làm cơ sở cho việc học thực sự là một ý tưởng tuyệt vời!

Thật không may, nhiều hành động của các chương trình GUI được thực hiện trong chính chương trình, không sử dụng các lệnh bên ngoài; Và ngay cả khi nó sử dụng các lệnh bên ngoài, nó có thể theo một cách khác với cách người ta thực hiện nó trong một vỏ;
Vì vậy, điều đó không tồn tại, và không dễ thực hiện.

Nhưng tôi có một giải pháp cho một phần của vấn đề: Tên chương trình trong GUI đôi khi khác với tên chương trình mà người ta cần biết cho lệnh shell - không chỉ khi tên GUI được dịch sang ngôn ngữ địa phương.

Ví dụ, làm thế nào để bắt đầu chương trình Filestrong dòng comman?

Chúng ta cần xem xét tất cả *.desktopcác tập tin cho tên. Ở đó, chúng tôi tìm thấy lệnh trong Execdòng:

locate -b '.desktop' | xargs grep -ls '^Name.*=Files$' | xargs grep '^Exec.*'

liệt kê các tên và lệnh của tệp máy tính để bàn cho chương trình GUI File- thay thế tên đó bằng tên chính xác mà bạn tìm kiếm - ngay cả khi đó là nhiều từ (để tìm kiếm chuỗi con, hãy bỏ qua =$).

Với lệnh, tôi tìm thấy Filescó thể nautilus, dolphinhoặc active-filebrowser:

/etc/xdg/autostart/nautilus-autostart.desktop:Exec=nautilus -n
/usr/share/app-install/desktop/nemo:nemo.desktop:Exec=nemo %U
/usr/share/app-install/desktop/plasma-active:kde4__active-filebrowser.desktop:Exec=active-filebrowser -graphicssystem raster %u
/usr/share/applications/nautilus-folder-handler.desktop:Exec=nautilus %U
/usr/share/applications/nautilus.desktop:Exec=nautilus --new-window %U
/usr/share/applications/nautilus.desktop:Exec=nautilus --new-window

Mmm, câu hỏi của tôi làm cơ sở cho quan điểm về độ phức tạp của linux, trong đó các chương trình phức tạp hơn được xây dựng dựa trên mã đơn giản hơn, vì vậy tôi nghĩ rằng bất kỳ ứng dụng GUI nào đều dựa vào các lệnh đầu cuối nhưng có thể không phải là trường hợp vì thiết bị đầu cuối dựa trên mã bash trong khi phần mềm có thể được viết bằng python hoặc c ++ hoặc vv Tôi có sai không?

Các lớp phức tạp tồn tại, nhưng theo một cách khác: thực tế, có các cuộc gọi hệ thống, chức năng thư viện và trên đầu là giao diện người dùng đồ họa hoặc giao diện dòng lệnh - chúng là các lựa chọn thay thế.
Volker Siegel
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.