Running Laravel 5 on a shared host subdomain (I use Vidahost) is a little daunting because Laravel requires the web root to point to the /public folder and generally with a subdomain the website root is the root folder that is created for you.
My solution was to create a directory in the subdomain root folder and copy all the code into there. I then copied the contents of the /public folder into the subdomain root folder and edited index.php.
The two require lines need modifying to remove the ‘..’ characters and replace with the actual path.
Here is an SQL query I construct to extract customers with billing and shipping address from a Magento 1.9 store.
This joins on table sales_flat_order_address to ensure that only customers that have ordered are included.
You may need to adjust the entity attribute id’s – if you look in those tables it is pretty obvious what each value represents.
ce.entity_id AS customer_id,
cev2.value AS firstname,
cev3.value AS lastname,
caet.value AS billing_first_line,
caev1.value AS billing_town,
caev2.value AS billing_postcode,
sfoa.entity_id AS sfoa_entity_id,
sfoa.street AS shipping_first_line,
sfoa.city AS shipping_city,
sfoa.postcode AS shipping_postcode
-- first nameINNERJOIN
customer_entity_varchar cev2 ON(ce.entity_id = cev2.entity_id
AND cev2.attribute_id =5)-- last nameINNERJOIN
customer_entity_varchar cev3 ON(ce.entity_id = cev3.entity_id
AND cev3.attribute_id =7)-- address first lineINNERJOIN
customer_address_entity cae ON(ce.entity_id = cae.parent_id)INNERJOIN
customer_address_entity_text caet ON(cae.entity_id = caet.entity_id)-- townINNERJOIN
customer_address_entity_varchar caev1 ON(cae.entity_id = caev1.entity_id
AND caev1.attribute_id =26)-- postcodeINNERJOIN
customer_address_entity_varchar caev2 ON(cae.entity_id = caev2.entity_id
AND caev2.attribute_id =30)-- salesINNERJOIN
sales_flat_order sfo ON(ce.entity_id = sfo.customer_id)-- shipping addressINNERJOIN
sales_flat_order_address sfoa ON(sfo.entity_id = sfoa.parent_id)WHERE sfo.status ='complete'
If you are using CentOS then the group should be apache instead of www-data.
You can boost Magento performance (or any complicated PHP app) when running from a VM by changing the PHP OPcache revalidate frequency. It defaults to 2 seconds which means when you are navigating a site all the PHP files are recompiled with every click. With tens of thousands of PHP files that’s a hefty penalty.
Changing this to something like 20 seconds means you’ll be using cached code. Do this with:
My times tables site is now back online at times-tables.willis-owen.co.uk. Rote learning is no longer fashionable but it still remains an effective tool to get kids to memorise times tables instead of trying to work out the sum in their heads each time.
Although this site is simple, it gives competitive kids a sense of achievement and there is nothing to distract them from the task at hand.
For parents there is no marketing / advertising and no agenda.
It has been updated to use the superb PHP Fat-Free Framework v3.5 which is now installable using Composer.
WordPress brute force attacks are increasingly common at the time I write this – September 2014. Recently a server I look after was coming under attack and then after a few minutes the site would display ‘Error establishing a Database Connection’. When I logged into the server the MySQL service wasn’t running.
My first thoughts were that something in the attack was causing MySQL to crash, There was no information in the MySQL error.log to indicate why though so I spent time looking at plugins to help mitigate a brute force attacks, which tend to focus on the WordPress wp-login.php and xmlrpc.php files:
Disable XML-RPC will disable WordPress XML-RPC functionality meaning that nothing can be done to your content, however this does nothing to prevent initial database queries so MySQL can still be affected when running this, and it does nothing about wp-login.php either.
BruteProtect – I’ve seen comments that it will protect xmlrpc but I’ve seen it in action during an attack and as of version 2.2.2 it did nothing to stop it.
NinjaFirewall – there are a lot of configuration options but this one does the job. It sits in front of WordPress and so it can intercept the attack before all the database activity starts up. This worked great when I used it during an attack.
However you may host multiple WordPress sites on a single server and it could be tedious having to install this and configure it for each site, plus there is going to be duplication of what the code is doing and Apache still has to handle all the incoming requests.
It may be better to stop any attacks at the firewall because that’s the single point of entry to your server. This approach still requires a plugin – WP fail2ban but this one will log attacks to your systems auth.log which can be picked up by fail2ban and automatically added for a temporary period to your firewall rules. It is more complicated than the other plugins to install but once a malicious IP has been blocked it can’t affect any of the sites on your server will keep the system load much lower.
After getting the fail2ban solution in place the database was brought down yet again. I ended up looking in kern.log and at the time of the attack was the line ‘apache2 invoked oom-killer’ – that revealed the problem… Apache was using so many processes that it was running out of memory and as this particular server runs off an SSD the swap file is disabled. As there was nowhere else to get memory from it started killing off other processes, the biggest of these was MySQL.
What a relief to find the cause – MySQL wasn’t crashing at all. The solution was just to reduce the MaxClients value in apache2.conf – the default value of 150 is way too big for a modest sized server. If each process takes 40 MB then 150 processes require 6 GB of RAM. Getting a realistic value for this requires a little load testing plus the use of some tools to see how the memory usage increases as Apache has to handle more requests.