sed question

Hi,

I am trying to write a script which will do the following:

  1. edit the cron entries for specific scripts.
  2. comment out the cron entries
  3. make them out of schedule.
  4. do some other operation.
  5. remove the comments from crontab.
  6. reschedule the scripts.

I believe we can use 'sed' statement to do this entire operation in one line, but i am a beginner in sed.

Please let me know if you have any ideas on this.

-Sam

Please provide Input datafiles and expected output.

Anurag,

My crontab looks like this.

0-59 * * * * /dev1/scripts/check_proc.sh >> /tmp/check_infa_proc_cron.log 2>&1
0-59 * * * * /dev1/scripts/check_cores.sh >> /tmp/check_cores_cron.log 2>&1
0-59 * * * * /dev1/scripts/check_repo_conn.sh >> /tmp/check_repo_conn_cron.log 2>&1
0-59 * * * * /dev1/scripts/check_num_proc.sh >> /tmp/check_num_proc_cron.log 2>&1
0-59 * * * * /dev1/admin/check_pc.ksh >> /tmp/check_powercenter_cron.log 2>&1

There may be other cron entries in the file. But I want to comment out only those entries specific to my project.

for example, the last cron entry is not specific to our project.

0-59 * * * * /dev1/admin/check_pc.ksh >> /tmp/check_powercenter_cron.log 2>&1

Thanks,
Sam

You can't possibly do all that in a "one-liner".

Where is your script up to now?

I am not sure if this will work or not, but this is how I wrote the script.

#!/bin/ksh

. /home/.profile

. /home/.inf_env

scripts_path=/dev1/scripts

crontab -l > cronfile.txt

sed 's/[$script_path]/^#/gpw' cronfile.txt

To do some action on some specific lines, some pattern has to be identified for them. Say we want to comment all lines where "pc" is a substring of script name, then:

sed '/pc/ s!.*!#&!' cron_file

Still your overall requirements are not clear. Input file is known but you need multiple processing on that file. You need to mention everything you need to do on that file along with complete expected output.

Thanks for your input.

my requirement is.

get the crontab entries from the crontab command and create a tempfile.

crontab -l > cronfile.txt

Now the cronfile looks like this.

0-59 * * * * /dev1/scripts/check_proc.sh >> /tmp/check_infa_proc_cron.log 2>&1
0-59 * * * * /dev1/scripts/check_cores.sh >> /tmp/check_cores_cron.log 2>&1
0-59 * * * * /dev1/scripts/check_repo_conn.sh >> /tmp/check_repo_conn_cron.log 2>&1
0-59 * * * * /dev1/scripts/check_num_proc.sh >> /tmp/check_num_proc_cron.log 2>&1
0-59 * * * * /dev1/scripts/check_pc.ksh >> /tmp/check_powercenter_cron.log 2>&1
0-59 * * * 7 /dev1/admin/scripts/check_users.ksh /tmp/check_users.log 2>&1

update the cronfile.txt by commenting all the entries where the script path is /dev1/scripts/

#0-59 * * * * /dev1/scripts/check_proc.sh >> /tmp/check_infa_proc_cron.log 2>&1
#0-59 * * * * /dev1/scripts/check_cores.sh >> /tmp/check_cores_cron.log 2>&1
#0-59 * * * * /dev1/scripts/check_repo_conn.sh >> /tmp/check_repo_conn_cron.log 2>&1
#0-59 * * * * /dev1/scripts/check_num_proc.sh >> /tmp/check_num_proc_cron.log 2>&1
#0-59 * * * * /dev1/scripts/check_pc.ksh >> /tmp/check_powercenter_cron.log 2>&1
0-59 * * * 7 /dev1/admin/scripts/check_users.ksh /tmp/check_users.log 2>&1

now execute the cronfile.txt using crontab command.

crontab cronfile.txt

Hope this is clear now.

OK, so here you have only one requirement. In my previous post, I was talking about many more processing on crontab files mentioned in post #1.
if -i switch is supported:

sed -i 's!.*\/dev1\/scripts\/.*!#&!' cronfile.txt

If not:

sed 's!.*\/dev1\/scripts\/.*!#&!' cronfile.txt > temp; mv temp cronfile.txt
2 Likes

OK. Great.

Can I use a variable which contains the path in it and use it in sed statement, rather than hard coding it?

for example,

export script_path=/dev1/scripts
$echo $script_path
/dev1/scripts
sed "s|.*${script_path}.*|#&|" cronfile.txt > cronfile.new 
1 Like

Hi Anurag,

I am a newbie to this scripting. can you please explain me what "s!.*!#&!" does in the code you have written above.

i really appreciate your solutions to users queries.
Thanks in advance.

---------- Post updated at 03:47 PM ---------- Previous update was at 03:46 PM ----------

can you please explain this. I am a newbie

@Scrutinizer - Your solution commenting out all the entries in cron file which i do not want to do. I want to comment only the entries matching the value in $script_path which is /dev1/scripts/

#!/bin/ksh

. /home/.profile

crontab -l > temp

sed "s|.*${script_path}.*|#&|" temp > cronfile.txt
ussbazudb129[infrep9d]:/info_d16/PC_Intg_Svc_01/Scripts/Admin_Utils>cat cronfile.txt
#0-59 * * * * /dev1/scripts/check_proc.sh >> /tmp/check_infa_proc_cron.log 2>&1
#0-59 * * * * /dev1/scripts/check_cores.sh >> /tmp/check_cores_cron.log 2>&1
#0-59 * * * * /dev1/scripts/check_repo_conn.sh >> /tmp/check_repo_conn_cron.log 2>&1
#0-59 * * * * /dev1/scripts/check_num_proc.sh >> /tmp/check_num_proc_cron.log 2>&1
#0-59 * * * * /dev1/scripts/check_pc.ksh >> /tmp/check_powercenter_cron.log 2>&1
#0-59 * * * 7 /dev1/admin/scripts/check_users.ksh /tmp/check_users.log 2>&1

Don't forget to set the variable $script_path first..

---------- Post updated at 22:02 ---------- Previous update was at 21:51 ----------

Sure, with the substitution operator s you can use any character (except backslash and newline ) as a delimiter so instead of / I used | .
The pattern to match is .*${script_path}.* which matches the whole line if the contents of $script_path are part of the line. If the latter is the case then it gets replaced by a # , followed by the line that was matched ( & ) . Everything is in double quotes so that variables get expanded by the shell.

I hope I explained it clearly?

2 Likes

Yes I am doing that prior to the execution of sed statement.

. /home/.profile
$cat .profile
export scripts_path=/dev1/scripts

See the variable name in your command..
${script_path}
it's different than the one you exported (scripts_path).Correct the variable name in sed command.

$script_path not $scripts_path

Yes thats my bad. Thanks much.

---------- Post updated at 04:16 PM ---------- Previous update was at 04:08 PM ----------

@Anurag, scrutinizer,

I also need to remove the comment from the entries after some operation. Probably i am going to use another script for this. Can you guide me on this?

i think i can use 'd' option to remove the comments. but not sure how to do it.

sed -e 's/#.*//'

but i guess this will remove the '#' from all other entries which someone might have commented out. Can you let me know how to remove the comments for the entries which i commented out?

sed "s|^#\(.*${script_path}.*\)|\1|" infile