Im trying to extract the last line of a text file using sed and move it to a variable. However, command substitution using quotes breaks the sed command which already uses quotes.
sed '$!d' cookie.txt
Returns: localhost FALSE /XSS/ FALSE ****** loggedIn No
However, trying to move it to a variable, like so:
varin='sed '$!d' cookie.txt'
provides no output for the variable $varin
For PHP, we can have nested quotes using double and single quotes, is there anything similar here?
Try this:
var=$(tail -1 cookie.txt)
or with sed:
var=$(sed '$!d' cookie.txt)
If you are getting an error like "localhost:command not found" with $(...), it sounds like you are nesting backticks inside the command substitution, like
variable=$(`sed '$!d' cookie.txt`)
The backticks would run the sed command to produce the string beginning with "localhost", then because that string is inside $(...), it would be treated as a command to run. Simply using
variable=$( sed '$!d' cookie.txt )
should do what you want.
Related
I have a script that restores db dump. As a parameter a database name is passed to this script. In a dump there is a following line:
ALTER DATABASE `previosDbName` CHARACTER ... ;
I have to change previosDbName to a value, passed as a parameter. I try to use sed, but it does not work.
Here is a script:
echo $3
export updateValue="ALTER DATABASE \`$3\`"
echo $updateValue
sed -i 's/ALTER DATABASE `\(.*\)`/${updateValue}/' $4
Here how I run it:
./test.sh dbP dbN medi_6_0 full_path_to_test.sql
The output of the script tells us, that updateValue is a correct one:
medi_6_0
ALTER DATABASE `medi_6_0`
But the result string:
${updateValue} CHARACTER ...;
Instead of:
ALTER DATABASE `medi_6_0` CHARACTER ...;
I've also tried to use double quotes, but it did not help:
sed -i 's/ALTER DATABASE `\(.*\)`/"${updateValue}"/' $4
Update: Solution offered by #Sundeep helped:
sed -i 's/ALTER DATABASE `\(.*\)`/'"${updateValue}"'/' $4
None of solutions described in:
How to use variables in a command in sed?
Helped. As most of solutions (did not check all of them), offered in this topic.
To allow variable interpolation enclose sed expression with double quotes.
Also, backtick ` sign has a special meaning. Everything between backticks is evaluated. So it should be escaped with a backslash \
...
export updateValue="$3"
sed "s/\(ALTER DATABASE\) \`.*\`/\1 \`$updateValue\`/" $4
...
The output:
ALTER DATABASE `medi_6_0` CHARACTER ... ;
You can use:
sed -iE "s/(ALTER DATABASE \`).*(\`)/\1$3\2/" file.sql
Use double quotes so that "$3" can be expanded by shell
Escape the reverse quotes, otherwise it tells shells to execute the text between ` and ` as a command.
bash variables can only expand inside double quotes and backtick needs to be escaped, i.e.:
sed -i "s/\(ALTER DATABASE\) \`.*\`/\1 \`$3\`/" $4
# ALTER DATABASE `medi_6_0` CHARACTER ... ;
Options:
-i Edit files in-place (otherwise sends to stdout)
I'm new in bash script and trying to replace some words in my file using sed. Following is the bash I use in my script:
sed -i '' "s/<pre>.*<\/pre>/<pre>($NEWNAME) $MD5<\/pre>/"~/Desktop/replace.html
And I got error message saying: bad flag in substitute command: 'U'. I use double quote because I need to put variables in.
My environment is Mac.
======================================
1.Turns out I forgot to leave a space between replace string and file name. Which led to the result always showing: bad flag in substitute command: '~'. It works now.
2.The reason is I used MD5=$(md5 path) to create MD5 value which gets the reault of MD5 (path) *****, and the path contains / which breaks the regex. After changing MD5=$(md5 -q path), it will be ok.
Most likely your $NEWNAME variable has a forward slash in it, which is being used as regex delimiter in sed. Try this sed with an alternate delimiter e.g. ~:
sed -i '' "s~<pre>.*</pre>~<pre>($NEWNAME) $MD5</pre>~" ~/Desktop/replace.html
I want to change some names in a file using sed. This is how the file looks like:
#! /bin/bash
SAMPLE="sample_name"
FULLSAMPLE="full_sample_name"
...
Now I only want to change sample_name & not full_sample_name using sed
I tried this
sed s/\<sample_name\>/sample_01/g ...
I thought \<> could be used to find an exact match, but when I use this, nothing is changed.
Adding '' helped to only change the sample_name. However there is another problem now: my situation was a bit more complicated than explained above since my sed command is embedded in a loop:
while read SAMPLE
do
name=$SAMPLE
sed -e 's/\<sample_name\>/$SAMPLE/g' /path/coverage.sh > path/new_coverage.sh
done < $1
So sample_name should be changed with the value attached to $SAMPLE. However when running the command sample_name is changed to $SAMPLE and not to the value attached to $SAMPLE.
I believe \< and \> work with gnu sed, you just need to quote the sed command:
sed -i.bak 's/\<sample_name\>/sample_01/g' file
In GNU sed, the following command works:
sed 's/\<sample_name\>/sample_01/' file
The only difference here is that I've enclosed the command in single quotes. Even when it is not necessary to quote a sed command, I see very little disadvantage to doing so (and it helps avoid these kinds of problems).
Another way of achieving what you want more portably is by adding the quotes to the pattern and replacement:
sed 's/"sample_name"/"sample_01"/' script.sh
Alternatively, the syntax you have proposed also works in GNU awk:
awk '{sub(/\<sample_name\>/, "sample_01")}1' file
If you want to use a variable in the replacement string, you will have to use double quotes instead of single, for example:
sed "s/\<sample_name\>/$var/" file
Variables are not expanded within single quotes, which is why you are getting the the name of your variable rather than its contents.
#user1987607
You can do this the following way:
sed s/"sample_name">/sample_01/g
where having "sample_name" in quotes " " matches the exact string value.
/g is for global replacement.
If "sample_name" occurs like this ifsample_name and you want to replace that as well
then you should use the following:
sed s/"sample_name ">/"sample_01 "/g
So that it replaces only the desired word. For example the above syntax will replace word "the" from a text file and not from words like thereby.
If you are interested in replacing only first occurence, then this would work fine
sed s/"sample_name"/sample_01/
Hope it helps
What I want to achieve:
Suppose I have a file file with the following content:
ENV_VAR='/foo/`whoami`/bar/'
sh my_script.sh 'LOL'
I want to replace - using sed - the single quotes that surrounds the directory names, but not the ones that surrounds stuff that does not seem like a directory, for example, the arguments of a script.
That is, after running the sed command, I would expect the following output:
ENV_VAR="/foo/`whoami`/bar/"
sh my_script.sh 'LOL'
The idea is to make this happen without using tr to replace ' with ", nor sed like s/'/"/g, as I don't want to replace the lines that does not seem to be directories.
Please note that sed is running on AIX, so no GNU sed is available.
What I have tried:
If I use sed like this:
sed "s;'=.*/.*';&;g" file
... the & variable hold the regex previously matched, that is: ='/foo/`whoami`/bar/'. However, I can't figure out how to make the replacement so the single quotes gets transformed into double quotes.
I wonder if there's a way to make this work using sed only, via a one-liner.
This will do the job:
/usr/bin/sed -e "/='.*\/.*'/ s/'/\"/g" file
Basically, you just want the plain ' => " replacement, but not for all lines, just for those that match the pattern ='.*\/.*'/. And, in the s command you just need to escape the ".
This should work:
sed "s/'\(.*\/.*\)'/\"\1\"/g"
Captures the part between ' and uses a backreference.
I am using sed command in Ubuntu for making shell script.
I have a problem because the string I am inserting has both single and double quotes. Dashes also. This is the expample:
sed -i "16i$('#myTable td:contains("Trunk do SW-BG-26,
GigabitEthernet0/22")').parents("tr").remove();" proba.txt
It should insert
$('#myTable td:contains("Trunk do SW-BG-26, GigabitEthernet0/22")').parents("tr").remove();
in line 16 of the file proba.txt
but instead it inserts
$('#myTable td:contains(
because it exits prematurely . How can resolve this, I cannot find solution here on site bcause I have both quotation signs and there are explanations only for one kind.
2nd try
I set \ in front every double quote except the outermost ones but I still didn't get what I want. Result is:
.parents("tr").remove();
Then I put \ in front of every ' too but the result was an error in script. This is the 4th row:
sed -i "16i$(\'#myTable td:contains(\"QinQ tunnel - SCnet wireless\")\').parents(\"tr\").remove();" proba.txt
This is the error:
4: skripta.sh: Syntax error: "(" unexpected (expecting ")")
Maybe there is easier way to insert line into the file at the exact line if that line has ", ', /?
3rd time is a charm
Inserting many lines last day I came across another problem using sed. I want to insert this text:
$(document).ready( function() {
with command:
sed -i "16i$(document).ready( function() {" proba.txt
and I get as result this text inserted as document is something special or because of the $:
.ready( function() {
Any thoughts about that?
There are two ways around this. The easy way out is to put the script into a file and use that on the command line. For example, sed.script contains:
16i\
$('#myTable td:contains("Trunk do SW-BG-26, GigabitEthernet0/22")').parents("tr").remove();
and you run:
sed -f sed.script ...
If you want to do it without the file, then you have to decide whether to use single quotes or double quotes around your sed -e expression. Using single quotes is usually easier; there are no other special characters to worry about. Each embedded single quote is replaced by '\'':
sed -e '16i\
$('\''#myTable td:contains("Trunk do SW-BG-26, GigabitEthernet0/22")'\'').parents("tr").remove();' ...
If you want to use double quotes, then each embedded double quote needs to be replaced by \", but you also have to escape embedded back quotes `, dollar signs $ and backslashes \:
sed -e "16i\\
\$('#myTable td:contains(\"Trunk do SW-BG-26, GigabitEthernet0/22\")').parents(\"tr\").remove();" ...
(To the point: I forgot to escape the $ before I checked the script with double quotes; I got the script with single quotes right first time.)
Because of all the extra checking, I almost invariably use single quotes, unless I need to get shell variables substituted into the script.
sed -i "6 i\\
\$('#myTable td:contains(\"Trunk do SW-BG-26, GigabitEthernet0/22\")').parents(\"tr\").remove();" proba.txt
escape the double quote, the slash and new line needed after the i instruction and the $ due to double quote shell interpretation