Динамическое конфигурирование подключения к БД

Общие вопросы по использованию фреймворка. Если не знаете как что-то сделать и это про Yii, вам сюда.
Ответить
xstupid_kidzx
Сообщения: 10
Зарегистрирован: 2010.07.26, 16:53

Динамическое конфигурирование подключения к БД

Сообщение xstupid_kidzx »

Здравствуйте!
С некоторых пор я разрабатываю сайт, который в дальнейшем необходимо было расширить на еще одну страну. Так как не было времени осуществлять гибкость первоначального варианта для поддержки нескольких стран, пришлось просто скопировать веб-приложение в новую папку /ua/

Таким образом получилась ситуация, что информацияи конфигурация на этих двух сайтах практически одинаковая, за исключением некоторых параметров, а именно: валюта, некоторые абзацы и подключение к БД.

Сейчас я решил начать изучение фреймворка Yii и переписать данный проект, но сделать его гибким, чтобы можно было безболезненно добавлять все новые и новые конфиги для разных стран.

Я почти все продумал, как это можно сделать, но именно сейчас меня интересует то, как мне обеспечить подключение к нужной базе.

Я уже читал статьи про динамический выбор конфига, а также про использование нескольких БД в одном проекте, но это не совсем то, что мне нужно.

Сейчас постараюсь объяснить, как хочу это реализовать.

Как вариант:

Код: Выделить всё

//config/main.php

'db_ru' => array(
            'connectionString' =>
            'mysql:host=localhost;dbname=db_ru',
            'emulatePrepare' => true,
            'username' => 'root',
            'password' => '',
            'charset' => 'utf8',
        ),
'db_ua' => array(
            'connectionString' =>
            'mysql:host=localhost;dbname=db_ua',
            'emulatePrepare' => true,
            'username' => 'root',
            'password' => '',
            'charset' => 'utf8',
        ),

 
Но я хочу всегда обращаться просто к объекту db, и всегда получать именно то подключение, которое мне нужно:

Код: Выделить всё

//config/main.php

'db_ru' => array(
            'connectionString' => array(
                'ru' =>  'mysql:host=localhost;dbname=db_ru',
                'ua' =>  'mysql:host=localhost;dbname=db_ua'
            ),
            'emulatePrepare' => true,
            'username' => 'root',
            'password' => '',
            'charset' => 'utf8',
        ),
 
После чего переопределить класс CDbConnection и в нем уже выбрать нужный конфиг, в зависимости от выбранной страны.
По этому пути я сейчас и иду.

Я переопределил класс CUrlManager, и теперь в функции init() он динамически формирует правила разбора вида:
'<lang:(язык1|язык2|...)>(/)?<uri:(.*)>' => '<uri>'

И по-хорошему, когда я обращусь к своей БД первый раз, то переопределенный класс CDbConnection и узнает из $_GET['lang'], какую базу мне включить. Но тут у меня возник такой вопрос, а что будет если я обращусь к БД раньше, чем УРЛ успеет распарситься?
И собственно мой вопрос состоит в том, как мне сделать так, чтобы при первом обращении к БД, переопределенный класс смотрел - распарсилась ли уже УРЛ, либо нужно распарсить ее?
Пока предметная область (Yii framework) мною не очень хорошо понята и изучена, поэтому я бы хотел выслушать конструктивную критику и предложения.
Мне кажется нужно смотреть на события
isergey
Сообщения: 83
Зарегистрирован: 2010.01.16, 21:05

Re: Динамическое конфигурирование подключения к БД

Сообщение isergey »

Напишите наследника от CDbConnection и в нем распарсите URL. URL передается на сервер и парсится самим интерпритаторм, так что вы можете извлеч параметр подключения еще до установления соединения с базой.
xstupid_kidzx
Сообщения: 10
Зарегистрирован: 2010.07.26, 16:53

Re: Динамическое конфигурирование подключения к БД

Сообщение xstupid_kidzx »

isergey писал(а):Напишите наследника от CDbConnection и в нем распарсите URL. URL передается на сервер и парсится самим интерпритаторм, так что вы можете извлеч параметр подключения еще до установления соединения с базой.
но в таком случае УРЛ будет парситься дважды, а вдруг правил парсинга будет очень много в дальнейшем? Не сказится ли это на скорости работы приложения?
isergey
Сообщения: 83
Зарегистрирован: 2010.01.16, 21:05

Re: Динамическое конфигурирование подключения к БД

Сообщение isergey »

зачем два раза. php обрабатывает юрл один раз, а приложение использует массив $_GET или $_POST для доступа к переменным
xstupid_kidzx
Сообщения: 10
Зарегистрирован: 2010.07.26, 16:53

Re: Динамическое конфигурирование подключения к БД

Сообщение xstupid_kidzx »

Последовал совету isergey, вот что у меня получилось.

Мой компонент "Менеджер страны" загружается перед загрузкой всех остальных модулей:

Код: Выделить всё

//config/main.php

'preload' => array('log', 'CountryManager'),
 
При инициализации он выполняет следующие действия:

Код: Выделить всё

public function init()
{
    //Загружаем урл менеджер
    $urlManager = Yii::app()->getUrlManager();
    //Добавляем свои правила к существующим
    $urlManager->rules['<lang:(' . implode('|', $this->languages) . ')>(/)?<uri:(.*)>'] =  '<uri>';
    //Заново инициализируем компонент урл менеджера, чтобы компонент прошел новые правила (processRules())
    $urlManager->init();
    //Парсим запрос пользователя
    $urlManager->parseUrl(Yii::app()->getRequest());
    //Проверяем работоспособность
    echo print_r($_GET);
}
 
После чего и будет расширен компонент CDbConnection, который и подгрузит необходимую страну со 100% уверенностью, что УРЛ уже распарсилась.

Но здесь есть некоторые минусы:
1. УРЛ менеджер инициируется 2 раза (когда я получаю его объект и после добавлений своих правил) - как дописать конфигурацию на лету к еще не созданному компоненту я так и не нашел.
2. Запрос пользователя парсится 2 раза (в моем компоненте и при вызове processRequest).

Кто что думает по этому поводу?
isergey
Сообщения: 83
Зарегистрирован: 2010.01.16, 21:05

Re: Динамическое конфигурирование подключения к БД

Сообщение isergey »

Хм, а завести статические переменные, например, для юрл менеджера?
Ответить