Php 对如何改进此功能感到困惑。。?
我的控制器中有以下函数,用于准备和加载我的主页Php 对如何改进此功能感到困惑。。?,php,laravel,laravel-4,Php,Laravel,Laravel 4,我的控制器中有以下函数,用于准备和加载我的主页 public function index() { // GetBalance $current_balance = $this->PayPal->getBalance(); if(Session::has('errors')) { return Redirect::to('error'); } // Tr
public function index()
{
// GetBalance
$current_balance = $this->PayPal->getBalance();
if(Session::has('errors'))
{
return Redirect::to('error');
}
// TransactionSearch
$params = array(
'number_of_days' => 1
);
$recent_history = $this->PayPal->transactionSearch($params);
if(Session::has('errors'))
{
return Redirect::to('error');
}
// Make View
$data = array('current_balance' => $current_balance, 'recent_history' => $recent_history);
return View::make('index')->with('data', $data);
}
如您所见,我通过我的模型对PayPal API进行了两次不同的调用,每次调用之后,我都会检查错误。当发生错误时,我会闪现错误消息并相应地重定向到错误页面
我希望改进这一点,这样在加载视图之前进行大量调用时,就不必反复使用相同的代码片段
if(Session::has('errors'))
{
return Redirect::to('error');
}
我试着把它移到它自己的功能上
public function errorCheck()
{
if(Session::has('errors'))
{
return Redirect::to('error');
}
}
// GetBalance
$current_balance = $this->PayPal->getBalance();
$this->errorCheck();
然后,我想我可以在我的索引函数中这样做
public function errorCheck()
{
if(Session::has('errors'))
{
return Redirect::to('error');
}
}
// GetBalance
$current_balance = $this->PayPal->getBalance();
$this->errorCheck();
不过,我想这是行不通的,因为errorCheck()只是返回一个值,而不是实际触发重定向,所以我在主页上出现了一个错误,因为它所期望的数据都不存在(因为API调用失败)
任何关于我需要在这里做什么的信息,以便我的errorCheck()函数在应该的时候触发重定向都会非常感激
谢谢 我能想到的避免这种情况的唯一方法是使用异常 使用
errorCheck()
方法,您可以尝试以下操作:
// GetBalance
$current_balance = $this->PayPal->getBalance();
return $this->errorCheck();
但那不是你想要的。。。它将在第一次调用后退出您的方法。您真正需要的是一种方法,无论错误发生在何处,都能捕获并处理它,而异常就是这样做的
我将假设您的PayPal
类是一个第三方包,您不能重写它来抛出异常。基于这一假设,您可以这样做:
重写errorCheck()
方法,如下所示:
public function errorCheck()
{
if(Session::has('errors'))
{
throw new Exception("Problem with Paypal!");
}
}
然后将所有Paypal访问代码包装在一个try/catch块中:
public function index()
{
try {
// GetBalance
$current_balance = $this->PayPal->getBalance();
$this->errorCheck();
// TransactionSearch
$params = array(
'number_of_days' => 1
);
$recent_history = $this->PayPal->transactionSearch($params);
$this->errorCheck();
// Make View
$data = array('current_balance' => $current_balance, 'recent_history' => $recent_history);
return View::make('index')->with('data', $data);
} catch(Exception $e) {
return Redirect::to('error');
}
}
每次调用errorCheck()
时,它都会检查错误并引发异常。在这种情况下,执行将立即跳转到catch
块并重定向到错误页面
更好的解决方案是将异常抛出到更接近错误源的位置,即错误发生时在
Paypal
类中的某个位置。这里的想法是,异常包含许多有用的信息,告诉您发生了什么,比如堆栈跟踪。在我给出的代码中,堆栈跟踪将显示异常是在errorCheck()
方法中抛出的,虽然该方法为true,但没有真正的帮助。如果异常可以在Paypal
类中的某个地方抛出,它将为您提供一个更好的指示,说明真正出了什么问题。为什么您甚至需要检查两次错误?它似乎与每个电话都不相关?i、 e.如果余额调用失败,则if似乎无关紧要,因为您没有在交易搜索中使用结果
我就这么做
public function index()
{
// GetBalance
$current_balance = $this->PayPal->getBalance();
// TransactionSearch
$recent_history = $this->PayPal->transactionSearch(array('number_of_days' => 1));
if(Session::has('errors'))
{
return Redirect::to('error');
}
else
{
return View::make('index')->with('current_balance', $current_balance)
->with('recent_history', $recent_history);
}
}
虽然抛出一个错误肯定是正确的做法,但我认为您可以更进一步,并概括重定向。您可以使用
App::error
全局重定向,而不是在每次调用PayPal API时执行try catch块
在适当的位置创建异常类:
class PayPalApiException extends Exception {}
然后在start/global.php
中添加以下内容(在另一个App::error
调用之前):
然后,控制器中的代码可以变得更简单:
public function index()
{
$current_balance = $this->PayPal->getBalance();
$this->errorCheck();
$recent_history = $this->PayPal->transactionSearch([
'number_of_days' => 1
]);
$this->errorCheck();
$data = compact('current_balance', 'recent_history');
return View::make('index')->with('data', $data);
}
protected function errorCheck()
{
if (Session::has('errors'))
{
throw new PayPalApiException("Problem with Paypal!");
}
}
我没有在transactionSearch()中使用getBalance()的结果,没有,但是如果getBalance()中的数据没有返回,那么我的主页将无法正确加载,因此我甚至可以不浪费资源来额外调用transactionSearch()。资源量可能微不足道。代码的可维护性和调试的简易性在这里将变得更加重要。由你决定……PayPal/eBay/等。当你对他们的系统进行大量不必要的调用时,他们不喜欢这样,并且他们可能会限制任何给定应用程序在一段时间内可以进行的API调用的数量。因此,这与其说是我自己的服务器资源的问题,不如说是它正在扼杀对服务提供商的API调用可能存在的任何潜在限制。不过,我很感谢你的反馈。