wordpress file owner and permission with nginx on Centos 7 (SElinux on)

As a security tool, SElinux is great. Howere, it gives me nightmares when I setup a wordpress sites with nginx.

File owner and permission setup:

  • I set the owner of all wordpress files as MY_USER_NAME
  • I add MY_USER_NAME to nginx group
  • I set all wordpress files to group-readable and group-writable, (so that nginx can read and write)
sudo usermod -a -G nginx MY_USER_NAME

sudo chown -R MY_USER_NAME:nginx *

sudo find . -type d -exec chmod 775 {} \;
sudo find . -type f -exec chmod 664 {} \;

Problem 1: cannot upload media file
Problem 2: cannot install plugin (wordpress asks for FTP)

Fix 1:

chcon -t httpd_sys_rw_content_t html

sudo chcon --reference=html example.com
sudo chcon --reference=html example.com/html

When I check SElinux log with:

sudo sealert -a /var/log/audit/audit.log

I find SElinux prevents nginx/php-fpm write example.com/html.

But I did not get any warning when I start nginx. As I remember, starting Apache without this fix will fail?

Fix 2:

sudo chown -R nginx wp-content
sudo chown -R nginx wp-admin

sudo chcon --reference=../html wp-content

I though changing the owner of wp-content should be enough, but no, it does not work. I have to change the owner of wp-admin as well.

On Fedora 25:
selinux blocks php-fpm for access of mysql port, to enable this access:

setsebool -P httpd_can_network_connect_db 1

For memcache:

setsebool -P httpd_can_network_memcache 1

More details are HERE.

Google Compute Engine (GCE) firewall and iptables at VM host

After I click “Allow HTTP” and “Allow HTTPS” in the settings of Centos 7 vm, I can get http or https pages of my site. What? I thought I need to explicitly allow port 80 and port 443 in iptables like I did in other servers. Why don’t I need to touch iptables in this case?

sudo iptables -L -n | less

Chain INPUT (policy ACCEPT)
target     prot opt source               destination         
ACCEPT     all  --              ctstate RELATED,ESTABLISHED
ACCEPT     all  --             
INPUT_direct  all  --             
INPUT_ZONES_SOURCE  all  --             
INPUT_ZONES  all  --             
DROP       all  --              ctstate INVALID
REJECT     all  --              reject-with icmp-host-prohibited
Chain INPUT_ZONES (1 references)
target     prot opt source               destination         
IN_trusted  all  --             
IN_trusted  all  --   
Chain IN_trusted (2 references)
target     prot opt source               destination         
IN_trusted_log  all  --             
IN_trusted_deny  all  --             
IN_trusted_allow  all  --             
ACCEPT     all  --      

The last line “ACCEPT all” does not look right to me. In Chain IN_trusted, iptables does IN_trusted_{log,deny,allow} and “ACCEPT all” for the rest. Should it DROP all the others by default for security?

(Since GCE has its own firewall and it blocks all except for things allowed, “ACCEPT all” here in iptables probably won’t bring any security issues.)

When I delete the last rule, I cannot get access to my sites by port 80.

[X ~]$ sudo iptables -L IN_trusted --line-numbers

Chain IN_trusted (2 references)
num  target     prot opt source               destination         
1    IN_trusted_log  all  --  anywhere             anywhere            
2    IN_trusted_deny  all  --  anywhere             anywhere            
3    IN_trusted_allow  all  --  anywhere             anywhere            
4    ACCEPT     all  --  anywhere             anywhere

[X ~]$ sudo iptables -D IN_trusted 4
[X ~]$ sudo iptables -L IN_trusted --line-numbers

Chain IN_trusted (2 references)
num  target     prot opt source               destination         
1    IN_trusted_log  all  --  anywhere             anywhere            
2    IN_trusted_deny  all  --  anywhere             anywhere            
3    IN_trusted_allow  all  --  anywhere             anywhere 

I checked other server images, in Fedora 25 server edition:

Chain FWDI_FedoraServer (2 references)
target     prot opt source               destination         
FWDI_FedoraServer_log  all  --             
FWDI_FedoraServer_deny  all  --             
FWDI_FedoraServer_allow  all  --             
ACCEPT     icmp --   

It only accepts icmp for the rests, which make much more sense to me.

Use Let’s Encrypt to Create Certificates

Let’s Encrypt is a Certificate Authority (CA) and provides FREE certificates. As of 2017/05/29, the official tool to get a certificate with shell access is Certbot.

It’s great that certbot provides convenient plugins to install and certificates for command web server software, such as apache and nginx.

However, I would prefer to NOT let any other program to touch server process and configuration. So I choose  --manual.

sudo certbot certonly --manual --preferred-challenges dns -d www.xyz.com,xyz.com

This works but renewing cert is a problem because of --manual.

An alternative way it to use --webroot when generating the certificates:

sudo certbot certonly --rsa-key-size 4096 --webroot -w /var/www/example/ -d www.example.com,example.com

Set up a cron job for renewing the certificates:

0 3,15 * * * certbot renew --quiet --no-self-upgrade --webroot && apachectl graceful

Linux cannot boot, only shows grub prompt

Today, after a reboot, my laptop (Fedora 25) cannot boot and only shows grub prompt. I have no idea what happened or what changes I made to the system.

Here is how I fixed it:

1. use ls command to find the partition that has kernel images,

for example,
ls (hd0,gpt5)

shows something like:

2. select kernel image and boot

(I have UEFI enabled and use lvm partition)

Because of lvm partitionm, I need to specify where the root is. My root partition is mapped as /dev/fedora/root.

set root=(hd0,gpt5)
linuxefi /vmlinuz-4.10.5-200.fc25.x86_64 root=/dev/fedora/root ro
initrdefi /initramfs-4.10.5-200.fc25.x86_64.img

After successfully login, we need regenerate grub.cfg. (for unknown reason, my grub.cfg was an empty file…)

grub2-mkconfig -o /boot/efi/EFI/fedora/grub.cfg

That’s all and everything looks good now.



open service by allowing addresses with firewall-cmd:
sudo firewall-cmd --add-rich-rule='rule family="ipv4" source address="" service name="dns" log prefix="dns" level="info" accept'

directly add service without filtering addresses:
sudo firewall-cmd --add-service=dns

to make it permanent:

move gnome-boxes image to another host

Let’s answer a few questions before we move:

Q: where does gnome-boxes store images?

Q: Are there other directories I need to backup?

If you do not have any existing gnome-boxes images on your new host, please copy these three directories to your new host. It just works!

If you have existing images at your new host, do NOT directly copy these directories to your new hosts. Otherwise, you will overwrite your existing images and configurations.

Let’s assume the image you want to move is:

so there is a config file corresponding to this image:

Step 1: copy the above two files to the new host

Step 2: find the correct uuid for your image in: ~/.config/libvirt/qemu/win10.xml

Step 3:
open qemu session file:
~/.config/gnome-boxes/sources/'QEMU Session'
(I think this file is used to display the sessions at gnome-box main window when you open the application)

you will see something like:

[display A-B-C]
last-seen-name=Microsoft Windows 10

append the corresponding session information with the same uuid to new host at: ~/.config/gnome-boxes/sources/'QEMU Session'

Step 4: restart gnome-boxes and you will see your old VM image