# trying to get 'sed' to work



## paulfrottawa (Oct 16, 2018)

Hi I'm trying to use sed in a sudoers file.

This works from root and removes this number sign.
`sed -i '' 's/# %wheel ALL=(ALL) NOPASSWD: ALL/%wheel ALL=(ALL) NOPASSWD: ALL/' /usr/local/etc/sudoers`

However this one doesn't
`sed -i "" 's/# %sudo ALL=(ALL) ALL/%sudo ALL=(ALL) ALL/' /usr/local/etc/sudoers`

can someone else test this.


----------



## yuripv (Oct 16, 2018)

```
/usr/local/etc/sudoers: No such file or directory
```

Seriously though, it should have worked if there's such line to match in sudoers:

```
$ echo '# %sudo ALL=(ALL) ALL' | sed 's/# %sudo ALL=(ALL) ALL/%sudo ALL=(ALL) ALL/'
%sudo ALL=(ALL) ALL
```


----------



## aragats (Oct 16, 2018)

Paul Belair , the problem is that you rely on particular characters, and even an extra space (which may appear in the future) will brake your script. In this particular case there is a tab character.
I'd suggest making the pattern more universal (not perfect though, you can work on it further):
	
	



```
sed -i '' 's/#\(.*%sudo.*ALL=(ALL).*ALL.*\)/\1/' /usr/local/etc/sudoers
```
You can test it first by running:
	
	



```
sed -n 's/#\(.*%sudo.*ALL=(ALL).*ALL.*\)/\1/p' /usr/local/etc/sudoers
```
[EDIT] Fixed typos


----------



## paulfrottawa (Oct 17, 2018)

Thanks both
The replacement text left a space at the beginning of the line. This worked
`sed -i '' 's/#\(.*%sudo.*ALL=(ALL).*ALL.*\)/%sudo ALL=(ALL) ALL/' /usr/local/etc/sudoers`


----------



## aragats (Oct 17, 2018)

As I mentioned above, the pattern can still be improved, for example, you can tell *sed* that the "spaces" are any number of spaces or tabs by using *[:blank:]*:
	
	



```
sed -i '' 's/#[[:blank:]]*\(%sudo[[:blank:]]*ALL=(ALL)[[:blank:]]*ALL.*\)/\1/p' /usr/local/etc/sudoers
```
Pay attention that the first "space" is outside of the remaining pattern now, thus you'll not get it in the result.


----------



## woodsb02 (Nov 23, 2019)

Thanks. I found that the "/p" at the end was causing the line to both be uncommented, and duplicated. I instead replaced it with "/g".

The command which works for me:

```
sed -i '' 's/#[[:blank:]]*\(%wheel[[:blank:]]*ALL=(ALL)[[:blank:]]*ALL.*\)/\1/g' /usr/local/etc/sudoers
```

Output showing the issue with "/p" and the improved output of "/g":

```
# cp /usr/local/etc/sudoers.dist /usr/local/etc/sudoers
# sed -i '' 's/#[[:blank:]]*\(%wheel[[:blank:]]*ALL=(ALL)[[:blank:]]*ALL.*\)/\1/p' /usr/local/etc/sudoers
# diff -u /usr/local/etc/sudoers.dist /usr/local/etc/sudoers
--- /usr/local/etc/sudoers.dist 2019-11-14 05:06:31.000000000 +0000
+++ /usr/local/etc/sudoers      2019-11-23 03:26:52.761581000 +0000
@@ -87,7 +87,8 @@
 root ALL=(ALL) ALL
 
 ## Uncomment to allow members of group wheel to execute any command
-# %wheel ALL=(ALL) ALL
+%wheel ALL=(ALL) ALL
+%wheel ALL=(ALL) ALL
 
 ## Same thing without a password
 # %wheel ALL=(ALL) NOPASSWD: ALL

# cp /usr/local/etc/sudoers.dist /usr/local/etc/sudoers
# sed -i '' 's/#[[:blank:]]*\(%wheel[[:blank:]]*ALL=(ALL)[[:blank:]]*ALL.*\)/\1/g' /usr/local/etc/sudoers
# diff -u /usr/local/etc/sudoers.dist /usr/local/etc/sudoers
--- /usr/local/etc/sudoers.dist 2019-11-14 05:06:31.000000000 +0000
+++ /usr/local/etc/sudoers      2019-11-23 03:27:37.038799000 +0000
@@ -87,7 +87,7 @@
 root ALL=(ALL) ALL
 
 ## Uncomment to allow members of group wheel to execute any command
-# %wheel ALL=(ALL) ALL
+%wheel ALL=(ALL) ALL
 
 ## Same thing without a password
 # %wheel ALL=(ALL) NOPASSWD: ALL
```


----------

