Паттерны в веб приложениях

Первый пост о тех паттернах используемых в своей работе.

Первый паттерн: Конфигурации приложения.

Проблема: Многие приложения сталкиваются с необходимостью иметь системные настройки приложения (application preferences), это может быть название приложения, курсы валют, частота обновления или запуска какого-то сервиса. Часто такого рода задачу решают с помощью файлов настроек (*.yml, *.properties), но это в случае когда они не меняются. Как только возникает необходимость вынести эти настройки на уровень пользователя, то решения с конфигурационными файлами не хватает.

Концептуальное решение: Хранить настройки в базе данных и при старте приложения загружать их в память в виде констант. Как только происходит запись в таблицу настроек, все константы, либо изменившуюся следует перечитать.

Пример реализвации на ruby:

1. шаг - миграция


class CreateProperties < ActiveRecord::Migration
def self.up
create_table :properties, :options => 'ENGINE=InnoDB CHARSET=utf8' do |t|
t.string :name
t.string :value
end
end

def self.down
drop_table :properties
end
end


2. шаг - модель


class Property < ActiveRecord::Base

validates_presence_of :name
validates_presence_of :value

after_save :property_changed

PROPERTIES = {:pvn => 0.18, :eur_rate => 0.7}

private
def property_changed
Property.load_properties
end

def self.load_properties
PROPERTIES.each {|name, value|
Property.create(:name => name.to_s, :value => value) unless
Property.find_by_name(name.to_s)}
Property.find(:all).each do |property|
class_eval <<-EOF
#{property.name.upcase} = #{property.value}
EOF
end
end

load_properties

BACK_PVN = Property::PVN + 1

end


В принципе это все. Далее используем Propert::PVN, Property::EUR_RATE, ... при обновлении значения какой-то переменной, она автоматически перегрузится. Так же есть возможность внести стартовые значения по умолчанию PROPERTIES = {:pvn => 0.18, :eur_rate => 0.7}, которые автоматически запишутся в базу при первом обращении ClassLoader'а к Property.

Simple linux web-server information backup

Recently had some bad experience moving site to pre-production mode and accidentally (caused by software), all user information had partly lost and broken.

I had very unpleasant conversation with customer, so since that time I always setup backups for a new site.

Usually, when you dealing with ror project, it's very simple to backup everything by using backup_fu.

But we have no ruby and non ruby project, I've reviewed some freeware backup software and found it too difficult for such task. So let's write our own backup scripts manually.

Objectives for backup:
  • source code
  • data from database (mysql)
  • static files
Source backup is usually done by version control, so we'll skip this step.

According to database there is a great utility mysqldump.
First we need to mount another disc and let's mount it to /backups
The script is:

#!/bin/bash
echo Starting mysql backup `date`
mysqldump --complete-insert --skip-extended-insert --user=username --password="password" site > /backups/mysql_dump_`date "+%Y%m%d"`.sql
gzip /backups/mysql_dump_`date "+%Y%m%d"`.sql


Make file executable
host:~# chmod +x backup_mysql.sh


Then you need to setup cron to execute the script once a day or whatever you need.
host:~# crontab -e
0 1 * * * /root/backup_mysql.sh > backup.log

Lets move to static files content backup.
We have a lot of user files and we don't want to backup all static files everyday. (I didn't manage setup incremental backup for backup_fu) So we need some tool for incremental backup. For this task we'll use rdiff-backup utility.

apt-get install rdiff-backup

Create a script file backup_static.sh in /root and make it executable:

#!/bin/bash
echo Starting static files backup `date`
rdiff-backup /var/www/adultsgowild/_files /backups/static
echo Backup finished

chmod +x backup_static.sh

Add task to cron

host:~# crontab -e
0 1 * * * /root/backup_static.sh > backup.log

And that is actually it.

Linux server monitoring tools.

Some days ago we have started another portal, and the customer informed me about huge spam action, more than 60m spam emails, so we expected a huge traffic and a great stress testing. So the task is to determine if our current hardware and software is able to handle this kind of load.

The first thing came to my mind is setting up monitoring tools. After googling some time I've found some freeware tools. The most interesting were munin and nagios.

The first one installed on my server was nagios. The installation was pretty simple using standard configurations (in my case Ubuntu 6.06 server), following by great documentation http://www.onlamp.com/pub/a/onlamp/2002/09/26/nagios.html?page=1.
On the official site I found lots of features, but in real system I didn't found that I need.

I was looking for CPU and memory charts. So, I moved to another tool - munin
Well, installation was simple too, following the instructions found at http://www.ubuntugeek.com/monitoring-servers-and-clients-using-munin-in-ubuntu.html
One thing is missed in tutorial is apache configuration, but it's pretty simple.

Everything you need is setup account and add munin configuration to apache enabled sites


cd /var/www/munin
nano .htaccess

#.htaccess
AuthUserFile /etc/munin/munin-htpasswd
AuthName "D"
AuthType Basic
require valid-user
# EOF

htpasswd -c /etc/munin/munin-htpasswd muinin_username
nano /etc/apache2/sites-available/munin.conf

#munin.conf
ScriptAlias /munin/cgi/ /var/www/munin/cgi/
Alias /munin/ /var/www/munin/
#EOF

a2ensite munin
/etc/init.d/apache restart


And that is actually it. Open http://you-server-ip/munin and you can see the server load by days, weeks. So you know the peak of system load, can analyze it and make something to prevent server crushing.
Finally I've got tired of pressing 'spec spec/model/*' , so I decided to try autotest.

The idea of autotest is just running and informing you about test results without manual runs. It looks simple, you run 'autotest' from console and see results. It automatically triggers test when you edit the test file. You also can configure and add some visualization by editing .autotest file, which should be located in your rails root directory.

There are plenty of documentation on installation but I still got some issues.
Here are some usefull links on this topic:

  • http://ph7spot.com/articles/getting_started_with_autotest
The nube documentation.

  • http://pragmatig.wordpress.com/2008/04/15/autotest-rspec-notifications-for-ubuntu/
And the script for Ubuntu to see linux like flashing messages about test completion.

  • http://blog.nicksieger.com/articles/2006/11/15/rspec-autotest-now-a-rails-plugin
Autotest plugin for rails


.autotest example for ubuntu

require 'autotest/redgreen'

module Autotest::Notify
def self.notify title, msg, img, pri='low', time=3000
`notify-send -i #{img} -u #{pri} -t #{time} '#{msg}'`
end

Autotest.add_hook :ran_command do |autotest|
results = [autotest.results].flatten.join("\n")
output = results.slice(/(\d+)\s+examples?,\s*(\d+)\s+failures?(,\s*(\d+)\s+pending)?/)
folder = "~/Pictures/rails/"
if output =~ /[1-9]\d*\sfailures?/
notify "FAIL:", "#{output}", folder+"rails_fail.png", 'critical', 10000
elsif output =~ /[1-9]\d*\spending?/
notify "PENDING:", "#{output}", folder+"rails_pending.png", 'normal', 10000
else
notify "PASS:", "#{output}", folder+"rails_ok.png"
end
end
end

ER diagramm design tools

Понадобилось тут нарисовать пару ER диаграмм, и столкнулся с проблемой, что программ для их рисования не так и много, а те что есть довольно убогие, конечно учитывая кое-какие ограничения, софт должен быть бесплатным и работать на ubuntu feisty fawn'e. Должен поддерживать нотацию crows foot. Вообщем google напару с wikipedia сразу выдали небольшой списочек потенциальных программ:
  • dia (http://live.gnome.org/Dia)
Довольно удобная штука, легковесная, устанавливается одним кликом, поддерживает разные виды диаграмм, но нет нотации crows foot + нельзя установить вид связи м/у entity'ями.

  • ferret (http://gnuferret.org/)
Распространяется с Debian и Ubuntu. Довольно сырая штука, о чем и говорит текущая стабильная версия(0.6)

  • DBDesigner 4
Довольно неплохая штука, одна проблема, изначально она была написана под windows. И если под windows она работает отлично, есть разные ER нотации, интегрируется с MySql, есть возможность писать плагины, то на ubuntu проблемы начинаяются уже при инсталяции. Также много разных issues связанных с поддержкой шрифтов.

  • kivio (http://www.koffice.org/kivio/)
Отличная штука, очень похоже на Visio от microsoft. Все просто, понятно и удобно, при это довольно функциональная, есть возможность рисовать UML.

  • gliffy (http://www.gliffy.com/)
Ну и наконец один довольно удобный online tool, по функциональности, касательно ER диаграмм, он ничуть не отсает ни от одного вышеперечисленного. Есть поддержка многих видов диаграмм, единственная его проблема, в том, что все документы вами создаваемые, являются публичными, но это можно легко исправить, внесением некоторой суммы на счет владельцeв сервиса.

Сам я остановился на gliffy. Будет интересно услышать Ваше мнение, кто чем пользуется.