• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1#!/bin/sh
2
3# Copyright (c) International Business Machines Corp., 2001
4# Copyright (c) 2017 Petr Vorel <pvorel@suse.cz>
5#
6# This program is free software; you can redistribute it and/or
7# modify it under the terms of the GNU General Public License as
8# published by the Free Software Foundation; either version 2 of
9# the License, or (at your option) any later version.
10#
11# This program is distributed in the hope that it would be useful,
12# but WITHOUT ANY WARRANTY; without even the implied warranty of
13# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14# GNU General Public License for more details.
15#
16# You should have received a copy of the GNU General Public License
17# along with this program; if not, write the Free Software Foundation,
18# Inc.,  51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
19#
20# Author: Manoj Iyer <manjo@mail.utexas.edu>
21
22TST_ID="cron_tests01"
23TST_CNT=3
24TST_TESTFUNC=do_test
25TST_NEEDS_TMPDIR=1
26TST_SETUP=setup
27TST_CLEANUP=cleanup
28. tst_test.sh
29
30. daemonlib.sh
31
32SYSLOG_STARTED=
33CROND_STARTED=
34LOGS=
35
36grep_logs()
37{
38	local pattern="$1"
39	local fail_msg="$2"
40	local pass_msg="${3:-}"
41	local n="${4:-10}"
42
43	local lines=10
44	local out=out.$$
45	local err=err.$$
46	local i ret
47
48	for i in $(seq 1 $n); do
49		if [ "$LOGS" ]; then
50			tail -n $lines $LOGS | grep "$pattern" > $out 2> $err
51		else
52			journalctl -n $lines | grep "$pattern" > $out 2> $err
53		fi
54		ret=$?
55		[ $ret -eq 0 ] && break
56		sleep 1
57	done
58
59	if [ $ret -ne 0 ]; then
60		tst_res TFAIL "$fail_msg: `cat $err`"
61	else
62		[ "$pass_msg" ] && tst_res TPASS "$pass_msg"
63	fi
64}
65
66create_crontab()
67{
68	local crontab=cronjob.cron
69	local script=$1
70	local out=out.$$
71
72	tst_res TINFO "creating crontab: $script"
73
74	cat > $crontab <<EOF
75* * * * * $script
76EOF
77
78	tst_res TINFO "installing crontab file"
79	crontab $crontab > $out 2>&1
80	if [ $? -ne 0 ]; then
81		tst_brk TBROK "crontab: error while installing crontab file: `cat $out`"
82		return 1
83	fi
84	return 0
85}
86
87remove_crontab()
88{
89	local out=out.$$
90	tst_res TINFO "removing crontab file"
91	crontab -r > $out 2>&1
92	if [ $? -ne 0 ]; then
93		tst_brk TBROK "crontab: error while removing crontab file `cat $out`"
94		return 1
95	fi
96	return 0
97}
98
99create_hello_script()
100{
101	local script=$1
102
103	cat > $script <<EOF
104#!/bin/sh
105echo "Hello Hell"
106exit 0
107EOF
108	chmod +x $script
109}
110
111install_cron_test()
112{
113	local script=$PWD/cronprg.sh
114	local cron_out=$PWD/tst1_cron.out
115	local err=err.log
116	local sleep_sec
117	local ts_min1 ts_min2 fail
118
119	tst_res TINFO "test install cron job"
120
121	cat > $script <<EOF
122#! /bin/sh
123DATE=\`LC_ALL=C date\`
124echo "Hello Hell today is \$DATE" > $cron_out 2>&1
125exit 0
126EOF
127	chmod +x $script
128
129	create_crontab $script 2> $err
130
131	if [ $? -ne 0 ]; then
132		tst_brk TBROK "crontab: error while creating cron job: `cat $err`"
133	else
134		tst_res TINFO "cron job installed successfully"
135	fi
136
137	grep_logs 'crontab.*REPLACE' \
138		"cron activity not recorded" \
139		"cron activity logged"
140
141	# Sleep 3s after next minute since the loop below sleeps for 62 seconds, we
142	# should start this 5-iteration loop closely following the start of a
143	# minute.
144	sleep_sec=$((123-`date +%-S`))
145	tst_res TINFO "sleep for ${sleep_sec}s"
146	sleep $sleep_sec
147
148	# $script executed by the cron job will record the date and time into file
149	# $cron_out. Get the minute recorded by the program, sleep to allow the cron
150	# job to update file after 1m, and check if the value is advanced by 1.
151	for i in $(seq 1 5); do
152		tst_res TINFO "loop: $i: start"
153
154		if [ ! -f "$cron_out" ]; then
155			tst_res TFAIL "loop $i: file $cron_out doesn't exist"
156			fail=1
157			break
158		fi
159
160		ts_min1=$(awk '{print $8}' $cron_out | awk -F: '{printf("%d", $2);}')
161
162		# wait for the cron job to update output file
163		sleep 62
164
165		# Check the time recorded in output file, this should be 1 minute ahead of
166		# what was recored earlier.
167		ts_min2=$(awk '{print $8}' $cron_out | awk -F: '{printf("%d", $2);}')
168
169		if [ "x${ts_min1}" = "x" ] || [ "x${ts_min2}" = "x" ]; then
170			tst_res TFAIL "loop $i: failed to get time: ts_min1: $ts_min1, ts_min2: $ts_min2"
171			fail=1
172			break
173		fi
174
175		[ $ts_min1 -eq 59 ] && ts_min1=0 || ts_min1=$(( $ts_min1+1 ))
176
177		if [ $ts_min2 -ne $ts_min1 ]; then
178			tst_res TFAIL "loop $i: failed to update every minute: expected: $ts_min1, received: $ts_min2"
179			fail=1
180			break
181		fi
182	done
183
184	if [ ! "$fail" ]; then
185		grep_logs "CMD ($script)" \
186			"failed to install cron job installed and execute it" \
187			"cron job installed and executed" 1
188	fi
189
190	remove_crontab
191}
192
193remove_cron_job_test()
194{
195	local script=$PWD/cronprg.sh
196
197	tst_res TINFO "test remove cron job"
198
199	create_hello_script $script
200	create_crontab $script
201
202	grep_logs 'crontab.*REPLACE' \
203		"crontab activity not recorded"
204
205	remove_crontab && grep_logs DELETE \
206		"crontab activity not recorded" \
207		"crontab removed the cron job" 1
208}
209
210list_cron_jobs_test()
211{
212	local script=$PWD/cronprg.sh
213	local out=cron.out
214
215	tst_res TINFO "test list installed cron jobs"
216
217	create_hello_script $script
218	create_crontab $script
219
220	tst_res TINFO "crontab: listing cron jobs"
221	crontab -l | grep "$script" > $out 2>&1 || \
222		tst_brk TBROK "crontab failed while listing installed cron jobs: `cat $out`"
223
224	remove_crontab
225
226	crontab -l > $out 2>&1
227	if [ $? -ne 0 ]; then
228		grep -q "no crontab for" $out
229		if [ $? -ne 0 ]; then
230			tst_res TFAIL "crontab failed removing cron job: `cat $out`"
231		else
232			tst_res TPASS "crontab did not list any cron jobs"
233		fi
234	else
235		tst_res TFAIL "crontab failed removing cron job: `cat $out`"
236	fi
237}
238
239setup()
240{
241	if [ "$SYSLOG_DAEMON" ]; then
242		status_daemon $SYSLOG_DAEMON
243		if [ $? -ne 0 ]; then
244			restart_daemon $SYSLOG_DAEMON
245			SYSLOG_STARTED=1
246		fi
247	fi
248
249	if [ "$CROND_DAEMON" ]; then
250		status_daemon $CROND_DAEMON
251		if [ $? -ne 0 ]; then
252			restart_daemon $CROND_DAEMON
253			CROND_STARTED=1
254		fi
255	fi
256
257	for f in /var/log/syslog /var/log/messages /var/log/cron /var/log/cron.log; do
258		[ -f "$f" ] && LOGS="$f $LOGS"
259	done
260}
261
262cleanup()
263{
264	[ "$SYSLOG_STARTED" = "1" ] && stop_daemon $SYSLOG_DAEMON
265	[ "$CROND_STARTED" = "1" ] && stop_daemon $CROND_DAEMON
266}
267
268do_test()
269{
270	case $1 in
271	1) install_cron_test;;
272	2) remove_cron_job_test;;
273	3) list_cron_jobs_test;;
274	esac
275}
276
277tst_run
278