允许 public 查看所有受限页面的订阅者中间件路由
Subscriber middleware route allowing public to view all restricted pages
我在项目中遇到路由和中间件问题。我有一个仅对订阅者锁定的主题列表。但是,主题可以标记为 public,允许来宾用户/public 查看主题。
我面临的问题是我要么让 public 或 none 可见所有主题。
我有以下订阅者中间件。
public function handle(Request $request, Closure $next)
{
if ( $request->user() && ! $request->user()->subscribed('annual_membership') ) {
return redirect('profile');
}
if( Auth::Guest() ) {
return redirect('topics')->with('error', 'You need to be a registered memeber to view this topic.');
}
return $next($request);
}
这是像这样添加到我的内核中的。
protected $routeMiddleware = [
// ...
'subscriber' => \App\Http\Middleware\Subscriber::class,
];
然后我设置了以下路由。
Route::get('voting-topics', [TopicController::class, 'topics'])->name('topics');
Route::get('voting-topics/{topic}', [TopicController::class, 'topic'])->name('topic');
Route::group(['middleware' => ['subscriber']], function ()
{
Route::get('profile/billing', function (Request $request) {
return $request->user()->redirectToBillingPortal();
});
Route::get('voting-topics/{topic}', [TopicController::class, 'topic'])->name('topic');
});
还有我的主题控制器。
class TopicController extends Controller
{
public function topics(Request $request)
{
if ( $request->user() && $request->user()->subscribed('annual_membership') ) {
return $this->subscriberTopics();
} else {
return $this->publicTopics();
}
}
private function publicTopics()
{
$topics = Topic::orderBy('date', 'asc')->where('free_to_view', 1)->paginate(50);
return view('topics.topics', compact('topics'));
}
private function subscriberTopics()
{
$topics = Topic::orderBy('date', 'desc')->paginate(50);
return view('topics.topics', compact('topics'));
}
public function topic(Request $request, Topic $topic)
{
$topic = Topic::find($topic)->first();
return view('topics.topic', compact(['topic',));
}
}
主题目录工作正常。它只为来宾显示标记为 public 的主题,为订阅者显示所有主题。我的代码目前只允许订阅者查看所有主题,访客可以看到 public 个,这不是我想要的。
如果我删除中间件路由,相反的情况会发生,如果来宾输入主题的 URL,他们就可以访问所有主题。
编辑
为了更好地阐明和解释,我有一个主题列表(基本上类似于博客文章)。主题仅供我网站的付费订阅者查看。但是,有些主题可以标记为免费查看,所有人都可以看到。
如果我转到示例com/voting-topics,那么我只会看到免费主题。 (这是正确且有效的)如果我登录并转到相同的 URL,我会看到所有主题,因为我已登录,而且我是付费订阅者。 (这又是正确的并且有效)
如果我删除了我的中间件中的重复路由,则转到 example.com/voting-topics/123 或直接通过 URL 的任何其他主题 ID。我可以查看主题,即使它应该只锁定订阅者。
如果我将重复的路由添加回我的中间件,一般 public 将无法访问免费主题。
我需要访客/一般 public / 非订阅者只能访问标记为 public 的主题,但付费订阅者可以访问所有主题。 `
所以看起来这毕竟是一个简单的修复,而不是在我的路由中进行检查,我需要在我的控制器中进行检查。
我从我的中间件中删除了 Route::get('voting-topics/{topic}', [TopicController::class, 'topic'])->name('topic');
,然后在我的控制器中添加了以下代码。
if( $topic->free_to_view === 1 || Auth::check() && auth()->user()->subscribed('annual_membership')) {
return view('topics.topic', compact('topic'));
} else {
return redirect()->back()->with('error', 'You need to be a paying member to view this topic');
}
我在项目中遇到路由和中间件问题。我有一个仅对订阅者锁定的主题列表。但是,主题可以标记为 public,允许来宾用户/public 查看主题。
我面临的问题是我要么让 public 或 none 可见所有主题。
我有以下订阅者中间件。
public function handle(Request $request, Closure $next)
{
if ( $request->user() && ! $request->user()->subscribed('annual_membership') ) {
return redirect('profile');
}
if( Auth::Guest() ) {
return redirect('topics')->with('error', 'You need to be a registered memeber to view this topic.');
}
return $next($request);
}
这是像这样添加到我的内核中的。
protected $routeMiddleware = [
// ...
'subscriber' => \App\Http\Middleware\Subscriber::class,
];
然后我设置了以下路由。
Route::get('voting-topics', [TopicController::class, 'topics'])->name('topics');
Route::get('voting-topics/{topic}', [TopicController::class, 'topic'])->name('topic');
Route::group(['middleware' => ['subscriber']], function ()
{
Route::get('profile/billing', function (Request $request) {
return $request->user()->redirectToBillingPortal();
});
Route::get('voting-topics/{topic}', [TopicController::class, 'topic'])->name('topic');
});
还有我的主题控制器。
class TopicController extends Controller
{
public function topics(Request $request)
{
if ( $request->user() && $request->user()->subscribed('annual_membership') ) {
return $this->subscriberTopics();
} else {
return $this->publicTopics();
}
}
private function publicTopics()
{
$topics = Topic::orderBy('date', 'asc')->where('free_to_view', 1)->paginate(50);
return view('topics.topics', compact('topics'));
}
private function subscriberTopics()
{
$topics = Topic::orderBy('date', 'desc')->paginate(50);
return view('topics.topics', compact('topics'));
}
public function topic(Request $request, Topic $topic)
{
$topic = Topic::find($topic)->first();
return view('topics.topic', compact(['topic',));
}
}
主题目录工作正常。它只为来宾显示标记为 public 的主题,为订阅者显示所有主题。我的代码目前只允许订阅者查看所有主题,访客可以看到 public 个,这不是我想要的。
如果我删除中间件路由,相反的情况会发生,如果来宾输入主题的 URL,他们就可以访问所有主题。
编辑
为了更好地阐明和解释,我有一个主题列表(基本上类似于博客文章)。主题仅供我网站的付费订阅者查看。但是,有些主题可以标记为免费查看,所有人都可以看到。
如果我转到示例com/voting-topics,那么我只会看到免费主题。 (这是正确且有效的)如果我登录并转到相同的 URL,我会看到所有主题,因为我已登录,而且我是付费订阅者。 (这又是正确的并且有效)
如果我删除了我的中间件中的重复路由,则转到 example.com/voting-topics/123 或直接通过 URL 的任何其他主题 ID。我可以查看主题,即使它应该只锁定订阅者。
如果我将重复的路由添加回我的中间件,一般 public 将无法访问免费主题。
我需要访客/一般 public / 非订阅者只能访问标记为 public 的主题,但付费订阅者可以访问所有主题。 `
所以看起来这毕竟是一个简单的修复,而不是在我的路由中进行检查,我需要在我的控制器中进行检查。
我从我的中间件中删除了 Route::get('voting-topics/{topic}', [TopicController::class, 'topic'])->name('topic');
,然后在我的控制器中添加了以下代码。
if( $topic->free_to_view === 1 || Auth::check() && auth()->user()->subscribed('annual_membership')) {
return view('topics.topic', compact('topic'));
} else {
return redirect()->back()->with('error', 'You need to be a paying member to view this topic');
}