Барахолка с нуля. Часть 1

    Итак, как я и обещал, начинаем цикл статей о разработке барахолки на Codeigniter.
    Мы вместе, пошагово будем разрабатывать барахолку.

    1.1 Начало


    Давайте сначала подготовимся. Что нужно для работы?
    1. Конечно Apache + Mysql + PHP = Denwer (для начинающих — супер)
    2. Редактор – в моем случае это простенький блокнот-редактор PsPad с подсветкой синтаксиса. Знаю, что есть навороченные Zend Studio и Eclipse – мы не будем себе пока ничего усложнять
    3. Связка IE 6 + Opera + Firefox – нужно делать сайт кроссбраузерным

    Для этого сайта я зарезервировал домен baraholka.rv.ua, потому что я живу в Украине, в городе Ровно.

    Для нормального понимания нужно быть знакомым с Php, Mysql, CSS, HTML, JS(jQuery) и все-таки с Codeigniter`ом.

    Будем предполагать, что шаблон у нас уже есть. И хотя в моем случае не супер дизайнерский – для обучения подойдет.

    Я думаю установку denwer`a можно пропустить. Теперь в папке home, куда вы установили Denwer, создаем папку baraholka.local. В ней папку www.
    Также нужно поставить и сам Codeigniter. Заходим на сайт codeigniter.com, качаем последнюю версию.
    Распаковываем содержимое архива в папку www.

    С этого момента, в статьях путь к папке www я буду заменять на WEB_ROOT, то есть стандартно это Z:\home\baraholka.local\www
    Также иногда будет употребляться сокращенная форма Codeigniter — CI


    Перезапускаем Apache, и пытаемся зайти на baraholka.local – если сработало, значит все ок.
    Итак, я сверстал вот такой шаблон – baraholka.rv.ua/lesson/1/template.zip. Распаковываем архив также в WEB _ROOT.
    Что же мы сейчас имеем? Шаблон и установленный Codeigniter.

    1.2 Настройка Codeigniter



    Теперь, мы должны подготовить настройки Codeigniter к правильной работе. В файле WEB_ROOT/system/application/config находятся все основные конфигурационные файлы.
    1. Правим autoload.php
      $autoload['libraries'] = array('database', 'session'); - мы все равно будем использовать базу данных и сессии. А остальное допишем потом.
    2. Правим config.php
      $config['base_url'] = "http://baraholka.local/"; - базовый урл, используется хелпером для создания ссылок
      $config['index_page'] = ""; - так как мы хотим иметь красивый URL, нужно будет еще добавить файлик .htaccess + изменить индексную страницу на пустую
      $config['charset'] = "Windows-1251"; - и хотя все гласят использовать UTF-8, мне пока это по душе

    3. Правим database.php
      $db['default']['hostname'] = "localhost";
      $db['default']['username'] = "root";
      $db['default']['password'] = "";
      $db['default']['database'] = "baraholka";
      Думаю добавить новую базу “baraholka” смогут все. А сами параметры подключения – стандартные для Denwer`a
      $db['default']['char_set'] = "cp1251";
      $db['default']['dbcollat'] = "cp1251_general_ci";
      Так как кодировка на сайте 1251, то и с базой должны работать в этой кодировке

    4. Правим routes.php
      $route['default_controller'] = "main"; - как то более правильно, чем welcome.


    Также, что бы убрать из URL index.php, мы должны добавить .htaccess в папку WEB_ROOT
    Качаем его baraholka.rv.ua/lesson/1/htaccess. Переименовываем в .htaccess

    Кто не разобрался с некоторыми значениями – прошу в документацию — codeigniter.com/user_guide

    1.3 Дефолтный контроллер и нарезка шаблона


    Теперь нужно порезать наш шаблон на основные части – header,footer. Кто то может спросить:
    «Зачем таким заниматься? Можно же просто для каждого нового контроллера создавать отдельный шаблон»
    А если вы захотите сменить логотип? Будете каждую страницу менять?
    Поэтому давайте создадим новый контроллер – WEB_ROOT/ system/application/controllers/main.php
    У него будет вот такой код:
    <?php
    
    class Main extends Controller {
    
    	function Main()
    	{
    		parent::Controller();	
    	}
    	
    	function index()
    	{	
    				
    		$this->load->view('header');
    		$this->load->view('main/index');
    		$this->load->view('footer');
    	}
    }
    ?>
    


    Как видно по коду, мы должны так разделить шаблон, что бы при соединении header + footer мы получили полностью изначальный шаблон. А граница между ними – это место, куда мы будем загружать наши шаблоны. Таким образом у нас будет такая методика:
    Мы всегда подключаем header и footer. Между ними файл, который находится в папке с именем текущего контроллера и в файле с именем действия. Такая структура есть достаточно удобной и не путает.

    Теперь нужно все-таки поделить шаблон.
    Создаем файлы header.php и footer.php и main/index.php в
    WEB_ROOT/ system/application/views/footer.php
    WEB_ROOT/ system/application/views/header.php
    WEB_ROOT/ system/application/views/main/index.php

    Теперь берем наш шаблон, который подготовил я и открываем его редактором. Выделаем все содержимое до строки
    <div id="center" class="column" >

    Включительно. Все перемещаем в файл header.php и сохраняем.
    Теперь, ищем закрывающий тег этого div (что бы проще найти, используйте редакторы с подсветкой кода)
    И все, начиная с него и до конца копируем в footer.php.
    В файл main/index.php пишем просто TEST.
    Теперь если вы загрузите baraholka.local, вы должны увидеть наш шаблон, но уже теперь он выводится с помощью PHP.
    Казалось бы, что все хорошо. Но посмотрите – в footer.php мы держим шаблоны левой и правой колонки, что есть не правильно. Поэтому вырезаем их содержимое из footer
    от <div id="left" class="column">

    до закрывающего тега. Аналогично с правой колонкой. Вырезанные данные помещаем в left.php и right.php соответственно. На месте выреза пишем:
    <?$this->load->view('left');?>
    и
    <?$this->load->view('right');?>

    соответственно.

    В Украине популярный как украинский язык, так и российский. Никого из пользователей обижать не хочется, поэтому нужно поддерживать два языка. Сама идея такая – в файле мы держим набор преопределенных названий выражений. И используем их из разных файлов в зависимости от текущего языка. Техническая реализация мне понравилась от человека с ником mihailt — habrahabr.ru/blogs/codeigniter/30521. Я возьму от его примера только часть – реализация многоязычности.
    Вырезка из его статьи:
    Для начала подготовим наше приложение:
    расширяем роуты:
    Открываем routes.php(/system/application/config/routes.php)
    добавляем следующие строчки:
    $route['(ru|ua)'] = $route['default_controller'];
    $route['(ru|ua)/(.+)'] = "$2";


    таким образом, теперь мы к любому методу, любого контроллера можем обращаться 3 способами:
    baraholka.local/controller/action
    http:// baraholka.local/ru/controller/action
    http:// baraholka.local/ua/controller/action

    Создаём также 2 языковых файла main_lang.php (/system/application/language/english/main_lang.php и /system/application/language/russian/main_lang.php)

    Создадим файл My_Controller.php (/system/application/libraries/My_Controller.php)

    <?php
    class MY_Controller extends Controller {
    
    	var $language;
    	
    	public function MY_Controller()
    	{
          	parent::Controller();
          	//$this->output->enable_profiler(true);
          	// определяем язык
          	$lang = $this->uri->segment(1);
    
          	if($lang == 'ru')
    		  {
            	$this->language = $lang;
          	}
          	else 
    		{
             	$this->language = 'ua';
          	}
    
          	// подгружаем нужный язык
          
          	switch($lang)
    		{
          	
             case 'ru':
             
    	         $this->lang->load('main', 'ru');
    	         $this->config->set_item('language', 'ru');
    	         break;
    
             default:
             
    	         $this->lang->load('main', 'ua');
    	         $this->config->set_item('language', 'ua');
    	         break;
    
          	}
    
        }
    }
    
    
    




    Измените наш контроллер main. Теперь он должен наследоватся от MY_Controller, а не от Controller.
    Протестируйте нашу страницу. Она должна откликаться на
    1. baraholka.local/main/index
    2. baraholka.local/ua/main/index
    3. baraholka.local/ru/main/index


    Перейдем к последней главе в этой части.

    1.4 Структура базы данных



    Теперь нам нужно продумать хоть немного структуру БД.
    Сначала нужно создать саму БД. Я назвал ее baraholka.
    Так как я планирую выводить в левой колонке список разделов и категорий, нам нужно их описать в базе.
    Я выбрал названия таблиц cat_main и cat_sub.

    cat_main //таблица разделов
    • INT main_id PK autoincrement //ид раздела
    • VARCHAR(50) main_name_ua //имя раздела на украинском
    • VARCHAR(50) main_name_ru //имя раздела на русском


    cat_sub //таблица категорий
    • INT main_id //ид раздела к которому принадлежит эта категория
    • INT sub_id PK autoincrement //ид категории
    • VARCHAR(50) sub_name_ua //имя раздела на украинском
    • VARCHAR(50) sub_name_ru //имя раздела на русском


    Я подготовил дампы этих двух таблиц, так что вам остается только выполнить запросы
    baraholka.rv.ua/lesson/1/cat_main.sql
    baraholka.rv.ua/lesson/1/cat_sub.sql

    В этой части все. В следующей части мы будем добавлять боковую панель категорий, с использованием jQuery. А также сделаем авторизацию пользователей.

    Цикл статей «Барахолка с нуля»
    Часть 1

    Поделиться публикацией

    Похожие публикации

    Комментарии 137

      0
      ух-ты! буду следить за прогрессом!
        +1
        ТыманчиЫрган — Сodeigniter Шаг за Шагом. Пример построения простейшего блога/CMS на Сodeigniter — этот цикл уроков мне понравился значительно больше статьи выше.
        +1
        Раз уж затрагивается кроссбраузерность — укажите в Content-Type в мете кодировку.
          +6
          Если уж вы постоянно вызываете футер и хидер, не проще ли использовать один шаблон (с футером и хидером) и в него подключать уже само содержимое?
          Тогда вместо
          $this->load->view('header');
          $this->load->view('main/index');
          $this->load->view('footer');
          

          можно использовать что-то вроде
          $data['body'] = 'page';
          $this->load->view('main/index', $data);
          


          a сам шаблон построить примерно так:
          <div id='header'>какой-то хтмл-код</div>
          <div id='body'>
               <?php $this->load->view($data) ?>
          </div>
          <div id='footer'>какой-то хтмл-код</div>
          


          И все-таки, предпочтительнее UTF-8 кодировка
            0
            Извиняюсь, конечно же не <?php $this->load->view($data) ?> а <?php $this->load->view($body) ?>
              0
              Можно и так. Только подуймате о данных. Прийдется собирать все в матрицу, что бы когда будет сделан extract, вашы данные остались в массиве
                0
                Не понял немного. Какой extract и зачем его делать? Приведите пример того, что вы имеете в виду.

                Данные в шаблон в любом случае придется передавать.
              +2
              А мне нравится подход:
              $Content = $this->load->view("sometemplate",$templatedata,TRUE);
              $this->load->view("maintemplate",array("Content"=>$Content));
              

              А в шаблоне maintemplate:
              <title>Шаблон</title>
              <?=$Content;?>
              
                0
                В принципе, так же как и у меня, только здесь вместо передачи имени шаблона, передается содержимое шаблона в переменной
                  +1
                  Не совсем так, у Вас происходит загрузка вида
                  $this->load->view($body)
                  внутри вида
                  $this->load->view('main/index', $data);.

                  а у HeadWithoutBrains все виды формируются в контроллерах и загрузка вида происходит 1 раз, что мне кажется, более правильно. + видно где и что подгружается.

                  а в Вашем варианте нужно открывать виды и смотреть где и что грузится + таскать данные все время для внутренних видов, возможно в $this->load->view($body) нужно будет передать что — то.
                    0
                    Ну тут уже кто к чему привык :)
                    А в $this->load->view($body) данные передаются из вызывающего контроллера без проблем.
                  +2
                  PHP short tag не рекомендованы к употреблению.
                    +1
                    и действительно:
                    ; NOTE: Using short tags should be avoided when developing applications or
                    ; libraries that are meant for redistribution, or deployment on PHP
                    ; servers which are not under your control, because short tags may not
                    ; be supported on the target server. For portable, redistributable code,
                    ; be sure not to use short tags.

                    НО!!! т. к. сервер все-таки под контролем, никто не помешает их использовать.
                    (вы вообще видели хостинг где short tags отключены?)
                      +7
                      Есть стандарты и рекомендации. И следование им еще никому не вредило.
                      –1
                      Да, не рекомендованы. Поэтому в codeigniter есть функция, которая короткие переводит в полные.
                      А вообще, то мне так нравиться — <?=$var?> — почти так удобно, как и шаблонизаторе типа Smarty, зато не используем шаблонизатор.
                        +1
                        См выше. Смарти — это другое. И если в ущерб удобству идти против стандартов, то получим еще один IE
                          +1
                          Я думаю, что все же лучше прислушаться к рекомендациям, иначе может случиться, что вы будете писать код, для какого-либо клиента, используя <?= ?> и в один прекрасный момент вас достанут с тем, что «вдруг сайт перестал работать».
                        0
                        считаю наиболее правильным и удобным с точки зрения верстки. Нету разрыва кода. + то, что я описал для larikov
                      +5
                      О, клас. Я постараюсь написать как создать такую же барахолку с помощью Kohana.
                        0
                        А я тогда могу на выбор: CakePHP или Symfony :-)
                          0
                          Будет здорово, если напишете. Кстати, Вы используете встроенный ORM? Смотрел пример создания блога на Кохане и столкнулся спроблемой удаления записей в связанных таблицах.
                          +1
                          А на счет мультиязычности, то так же интересующимся людям предлагаю посмотреть на это решение
                          Пока что оно меня не подводило, и очень удобное. В $this->config->item(«language») сразу сваливается язык который был в урле, и позволяет добавлять новые языки через два массива, не редактируя код.
                            +1
                            Было бы замечательно, если бы код был с отступами, а не выровнен по левому краю…
                            Проставьте хотя бы pre…
                              0
                              проставил
                                0
                                Спасибо, так гораздо удобнее читать
                              0
                              Мультиязычность лучше всего реализовывать через языковые константы.
                                0
                                Удобнее всего работать с gettext. Где есть уже обкатанные инструменты для просмотра различий, изменений, поиска новых строк.

                                Изобретая очередной велосипед, вы вновь сталкивайтесь с уже решёнными проблемами.

                                Признайтесь, когда нужно что-то по-быстрому поправить в локализации, вы всегда будете поправлять это в других языковых файлах?
                                0
                                Правильно. Я с вами согласен

                                Например:

                                /ru/main_lang.php
                                $lang['registration'] = 'Регистрация';

                                /ua/main_lang.php
                                $lang['registration'] = 'Реєстрація';
                                  +1
                                  Извените, хабра глючит. Продолжу:
                                  1. для каждокой надписи определяется константа
                                  (4example: P1_ENTER)
                                  2. для каждого языка выделяется языковой файл
                                  (4example: lang_ru.php)
                                  3. в языковом файле определяем все константы
                                  (4example: )
                                  4. в зависимости от языка полключаем нужный файл
                                  (4example: )
                                  5. отображаем константу в документе
                                  (4example: )
                                  6. выбранный язык хранится в сессии или куках, дефолтный язык можно определить по ИП или поставит в конфиге.

                                  Проверено, работает максимально быстро. Трудностей в разработки нет, даже легче, не нужно сразу думать над названием кнопочки или ссылочки.
                                    0
                                    :( хабра зажевала PHP код

                                    3. define('P1_ENTER', 'Вход')
                                    4. include lang_ru.php
                                    5. echo P1_ENTER (я хотел написать вывод через шот-тег, но не понятно как тут хабр питается этим)

                                    Почему константы, а не "$lang['registration'] ", как выше? Очень просто, константы будут отображаться при автокомплите, что исключит лишние заморочки с их запоминанием и возможные ошибки из-за опечаток.
                                      0
                                      разницы практически нет. можно и с константами, а можно без.

                                      на сколько по вашему код
                                      switch($lang):

                                      case 'en':
                                      $this->lang->load('main', 'english');
                                      break;

                                      case 'ru':
                                      $this->lang->load('main', 'russian');
                                      break;

                                      default:
                                      $this->lang->load('main', 'english');
                                      break;

                                      endswitch;


                                      отличается от:

                                      switch($lang):

                                      case 'en':
                                      include_once('/lang/main_english.php');
                                      break;

                                      case 'ru':
                                      include_once('/lang/main_russian.php');
                                      break;

                                      default:
                                      include_once('/lang/main_english.php');
                                      break;

                                      endswitch;


                                      на мой взгляд практически ни чем.
                                        0
                                        отличие в define('P1_ENTER', 'Вход'). Как я сказал, многие редакторы учитывают константы в автокомплите
                                          +1
                                          а многие не учитывают. и что?
                                          +1
                                          switch($lang){

                                          case 'en':
                                          case 'ru':
                                          include_once('/lang/main_'.$lang.'.php');
                                          break;

                                          default:
                                          include_once('/lang/main_en.php');
                                          break;

                                          }
                                            0
                                            извините, но это вы к чему?
                                              +1
                                              Убери switch )
                                                0
                                                а то, что при таком раскладе может быть main_paragvaj.php вы не подумали?

                                                ИМХО в статьях подобного типа не стоит максимально сокрощать код, потому как читаемость сразу падает.

                                                и ещё ИМХО — нисподающий switch в реальных проектах — затрудняет отладку.
                                                  +1
                                                  а как это может main_paragvaj.php заинклудится? в case'ах его нет, потому при попытке передать paragvaj заинклудится main_en.php

                                                  по поводу switch — затрудняет лишь когда нагромождения кода. если же в case'ах вызов одного-двух методов — читабельность не пострадает
                                                    –1
                                                    case 'py':
                                                    PY — код парагвая ))))

                                                    и т. д. и т. п.

                                                    вы уж сами забейте что вам надо, код привел для примера онли)

                                                    зы:

                                                    Официальный язык Парагвая — Испанский и Гуарани

                                                    тогда скорее будет case 'es': и case 'gua': соответственно
                                              +1
                                              Согласен с тем что ваш вариант быстр, удобен и проверен годами :)
                                              но появилась у меня тут мысль попробовать подход, который с первого взгляда кажется нелогичным.
                                              Выделять под языки отдельные шаблоны, ну чтобы было понятнее это можно описать так:
                                              /view/ru/ русские шаблоны /view/ua/ украинские.
                                              казалось бы что за бред, однако у этого подхода есть свои преимущества. например для разных языков мы можем использовать по-разному свёрстанный шаблон.
                                              Не знаю может я не прав, но после много часового набивания и правки (или перевода) языковых файлов, начинаешь понимать что текст лучше переводить в контексте HTML. + это поможет побороть возможные проблемы верстки на различных языках (например в немецком есть слова из 30-40 букв, и они могут порвать вашу ячейку по горизонтали)
                                                0
                                                такой подход имеет один большой минус а именно дублирование кода — представьте себе ситуацию у вас есть сайт с 4-5 языками и в один момент нужно изменить ну скажем нумерованные списки в шаблоне на не нумерованные и получается что изменения нужно производить в 4-5 файлах вместо одного.
                                                  0
                                                  У каждого варианта есть + и -. Для каждого сайта должен выбираться оптимальный, а не тот, который «я хочу попробывать».
                                                    0
                                                    Именно так, а дублирование кода как раз один из признаков того, что подход не является оптимальным.
                                                      0
                                                      Если это дублирование)) Просто для каждого варианта может быть дизайн отдельный). Я вообще поклонник gettext :)
                                            0
                                            Ребят, а кто подскажет как можно при работающем mod_rewrite распознавать url типа /controller/method/?param1=par_val1¶m2=par_val2
                                            чтобы можно было в методе получить значения param1, param2
                                            (В cakePHP это возможно, а в CodeIgniter не получается никак, даже через routes)
                                              +1
                                              то есть хочешь получать GET значения?
                                              code-igniter.ru/forum/topic154.html
                                              может быть, то что нужно
                                                0
                                                Именно то что нужно!!!

                                                Главное включить
                                                $config['uri_protocol'] = 'PATH_INFO';
                                                $config['enable_query_strings'] = TRUE;

                                                и вперед $this->input->get('param1')
                                                0
                                                $_GET['param1'] разве не сработает? Я при включённом mod_rewrite для ZF спокойно получал доступ к массивам $_GET и $_POST.
                                                  0
                                                  С CI по умолчанию чистится массив $_GET, а всё, что через адресную строку нужно получать, получаете через сегменты ЧПУ. Для безопасности и красоты урлов сделано.
                                                    +1
                                                    поэтому нужно использовать $this->input->get('param');
                                                0
                                                кстати если вы контроллер расширяете только для загрузки языка, то на мой взгляд, логичнее будет это дело запихнуть в библиотеку и вызывать в автолоуде.
                                                  +1
                                                  Плюс за статью за проделанную работу и за то, что автор поделился опытом.
                                                  НО такие статьи очень вредны. Более правильно было бы выложить исходники с комментами, не более… Для опытного программиста этого будет достаточно. Для новичков, без теоретической базы эта статья будет вредна, т. к. сейчас многие перейдут на CI и начнут делать откровенную чушь, т. к. не знают толком даже азов PHP. Читая такую статью не нужно думать – просто делай то написано.
                                                    +2
                                                    В config.php, $config['base_url'] я думаю луче будет так прописать:

                                                    $config['base_url'] = «http://».$_SERVER['HTTP_HOST'];
                                                    $config['base_url'] .= str_replace(basename($_SERVER['SCRIPT_NAME']),"",$_SERVER['SCRIPT_NAME']);
                                                      0
                                                      я, если чесно, не очень люблю использовать хелперы. Ссылки генерирую сам. А вообще конечно иногда в этом есть смысл
                                                        0
                                                        URL хелперы просто необходимо использовать в CI.
                                                        Или как вы прописываете в шаблонах ссылки на js, css, img файлы? Да и просто ссылки на страницы?
                                                          0
                                                          Ну он просто делает абсолютные ссылки типа /js/file.js.
                                                            0
                                                            Думаю, что автор скоро осознает, что все-таки хелперы надо использовать.
                                                            особенно, если проект вдруг необходимо будет перенести с site.ru на site.ru/path/
                                                              0
                                                              как это вдруг? я четко знаю что сайт будет в корне, и полные адреса ни к чему.
                                                              Но я не собираюсь доказывать что это очень хорошо, но и не согласен что это очень плохо.
                                                                +3
                                                                Если уж вы пишете туториал, то лучше не вводить в заблуждение тех, кто по этому материалу будет делать сайт. Вы тем самым, толкаете их на совершение ошибок в проектировании.
                                                                Вобщем, похоже что вы не воспринимаете другую точку зрения, считая что все что вы делаете — правильно.

                                                                И неужели вы собираетесь сделать только этот сайт и всё?
                                                                  0
                                                                  нет. я учитываю все замечания, и в следующих статьях исправлюсь.
                                                                  просто я люблю по дискутировать )
                                                                    0
                                                                    Но у вас странная дискуссия, что-то вроде «да, это хорошо, но у меня тоже неплохо поэтому оставлю как есть»

                                                                    Вы еще не сталкивались, видимо, со сторонними заказами, но бывает так, что работающий сайт расположен, а разрабатываемый — в субдиректории, вот тогда вы и вспомните о хелперах и о том, что их все-таки нужно было использовать.
                                                                  +1
                                                                  Вам говорят дело :-) Вот понадобится показать заказчику новую версию сайта. Что делать будете?

                                                                  А если он захочет убедиться что на его хостинге все будет работать? А предыдущую версию сайта убирать нельзя :-)

                                                                  Таких ситуаций встречается много.
                                                                    0
                                                                    ок, убедили )
                                                                    в следующей статье учту все свои ошибки
                                                                    0
                                                                    Лучгше бы ы упомянули, как это делается, с ходу не разбираясь во фреймворке и не сообразишь, а абс. пути писать не хочется.
                                                                  0
                                                                  Ненене, абсолютные ссылки — зло, мне например влом ставить каждую WVC на отд. вирт. хост, я их принципиально ставлю на один, но в разные папки
                                                                    0
                                                                    *CMS
                                                                      0
                                                                      поддомены 3 уровня имхо проще
                                                                        0
                                                                        Не, я про локалхост, папку создать быстрее чем вирт. хост. предупреждая след. вопрос, скажу — денвер — не хочу))
                                                              0
                                                              это удобно для разработки, однако попробуйте с таким конфигом вызвать index.php из php-cli
                                                                0
                                                                $config['base_url'] = ((isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] == «on»)? «https»: «http»);
                                                                $config['base_url'] .= "://".$_SERVER['HTTP_HOST']."/";
                                                                +1
                                                                Согласен. Но я и не все разжовывал. поэтому вообще новичкам будет сложно + они не сделают копипаст, потому что много чего нужно сделать ручками. В основном расчитывал на людей, которые только начали интересоватся фреймворком. И хотелось бы верить, что несколько моих статей позволят понимать CI с полуслова )
                                                                  0
                                                                  Дерзай. Если хоть кому-то твая работа будет полезна, это уже плюс.
                                                                    +3
                                                                    ИМХО. Было бы не плохо, если вы в след. статье опишите понятие паттерна MVC, назначение модели и т. д. По личному опыту, у многих начинающих много вопросов и неопределённости по использованию MVC, в часности моделей.
                                                                      +2
                                                                      без проблем. попробую )
                                                                        –1
                                                                        Позвольте с вами не согласиться, паттерн MVC не такой уж и новый и по нему уже существует не мало хороших статей. Я бы лучше послушал(почитал, порекомендовал почитать новичкам) об использовании методик системного анализа в разработке интернет приложений(сайтов), а ещё лучше методик ТРИЗ.
                                                                      0
                                                                      Супер! Всегда хотел начать учить Codeigniter всё рука не поднималась, теперь точно придётся. Надеюсь сэр вы нас не оставите в этом можно сказать онлайн курсе.
                                                                        0
                                                                        постараюсь… :)
                                                                        0
                                                                        INT main_id PK autoincrement //ид раздела к которому принадлежит эта категория
                                                                        INT sub_id //ид категории


                                                                        а разве одному разделу не может принадлежать несколько категорий?
                                                                        в смысле что может «autoincrement» должен быть у «sub_id»?
                                                                          0
                                                                          да, моя ошибка
                                                                          вот что делает плохой копипаст + невнимательность )
                                                                          0
                                                                          На самом деле код не очень хороший… Он многословен и не предназначен для повторного использования…
                                                                          Чтобы не быть голословным, пример с языками (определением)…

                                                                          public function __construct()
                                                                          {
                                                                              $this->setLanguage();
                                                                          }
                                                                          
                                                                          private function setLanguage()
                                                                          {
                                                                              $supportedLanguageList = //получаем из КОНФИГА список поддерживаемых языков
                                                                              $defaultLanguage            = //получаем из КОНФИГА дефолтовый язык
                                                                              $requestLanguage = $this->request->getParam('language', $defaultLanguage);
                                                                              $this->language = (in_array($supportedLanguageList, $requstLanguage)) ? $requestLanguage : $defaultLanguage; // Я подключаю дефолтовый, хотя можно и выдать ошибку "Такой язык не поддерживается".
                                                                          }
                                                                          


                                                                          Так мы получаем гораздо больше возможностей, за минимум усилий)).

                                                                          PS Автор, без обид, но наберись побольше опыта, прежде чем писать…
                                                                          PSS Данные даны на примере моей системки, но я думаю, что тут всё понятно.
                                                                          • НЛО прилетело и опубликовало эту надпись здесь
                                                                              0
                                                                              Как вы можете определить мой уровень, если моего то кода и нет?
                                                                              Загрузка шаблонов — мне так удобно. Языковый вариант — не мой, но мне понравился и подходит. Тем более что он правится очень редко. Моего кода в этой статье почти нет. Как можно определить мой уровень по добавлению елемента в массив?
                                                                                0
                                                                                > Код ну очень дилетанский
                                                                                Приведите конкретные примеры, кроме выбора языка, он не в счет
                                                                                  0
                                                                                  Когда человек пишет и приводит пример, то это его код и он с ним согласен. Если это не ты написал код, то кто?
                                                                                    –1
                                                                                    Да, с твоим кодом я согласен. Но это решение mihailt, которое работает нормально.
                                                                                    Если ты используешь какую нибудь чужую библиотеку, ты смотришь ее код и начинаешь исправлять?
                                                                                    Решение рабочее, возможно чуть чуть долгое. И что? Я уверен, если ты заглянешь в любой продукт с открытыми исходными кодами, там будет простор для рефакторинга. Вот если бы я начал стучатся к базе из контроллера напрямую — это был бы дилетант.
                                                                                      +1
                                                                                      Если видешь что что-то не так и собираешься это использовать, то это «что-то не так» нужно исправлять. Сейчас получается детский сад из разряда «а вот он то же так же сделал, почему мне сказали, а ему нет?»
                                                                                    0
                                                                                    Теперь примеры))
                                                                                    1. конструкция (в выборе языка) switch case — неоправданное зло т. к. сложна для модификации
                                                                                    2. Что за подключение хедера и футера в index (indexAction)? Вот только не надо «мне так удобно», мы должны писать код не «мне так удобно», а «чтобы всем было понятно».
                                                                                    3. Опять же вернёмся к выбору языка… Просмотри кусок ещё раз… Для чего 2 раза (первый в ифе, второй в свитче) определять что за язык?
                                                                                    4. Давай не будем утверждать «раз новичёк, значит денвер это круто». Первый www сервер что я воздвиг был апач и я ничуть не жалею, что я не воспользовался денвером… К тому же сейчас с этим (установка) гораааздо проще, т. к. материалов и манов на русском по установке LAMP (WAMP/MAMP) просто вагон…

                                                                                    Этого хватит?
                                                                                      0
                                                                                      1. согласен в данном случае. но вообще это не зло
                                                                                      например: есть переменная, может иметь значения 1,2,3 или другое
                                                                                      при 1,2,3 должны быть конкретные действия
                                                                                      будете писать
                                                                                      if($var == 1)

                                                                                      elseif($var == 2)

                                                                                      elseif($var == 3)

                                                                                      else


                                                                                      ?
                                                                                      2. Бывает, что нужно изменить только маленькую часть в header. Если использовать так называемые «темы», то при таком изменении нужно создавать новую тему, или писать еще код для различных вариантов.
                                                                                      Я показываю свое мнение, и каждый имеет свою точку зрения. А насчет «понятно» — я думаю как раз всем и понятно.

                                                                                      3. да, тут согласен, без вопросов
                                                                                      4. А вот тут не надо. Нужно уметь и то, и другое.
                                                                                      Например denwer автоматом сканит папку home, прописывает виртуальные хосты и прописывает их в hosts
                                                                                      Если ставить вручную, то и делать нужно это вручную, или писать свой скрипт.
                                                                                        0
                                                                                        По п.2, shaelf имеет в виду, что шаблон из контроллера надо вызывать один раз, а не формировать его, как это делаете вы.
                                                                                        Если посмотрите мой комментарий, в контроллере как раз таки шаблон вызывается один раз. И существует один главный шаблон, в него уже подключается изменяемый контент. Чтобы изменить что-то, надо менять только этот один шаблон. Но вы мне так и не ответили, почему это на ваш взгляд плохо, и почему надо делать какой-то extract, и куда потеряются данные.
                                                                                  0
                                                                                  Чтобы не быть голословным напишите пожалуйста поконкретнее какой код писать в каком файле
                                                                                  0
                                                                                  1. Имелся в виду данный вариант. Многие приверженцы ООП данную конструкцию называют «пережитком процедурного программирования», т. к. она в одну функцию много условностей добалвяет.

                                                                                  2. Название тем ты пишешь в шаблонах ручками????

                                                                                  4. Никогда не рассказывали, что на тестовом и продакшн сервере должен одинаковый софт стоять? По поводу «сканит и добавляет»… Сколько проектов в месяц ты поднимаешь?
                                                                                    0
                                                                                    давай 4 вопрос снимем. я скажу так: каждый разработчик должен уметь вручную поставить WAMP или LAMP, но и уметь использовать инструменты. Иногда на флешке нужно носить и показать что я сделал. И на чужом компе ставить с нуля WAMP — глупо. А так с флешки запустил denwer, он шустро все прописал и работаешь себе дальше.

                                                                                    2 вопрос напиши подробней.
                                                                                    Я темы понимаю так:
                                                                                      0
                                                                                      или лучше так. я не собираюсь доказывать правильность своего подхода. да, в нем есть недостатки, но есть и плюсы.
                                                                                      когда мы подставляем в шаблон переменные, они extract`ятся.
                                                                                      $pdata['a'] = 'a';
                                                                                      $pdata['b'] = 'b';
                                                                                      $pdata['c'] = 'c';

                                                                                      если мы подставим все в шаблон, мы получим $a,$b,$c. Что бы этого избежать, нужно писать
                                                                                      $pdata['data']['a'] = 'a';
                                                                                      $pdata['data']['b'] = 'b';
                                                                                      $pdata['data']['c'] = 'c';
                                                                                      мне так тоже не нравится.

                                                                                      иногда после вставки
                                                                                      $this->load->view('main/index');
                                                                                      нужно вставить что-то общее для многих страниц, но не всех.
                                                                                      Если будет тема, нужно писать в ней «обходной путь»

                                                                                      Но после всех слов, я с тобой согласен. Много чего можно еще дорабатывать и дорабатывать.
                                                                                      Для этого люди и обмениваются опытом.

                                                                                      Но согласись, за такие помарочки, обзывать человека дилетантом нельзя.
                                                                                        0
                                                                                        1. Дилетантом я никого не называл.
                                                                                        2. «Общее для всех страниц» обычно называют: обвязка, skeleton, layout (чаще всего).
                                                                                        3. «Обходной путь» называют обычно «хлебные крошки» и они должны генериться автоматм исходя из навигации (структуры) сайта.
                                                                                          0
                                                                                          1. сорри, это написал другой человек )
                                                                                          2. я знаю как называется. но ты меня не понял. я это называл «темой» (theme).
                                                                                          3. Нет, я совсем о другом. Понятно что «хлебные крошки» генерятся автоматом.
                                                                                          Я имел в виду, что если после основного контента нужно что то добавить, то мы просто пишем
                                                                                          $this->load->view('after_content'), а если это будет layout, то нужно уже думать.
                                                                                          ладно, давай остановим дискуссию. я спать хочу )
                                                                                          0
                                                                                          Так вот оно что вы имеете в виду под extract, не понимаю только, почему вам не нравится это. И как вы собираетесь передавать результаты в шаблон?

                                                                                          Если уж вы взялись писать обучающую статью, пишите не только _что_ вы делаете, но и объясняйте _почему_
                                                                                        +1
                                                                                        3. Правим config.php
                                                                                        $db['default']['hostname'] = «localhost»;
                                                                                        $db['default']['username'] = «root»;
                                                                                        $db['default']['password'] = "";
                                                                                        $db['default']['database'] = «baraholka»;


                                                                                        это не в config.php, а в database.php

                                                                                          0
                                                                                          А $route['default_controller'] правим в routes.php
                                                                                            –3
                                                                                            А это уже кому как нравиться. Мне нравиться, что при переводе на новый сервер нужно править только 1 файл.
                                                                                              +1
                                                                                              Эх… Извеняюсь за лирическое отступление. В руки бы насрать тем, кто минусует не обосновав за что…
                                                                                            +1
                                                                                            Почему не Unicode? И попробуйте какой-нибудь ORM. Например, Doctrine — он очень просто прикручивается к CI.
                                                                                              0
                                                                                              Спасибо, будет отличная практика!
                                                                                                +1
                                                                                                Статья интересна, но есть, на мой взгляд, несколько досадных упущений:
                                                                                                1) Для расширения языковых параметров CI, мне кажется лучше унаследовать и расширить именно языковую библиотеку (Language.php), а не контроллер. Пример файла application/library/My_Language.php (на PHP5, но можете переписать под ныне покойный PHP4):
                                                                                                <?php  if (!defined('BASEPATH')) exit('No direct script access allowed');
                                                                                                class XT_Language extends CI_Language
                                                                                                {
                                                                                                	private $hasURLIdiom = FALSE;
                                                                                                	private function setURLIdiom() {
                                                                                                		$CI =& get_instance();
                                                                                                		$idiom = $CI->uri->segment(1);
                                                                                                		$CI->config->set_item('def_language', $CI->config->item('language'));
                                                                                                		if (strlen($idiom) == 2 && is_dir(APPPATH . 'language/' . $idiom)) {
                                                                                                			$CI->config->set_item('language', $idiom);
                                                                                                		}
                                                                                                	}
                                                                                                	public function __construct() {
                                                                                                		parent::CI_Language();
                                                                                                	}
                                                                                                	public function load($langfile = '', $idiom = '', $return = FALSE) {
                                                                                                		if (! $this->hasURLIdiom) {
                                                                                                			$this->setURLIdiom();
                                                                                                			$this->hasURLIdiom = TRUE;
                                                                                                		}
                                                                                                		parent::load($langfile, $idiom, $return);
                                                                                                	}
                                                                                                }
                                                                                                

                                                                                                2) Также следует расширить URL helper, изменив функцию site_url для поддержки языкового сегмента в ссылке. В противном случае, зайдя по ссылке baraholka.rv.ua/ru/, все ссылки, созданные при помощи site_url будут все-равно вести на baraholka.rv.ua/. Пример файла application/helpers/My_url_helper.php:
                                                                                                <?php  if ( ! defined('BASEPATH')) exit('No direct script access allowed');
                                                                                                function site_url($uri = '') {
                                                                                                	$CI =& get_instance();
                                                                                                	$idiom = ($CI->config->item('language') == $CI->config->item('def_language')) ? "" : "/" . $CI->config->item('language') . "/" ;
                                                                                                	return $CI->config->site_url($idiom . $uri);
                                                                                                }
                                                                                                
                                                                                                  0
                                                                                                  3) И роуты можно немного изменить на случай, если вам захочется добавить еще парочку языков к вашему сайту (и такое случается). В таком случае, я исходил из принципа, что любой язык можно представить в двухбуквенном виде, однако у меня нет и не должно быть ни одного контроллера, в названии которого меньше 3 букв. Тогда роуты прописываются так:
                                                                                                  $route['[a-z]{2}'] = $route['default_controller'];
                                                                                                  $route['([a-z]{2}/)?(.*)'] = "$2";
                                                                                                  

                                                                                                  Дописав это в конец config/routes.php (вместо $route['(ru|ua)'] = $route['default_controller']; $route['(ru|ua)/(.+)'] = "$2";) и положив приведенные мной выше файлы в helpers и libraries мы получим полную языковую поддержку, не влазя в контроллеры или вьюшки.
                                                                                                    0
                                                                                                    насчет пункта 2: согласен. это я уже давно написал. но это должно было быть озвучено в следующих статьях
                                                                                                    0
                                                                                                    вместо свитча — так не лучше?
                                                                                                    // подгружаем нужный язык
                                                                                                    $this->lang->load('main', $this->language);
                                                                                                    $this->config->set_item('language', $this->language);
                                                                                                      +2
                                                                                                      Я весьма далек от разработки с помощью CodeIgniter. Но все же. Не кажется ли Вам что лучше сделать отдельную таблицу с полями id, lang_id, text и ее джойнить к таблицам с названиями категорий и пр.?
                                                                                                        0
                                                                                                        это тоже вариант. возможно будет несколько менее производительно, но вариант очень даже хороший
                                                                                                          0
                                                                                                          Если использовать кеширование запросов к БД (вы ведь собираетесь их использовать?), то будет менее производительно только при первом запросе или при изменении категорий
                                                                                                            0
                                                                                                            да.
                                                                                                        0
                                                                                                        вот мне интересно, будете вы осуждать мой подход
                                                                                                        например на каждой странице у нас должен быть список категорий. Я видел много всяких расширений, но мне нравится так:
                                                                                                        1. создаем модель с именем module
                                                                                                        2. пишем ее в автолоад
                                                                                                        3. в шаблоне, где нужно, вызываем ее и производим обход по категориям

                                                                                                        Какие можете предложить красивые решения?
                                                                                                          –1
                                                                                                          В шаблоне вызывать модель?
                                                                                                          Модель надо вызывать в контроллере
                                                                                                            0
                                                                                                            да, в контроллере.
                                                                                                            но вы же не будете в каждом действии каждого конроллера стучатся к модели и задавать переменные в шаблон
                                                                                                            хотя если не нравится модель, можна тоже самое сделать в библиотеке или вроде даже и в хелпере, и тоже ее в автозагрузку
                                                                                                              +1
                                                                                                              Именно в каждом контроллере вам надо вызывать модель для того, чтобы получить список категорий, и затем передавать этот список в шаблон.

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

                                                                                                              Я бы сделал приблизительно так:
                                                                                                              categories_model.php
                                                                                                              function getAllCategories(){
                                                                                                                 .......
                                                                                                                 return $data;
                                                                                                              }
                                                                                                              


                                                                                                              контроллер
                                                                                                              function index(){
                                                                                                                 $data['categories'] = $this->categories_model->getAllCategories();
                                                                                                                 $this->load->view('main', $data);
                                                                                                              }
                                                                                                              


                                                                                                              шаблон
                                                                                                              <?php foreach ($categories as $category):?>
                                                                                                               <?php echo anchor('show/category/' . $category->id, $category->name); 
                                                                                                              <?php endforeach;?>
                                                                                                              


                                                                                                              И внимательно посмотрите и осознайте следующую диаграмму:
                                                                                                                0
                                                                                                                да, тут я с вами полностью согласен. Но список категорий слева должен быть всегда. Какой бы я контроллер/действие не загрузил, оно должно быть слева. Вы будете каждый раз это присваивать?
                                                                                                                  0
                                                                                                                  Ну хорошо. Вот вы в самой статьей сделали MY_controller и от него отнаследовали контроллер main. Что вам мешает сделать контроллер MY_controller_with_categories (наследованием от MY_controller), который будет в конструкторе дёргать данные из модели и заносить их в специальную переменную, а те контроллеры в чьих view вам требуются эти данные наследовать соответственно уже от MY_controller_with_categories?
                                                                                                                    0
                                                                                                                    можно и так.
                                                                                                                    мне кажется мой способ нормальный
                                                                                                                    вот как будет выглядить:
                                                                                                                    <?foreach($this->module->get_cats() as $cat_main):?>
                                                                                                                    <?foreach($cat_main as $cat_sub):?>

                                                                                                                    <?endforeach;?>
                                                                                                                      +1
                                                                                                                      Вы можете делать так как Вам хочется, но поскольку Вы пытаетесь сделать учебное пособие, то было бы лучше сделать его грамотным
                                                                                                              +1
                                                                                                              В классическом MVC это не запрещено
                                                                                                              www.phpwact.org/pattern/model_view_controller#view
                                                                                                                0
                                                                                                                хоть где то прав )
                                                                                                                  +1
                                                                                                                  В целом я бы сделал это немножечко по-другому. Я не владею CI, потому буду писать в терминах абстрактного MVC-фреймворка.

                                                                                                                  View всегда декорируется некоторым шаблоном — layout-ом. Вы пытаетесь это сделать средствами CodeIgniter
                                                                                                                  Я бы сделал шаблон сайта в котормо указал куда помещать текущий view. Далее в месте где требуется выводить список категорий я бы написал код типа
                                                                                                                  <?php
                                                                                                                    Dispatcher::execute('category_list);
                                                                                                                  ?> 
                                                                                                                  


                                                                                                                  который бы запускал стандартные механизмы фреймворка, т. е. как будто юзер запросил контроллер category_list. В этом случае View я бы запретил декорировать шаблоном.
                                                                                                                    0
                                                                                                                    Ну вот по похожему действует HMVC расширение. Но мне оно показалось громоздким.
                                                                                                                        0
                                                                                                                        Прочитал. Вроде именно то что я и имел ввиду. Доков еще не читал по самому CI, но думаю там в любом случае можно запустить выполнение еще одного запроса внутри текущего.
                                                                                                                        0
                                                                                                                        Если это не грозит потерей производительности, то это самый удачный вариант, только надо бы добавить парамтры, типа ид выбранного раздела
                                                                                                                      –1
                                                                                                                      В таком случае автор может вообще не использовать контроллеры (они ведь ему будут нужны только для отображения шаблонов), а все действия производить в шаблонах.
                                                                                                                      Но это будет довольно странно :)
                                                                                                                        +1
                                                                                                                        В целом это никак не противоречит MVC. Главное чтобы модель ничего не знала о View.
                                                                                                                  0
                                                                                                                  ну что, в приниципе терпимо? или лучше мне даже и не соватся в это дело?
                                                                                                                    0
                                                                                                                    я о топике, если что )
                                                                                                                      0
                                                                                                                      Думаю что стоит продолжать
                                                                                                                        0
                                                                                                                        да продолжайте раз уж взялись ;)
                                                                                                                          0
                                                                                                                          да, буду
                                                                                                                            0
                                                                                                                            просто пока времени мало, думаю взятся за это на выходных
                                                                                                                          0
                                                                                                                          Видимо часть 2 мы не увидим никогда :)
                                                                                                                            0
                                                                                                                            Видимо, да :)
                                                                                                                              –1
                                                                                                                              а начало было хорошим =(
                                                                                                                                –1
                                                                                                                                Извините что дальше не напрягся… Появилась робота и стало очень мало времени, даже на выходных…
                                                                                                                                Но после долгих разработок хочу посоветовать сразу перейти на Kohana, и не тратить время на Codeigniter.
                                                                                                                                После Kohana смотрите Symfony + Doctrine и получайте удовольствие)))

                                                                                                                                Хотя в планах есть написать что то новенькое, не такое обьемное, что бы дописать до конца. Но это уже будет по Symfony или Kohana или Yii. Для себя CI я вычеркнул.

                                                                                                                              Только полноправные пользователи могут оставлять комментарии. Войдите, пожалуйста.

                                                                                                                              Самое читаемое