Русскоязычный форум, посвященный фреймворку Kohana

Все о фреймворке Kohana. Обсуждение уроков, документации.
Текущее время: 29 мар 2024, 03:45

Часовой пояс: UTC + 4 часа [ Летнее время ]




Начать новую тему Ответить на тему  [ Сообщений: 15 ]  На страницу 1, 2  След.
Автор Сообщение
СообщениеДобавлено: 04 июн 2013, 10:43 
Не в сети
Новичок

Зарегистрирован: 19 фев 2013, 08:32
Сообщения: 23
Здравствуйте, помогите пожалуйста с такой проблемой - при добавлении комментария все добавляется но как то коряво происходит редирект и не выводится блок с коментами, при этом ошибки не выдает
Код:
class Controller_Comments extends Controller {
 
    public function action_index()
    {
        if($this->request->is_initial())
            Request::initial()->redirect(URL::site(''));
 
        if(Request::initial() === Request::current())
      HTTP::redirect(URL::site());// защита от прямого доступа к коментариям
      
      $company_id = $this->request->param('id');
 
       
 
      if($_POST)
      {
         $_POST['user'] = trim($_POST['user']);
         $_POST['message'] = trim($_POST['message']);
   
         $post = Validation::factory($_POST);
         $post -> rule('user', 'not_empty')
         -> rule('user', 'min_length', array(':value', 4))
         -> rule('user', 'max_length', array(':value', 20))
         -> rule('email', 'email')
         -> rule('email', 'not_empty')
         -> rule('message', 'not_empty')
         -> rule('message', 'max_length', array(':value', 300));
   
         if($post -> check())
         {
            Model::factory('Comment')->create_comment($company_id, $_POST['user'], $_POST['email'], $_POST['message']);
            
            /*$uri = Request::detect_uri();
            
                                Controller::redirect($uri = '');*/
//если закоментировать этот кусок то все работаетно не очень корректно, не сбрасываются значения введенные пользователемкаким то образом в редирект попадает неправильный адрес
         }
         else
         {
            $errors = $post -> errors('validation');
         }
         
      }
 
        $comments = Model::factory('Comment')->get_company($company_id);
      $content = View::factory('/comment/companyshow')
                    ->bind('comments', $comments)
               ->bind('errors', $errors);
        $this->response->body($content);
    }
 
}


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: 05 июн 2013, 04:18 
Не в сети
Администратор
Аватара пользователя

Зарегистрирован: 24 июл 2012, 18:00
Сообщения: 701
Откуда: Murom, Russia
Совет: в таких ситуациях, когда непонятно как оно работает, нужно отсечь всё, оставить голый метод, добавлять требуемый функционал чуть ли не по строчке и смотреть (желательно в отладчик) что получается. Само собой те методы, которыми вы пользуетесь должны быть вам хотя бы поверхностно знакомы. Не достаточно просто скопировать кусок кода и потом удивляться, что происходит какая то магия ) Начните с малого

Вопрос на засыпку:
Вы используете здесь Request::redirect() и HTTP::redirect(). Почему? В чём их разница?


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: 05 июн 2013, 10:18 
Не в сети
Новичок

Зарегистрирован: 19 фев 2013, 08:32
Сообщения: 23
Sergey писал(а):
Вопрос на засыпку:
Вы используете здесь Request::redirect() и HTTP::redirect(). Почему? В чём их разница?

могу конечно ошибаться, я в программировании не то что бы чайник, самовар наверно вернее будет. Request::redirect() - это запрос к внутренней структуре приложения т.е. находим нужный роут и через него запускаем определенный в нем контроллер. HTTP - обращение к внешнему адресу. Применительно к моей ситуации - у меня после добавления комента запускается именно HTTP и соответственно кохана просто не находит роут комментариев ну и со всеми вытекающими.
Код:
$uri = Request::detect_uri();
в этом методе происходит, как я понял из мануала, автоматическое определение url основного запроса и в следующей строке нам надо определить адрес редиректа в уроке на сайте используется запрос
Код:
Request::initial()->redirect($uri);
но данный метод не работает в ко 3.3
Код:
Controller::redirect($uri = '');
при использовании такой конструкции положительного результата не происходит , ошибки не выдаются потому что кохана делает то что ей сказали, вот и вопрос как ей сказать что надо осуществить внутренний редирект в ко3.3
Сергей благодарю за наводку, поправьте если не так.


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: 05 июн 2013, 13:14 
Не в сети
Бывалый
Аватара пользователя

Зарегистрирован: 02 апр 2013, 16:26
Сообщения: 474
Откуда: Сергиев Посад
хм, он все-таки статический, почему-то мне казалось что наоборот
public static function redirect($uri = '', $code = 302)
{
return HTTP::redirect($uri, $code);
}

_________________
Майкл Джордан играет в баскетбол. Чарльз Мэнсон убивает людей. Я пишу код. У каждого свой талант.


Последний раз редактировалось WinterSilence 05 июн 2013, 14:07, всего редактировалось 1 раз.

Вернуться к началу
 Профиль  
 
СообщениеДобавлено: 05 июн 2013, 13:58 
Не в сети
Новичок

Зарегистрирован: 19 фев 2013, 08:32
Сообщения: 23
WinterSilence писал(а):
дело было не в бобине.. Controller->redirect($uri)

ErrorException [ Parse Error ]: syntax error, unexpected T_OBJECT_OPERATOR
неправильный синтаксис, и вообще методом научного тыка, а кохана большая, можно тыкаться хоть до морковкиной завязи. Вообще прекрасно работает и без редиректа, тут проблема скорее в том чтобы сбросить данные введеннве пользователем в форму.


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: 06 июн 2013, 03:15 
Не в сети
Администратор
Аватара пользователя

Зарегистрирован: 24 июл 2012, 18:00
Сообщения: 701
Откуда: Murom, Russia
Я в Gleez в качестве отправной точки использовал Kohana 3.2, многое конечно уже переписано, но всё же.
Ниже я опустил некоторые подробности, оставив лишь суть:

Основной класс шаблонов
Код:
<?php defined('SYSPATH') OR die('No direct access allowed.');

abstract class Gleez_Template extends Controller {
    protected $_internal = FALSE;

    public function before()
    {
        parent::before();
        if ( ! $this->request->is_initial())
        {
            $this->_internal   = TRUE;
            $this->auto_render = FALSE;
        }
        // ...
    }

    public function after()
    {
        if ($this->auto_render)
        {
            // ...        
        }
        elseif ($this->_internal)
        {
            $output = $this->response->body();
            $this->response->body($output);
        }
        // ...
        parent::after();
    }
 


Контролёр комментариев
Код:
<?php defined('SYSPATH') OR die('No direct script access.');

class Controller_Comment extends Template {

    protected $_route;

    public function before()
    {
        $this->_route = Route::get('comment')->uri(array('action' => 'list'));
        parent::before();
    }

    public function action_edit()
    {
        $id = (int) $this->request->param('id', 0);
        $comment  = ORM::factory('comment', $id);

        if ( ! $comment->loaded())
        {
            Kohana::$log->add(Log::ERROR, 'Attempt to access non-existent comment');

            if ( ! $this->_internal)
            {
                $this->request->redirect($this->_route, 404);
            }
        }

        // ...    
        $view = View::factory('comment/form')
                    ->bind('errors',      $this->_errors)
                    ->bind('post',        $comment);

        if ($this->valid_post('comment'))
        {
            $redirect = empty($this->redirect) ? $this->_route : $this->redirect ;

            try
            
{
                $comment->values($_POST)->save();
                Kohana::$log->add(LOG::INFO, 'Comment: :title updated.', array(':title' => $comment->title));

                if ( ! $this->_internal)
                {
                    $this->request->redirect($redirect, 200);
                }
            }
            catch (ORM_Validation_Exception $e)
            {
                $this->_errors = $e->errors('models', TRUE);
            }
        }

        $this->response->body($view);
    }
 


Многое опущено, код не идеальный, но суть кажется ясна.
Это что касается комментариев.
А то, что в Kohana 3.3 метод redirect появился у HTTP так это ж сути дела не меняет :)
Или вы хотите асинхронный запрос/ответ?


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: 06 июн 2013, 11:31 
Не в сети
Бывалый
Аватара пользователя

Зарегистрирован: 02 апр 2013, 16:26
Сообщения: 474
Откуда: Сергиев Посад
Sergey
Решение на основе $this->request->is_initial() понравилось, я как-то не учел этот момент -сделаю также :P
А сами контроллеры не очень: много действий производится вручную и не логично. Можно все оптимизировать и код контроллеров станет вдвое меньше.
Доберусь до дома, покажу свой вариант. Я как раз об этом собирался писать в следующем уроке по созданию cms

Код:
$output = $this->response->body();
$this->response->body($output);

для чего?

Код:
$id = (int) $this->request->param('id', 0); 

проще фильтр в орм настроить, чем приводить типы каждый раз

Код:
$comment->values($_POST)->save(); 

$_POST ? а почему не $this->request->post()? там вроде переменные уже подготовлены

Вместо:
Код:
$this->_route = Route::get('comment')->uri(array('action' => 'list'));

можно же было сделать универсальный вариант:
Код:
$this->_route = $this->request->route()->uri();

или
Код:
$class = strtolower(substr(get_class(), 11)); // Controller_Comment => comment
$this->_route = Route::get($class)->uri();

а array('action' => 'list') в default прописать

Код:
$view = View::factory('comment/form')
->bind('errors', $this->_errors);
..
$this->response->body($view);

тоже можно было сделать универсальным: задание $view перенести в before, задание ответа в after, место 'comment/form'
Код:
$class = strtolower(substr(get_class(), 11));
$class = str_replace('_', DS, $class) .  DS . $this->request->action();


Код:
$redirect = empty($this->redirect) ? $this->_route : $this->redirect; 

в before забиндить

Код:
$this->valid_post('comment') 

это должно быть в модели

код сохранения в метод модели инкапсулировать, например:
Код:
if ( ! $this->_errors = $comment->save($this->request->post()))
{
   Kohana::$log->add(LOG::INFO, 'Comment: :title updated.', array(':title' => $comment->title));
   if (!$this->_internal)
   {
      $this->request->redirect($redirect, 200);
   }
}

_________________
Майкл Джордан играет в баскетбол. Чарльз Мэнсон убивает людей. Я пишу код. У каждого свой талант.


Последний раз редактировалось WinterSilence 06 июн 2013, 12:02, всего редактировалось 1 раз.

Вернуться к началу
 Профиль  
 
СообщениеДобавлено: 06 июн 2013, 11:59 
Не в сети
Бывалый
Аватара пользователя

Зарегистрирован: 02 апр 2013, 16:26
Сообщения: 474
Откуда: Сергиев Посад
vchv
Код:
// при внешнем запросе или прямом обращении редирект на главную
if ($this->request->is_external() OR $this->request->is_initial())
{
   HTTP::redirect(URL::site());
}


но надо понимать, что данный контроллер по сути выступает виджетом и должен вызываться в основном контроллере
Код:
$comments_content = Request::factory('comments/index')->method(Request::POST)->post($this->request->post())->execute()->body();


если что можно попробовать вариант который учитывает редиректы
Код:
Request::factory('comments/index', array('follow' => TRUE))


я кстати понял почему я так был уверен, что redirect в контроллере не статичная функция - опечатка в мануале:
http://kohanaframework.org/3.3/guide/kohana/upgrading#redirects-http-300-301-302-303-307
http://kohanaframework.org/3.3/guide-api/Controller#redirect

_________________
Майкл Джордан играет в баскетбол. Чарльз Мэнсон убивает людей. Я пишу код. У каждого свой талант.


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: 07 июн 2013, 02:02 
Не в сети
Администратор
Аватара пользователя

Зарегистрирован: 24 июл 2012, 18:00
Сообщения: 701
Откуда: Murom, Russia
WinterSilence писал(а):
SergeyА сами контроллеры не очень: много действий производится вручную и не логично. Можно все оптимизировать и код


Ну, во первых я знаю :) Я же писал сам об этом выше. А во вторых, у нас сейчас в Gleez чётко обозначенный план действий, и оптимизация кода конролёра комментариев, даже не в первой десятке. Очень много работы в связи с тем, что мы переходим на использование сторонних (открытых) библиотек. В частности большинство контролёров будет "общаться" с ядром/базой данных/клинтом асинхронно


Вернуться к началу
 Профиль  
 
СообщениеДобавлено: 07 июн 2013, 03:04 
Не в сети
Бывалый
Аватара пользователя

Зарегистрирован: 02 апр 2013, 16:26
Сообщения: 474
Откуда: Сергиев Посад
ну так у вас на Gleez_Template базируются и другие контроллеры, в конечном итоге ведь задача в создании cms к которой сторонние программисты быстро и просто смогут добавлять разделы\модули, по крайней мере если планируете коммерческое\массовое применение. Ну если учесть, что в качестве ядра Кохана, то первый шаг уже сделан) А что планируете использовать? Асинхронно в данном случае через AJAX?

_________________
Майкл Джордан играет в баскетбол. Чарльз Мэнсон убивает людей. Я пишу код. У каждого свой талант.


Вернуться к началу
 Профиль  
 
Показать сообщения за:  Поле сортировки  
Начать новую тему Ответить на тему  [ Сообщений: 15 ]  На страницу 1, 2  След.

Часовой пояс: UTC + 4 часа [ Летнее время ]


Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 9


Вы не можете начинать темы
Вы не можете отвечать на сообщения
Вы не можете редактировать свои сообщения
Вы не можете удалять свои сообщения
Вы не можете добавлять вложения

Найти:
Перейти:  
cron
Все о фреймворке Kohana  | 
Powered by phpBB® Forum Software © phpBB Group