Если вы не контролируете источник для запускаемой программы, одна из возможностей состоит в том, чтобы иметь другой скрипт, выполняемый как запланированное задание, которое выключает программу , перемещает файл журнала и перезапускает программу. Запланируйте это где-нибудь около полуночи.
Если вы не можете периодически выключайте программу, другая возможность - разработать программу фильтра, которая будет принимать стандартный ввод и отправить его в файл журнала на основе сегодняшней даты. Эта программа может определять изменения даты и закрывать/открывать файл, когда он пересекает границу полуночи.
Затем пропустите выход вашей исходной программы через этот фильтр. Кстати, это правда. То, что вы сейчас делаете, не связано с техническими связями, а перенаправляется (переходы идут в процесс, перенаправление переходит к файлу).
псевдокод будет что-то вроде:
lastDate = ""
currFile = null
while not end of file on standard input:
get line from standard input
currDate = getDate()
if currDate not equal to lastDate:
if currFile not null:
close currFile
currFile = open("prefix_"+currDate+".log")
write line to currFile
if currFile not null:
close currFile
exit
Как доказательство концепции, вот скрипт (qqtest.sh
), который работает, генерируя дата истечения каждые тринадцать секунд, десять раз:
#!/usr/bin/bash
for i in 0 1 2 3 4 5 6 7 8 9 ; do
echo $i $(date)
sleep 13
done
И вот программа фильтра C (qq.c
), которая делает то, что я опишу в своем ответе выше:
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <time.h>
static char *getDate (void) {
static char tbuff[sizeof("yyyymmddhhmm")]; // "yyyymmdd" for date.
time_t now = time (0);
struct tm *tm = localtime (&now);
strftime (tbuff, 100, "%Y%m%d%H%M", tm); // "%Y%m%d" for date.
return tbuff;
}
int main (void) {
int ch, lastCh = '\n';
FILE *fOut = NULL;
char *currDate, *lastDate = strdup ("");
char fspec[1000];
// Just process characters until finished.
while ((ch = fgetc (stdin)) != EOF) {
// Only switch logs if first character of a line.
if (lastCh == '\n') {
// Has date changed?
currDate = getDate();
if (strcmp (currDate, lastDate) != 0) {
// Yes, close old file if there was one.
if (fOut != NULL)
fclose (fOut);
// Then store new date and open new file.
free (lastDate);
lastDate = strdup (currDate);
sprintf (fspec, "qqfile_%s.log", lastDate);
fOut = fopen (fspec, "w");
}
}
// Output character to current file then save.
fputc (ch, fOut);
lastCh = ch;
}
// Clean up memory and file handles, then exit.
free (lastDate);
if (fOut != NULL)
fclose (fOut);
return 0;
}
При выполнении:
./qqtest.sh | ./qq
создает следующие файлы.
$ cat qqfile_201005211146.log
0 Fri May 21 11:46:40 WAST 2010
1 Fri May 21 11:46:53 WAST 2010
$ cat qqfile_201005211147.log
2 Fri May 21 11:47:06 WAST 2010
3 Fri May 21 11:47:19 WAST 2010
4 Fri May 21 11:47:33 WAST 2010
5 Fri May 21 11:47:46 WAST 2010
6 Fri May 21 11:47:59 WAST 2010
$ cat qqfile_201005211148.log
7 Fri May 21 11:48:12 WAST 2010
8 Fri May 21 11:48:25 WAST 2010
9 Fri May 21 11:48:38 WAST 2010
Обратите внимание, что для переключения файлов журнала используется минутная граница. Просто изменить функцию getDate
для использования границы дня (см. Комментарии).