您好,UncleToo欢迎您!  为了更好的浏览本站,请使用高版本浏览器
RSS  Tag     设为首页 | 加入收藏
 您所在的位置:首页 > PHP技术 > PHP应用

使用 Laravel4 创建博客(二):Controllers/控制器

作者:UncleToo  来源:原创  日期:2014-02-18 8:13:36
收藏  评论:( 2 )  阅读:5710

在之前UncleToo已经发布了使用 Laravel4 创建博客(一),介绍了Laravel的安装及创建Model。本文,我将继续给大家介绍使用 Laravel4 创建博客的第二部分——Controllers/控制器


创建控制器

在Laravel中,我们通过扩展 app/controllers 目录的BaseController类来创建控制器,我们所有的控制器都存在app/controllers目录中。

注意:

Laravel没有任何限制应用程序的目录结构,我们可以根据我们的需要重新排列应用程序的目录结构,并相应地调整相关设置。

下面是一个控制器的例子:

<?php
//file: app/controllers/IndexController.php
                                                                                                                              
class IndexController extends BaseController {
                                                                                                                              
    public function showIndex()
    {
        // generates response from index.blade.php
        return View::make('index');
    }
}
                                                                                                                              
//file: app/routes.php
//registering route to controller actions
                                                                                                                              
Route::get('index','IndexController@showIndex');
                                                                                                                              
//In general
Route::get('route.name','SomeController@someAction');
Route::post('route.name','SomeController@someAction');
?>

从这个例子可以看出,控制器内部的action在app/routes.php只能怪已经有相应的路由表项,我们仍然可以通过前缀控制器的action名称与HTTP响应创建RESTful控制器,看下面的代码:

<?php
                                                                                                                         
class IndexController extends BaseController {
                                                                                                                         
    public function getAction()
    {
        //get request handling
    }
    public function postAction()
    {
        //post request handling
    }
}
                                                                                                                         
//registering route
Route::controller('index','IndexController);
?>

我们使用 Route::controller('route.name','ControllerName') 方法来注册RESTful控制器的路由,它会自动记录所有路由的动作。

注意事项:

1、通常一个动作都有一个关联的视图。 这种观点提供了action的预期响应的目的。

2、当我们从action返回一个数组,Laravel自动将此数组转换成JSON编码的响应。

3、我们使用protected $layout属性来设定一个主视图控制器。

4、我们可以使用内部主视图巢局部视图nest()方法。

5、我们可以使用nest()方法在试图中嵌套试图。

6、我们可以通过使用数据视图 with()方法或通过直接分配变量使用一个动态属性: $this->layout->variable='value'.


为我们的博客创建控制器

我们将通过创建启动BlogController用于博客的首页/索引页,查询和显示搜索结果,用户登录和注销,及处理其他类似的请求。

我们将创建一个 PostsController和一个 CommentsController,分别处理文章和评论。


BlogController

创建app/controllers/BlogController.php文件,并输入下面代码:

<?php
//file: app/controllers/BlogController.php
                                                                                                                  
class BlogController extends BaseController {
                                                                                                                  
    public function getIndex()
    {
        $posts = Post::orderBy('id','desc')->paginate(10);
        $posts->getEnvironment()->setViewName('pagination::simple');
        $this->layout->title = 'Home Page | Laravel 4 Blog';
        $this->layout->main = View::make('home')->nest('content','index',compact('posts'));
    }
                                                                                                                  
    public function getSearch()
    {
        $searchTerm = Input::get('s');
        $posts = Post::whereRaw('match(title,content) against(? in boolean mode)',[$searchTerm])
                     ->paginate(10);
        $posts->getEnvironment()->setViewName('pagination::slider');
        $posts->appends(['s'=>$searchTerm]);
        $this->layout->with('title','Search: '.$searchTerm);
        $this->layout->main = View::make('home')
                     ->nest('content','index',($posts->isEmpty()) ? ['notFound' => true ] : compact('posts'));
    }
                                                                                                                  
    public function getLogin()
    {
        $this->layout->title='login';
        $this->layout->main = View::make('login');
    }
                                                                                                                  
    public function postLogin()
    {
        $credentials = [
            'username'=>Input::get('username'),
            'password'=>Input::get('password')
        ];
        $rules = [
            'username' => 'required',
            'password'=>'required'
        ];
        $validator = Validator::make($credentials,$rules);
        if($validator->passes())
        {
            if(Auth::attempt($credentials))
                return Redirect::to('admin/dash-board');
            return Redirect::back()->withInput()->with('failure','username or password is invalid!');
        }
        else
        {
            return Redirect::back()->withErrors($validator)->withInput();
        }
    }
                                                                                                                  
    public function getLogout()
    {
        Auth::logout();
        return Redirect::to('/');
    }
                                                                                                                  
}
?>

当我们使用Route::controller()注册路由时(即:Route::controller('/','BlogController')),getIndex()将被映射到应用程序的默认路由

在getIndex()中,我们查询Post模型并得到一个Paginator实例与每页显示10条文章的paginate()方法,并将实例被传递给应用程序的索引视图。我们将通过这个变量循环索引视图,并在页面的底部显示文章分页。

我们使用 getSearch()action为博客提供搜索的功能。whereRaw()方法用于指定一个MySQL的全文搜索条件,匹配的结果是使用当时的检索paginate()方法来启用对结果模型的分页。另外,我们需要将搜索结果添加分页,否则,分页搜索结果将不会工作,这里使用 $post->appends()方法。

下面的三个action将用于用户身份验证。


PostsController

代码如下:

<?php
//file: app/controllers/PostsController.php
                                                                                                              
class PostController extends BaseController
{
                                                                                                              
    /* get functions */
    public function listPost()
    {
        $posts = Post::orderBy('id','desc')->paginate(10);
        $this->layout->title = 'Post listings';
        $this->layout->main = View::make('dash')->nest('content','posts.list',compact('posts'));
    }
    public function showPost(Post $post)
    {
        $comments = $post->comments()->where('approved', '=', 1)->get();
        $this->layout->title = $post->title;
        $this->layout->main = View::make('home')->nest('content', 'posts.single', compact('post', 'comments'));
    }
                                                                                                              
    public function newPost()
    {
        $this->layout->title = 'New Post';
        $this->layout->main = View::make('dash')->nest('content', 'posts.new');
    }
                                                                                                              
    public function editPost(Post $post)
    {
        $this->layout->title = 'Edit Post';
        $this->layout->main = View::make('dash')->nest('content', 'posts.edit', compact('post'));
    }
                                                                                                              
    public function deletePost(Post $post)
    {
        $post->delete();
        return Redirect::route('post.list')->with('success', 'Post is deleted!');
    }
                                                                                                              
    /* post functions */
    public function savePost()
    {
        $post = [
            'title' => Input::get('title'),
            'content' => Input::get('content'),
        ];
        $rules = [
            'title' => 'required',
            'content' => 'required',
        ];
        $valid = Validator::make($post, $rules);
        if ($valid->passes())
        {
            $post = new Post($post);
            $post->comment_count = 0;
            $post->read_more = (strlen($post->content) > 120) ? substr($post->content, 0, 120) : $post->content;
            $post->save();
            return Redirect::to('admin/dash-board')->with('success', 'Post is saved!');
        }
        else
            return Redirect::back()->withErrors($valid)->withInput();
    }
                                                                                                              
    public function updatePost(Post $post)
    {
        $data = [
            'title' => Input::get('title'),
            'content' => Input::get('content'),
        ];
        $rules = [
            'title' => 'required',
            'content' => 'required',
        ];
        $valid = Validator::make($data, $rules);
        if ($valid->passes())
        {
            $post->title = $data['title'];
            $post->content = $data['content'];
            $post->read_more = (strlen($post->content) > 120) ? substr($post->content, 0, 120) : $post->content;
            if(count($post->getDirty()) > 0) /* avoiding resubmission of same content */
            {
                $post->save();
                return Redirect::back()->with('success', 'Post is updated!');
            }
            else
                return Redirect::back()->with('success','Nothing to update!');
        }
        else
            return Redirect::back()->withErrors($valid)->withInput();
    }
                                                                                                              
}
?>


绑定模型路由

Laravel有一个很好的方法来将模型绑定到路由。我们使用 Route::model('parameter.name','model.name')指定绑定。

例如:

<?php
//file: app/routes.php
                                                                                                          
Route::model('post','Post');
                                                                                                          
Route::get('post/{post}',function(Post $post)
{
    echo $post->title;
                                                                                                          
});
?>

现在,当我们用文章id作为参数访问这个路由,文章与ID的对应关系将被自动注入到路由,这就是这个控制器的action。

在PostController中唯一的公共action是showPost,它用来在博客上显示一篇文章及其评论。在showPost action中,我们检索当前的所有允许评论文章,然后文章模型和评论传递给single视图(app/views/posts/single.blade.php)。

在这个控制器中,剩下所有的action将被用于在post模型中执行CRUD操作。我们将使用 listPost action在管理员界面以表格形式显示所有链接到CRUD的文章。

newPost action将被用来显示一个表单,管理员用户用来发布文章。 表单提交将通过savePost action处理。 在savePost中,如果它通过了验证规则,我们会保存请求数据,否则我们将返回并定位到错误。


CommentsController

代码如下:

<?php
//file: app/controllers/CommentsController.php
                                                                                                 
class CommentController extends BaseController {
                                                                                                 
    /* get functions */
    public function listComment()
    {
        $comments = Comment::orderBy('id','desc')->paginate(20);
        $this->layout->title = 'Comment Listings';
        $this->layout->main = View::make('dash')->nest('content','comments.list',compact('comments'));
    }
                                                                                                 
    public function newComment(Post $post)
    {
        $comment = [
            'commenter' => Input::get('commenter'),
            'email' => Input::get('email'),
            'comment' => Input::get('comment'),
        ];
        $rules = [
            'commenter' => 'required',
            'email' => 'required | email',
            'comment' => 'required',
        ];
        $valid = Validator::make($comment, $rules);
        if($valid->passes())
        {
            $comment = new Comment($comment);
            $comment->approved = 'no';
            $post->comments()->save($comment);
            /* redirect back to the form portion of the page */
            return Redirect::to(URL::previous().'#reply')
                    ->with('success','Comment has been submitted and waiting for approval!');
        }
        else
        {
            return Redirect::to(URL::previous().'#reply')->withErrors($valid)->withInput();
        }
    }
                                                                                                 
    public function showComment(Comment $comment)
    {
        if(Request::ajax())
            return View::make('comments.show',compact('comment'));
        // handle non-ajax calls here
        //else{}
    }
                                                                                                 
    public function deleteComment(Comment $comment)
    {
        $post = $comment->post;
        $status = $comment->approved;
        $comment->delete();
        ($status === 'yes') ? $post->decrement('comment_count') : '';
        return Redirect::back()->with('success','Comment deleted!');
    }
                                                                                                 
    /* post functions */
                                                                                                 
    public function updateComment(Comment $comment)
    {
        $comment->approved = Input::get('status');
        $comment->save();
        $comment->post->comment_count = Comment::where('post_id','=',$comment->post->id)
            ->where('approved','=',1)->count();
        $comment->post->save();
        return Redirect::back()->with('success','Comment '. (($comment->approved === 'yes') ? 'Approved' : 'Disapproved'));
    }
                                                                                                 
}
?>

在上面的代码中, listComment action将用于在管理员界面显示评论以及CRUD链接列表。当用户在博客上发表评论, newComment将回验证并保存发表评论到数据库。在 newComment action,我们将保存评论 approved默认字段设置为“no”。这将给管理员批准或不批准评论使用的机会 updateComment。在 updateComment我们也更新 comment_count字段。deleteComment action将从数据库中删除评论。

showComment只是返回一个局部视图,我们将利用在管理面板使用Ajax张贴评论快速查看这个局部视图。具体操作及实现将在下一章节为大家介绍,敬请关注本站!


相关推荐:使用 Laravel4 创建博客(一):Models and Seeding



除非特别声明,本站所有PHP教程及其他教程/文章均为原创、翻译或网友投稿,版权均归UncleToo中文网所有, 转载请注明作者及出处。
原文网址:http://www.uncletoo.com/html/application/817.html
读完这篇文章后,你是否有所收获? 分享是一种生活的信念!
  • 0
  • 0
我来说两句
更多>>网友评论