I have an action that takes POST data secured by sfGuard. This means that if the user is not logged in, the POST data will be sent to the log in form. Ordinarily, this is not a problem, the user continues to log in, and has to submit the data again.
Unfortunately, the log in form seems to be using the POST data as if it was submitted with the form itself. This means that it is complaining that the required username and password fields are missing, and it complains that it is missing a CSRF token. This last problem does not go away, after submitting the form, meaning the user cannot log in, anyway.
The user should not be presented with the form if not logged in, but it might be possible for the user to log out with the form still open. So I am asking in the interest of keeping the interface watertight and error-free.
Is this a shortcoming of sfGuard, can it be avoided, or am I doing something wrong altogether?
To clarify, the route looks like this:
add_subgroup:
url: /group/:id/add
class: sfPropelRoute
options:
model: Group
type: object
param: { module: subgroups, action: create }
requirements:
group_id: \d+
sf_method: [post]
The form used to submit the request is as follows:
<form action="<?php echo url_for('add_subgroup', $group) ?>" method="post">
<input type="hidden" name="group_id" value="<?php echo $group->getId() ?>" />
<input type="text" name="subgroup_id" />
<input type="submit" class="button" value="Add" />
</form>
It is a shortcoming of sfGuard, because the signin action will check for a POST request, and if so bind the form.
From the code in BasesfGuardActions.class.php:
if ($request->isMethod('post'))
{
$this->form->bind($request->getParameter('signin'));
I'm personally not a big fan of forwarding between actions in symfony, and just like in this case, I think it's more appropriate to redirect than forward. This also solves your problem because this will result in a new GET request. You can accomplish this behavior by extending sfGuardBasicSecurityFilter.
class mySecurityFilter extends sfGuardBasicSecurityFilter
{
protected function forwardToLoginAction()
{
$context = $this->getContext();
// If you want to redirect back to the original URI (note: original POST data will be lost)
$context->getUser()->setReferer($context->getRequest()->getUri());
$url = sfConfig::get('sf_login_module') . '/' . sfConfig::get('sf_login_action');
$context->getController()->redirect($url);
throw new sfStopException();
}
}
Now in app/myapp/config/filters.yml
security:
class: mySecurityFilter
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With