replace using sed - linux

I want to replace IP dynamically but somehwo sed is placing word $IP instead of actual value.
IP=10.50.33.44
PORT=5774
sed -i~ 's/https:\/\/10.11.12.13:8443/https:\/\/$IP:$PORT/g' abc.txt
Can you help me out in getting the correct value?

Use double quotes" for variable expansion:
sed -i~ "s/https:\/\/10.11.12.13:8443/https:\/\/$IP:$PORT/g" abc.txt
and as #Joachim said, use different delimiter. For example,
sed -i~ "s;https://10.11.12.13:8443;https://$IP:$PORT;g" abc.txt

Variation on a theme: I always use single quotes to surround sed/awk/perl... commands as the shell can sometimes trip you up when using double quotes.
I find it best to double quote the variables:
sed -i~ 's/https:\/\/10.11.12.13:8443/https:\/\/'"$IP"':'"$PORT"'/g' abc.txt
As a "belt and braces" and as I usually compose my commands interactively at the command line in bash, the key-binding M-C-e (that's Alt-Control-e on most keyboards) will interpolate the command before it's sent. Letting you visually see what the command is really getting.

Related

How to use variables in linux regex pattern?

I need to execute a sed command with pattern /^03.06.2014/ in a .sh script & command line. The date is a variable not a constant. How could i implement this? When I use a variable inside a regex pattern, the command breaks. Do I need to escape something here? Any help is appreciated. Thanks!
date=$(date +%m.%d.%Y)
sed -n '/^$date/,$p' filename
Use double quotes for variable expansion in sed
sed -n "/^$date/,\$p" filename
You need to use double quotes to allow for shell expansion. You'll need to escape the $ meaning EOF.
sed -n "/^$date/,\$p" filename

search and replace string using sed

i have a sed command like this for search and replace string inside a file:
sed -i -e 's/`db1`./`db2`./g' result/files1.sql
that is working fine to replace the db1 to db2 inside the file of: result/files1.sql
however when i change it to bash and variable format, it does not work.
sed -i -e "s/`${mydbname}`./`${mydbname2}`./g" "${mypath}"
i get error like:
./mycoolscript: line 241: db1: command not found
./mycoolscript: line 241: db2: command not found
any solution would be great.
If is something you need to replace, you will need to escape by . Here it is
sed -i -e "s/\`${mydbname}\`./\`${mydbname2}\`./g" "${mypath}"
Escape the backtick character
sed -i -e "s/\`${mydbname}\`./\`${mydbname2}\`./g" "${mypath}"
Bash treats the part within backticks as a command and first executes that.
Try this
sed -i -e "s/${mydbname}/${mydbname2}/g" "${mypath}"
There is one more way, of using single quotes for literals & double quotes only around variables/escape sequences.
sed -i -e 's/`'"${mydbname}"'`./`'"${mydbname2}"'`./g' "${mypath}"
Because of single quotes, you will not have to escape the special characters.
The trade-off between escaping special characters vs. using mix of single & double quotes would depend on number of special characters vs. number of variables.
If there are too many characters that would need escaping & less number of variables, I would prefer mix of single & double quotes.

Replacing strings with special characters with linux sed

I've read lots of posts to understand how to correctly escape white spaces and special characters inside strings using sed, but still i can't make it, here's what i'm trying to achieve.
I have a file containing the some strings like this one:
JAVA_OPTS="$JAVA_OPTS -Dorg.apache.catalina.jsessionid=some_value"
and i'm trying to replace 'some_value' using the following:
sed -i "s/^\(JAVA_OPTS=\"\$JAVA_OPTS[ \t]*-Dorg\.apache\.catalina\.jsessionid*=\s*\).*\$/\1$DORG_APACHE_CATALINA_JSESSIONID/" $JBOSS_CONFIGURATION/jboss.configuration
$JBOSS_CONFIGURATION is a variable containing an absolute Linux path.
jboss.configuration is a file i'm pointing as the target for replace
operations.
$DORG_APACHE_CATALINA_JSESSIONID contains the value i want instead
of 'some_value'.
Please note that the pattern:
JAVA_OPTS="$JAVA_OPTS -D
Is always present, and org.apache.catalina.jsessionid is an example of a variable value i'm trying to replace with this script.
What's missing/wrong ? i tried also escaping whitespaces using \s without success,
and echoing the whole gives me the following:
echo "s/^\(JAVA_OPTS=\"\$JAVA_OPTS[ \t]*-Dorg\.apache\.catalina\.jsessionid*=\s*\).*\$/\1$DORG_APACHE_CATALINA_JSESSIONID/"
s/^\(JAVA_OPTS="$JAVA_OPTS[ \t]*-Dorg\.apache\.catalina\.jsessionid*=\s*\).*$/\1/
is echo interpreting the search pattern as sed does ?
any info/help/alternative ways of doing it are highly welcome,
thank you all
echo 'JAVA_OPTS="$JAVA_OPTS -Dorg.apache.catalina.jsessionid=some_value"' | (export DORG_APACHE_CATALINA_JSESSIONID=FOO/BAR/FOOBAR; sed "s/^\(JAVA_OPTS=\"\$JAVA_OPTS[ \t]*-Dorg\.apache\.catalina\.jsessionid*=\s*\).*\$/\1${DORG_APACHE_CATALINA_JSESSIONID////\/}\"/")
Note the bash expansion (in order to escape any / that may trip up sed) and the extra \" after $DORG_APACHE_CATALINA_JSESSIONID in order to properly close the double quote. Other than that your sed expression works for me and the above command outputs the follwoing result:
JAVA_OPTS="$JAVA_OPTS -Dorg.apache.catalina.jsessionid=FOO/BAR/FOOBAR"
You can use sed like this:
sed -r '/\$JAVA_OPTS -D/{s/^(.+=).*$/\1'"$DORG_APACHE_CATALINA_JSESSIONID"'/;}' $JBOSS_CONFIGURATION/jboss.configuration
You can specify a pattern that'll match the desired string rather than trying to specify it exactly.
The following should work for you:
sed -i 's#^\(JAVA_OPTS.*Dorg.apache.catalina.jsessionid\)=\([^"]*\)"#\1='"$DORG_APACHE_CATALINA_JSESSIONID"'"#' $JBOSS_CONFIGURATION/jboss.configuration
sed 's/=\w.*$/='"$DORG_APACHE_CATALINA_JSESSIONID"'/' $JBOSS_CONFIGURATION/jboss.configuration

Replace string within a file from a bash script

I need to replace within a little bash script a string inside a file but... I am getting weird results.
Let's say I want to replace:
<tag><![CDATA[text]]></tag>
With:
<tag><![CDATA[replaced_text]]></tag>
Should I use sed? I think due to / and [ ] I am getting weird results...
What would be the best way of approaching this?
Perl with -p option works almost as sed and it has \Q (quote) switch for its regexes:
perl -pe 's{\Q<tag><![CDATA[text]]></tag>}
{<tag><![CDATA[replaced_text]]></tag>}' YOUR_FILE
And in Perl you can use different punctuation to delimiter your expressions (s{...}{...} in my example).
Yes, you need to escape the brackets, and either escape slashes or use different delimiters.
sed 's,<tag><!\[CDATA\[text\]\]></tag>,<tag><!\[CDATA\[replaced)text\]\]></tag>,'
That said, SGML and XML are not actually any better than HTML when it comes to using regexes; don't expect this to generalize.
This should be enough:
$ echo '<tag><![CDATA[text]]></tag>' | sed 's/\[text\]/\[replaced_text\]/'
<tag><![CDATA[replaced_text]]></tag>
You can also change your / separator inside sed to a different character like ,, | or %.
Just use a delimiter other than /, here I use #:
sed -i 's#<tag><!\[CDATA\[text\]\]></tag>#<tag><![CDATA[replaced_text]]></tag>#g' filename
-i to have sed change the file instead of printing it out.
g is for matching more than once (global).
But do you know the exact string you want to match, both the tag and the text?
For instance, if you want to replace the text in all with your replaced_text:
perl -i -pe 's#(<tag><!\[CDATA\[)(.*?)(\]\]></tag>)#\1replaced_text\3#g' filename
Switched to perl because sed doesn't support non-greedy multipliers (the *?).

' in sed appearing in the wrong place

I am trying to set an IP in a file with sed. I am running this command
sed -i 's:$dbserver='':$dbserver='10.0.0.2':' t.conf
but when I look in t.conf the line is
$dbserver=10.0.0.2''
Anyone know why the two single quotes are appearing at the end of the line?
I am running Debian Linux
You need to enclose the second sed argument in double quotes:
sed -i "s:$dbserver='':$dbserver='10.0.0.2':" t.conf
This way $dbserver will be substituted with its value before being passed to sed, and the single quotes won't need escaping.
If you want $dbserver to appear literally in the conf file, preceed the dollar signs with a backslash.

Resources