30

I'm running an application that writes to log.txt. The app was updated to a new version, making the supported plugins no longer compatible. It forces an enormous amount of errors into log.txt and does not seem to support writing to a different log file.

How can I write them to a different log?

I've considered replacing log.txt with a hard link (application can't tell the difference right?) Or a hard link that points to /dev/null. What are my options?

migrated from stackoverflow.com Dec 21 '16 at 20:56

This question came from our site for professional and enthusiast programmers.

  • You can't just chmod -w log.txt? – user168715 Dec 28 '16 at 9:55
29
# cp -a /dev/null log.txt

This copies your null device with the right major and minor dev numbers to log.txt so you have another null.

Devices are not known by name at all in the kernel but rather by their major and minor numbers. Since I don't know what OS you have I found it convenient to just copy the numbers from where we already know they are. If you make it with the wrong major and minor numbers, you would most likely have made some other device, perhaps a disk or something else you don't want writing to.

  • 4
    It is worth noting that this command requires sudo (or running as the root user). Please explain (in your answer) what you mean by "the right major and minor dev numbers". – mklement0 Dec 21 '16 at 3:40
  • 3
    (I'm not the OP.) I appreciate the update, but I'm still confused about how "major and minor numbers" relate to file path /dev/null, as used in your command. And, I think it would help future readers to note in your answer that sudo is required. – mklement0 Dec 21 '16 at 4:07
  • 1
    @wallyk: Thanks, that's indeed good to know. But my point is: How does come into play with respect to cp -a /dev/null log.txt and my comments? – mklement0 Dec 21 '16 at 4:17
  • 1
    @MALON: Indeed you did, and on Ubuntu 14.04 you do need sudo to perform this command, unless you happen to be running as user root (which is generally discouraged). Using sudo (or running as root) to create a hard link (this answer) or a symlink (@V.Michel's answer) may be the right solution after all, if the file must be placed in a location that any user account can write to, but the point is: do note that requirement explicitly. – mklement0 Dec 21 '16 at 4:34
  • 1
    P.S.: I know see that the major, minor comments probably relate to a comment on the question recommending use of mknod. Do note that comments generally receive little attention, so someone reading the question only and then your answer may be confused (as was I; also note that most people are never exposed to concepts such as major and minor device numbers). – mklement0 Dec 21 '16 at 4:58
64

You can make a symbolic link to /dev/null and you don't need to be root:

ln -s /dev/null log.txt
  • This also has the advantage of being self-documenting, in that ls -l log.txt would show that it's a symlink to /dev/null, rather than relying on knowing that e.g. "1, 3" is somehow significant. – Monty Harder Dec 21 '16 at 19:18
14

The other answers here will probably work. In particular, the symlink solution is probably going to be the easiest solution. I offer this mainly for completeness.

The solutions involing mknod (or cp -a) become problematic if the filesystem containing the file doesn't support devices (e.g., it was mounted with the nodev option, for example). And of course, hard links across filesystems simply won't work.

An alternative to hard links or creating new devices nodes is to use bind mounts, which let you mount a file or directory from one part of your filesystem tree onto another. So, for example, you can run:

mount -o bind /dev/null /path/to/log.txt

This acts a lot like a hard link, but:

  • It can operate across filesystems (because it's not based on filesystem inodes like a hard link)
  • It works on read-only filesystems (because you're not actually modifying the filesystem)

For a complete example:

bash-4.3# ls -l /var/log/boot.log
-rw-r--r--. 1 root root 7436 Dec 19 10:00 /var/log/boot.log
bash-4.3# mount -o bind /dev/null /var/log/boot.log
bash-4.3# ls -l /var/log/boot.log
crw-rw-rw-. 1 root root 1, 3 Dec 19 09:58 /var/log/boot.log
bash-4.3# echo words words words > /var/log/boot.log
bash-4.3# ls -l /var/log/boot.log
crw-rw-rw-. 1 root root 1, 3 Dec 19 09:58 /var/log/boot.log
  • But it only works on systems that have a bind mount. (Such as modern Linux.) – reinierpost Dec 21 '16 at 9:59
  • A log file wouldn't belong in a read-only filesystem anyway. – Monty Harder Dec 21 '16 at 19:20
  • 1
    You would be surprised how often you find yourself wanting to write to a single file on a read-only filesystem. And it may very well be on a nodev filesystem. – larsks Dec 21 '16 at 20:00
6

It depends critically on HOW the application handles log.txt.

If the application just opens the existing file and writes to it then as described in other answers you can symlink it to /dev/null, symlink it somewhere else, hardlink it somewhere else (though hardlinks can't be cross filesystem so there isn't a lot of point in this) create a copy of the /dev/null device node there etc.

OTOH if the application deletes and recreates log.txt none of that will work. You could symlink the whole directory somewhere else to redirect the writes to a different filesystem but thats about it and you would have to deal with other stuff in the directory.

I guess if you really wanted you could create a custom overlay filesystem that passed most operations right through while throwing away any attempts to create a file called log.txt.

  • chattr +i log.txt the first time and the application won’t delete the file anymore. – Marco Marsala Jan 16 at 16:52
3

Well, one ungraceful method with named pipe:

# create a named pipe
mkfifo /path/to/log.txt
# read contents from the pipe and redirect them to /dev/null
cat /path/to/log.txt > /dev/null

you almost can do anything with the dumped log, such as filter or send over nc.

  • If cat process is killed or crash, the login program will hang when the pipe is full. – Marco Marsala Jan 22 at 14:47
1

Consider making the file an actual null device. A file "log.txt" created with mknod, with the right file type and same minor and major numbers, will act as a null device because it is.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.