Вот как бывает. Стараешься что-то изучить, потом отвлекаешься, а потом, через несколько месяцев снова смотришь на свой код и думаешь - интересно, а как я это сделал?
Чтобы не забыть, опишу последовательность создания модели в Pylons.
1. Создаем новый проект, назовем его newapp.
$ paster create -t pylons newapp
$ cd newapp
2. В файл ./development.ini добавляем расположение файла базы данных, и указываем (опционально) автоматическую конвертацию в юникод.
sqlalchemy.url = sqlite:///%(here)s/newapp.sqlite
sqlalchemy.convert_unicode = true
3. В файл ./newapp/config/environment.py импортируем модуль алхимии и модель, которую создадим чуть позже.
import sqlalchemy as sa
from newapp import model
Там же, в методе load_environment добавим создание алхимического движка для нашей БД и запустим метод init_model
def load_environment(global_conf, app_conf):
____#.....................................#
____engine = sa.engine_from_config(config, "sqlalchemy.")
____model.init_model(engine)
4. В файле ./newapp/websetup.py импортируем модель
from newapp import model
И здесь же, в метод setup_config добавим строки, необходимые для генерирования базы данных из модели.
def setup_config(command, filename, section, vars):
____#...................................#
____log.info("Creating database tables")
____model.meta.create_all(bind=model.engine)
____log.info("Finished setting up")
5. Создаем модель в файле ./newapp/model/__init__.py
# Импортируем модули, которые могут нам понадобиться
from datetime import datetime
from sqlalchemy import Table, Column, Integer, String, DateTime, MetaData, ForeignKey, orm
meta = MetaData()
# Метод, стартуемый в шаге 3: публикуем алхимический движок и сессию, которую
# создаем для работы с БД с нужными нам опциями, и создаем привязки таблиц и
# классов, в т.ч. по внешним ключам.
def init_model(bind):
____global engine, Session
____engine = bind
____Session = orm.scoped_session(orm.sessionmaker(transactional=True, autoflush=True, bind=bind))
____orm.mapper(Sections,sections)
____orm.mapper(Articles,articles,properties={'section':orm.relation(Sections)})
# Описываем таблицы:
sections=Table('sections',meta,
____Column('id',Integer,primary_key=True,autoincrement=True,nullable=False),
____Column('name',String,default=u'',nullable=False)
)
articles=Table('articles',meta,
____Column('id',Integer,primary_key=True,autoincrement=True,nullable=False),
____# А эта колонка - с внешним ключом
____Column('section_id',Integer, ForeignKey('sections.id'),nullable=False,default=0),
____Column('name',String,default=u'',nullable=False),
____Column('body',String,default=u'',nullable=False),
____Column('created_at',DateTime(),nullable=False,default=datetime.now),
____# Обратим внимание, тут мы добавляем триггер на обновление записи
____Column('updated_at',DateTime(),nullable=False,default=datetime.now,onupdate=datetime.now)
)
class Sections(object):
____def __repr__(self):
________ return self.name.encode('utf8')
class Articles(object):
____ def __repr__(self):
________ return self.name.encode('utf8')
6. Реализуем модель в файл базы данных.
$ paster setup-app development.ini
7. Создаем контроллер ./newapp/controllers/index.py.
$ paster controller index
и добавляем в метод index код для добавления данных в наши таблицы и для извлечения.
section=model.Sections()
article.name=u'Раздел 1'
model.Session.add(section)
article=model.Articles()
article.section_id=1
article.name=u'Статья 1'
article.body=u'Много текста'
model.Session.add(article)
model.Session.commit()
sql=model.Session.query(model.Articles).get(1)
return sql.section # Вывод данных, получаемыех по внешнему ключу
Вот как-то так, если вкратце.
P.S. Чтобы было меньше проблем с кодировками, не лишним будет в начало каждого файла добавлять строку
#coding:utf8
2009-09-28
2009-09-04
Чужой среди своих: Linux в windows-домене
Об этом много чего написано, но если чисто-конкретно, то:
Указываем IP, маску подсети и шлюз в /etc/network/interfaces (с учетом, что IP статический):
iface eth0 inet static
address 192.168.xx.xx
netmask 255.255.0.0
gateway 192.168.xx.xx
auto eth0
Прописывем DNS сервера в /etc/resolv.conf (можно несколько):
nameserver xxx.xxx.xxx.xxx
nameserver xxx.xxx.xxx.xxx
Устанавливаем samba:
$ sudo apt-get install samba
Прописывем в /etc/samba/smb.conf доменное имя:
workgroup = DOMAIN
Перезапускаем сеть и samba:
$ sudo /etc/init.d/networking restart
$ sudo /etc/init.d/samba restart
Теперь, для удобства перемещения по сети можно установить удобную утилиту pyNeighborhood и smbfs
$ sudo apt-get install smbfs pyneighborhood
Настроить pyNeighborhood: указать папку для монтрования сетевых ресурсов, логин и пароль в сети, опции монтирования (очень актуальна кодировка, см тут). Остальное можно оставить по умолчанию. Программа проста и работает очень быстро. Особенно выручит она пользователей xfce, т.к. гномовский Nautilus умеет перемещаться по сетевым папкам, а Thunar - нет.
Указываем IP, маску подсети и шлюз в /etc/network/interfaces (с учетом, что IP статический):
iface eth0 inet static
address 192.168.xx.xx
netmask 255.255.0.0
gateway 192.168.xx.xx
auto eth0
Прописывем DNS сервера в /etc/resolv.conf (можно несколько):
nameserver xxx.xxx.xxx.xxx
nameserver xxx.xxx.xxx.xxx
Устанавливаем samba:
$ sudo apt-get install samba
Прописывем в /etc/samba/smb.conf доменное имя:
workgroup = DOMAIN
Перезапускаем сеть и samba:
$ sudo /etc/init.d/networking restart
$ sudo /etc/init.d/samba restart
Теперь, для удобства перемещения по сети можно установить удобную утилиту pyNeighborhood и smbfs
$ sudo apt-get install smbfs pyneighborhood
Настроить pyNeighborhood: указать папку для монтрования сетевых ресурсов, логин и пароль в сети, опции монтирования (очень актуальна кодировка, см тут). Остальное можно оставить по умолчанию. Программа проста и работает очень быстро. Особенно выручит она пользователей xfce, т.к. гномовский Nautilus умеет перемещаться по сетевым папкам, а Thunar - нет.
2009-09-02
Если FFmpeg при кодировании ругается на нехватку кодеков
На днях решил перекодировать пару видяшек для PSP жены, воспользовавшись ffmpeg, на что последний отреагировал, разведя руками - не знаю, мол, кодека mpeg4.
Стало ясно, что в системе установлен не полный набор кодеков. Чтобы решить эту проблему, делаем так:
Удаляем полностью ffmpeg и обновляем данные репозитариев:
$ sudo apt-get purge ffmpeg
$ sudo apt-get update
Устанавливаем полные библиотеки кодеков, они попросят удалить предыдущие. ОК.
$ sudo apt-get install libavcodec-unstripped-* libavdevice-unstripped-* libavformat-unstripped-* libavutil-unstripped-* libpostproc-unstripped-* libswscale-unstripped-*
Возвращаем ffmpeg:
$ sudo apt-get install ffmpeg
А вот скрипт, чтобы кодировать avi-шки в формат, который переваривает PSP:
#!/bin/bash
[ -d psp ] || mkdir psp
ffmpeg -i "$1" -f psp -s 368x208 -aspect 16:9 -vcodec mpeg4 -b 500k -acodec libfaac -ab 96k -ac 2 "psp/$1.MP4"
В интернетах встречается подобный скрипт, в котором написано "-acodec aac" - не верьте, будет ругаться.
Стало ясно, что в системе установлен не полный набор кодеков. Чтобы решить эту проблему, делаем так:
Удаляем полностью ffmpeg и обновляем данные репозитариев:
$ sudo apt-get purge ffmpeg
$ sudo apt-get update
Устанавливаем полные библиотеки кодеков, они попросят удалить предыдущие. ОК.
$ sudo apt-get install libavcodec-unstripped-* libavdevice-unstripped-* libavformat-unstripped-* libavutil-unstripped-* libpostproc-unstripped-* libswscale-unstripped-*
Возвращаем ffmpeg:
$ sudo apt-get install ffmpeg
А вот скрипт, чтобы кодировать avi-шки в формат, который переваривает PSP:
#!/bin/bash
[ -d psp ] || mkdir psp
ffmpeg -i "$1" -f psp -s 368x208 -aspect 16:9 -vcodec mpeg4 -b 500k -acodec libfaac -ab 96k -ac 2 "psp/$1.MP4"
В интернетах встречается подобный скрипт, в котором написано "-acodec aac" - не верьте, будет ругаться.
2009-08-18
MySQL, phpMyAdmin 3, root без пароля и backup.
phpMyAdmin не желает принимать авторизацию без пароля.
Правим файл /usr/share/phpmyadmin/libraries/config.default.php
# Строка 227:
$cfg['Servers'][$i]['nopassword'] = true;
# Строка 363
$cfg['Servers'][$i]['AllowNoPasswordRoot'] = true;
Забыт пароль root и его надо сменить или убрать вовсе.
Гасим MySQL сервер, например так:
$ sudo /etc/init.d/mysql stop
Запускаем его без учета привелегий:
$ sudo mysqld --skip-grant-tables
В консоли mysql вносим необходимые изменения в привелегии:
$ sudo mysql
mysql> UPDATE mysql.user SET Password='пароль_или_ничего' WHERE User='root';
mysql> FLUSH PRIVILEGES;
Перезапускаем сервер.
from sontan.name import this
Создание backup базы данных.
$ mysqldump --all-databases --user=NAME --password=PASS > /home/USER-NAME/sql-dump.sql
--all-databases можно заменить на конкретное имя БД.
Задать кодировку в скрипте:
--default-character-set=charset_name
Чтобы в коде дампа была команда установки кодировки:
--set-charset
И сожмем результат в gzip:
gzip --best /home/USER-NAME/sql-dump.sql
Читаем man mysqldump.
Правим файл /usr/share/phpmyadmin/libraries/config.default.php
# Строка 227:
$cfg['Servers'][$i]['nopassword'] = true;
# Строка 363
$cfg['Servers'][$i]['AllowNoPasswordRoot'] = true;
Забыт пароль root и его надо сменить или убрать вовсе.
Гасим MySQL сервер, например так:
$ sudo /etc/init.d/mysql stop
Запускаем его без учета привелегий:
$ sudo mysqld --skip-grant-tables
В консоли mysql вносим необходимые изменения в привелегии:
$ sudo mysql
mysql> UPDATE mysql.user SET Password='пароль_или_ничего' WHERE User='root';
mysql> FLUSH PRIVILEGES;
Перезапускаем сервер.
from sontan.name import this
Создание backup базы данных.
$ mysqldump --all-databases --user=NAME --password=PASS > /home/USER-NAME/sql-dump.sql
--all-databases можно заменить на конкретное имя БД.
Задать кодировку в скрипте:
--default-character-set=charset_name
Чтобы в коде дампа была команда установки кодировки:
--set-charset
И сожмем результат в gzip:
gzip --best /home/USER-NAME/sql-dump.sql
Читаем man mysqldump.
Редактируем текст в Firefox через Vim
Сразу к делу. Для того, чтобы редактировать тексты в полях форм интернет-страниц, для браузера Firefox есть замечательный плагин "It's all text!". Его настройки позволяют задать в том числе и горячую клавишу, что само по себе прекрасно. Представьте - переходите в поле ввода, чтобы отписаться на форуме или в гостевой, нажимаете сочетание клавиш - и пишете в вашем любимом редакторе, а сохраняя текст тем самым отправляете его в браузер. Красота!
Но что, если вы хотите воспользоваться консольным Vim?
При настройке плагина нужно указать полный путь к файлу редактора. Ну и запустим мы Vim. Ну и будет он где-то в бэкграунде. Неудобно! Нужно завернуть vim в консоль.
Хотел бы я воспользоваться таким способом, да только параметры запуска плагин не передает как надо. Что, руки вверх?
На помощь к нам спешит скрипт из трех строк. Я накидал его на питоне, но наверняка можно и десятком других способов. Делаем скрипт исполняемым и в настройках плагина указываем путь к нему. Назначаем горячую клавишу (у меня это Alt-W) и радуемся удобству.
#!/usr/bin/env python
import os,sys
os.system('gnome-terminal -e "vim %s" ' % sys.argv[1])
Или на bash:
#!/bin/bash
gnome-terminal -e "vim \"$*\""
Но что, если вы хотите воспользоваться консольным Vim?
При настройке плагина нужно указать полный путь к файлу редактора. Ну и запустим мы Vim. Ну и будет он где-то в бэкграунде. Неудобно! Нужно завернуть vim в консоль.
Хотел бы я воспользоваться таким способом, да только параметры запуска плагин не передает как надо. Что, руки вверх?
На помощь к нам спешит скрипт из трех строк. Я накидал его на питоне, но наверняка можно и десятком других способов. Делаем скрипт исполняемым и в настройках плагина указываем путь к нему. Назначаем горячую клавишу (у меня это Alt-W) и радуемся удобству.
#!/usr/bin/env python
import os,sys
os.system('gnome-terminal -e "vim %s" ' % sys.argv[1])
Или на bash:
#!/bin/bash
gnome-terminal -e "vim \"$*\""
Подписаться на:
Сообщения (Atom)