How to convert to / get RFC822 date in bash/linux? - linux

Looking at date's man page, I couldn't find a standard way to convert to rfc822 (eg: from unix timestamp). I took a brief look at the spec, but I don't know enough about the subject matter to get the format right. Is there a easy way to convert to rfc822 with standard linux terminal tools?

According to man 1 date:
-R, --rfc-email
output date and time in RFC 5322 format.
Example: Mon, 14 Aug 2006 02:34:56 -0600
And it looks like RFC5322:
[...] is a revision of Request For Comments (RFC) 2822, which itself superseded
Request For Comments (RFC) 822 [...]
Short answer use date -R (and -d #<unix> for the unix timestamp). For example, in my machine just now:
$ date -R
Mon, 11 Sep 2017 20:41:30 +0200
$ date -R -d #1505155314
Mon, 11 Sep 2017 20:41:54 +0200

Related

Convert GMT timestamp to local time using Bash and GNU tools

I am getting results to a log file that contain a line like this:
date: Sat, 12 Dec 2020 22:33:34 GMT
I want to use only Bash and GNU tools on my Ubuntu Linux box if possible to convert this to my local time "Eastern" or Michigan/Detroit. It should work even on Daylight Saving Time or if past/before Midnight. I want the result stored in a variable in a common format such as 2020-12-01 for December 1, 2020. One variable for the military time, a second for the date would probably be best. I can calculate the "Sat/Sun/Mon/etc" and probably don't need that anyway.
I would expect the "cut" command could separate out the different fields, but how to deal with GMT?
#!/bin/bash
datime="date: Sat, 12 Dec 2020 22:33:34 GMT"
#magic happens
echo dalocaltime is $dalocaltime and dalocaldate is $dalocaldate
results:
dalocaltime is 14:20:33 and dalocaldate is 2020-01-30
This works for me, but I can't explain the ${datime#* } part
datime="date: Sat, 12 Dec 2020 22:33:34 GMT"
dalocaltime=$(date -d "${datime#* }" '+%R')
dalocaldate=$(date -d "${datime#* }" '+%Y-%m-%d')
echo dalocaltime is $dalocaltime and dalocaldate is $dalocaldate

How to parse timezone with date

How do we get the date utility to parse the timezone strings?
$>date -d "2018-02-21T02:22:33.221" "+%Y-%m-%dT%H:%M:%S.%3N %Z"
2018-02-20T14:22:33.221 EST
But
$>date -d "2018-02-21T02:22:33.221 EST" "+%Y-%m-%dT%H:%M:%S.%3N %Z"
date: invalid date `2018-02-21T02:22:33.221 EST'
This the local info:
$>uname -r
2.6.32-696.13.2.el6.x86_64
$>date
Tue Jan 16 09:58:52 EST 2018
$>date --version
date (GNU coreutils) 8.4
Copyright (C) 2010 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>.
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.
Written by David MacKenzie.
ISO8601 allows you to replace T with space. Just do it, and your command will work fine:
# date -d "2018-02-21T02:22:33.221 EST" "+%Y-%m-%dT%H:%M:%S.%3N %Z"
date: invalid date `2018-02-21T02:22:33.221 EST'
but:
# date -d "2018-02-21 02:22:33.221 EST" "+%Y-%m-%d %H:%M:%S.%3N %Z"
2018-02-21 10:22:33.221 MSK
date -d is not the reverse of date +format, it can only accept some string from man date
-d, --date=STRING
display time described by STRING, not `now'
DATE STRING
The --date=STRING is a mostly free format human readable date string such as "Sun, 29 Feb 2004 16:21:42 -0800" or
"2004-02-29 16:21:42" or even "next Thursday". A date string may contain items indicating calendar date, time of day,
time zone, day of week, relative time, relative date, and numbers. An empty string indicates the beginning of the day.
The date string format is more complex than is easily documented here but is fully described in the info documentation.

Getting specific part of output in Linux

I have an output from a shell script like this:
aaa.sh output
Tue Mar 04 01:00:53 2014
Time drift detected. Please check VKTM trace file for more details.
Tue Mar 04 07:21:52 2014
Time drift detected. Please check VKTM trace file for more details.
Tue Mar 04 13:17:16 2014
Time drift detected. Please check VKTM trace file for more details.
Tue Mar 04 16:56:01 2014
SQL> ALTER DISKGROUP fra ADD DISK '/dev/rhdisk20'
Wed Mar 05 00:03:42 2014
Time drift detected. Please check VKTM trace file for more details.
Wed Mar 05 04:13:39 2014
Time drift detected. Please check VKTM trace file for more details.
Tue Mar 05 05:56:07 2014
GMON querying group 3 at 10 for pid 18, osid 27590856
GMON querying group 3 at 11 for pid 18, osid 27590856
I need to get the part, beginning from today's date:
Wed Mar 05 00:03:42 2014
Time drift detected. Please check VKTM trace file for more details.
Wed Mar 05 04:13:39 2014
Time drift detected. Please check VKTM trace file for more details.
Tue Mar 05 05:56:07 2014
GMON querying group 3 at 10 for pid 18, osid 27590856
GMON querying group 3 at 11 for pid 18, osid 27590856
You can get the date in the correct format like this:
today=$(date +'%a %b %d')
and then search for it like this:
grep "$today" aaa.sh
If there are lines from today without a date, such as your GMON lines, you could add -A to say how many lines after the match you want and use a big number:
grep -A 999999 "$today" aaa.sh
If you are on AIX and there is no -A option, use sed like this:
today=$(date +'%a %b %d')
sed -n "/${today}/,$ p" aaa.sh
Explanation:
That says store today's date in the variable today in the format "Wed Mar 05". Then search, without printing anything (-n) till you find that date, From that point on, till the end of file ($) print all lines (p).
I think I have an easy solution:
Get date to output the date in a format that would match the date in the file (check man date on formatting options). Since we don't want to match the hours/minutes/seconds we have to call date twice: once for the weekday/month/day half and once for the year half on the end of the full date. Between these two halves we match the horus/minutes/seconds with .* regex.
Then do:
aaa.sh | grep -E '`date --only-weekday-month-day`.*`date --only-year`' -A 999999
though I am using answer by NewWorld it can be modified as,
convert output of date similar to your file format
suppose in variable 'D'you get that output
sed '1,/${D}/d' aaa.sh
that will output all lines after match date match.
example: suppose you get D="Wed Mar 05 00:03:42 2014"
output will be as expected.
You can use
tail -n 7 filename
for getting the desired output . It will basically give you the last seven lines of the text file named filename .
For getting solution from today's date you can use :
k=$(date +"%a %b %d")
g=$(grep -nr "$k" in|cut -f1 -d:|head -1)
total=$(wc -l<in)
l=`expr $total - $g + 1
tail -n$l in
Try
sed -n '/Wed Mar 05/,$p' aaa.sh
Here -n means "don't print anything unless specified to".
First appearance of a line that matches the expression /Wed\ Mar\ 05/ till the end of the file, will be printed(p)"

How to remove terminal control escape sequences in the file?

I got a log from remote linux computer. It looks like:
2013-10-23T08:19:05+0300 Last login: Wed Oct 23 08:17:38 EEST 2013 from 10.9.167.55 on pts/0
2013-10-23T08:19:05+0300 Last login: Wed Oct 23 08:19:05 2013 from 10.9.167.55^M
2013-10-23T08:19:07+0300 ^[[?1034h-bash-4.1$ date
2013-10-23T08:19:07+0300 Wed Oct 23 08:19:07 EEST 2013
2013-10-23T08:19:08+0300 -bash-4.1$ ls
2013-10-23T08:19:08+0300 ^[[0m^[[01;34m99^[[0m #avail.info ^[[01;34mgmoTemp^[[0m raml21.dtd SNMP4JTestAgentBC.cfg
2013-10-23T08:19:08+0300 an_mainHost_localhost_20131023081654000136.xml #avail.info~ gsh.txt ^[[01;34mresults^[[0m
2013-10-23T08:19:09+0300 ^[[m-bash-4.1$ exit
2013-10-23T08:19:09+0300 logout
But it should be:
Last login: Wed Oct 23 08:17:38 EEST 2013 from 10.9.167.55 on pts/0
Last login: Wed Oct 23 08:19:05 2013 from 10.9.167.55
-bash-4.1$ date
Wed Oct 23 08:19:07 EEST 2013
-bash-4.1$ ls
99 #avail.info gmoTemp raml21.dtd SNMP4JTestAgentBC.cfg
an_mainHost_localhost_20131023081654000136.xml #avail.info~ gsh.txt results
-bash-4.1$ exit
logout
The messy codes are terminal control escape sequences, you can use command "infocmp xterm" and "man terminfo" to get more details.
My question is how can I remove these terminal control escape sequences in the file?
Thanks a lot!
Simple way to remove most parts of the control character is using the command below in vim:
:%s/<escape-key>\[[0-9;]*m/ /g
Press Ctrl+V followed by esc-key for the <escape-key> character above. Everything else is the same literal key as in your keyboard.
i use a pipe or direct sed like this
sed 's/[^[:print:]]\[[^a-zA-Z]*[a-zA-Z]//g' YourFile
I solved this issue using lots of regular expressions according to http://invisible-island.net/xterm/ctlseqs/ctlseqs.html

one week information of alertlofile

I want to view the ORA errors in alertlogfile of past 7 (monday-sunday)days,
by writting in shell scripts.
Can anybody help me.
Thanks
Something like:
sed -n -e '/start_time/,/end_time/ {/ORA/ p}' logfile
or with awk
$ start="Fri Feb 27 08:00:00 2009"
$ end="Fri Mar 6 08:00:00 2009"
$ awk -v prev="$start" -v last="$end" '$0 ~ prev,$0 ~ last' logfile
A more sophisticated script looking for last date entries in ORA file is available here, but also at dba-oracle.com
This does not answer exactly your request but might give you some clues to start your own script.
I want the scripts which give output as follows (one week errors) and it should be mail to my id.
Sat Mar 14 10:30:51 IST 2009
ORA-01157: cannot identify/lock data file 2 - see DBWR trace file
Sat Mar 12 12:35:06 IST 2009
ORA-01110: data file 2: '/u02/oradata/Globe/undotbs01.dbf'
Sat Mar 10 09:54:05 IST 2009
ORA-27037: unable to obtain file status
Sat Mar 08 :15:02 IST 2009
ORA-1157 signalled during: ALTER DATABASE OPEN...
Sat Mar 07 12:35:51 IST 2009
ORA-01157: cannot identify/lock data file 2 - see DBWR trace file

Resources