Ruby manages to fail opening a 644 file as read-only - ruby

$ ruby -v
ruby 1.8.7 (2010-01-10 patchlevel 249) [x86_64-linux]
This is the important line on the script (/etc/munin/plugins/nginx_status_codes.rb:31):
File.open("/var/log/nginx/access.log", File::RDONLY).readlines.each do |line|
My access log has global read permissions:
$ ls -lha /var/log/nginx/access.log
-rw-r--r-- 1 www-data adm 49M May 1 15:56 /var/log/nginx/access.log
The script works if I run from the terminal as a regular user...
$ /etc/munin/plugins/nginx_status_codes > /dev/null && echo $?
0
...but it fails if ran by Munin (which runs as root):
2012/05/01-15:54:05 [3988] /etc/munin/plugins/nginx_status_codes:31:in `initialize': Permission denied - /var/log/nginx/access.log (Errno::EACCES)
2012/05/01-15:54:05 [3988] from /etc/munin/plugins/nginx_status_codes:31:in `open'
2012/05/01-15:54:05 [3988] from /etc/munin/plugins/nginx_status_codes:31
It also fails if I set the file permissions to 777 or whatever. I'm thinking Ruby is just being stupid and reporting the wrong exception (Errno:EACCES) and masquerading the real issue. But what would it be?
UPDATE: Tried to "fix" it by having the script owned by root:root and even with sid/gid bits set it manages to fail with permission denied.

Nevermind. The problem was that logrotation was in place and it changed the log file permissions every now and then:
$ cat /etc/logrotate.d/nginx
/var/log/nginx/*.log {
daily
missingok
rotate 52
compress
delaycompress
notifempty
create 0640 www-data adm
sharedscripts
prerotate
if [ -d /etc/logrotate.d/httpd-prerotate ]; then \
run-parts /etc/logrotate.d/httpd-prerotate; \
fi; \
endscript
postrotate
[ ! -f /var/run/nginx.pid ] || kill -USR1 `cat /var/run/nginx.pid`
endscript
}

Related

Check if file exists remotly in bash

I have a bashscript which checks if a file exists on the remote server.
When i execute this bashscript on commandline it works fine and say to me the file exist (as it should). But when crontab is executing this bashscript it says that the file not exist (although it would exist
).
can anybody help me?
myscript.sh
#!/bin/bash
if $(sudo ssh -i <path/to/ssh/keys> <user>#<ip> "[[ -f /etc/ssl/file.txt ]]");then
echo "exist"
else
echo "not exist"
fi
crontab:
*/1 * * * * bash /home/user/myscript.sh | mail -s "betreff" user#email.com
stderr: (when i run the script on the commandline)
++ sudo ssh -i <path/to/ssh/keys> <user>#<ip> '[ -f /etc/ssl/file.txt ]'
+ echo exist
exist
stderr: (when i run the script in cron)
++ sudo ssh -i <path/to/ssh/key> <user>#<ip> '[ -f /etc/ssl/file.txt ]'
Warning: Identity file /root/.ssh/key/keyfile not accessible: No such file or directory.
Permission denied, please try again.
Permission denied, please try again.
root#<ip>: Permission denied (publickey,password).
Permission of ssh keyfile:
-rw------- 1 root root 3243 Sep 30 15:34 keyfile
-rw-r--r-- 1 root root 741 Sep 30 15:34 keyfile.pub
Thanks for helping :D

Run bash script with sudo but create files with user as owner

I have a bash script, create-file.sh, that creates a file named a:
$ cat create-file.sh
# /bin/bash
touch a
When I run the script it creates a file 'a' with my user as owner.
$ ./create-file.sh
$ ls -l
-rw-r--r-- 1 shai wheel 0 Aug 16 17:19 a
However when I run the script under sudo the file is created with root as user:
$ sudo ./create-file.sh
$ ls -l
-rw-r--r-- 1 root wheel 0 Aug 16 17:19 a
Is there a way to tell a script that runs under sudo to create the file with my user as owner?
you would be correct to say that a script that touches a single file does not need to run under sudo. This example is of course a reduction of the original problem, my script has much more and does need to run under sudo, but I still want the files to be created with my user as owner.
sudo exports the original username as SUDO_USER; you can chown to that.
#!/bin/bash
touch a
[[ $SUDO_USER ]] && chown "$SUDO_USER" a
Similarly, if your sudo configuration allows (as is default) root to drop privileges to any other user without an explicit password prompt, you can take advantage of that:
#!/bin/bash
# drop privileges back to non-root user if we got here with sudo
depriv() {
if [[ $SUDO_USER ]]; then
sudo -u "$SUDO_USER" -- "$#"
else
"$#"
fi
}
depriv touch a

Copy of /dev/null has different behaviours depending on location

I tried mimicking the behaviour of /dev/null in another location, but some strange error occurs. I learned how to generate a special file similar to /dev/null in -bash: /dev/null: Permission denied.
When in some folder, e.g. home, the following occurs:
$ sudo mknod -m 666 null2 c 1 3
$ cat null2
cat: null2: Permission denied
On the other hand, when in /dev, no error occurs:
$ cd /dev
$ sudo mknod -m 666 null2 c 1 3
$ cat null2
I can reproduce the error on another xubuntu machine, but on a third machine the error does not occur. Any clue whats going on there?
Strangely, on any of these machines, permissions and major/minor are identical:
$ ls -la null2
crw-rw-rw- 1 root root 1, 3 Mär 4 17:42 null2
$ ls -la /dev/null
crw-rw-rw- 1 root root 1, 3 Mär 4 11:46 /dev/null
Also same when copying /dev/null
$ sudo cp -pR /dev/null null2 && cat null2
cat: null2: Permission denied
Is the nodev mount option set for the file system containing your home directory?
Specifying nodev forces the file system to not interpret block special devices (like the null2 special file you create with mknod).

Why can't I echo contents into a new file as sudo? [duplicate]

This question already has answers here:
Bash Deployment Script Permission Problem
(2 answers)
Closed 8 years ago.
I came across this weird problem just now and I can't seem to get to the bottom of it. I'm trying to add a config file to /etc/sudoers.d/ but get permission denied. In the example below, the file "tweedle" doesn't exist and:
drwxr-xr-x 2 root root 4.0K Jan 2 18:27 sudoers.d/
So here's the command:
$ sudo echo "tweedle ALL=(ALL) ALL" > /etc/sudoers.d/tweedle
-bash: /etc/sudoers.d/tweedle: Permission denied
It doesn't even work when I break it into two commands:
$ sudo touch /etc/sudoers.d/tweedle
$ sudo echo "poodle" > /etc/sudoers.d/tweedle
When I tested it locally, same problem:
$ cd ~
$ mkdir -m 755 tweedle
$ sudo chown root:root tweedle
$ sudo echo "battle" > ~/tweedle/beetle
-bash: /home/spanky/tweedle/beetle: Permission denied
$ sudo touch tweedle/beetle
$ sudo echo "battle" > tweedle/beetle
-bash: tweedle/beetle: Permission denied
Without sudo, all is well:
$ cd ~
$ mkdir poodle
$ echo "noodle" > poodle/bottle
$ cat poodle/bottle
noodle
Thoughts?
The echo command is being run as root, but the redirection is done by your shell, so it's executed as the current user, not as root.
The simplest solution is to invoke a root shell to run both the command and the redirection.
Rather than:
sudo echo line > file
try this:
sudo sh -c 'echo line > file'
or
sudo bash -c 'echo line > file'
The answer is to use "tee" with a pipe, a command I wasn't familiar with, so you can use sudo for the second half:
$ echo "tweedle ALL=(ALL) ALL" | sudo tee /etc/sudoers.d/tweedle

Bash Deployment Script Permission Problem

I'm writing a deployment script and have run in to a strange problem...
ian#baster:~$ sudo echo "Build: "$REVISION" - Deployed: "$(date +%Y-%m-%d) > /home/www/prod/www/revision.html
-bash: /home/www/prod/www/revision.html: Permission denied
but...
root#baster:~# echo "Build: "$REVISION" - Deployed: "$(date +%Y-%m-%d) > /home/www/prod/www/revision.html
root#baster:~# more /home/www/prod/www/revision.html
Build: - Deployed: 2011-01-28
then...
ian#baster:~$ sudo ls -l /home/www/prod/www
total 28
-rw-r--r-- 1 root root 31 2011-01-28 21:56 revision.html
ian#baster:~$ sudo more /home/www/prod/www/revision.html
Build: - Deployed: 2011-01-28
What's the deal?
The usual way to do that is with tee:
echo "foo" | sudo tee filename
You can suppress the output to the screen which tee does like this:
echo "foo" | sudo tee filename >/dev/null
The echo is run as root, but not the redirection. Run the redirection in a sudo subshell.

Resources