【发布时间】:2016-10-19 14:35:50
【问题描述】:
更新:已解决 检查当前请求是否是帖子是不够的。表单仍按创建顺序传递给助手。如果传递给助手的第一个表单不是已发布的表单,则没有足够的验证来防止使用其详细信息而不是预期的已发布表单。
在 helper 中添加了 if 附加子句...
if ($postId)
应该是
if ($postId === $formId)
真的很直截了当……我只花了 2 天时间就找到了答案。
--- 下面是原帖---
我尝试在 ZF1 中实现自己的 PRG(Post/Redirect/Get)模式。
我使用扩展Zend_Form 的自定义表单类来添加setUniqueFormId 方法,该方法基本上是具有表单名称的隐藏元素。表单与 2 个变量($persistData 和 $redirectUrl)一起传递给操作助手。
问题是当我有多个表单时,第一个 从使用了对助手的最后一次调用。$persistData 和 $redirectUrl 值始终用于任何后续表单,即使这些已更改。
对为什么会出现这种情况有任何想法吗?非常感谢任何帮助。
更新:我认为这是使用动作助手的问题。每次调用它并传递新值时,所有先前的值都会更改。我对动作助手代理的内部不太熟悉。任何人都可以阐明或提出建议吗?
--- 控制器动作 ---
// Create 2 new forms
$testForm1 = new Application_Form_Test;
$testForm2 = new Application_Form_Test;
// Call a custom function on each form tp create a hidden field called
// "unique_form_id" to help identify the form that has posted the data
$testForm1->setUniqueFormId('test_form_1');
$testForm2->setUniqueFormId('test_form_2');
// Call "Post Redirect Get" Helper and pass a boolean variable for $persistData
$formData1 = $this->_helper->postRedirectGet($testForm1, true);
$formData2 = $this->_helper->postRedirectGet($testForm2, false);
--- 控制器动作助手---
public function direct($form, $persistData = false, $redirectUrl = null)
{
$formId = $form->getElement('unique_form_id')->getValue();
$currentUrl = implode (
'/',
array (
$this->getRequest()->getModuleName(),
$this->getRequest()->getControllerName(),
$this->getRequest()->getActionName()
)
);
$session = new Zend_Session_Namespace('prg');
$redirectUrl = $redirectUrl ? $redirectUrl : $currentUrl;
if ($this->getRequest()->isPost())
{
$postId = $this->getRequest()->getPost('unique_form_id');
if ($postId)
{
$redirector = Zend_Controller_Action_HelperBroker::getStaticHelper('Redirector');
$postUrl = $currentUrl;
$session->$postUrl->$postId = array (
'url' => (string) $redirectUrl,
'id' => (string) $postId,
'post' => (array) $this->getRequest()->getPost(),
'persist' => (bool) $persistData
);
Zend_Session::writeClose(true);
$response = $redirector ->setCode(303)
->setExit(true)
->gotoUrl($redirectUrl);
return $response;
}
else {
return false;
}
}
else {
$urlSessionData = $session->$currentUrl;
// Results shown below
Zend_Debug::dump($urlSessionData);
if ($urlSessionData->$formId != null)
{
$formSessionData = $urlSessionData->$formId;
$formPersist = $formSessionData['persist'];
$formPostData = $formSessionData['post'];
if (!$formPersist)
{
unset($urlSessionData->$formId);
}
if(!empty($formPostData))
{
$form->isValid($formPostData);
}
return $formPostData;
}
else {
return false;
}
}
}
--- 前端控制器插件---
function preDispatch()
{
$session = new Zend_Session_Namespace('prg');
$currentUrl = implode (
'/',
array (
$this->getRequest()->getModuleName(),
$this->getRequest()->getControllerName(),
$this->getRequest()->getActionName()
)
);
// Check if current url is in prg sesison
// If not, we have moved to another URL or its our first visit to the $currentUrl
if ($session->$currentUrl === null)
{
// Remove all prg sessions
Zend_Session::namespaceUnset('prg');
}
return;
}
--- 转储结果 ---
object(stdClass)#54 (2)
{
["test_form_1"] => array(4)
{
["url"] => string(21) "admin/timeclock/index"
["id"] => string(11) "test_form_1"
["post"] => array(4)
{
["test_element"] => string(0) ""
["submit"] => string(5) "Submit"
["unique_form_id"] => string(11) "test_form_1"
}
["persist"] => bool(false) <-- Expected to be 'true'
}
["test_form_2"] => array(4)
{
["url"] => string(21) "admin/timeclock/index"
["id"] => string(11) "test_form_2"
["post"] => array(4)
{
["test_element"] => string(0) ""
["submit"] => string(5) "Submit"
["unique_form_id"] => string(11) "test_form_2"
}
["persist"] => bool(false) <-- Expected to be 'false'
}
}
【问题讨论】:
-
你的方案是什么?验证form1和form2验证和显示?只是验证form1并显示?只是验证form2并显示?其他的?
-
您能否尝试将问题缩小到更少量的代码?您发布的代码量可能有问题,我们无法执行它来测试。
-
我理解为什么这总是错误的,但不是你有 2 种形式。你打电话给2?一个接一个?
-
您应该通过发布您的解决方案作为答案来解决您的问题,而不是通过编辑原始问题。这样你就可以接受你的答案,结束问题。
-
@ConspicuousCompiler 谢谢,我没有意识到这是一个选项。我自己已经回答了这个问题。如果没有更好的答案,我会在 2 天内接受。
标签: php session zend-framework post-redirect-get