Laravel show errors in view - php

if my validation fails I do this:
return Redirect::back()->with('validation', $validation->errors->all());
also I am using:
$restful = true;
so when I am on get_edit() - I'am getting an error that there are no $validation variable when generating my view, when in post_edit() - its all okay because its returns a redirect with errors...
this is my view:
<? foreach($validation as $e): ?>
<div><?= $e; ?></div>
<? endforeach; ?>
undefined variable $validation, right now I'am trying to put it on the Router::before
Route::filter('before', function()
{
View::share('validation', array());
});
so the variable exists but is empty, but now arises a new problem, everytime after this filter executes it overrides those $validation that generates my post_edit(), also i've seen a variable $errors in my view but is ever empty, i don't how to use it, can you help me?
so shortly my problem is:
public function get_edit($id)
{
//generate my view with all nessesary data, but i can't generate here an error variable
// or its better to put it in one place to globally share it in the views, otherwise i am //getting an error
}
public function post_edit($id)
{
//validating $_POST data, if there is an error redirect it back to the get_edit() WITH a //variable containing errors
}

Did you read the docs? http://laravel.com/docs/5.0/validation#error-messages-and-views
You can use return Redirect::back()->withErrors($validation);
In your views, you can always use redirect('register')->withErrors($validator)$errors, without binding them to the view.

Related

Error when trying to return Redirect in Laravel

When I submit a form in Laravel, the following controller method handles it:
public function update($id)
{
//handle input
return View::make('generic.success', ["message" => 'Data submitted successfully!']);
}
This works fine. However, instead of returning a view like above I'd like to return a redirect, because when I return the view directly, reloading the page resubmits the form.
So I tried to do this:
public function update($id)
{
//handle input
return Redirect::to('/success', ['message' => 'Data submitted successfully!']);
}
In my routes file I defined the success route:
Route::get('success', 'NotificationsController#success');
And set up a notification controller to display the view:
class NotificationsController extends BaseController {
public function success($message)
{
return View::make('generic.success', ["message" => $message]);
}
When I run the above code, I get the following error from Laravel:
InvalidArgumentException
The HTTP status code "1" is not valid.
I have no idea what this is supposed to tell me, and neither does Google apparently.
Can someone shed some light on this issue?
P.S.
Incidentally, being new to Laravel, I've noticed so far that Laravel's error reporting is very user-unfriendly, in that instead of telling me I have an issue with my router, or controller, or permissions, it displays these generic errors with no humane explanation of their cause. Is there a better way to troubleshoot problems in Laravel than relying on this?
For example, in the above incident, the error report points to this line of code...
public function setStatusCode($code, $text = null)
{
$this->statusCode = $code = (int) $code;
if ($this->isInvalid()) {
throw new \InvalidArgumentException(sprintf('The HTTP status code "%s" is not valid.', $code));
}
...which is completely useless, as all it does is show me the code that printed the error itself.
The second parameter of the redirector's to() method is the HTTP status code that will be returned by the response, not data that will be passed along. Passing data when redirecting to GET routes can be done either via the query string or the session. The recommended solution here is to pass data via the current session using the with() method which passes that data for the next request. So in your case this would be the approach needed:
public function update($id)
{
return Redirect::to('/success')->with('message', 'Data submitted successfully!');
}
Then in your success method you can have this:
public function success($message)
{
return View::make('generic.success', ["message" => Session::get('message')]);
}
When in doubt always try checking the documentation first. The solution to this is explicitly stated in the Laravel Response Redirects Documentation.
Thanks a lot -Bogdan I found in the documentation that you post answer to my problem. In my case the solution was redirect to an action in a controller, like this...
return
\Redirect::action(
'PqrController#solicitud',
array($id)
)
->with(
'message',
'¡El estado de la solicitud ha sido actualizado correctamente!'
)
;
I redirect to a method in a controller, with one parameter array($id) and I put too in the session a message using ->with('message','Mensaje')

Laravel - return a redirectResponse selectively generated in a function

Part of my application is a multi-stage checkout process; during the latter pages of this I first run a sanity check on each request to verify the user actually has some items in their basket: if not they're sent back to the beginning.
I have a controller function like this which is called from multiple routes for DRY purposes.
private function checkBasketFull($request)
{
if (self::isBasketEmpty($request)) {
return redirect('/')->with('status', config('app.empty_basket_message'));
}
}
When I call it, I can't just do:
self::checkBasketFull($request);
because without a return the redirect doesn't fire, only the session data is sent.
And I can't do:
return self::checkBasketFull($request);
because that will give an error if there's no redirect or abort the method if checkBasketFull returns anything else.
My current (working) code is:
$check = self::checkBasketFull($request);
if ($check) {
return $check;
}
Is there an alternative way of writing this on a single line, or modifying the checkBasketFull function, so the redirect will occur if the basket is empty but execution will continue as normal if it isn't?
Either use this:
if ($redirect = self::checkBasketFull($request)) return $redirect;
Or throw an error and catch it in the global error handler.
However, instead of returning and checking that for a redirect like that, I'd much rather keep it as two completely separate methods:
public function someRoute(Request $request)
{
if ($this->isBasketEmpty($request)) return $this->redirectBasketEmpty();
// Continue processing this request...
}
protected function isBasketEmpty(request)
{
// run your login here...
}
protected function redirectBasketEmpty()
{
return redirect('/')->with('status', config('app.empty_basket_message'));
}
Feels cleaner to me.

Submitting form to itself and echoing validation errors in CodeIgniter

I had few forms in my project, they were submitted to public function's like site.com/email => site.com/validate_email, but then I realized that that's not what I want.
Now I need to make them submit to themselfs ,check and display validation errors.
What is the appropriate way to do this? Check for emptyness of $_POST and then call my new _validate_email(//that will return true or false) if post isn't empty?
Or something else not that noobish?:)
for example:
public function login()
{
$this->load->view('login');
}
public function login_validation()
{
$this->load->library('form_validation');
$this->form_validation->set_rules('email', 'Email', 'required|valid_email|trim|xss_clean|callback_validate_credentials');
$this->form_validation->set_rules('password','Password','required|md5');
if($this->form_validation->run())
{
//some stuff here
}
else
{
$this->load->view('login'); //or redirect()?
}
view:
<?php $this->load->view('header'); ?>
<div class="form-container">
<?=$this->form_validation->validation_errors();?>
<?php
$form_atr = array(
'id' => 'form-set'
);
echo form_open('main/login_validation', $form_atr);//this should be 'main/login'
?>
<div class="header">
/*
here goes other parts of form
*/
</div><!--END form-container -->`
<?php $this->load->view('footer'); ?>
So, basicaly i need to combine login() and login_validation(), but make it so that when user`s input incorrect i get reloaded page of the same view with the same URL and get validation errors displayed.
I've tried to put code of validation into the same function that displays form, but I can't figure out how to redirect or reload the view to show val.errors if any.
So, I think this way is correct(It really should be):
I made my login_validation() private by adding '_' before it, like so _login_validation()
Than I added an if() statement that contains $_POST form variables and i am cheking them with php isset() function, that way the code can determine when user submitted a form. And after all that I just call _login_validation() if inputs are set or load again my login view if not.
public function login()
{
if(isset($_POST['password']) && isset($_POST['email']))
{
$this->_login_validation();
}
else
{
$this->load->view('login');
}
}
and dont forget to process your form so it would submit to the same URL:
echo form_open('', $form_atr);
Hope that will help someone someday.
First of all, validation_errors() is one kind of flash data, so whenever you redirect the page with error the validation errors will be displayed, if you reload it second time it will not be displayed.
From your question i could not understand, do you want to show the errors or not.
if you want to show the errors:
then just redirect the page to login and in the login view add a alert div.
if you don't want to show the errors:
then just remove the alert div.
*i don't see any alert div in your login view, if validation errors are still displayed then may be alert div is in the header view

How can I pass validationErrors from controller to a view?

Well I have set validationErrors for login in my UsersController:
public function login() {
if ($this->request->is('post')) {
$this->User->set($this->request->data);
if ($this->User->validates() && $this->Auth->login()) {
$this->set('ui', $this->Auth->user('id'));
$this->Session->setFlash(__('Loged in!'), 'flash_success');
$this->redirect($this->Auth->redirect());
} else {
$errors = $this->User->validationErrors;
}
}
}
Now how can I use $error in my view or as an element to be listed above my form?
Plz help I have searched a lot, but the answers were for old CakePHP, and I am using CakePHP 2.3.8.
Validation errors are available in the view automatically
There is no action required to get validation errors in the view, as they are a property of the view class. They can be inspected simply with:
debug($this->validationErrors);
In the view.
But you probably don't need to access them
Note however that it's not normal to need to look at this property directly. Using the form helper errors are displayed automatically, or you can generate errors individually
if ($this->Form->isFieldError('email')) {
echo $this->Form->error('email');
}

CodeIgniter form validation using session variables

How do I get the CodeIgniter form validation to validate the $_SESSION if there is no passed form data? I tried manually setting the $_REQUEST variable, but it doesn't seem to work.
i.e. I have a function search in the controller which validates the form input passed, and either returns you to the previous page with errors, or else moves you onto the next page. But I want this function to also work if you previously filled out this page, and the info is stored in the $_SESSION variable.
function search () {
$this->load->library("form_validation");
$this->form_validation->set_rules("flightID", "Flight Time", "required|callback_validFlightID");
$this->form_validation->set_rules("time", "Flight Time", "required|callback_validFlightTime");
$this->setRequest(array("flightID", "time"));
// adding session check allows for inter-view navigation
if ($this->form_validation->run()) {
// some application logic here
$this->load->view("seats", $data);
} else {
$this->logger->log($_REQUEST, "request");
// redirect back to index
$this->index();
}
}
function setRequest () {
// make sure none of the parameters are set in the request
foreach ($vars as $k) {
if (isset($_REQUEST[$k])) {
return;
}
}
foreach ($vars as $k) {
if (isset($_SESSION[$k])) {
$_REQUEST[$k] = $_SESSION[$k];
}
}
}
You can store the form post info in a session using the following codeigniter functions
$formdata = array(
'flightID' => $this->input->post('flightID'),
'time' => $this->input->post('time')
);
$this->session->set_userdata($formdata);
and the information can be retrieved with the following
$this->session->userdata('flightID')
$this->session->userdata('time')
form_validation works directly with $_POST, so use that instead of $_REQUEST.
What you're trying to do is setting Post values manually which is not natively
supported by CodeIgniter. So what we're doing first is extending the core.
Create a new file (MY_Input.php) and paste the following contents into it:
class MY_Input extends CI_Input{
function set_post($key, $value)
{
$_POST[$key] = $value;
}
}
That's a very basic implementation of your purpose but it's enough to test around. You might want to extend it to make it fit your needs (f.e. allowing the input of arrays).
So now. In your controller you can check if something has been posted by a user. If not you'll be just setting the post variable manually with your new method of the Input class.
class Some_Controller extends CI_Controller{
public function index()
{
// The user hasn't filled out a field?
if(!$this->input->post('a_key'))
{
// Let's set the postfield to the value of a session key
$this->input->set_post('a_key', $this->session->userdata('mystoredkey'));
}
}
}
After having set your postfield manually, it can be handled by the form validation library as it is meant to be.
That should be your way to go :)
You can really do some pretty things if you're not afraid of hacking the core. Many people are, don't be one of them!
Happy coding

Categories