如何获得每种类型的Laravel API的5个最新帖子?

时间:2017-12-14 16:35:17

标签: php mysql angular laravel api

我正在使用Laravel 5.4作为API和Angular 5构建应用程序(我的课程项目)。我的项目是一个音乐博客。我需要满足诸如类别和子类别之类的要求。

所以,我有流派,乐队和帖子。对于我的主页我想为每个类别显示5个最新帖子

我的表格

  • 流派(id,name,slug);
  • bands(id,name,slug,genre_id);
  • 帖子(id,title,content,band_id,slug,created_at,updated_at)。

我的人际关系

Genre.php

protected $fillable = ['name', 'slug'];

public function bands()
{
    return $this->hasMany('App\Models\Band');
}

public function posts()
{
    return $this->hasManyThrough('App\Models\Post', 'App\Models\Band');
}

Band.php

protected $fillable = ['name','slug','genre_id'];

public function genre()
{
    return $this->belongsTo('App\Models\Genre');
}

public function posts()
{
    return $this->hasMany('App\Models\Post');
}

post.php中

protected $fillable = ['title','content','image','band_id','slug'];

public function band()
{
    return $this->belongsTo('App\Models\Band');
}

在我的HomeController中,我尝试过:

$latest5PostsPerGenre = Genre::with([
        'posts' => function($query) {
            $query->take(5)
                  ->orderBy('id', 'desc')
                  ->get(['posts.id', 'title']);
        }])->orderBy('name')
           ->get();

但是它将所有类型的帖子总数限制为5。所以,有些类型根本没有帖子。

$latest5PostsPerGenre = Genre::with('latest5Posts')
                        ->orderBy('name')
                        ->get();

使用Genre模型中的这些方法:

public function latest5Posts()
{
    return $this->hasManyThrough('App\Models\Post', 'App\Models\Band')
        ->orderBy('id', 'desc')
        ->take(5)
        ->get();
}

or

public function latest5Posts()
{
    return $this->posts()->latest()->take(5)->get();
}

但是我得到 BadMethodCallException方法addEagerConstraints不存在

我甚至尝试过这样的事情:

        $genres = Genre::with('posts')->orderBy('name')->get();
    $latest5PostsPerGenre = [];

    foreach ($genres as $genre) {
        $genrePosts['posts'] = [];
        $posts = $genre->posts()->orderBy('id', 'desc')->take(5)->get();

        foreach ($posts as $post) {
            $singePost = [];

            $singePost['id'] = $post->id;
            $singePost['title'] = $post->title;
            $singePost['bandName'] = $post->band->name;

            array_push($genrePosts['posts'], $singePost);
        }

        array_push($latest5PostsPerGenre[$genre->name], $genrePosts);
    }

或者像这样

$genres = Genre::get();
foreach ($genres as $genre) { 
        $post[$genre->name] = $genre->posts()
                                    ->take(5)
                                    ->orderBy('id', 'desc')
                                    ->get(); 

}

但据我所知,它对db执行了很多查询,并且不对。

我尝试根据链接https://softonsofa.com/tweaking-eloquent-relations-how-to-get-n-related-models-per-parent/ Model.php 中创建方法 scopeNPerGroup ,但它给出了一堆sql错误。

我正在考虑使用Eloquent进行一些复杂的,嵌套的SQL查询,但不清楚如何编写它。

因此,我希望每个帖子的每个类型名称包含5个最新帖子,其中包含每个帖子的ID,标题和乐队名称,以便为我的Angular前端中的每个帖子编写链接,例如 rnmblog .com / api / {genre-slug} / {band-slug} / {post-id}或{post-slug} 获取单一帖子。

1 个答案:

答案 0 :(得分:0)

  

对于我的主页,我想为每个类别显示5个最新帖子。

你的第一次尝试已经做到了,不是吗?刚刚改进了一下

$latest5PostsPerGenre = Genre::with([ 
    'posts' => function($query) { 
        $query->with('bands')
            ->take(5)
            ->orderBy('id', 'desc') 
            ->get(); 
    }])
    ->orderBy('name') 
    ->get();