I encountered this bash script and wanted to know what sed -i
is doing and what’s up with the /s
and /g
? I looked at the manpages and it says text sed
is used to transform text and the i
flag is used to do it in place. But in the context of this script what is being transformed and what is it being transformed to?
#!/bin/sh
sed -i "s/$SENTINEL_QUORUM/$SENTINEL_QUORUM/g" /redis/sentinel.conf
sed -i "s/$SENTINEL_DOWN_AFTER/$SENTINEL_DOWN_AFTER/g" /redis/sentinel.conf
sed -i "s/$SENTINEL_FAILOVER/$SENTINEL_FAILOVER/g" /redis/sentinel.conf
redis-server /redis/sentinel.conf --sentinel
Here is sentinel.conf if it helps:
port 26379
dir /tmp
sentinel monitor redismaster redis-master 6379 $SENTINEL_QUORUM
sentinel down-after-milliseconds redismaster $SENTINEL_DOWN_AFTER
sentinel parallel-syncs redismaster 1
sentinel failover-timeout redismaster $SENTINEL_FAILOVER
4
Answers
As is these do nothing.
Assume the
bash
variable is set like such:The current call then becomes:
And since there’s no string
some_value
in the file nothing is changed.NOTE: Even if there was a string
some_value
in the file thissed
would overwrite the string with the same value (ie, changesome_value
=some_value
).Instead it looks like the intention is to replace the placeholder (eg,
$SENTINEL_QUORUM
) in the file with the contents of abash
variable ($SENTINEL_QUORUM
).But to do this the first
$
must be escaped so thatsed
matches on the literal$
in the file, eg:‘course, after the first run the contents of the file are going to be changed and the placholders (eg,
$SENTINEL_QUORUM
) will be gone so the next time the script runs nothing will be changed.Unless there are special regexp patterns in the values of the shell variables, it’s not doing anything, since it replaces the value of the variables with themselves. What they probably wanted was:
and similar for the other variables.
The pattern being replaced is in single quotes, so the variable is not expanded. And we escape the
$
so it won’t be treated as the end-of-line regexp pattern.The replacement is in double quotes, so the variable value will be substituted.
The -i option is used to change the file directly.
Otherwise you have to redirect to New file and then rename new file to old filename with mv command.
s is used to search for some pattern. In your case e.g.$SENTINEL_QUORUM and replace it with what can be found after next /
g is used to replace every pattern found and not only one.
In vi for example you can use the same method by writing the following:
By the way as search and replace in your case is the same it makes not much sense.
The -i option changes the file directly.
The /s option means ‘Substitute’ which as you can guess, substitutes a pattern for another pattern. But, this only runs once per line.
Example:
The /g option stands for ‘Global’ which causes an option to run globally instead of once per line.
Example:
If you want a better explanation on how sed works, I recommend watching Luke Smith’s video on it.