Laravel 5 - retrieving old input - laravel-5

I am passing one of my views a document object. Within my view, if I do
{{ $document }}
I can see the document
{
"id":2,
"projectId":1,
"name":"DocumentA"
}
This document has data, the form data that was submitted. In my view, if I do
{{ $document->documentData }}
I can see
[
{
"id":1,
"documentId":2,
"key":"_token",
"value":"WJGplDnTuMpDK7X3AD9dgIliX2SliBSz2sjxivVy"
},
{
"id":2,
"documentId":2,
"key":"teamLeader",
"value":"Jason Sullivan"
},
{
"id":3,
"documentId":2,
"key":"clientName",
"value":"Google"
},
{
"id":4,
"documentId":2,
"key":"projectName",
"value":"Analytics"
}
]
So all of this data is related to DocumentA, linked by documentId.
So my view now has this document object, and I can access the data for the document. The key is the input field, and the value was the inputted data. An input in my view generally looks like the following
{!! Form::label('teamLeader', 'Team Leader:', array('class' => 'col-sm-5 control-label green')) !!}
{!! Form::textArea('teamLeader', old('$document->documentData'), array('class' => 'form-control')) !!}
As you can see, I am trying to get the old data displayed in my edit form. This input is for teamLeader, so it should display the value where teamLeader is the key. So in the data I outputted above, you can see that this field should display Jason Sullivan.
How would I go about getting it to do this?
Thanks

Related

VueJS: v-for directive is not rendering items in spite of having objects in array

I am trying to render my API response object into the table rows. There is no problem with endpoints. I could fetch data without any issues. Data is paginated. I can see the content of the array object(by using double curly braces). But v-for direction doesn't affect anything.
I tried some ways to fix. One of them is using response.data.data to handle it but it didn't work. I also tried iterating through customers.data but I got the same results.
This part was taken from my component
import axios from 'axios'
export default {
data () {
return {
customers: [],
}
},
mounted: function() {
axios.get('http://127.0.0.1:8000/customer/all').then(res => {
this.customers.push(res.data);
});
},
Here it is the directive part:
<tr v-for="customer in customers">
<td>
<input class="uk-checkbox" type="checkbox">
</td>
<td>{{ customer.mail }}</td>
<td>
{{ customer.telephone }}
</td>
<td>
<ul class="uk-iconnav">
<li><span class="uk-icon" uk-icon="icon: check"></span></li>
<li><span class="uk-icon" uk-toggle="target: #user-request" uk-icon="icon: question"></span></li>
<li><span class="uk-icon" uk-icon="icon: trash"></span></li>
</ul>
</td>
</tr>
{{ customers }} => this is OK
customers json output
[ { "current_page": 1, "data": [ { "id": 1, "user_info": "test", "password": "test", "gsm": "123123213", "telephone": 124, "mail": "test#test", "address": "test", "created_at": null, "updated_at": null } ], "from": 1, "last_page": 1, "next_page_url": null, "path": "http://127.0.0.1:8000/customer/all", "per_page": 4, "prev_page_url": null, "to": 1, "total": 1 } ]
It should be rendered, but it's not rendering. I didn't get any console errors. What is the problem? Thanks anyway.
In your snippet, res.data is an array that contains an object with a data attribute that has for value the customer data you want to display.
To store the retrieved customer data values in your component's customers array you can spread them as the following :
mounted: function() {
axios.get('http://127.0.0.1:8000/customer/all').then(res => {
this.customers.push(...res.data[0].data);
});
}
If the customers array as no other modification source, you can even do :
mounted: function() {
axios.get('http://127.0.0.1:8000/customer/all').then(res => {
this.customers = res.data[0].data;
});
}

Laravel and vuejs -> how to pass Controller data into my Vue view?

I am discovering php, laravel, vuejs at the same time and I guess there are some things I didn't get well yet ;)
I made a new component "tableau" which is a basic table and would like to use it at many places in my app, where I would just specify its title, columns and data.
FootballerController is the place where I get all my data.
Here is what is working now:
app.js
const tableau = new Vue({
components:{tableau:Tableau
},
data: function() {
return {
title: "the best footballers",
searchQuery: '',
gridColumns: ['footballer', 'cote', 'nationalite'],
gridData: [
{ footballer: 'Remond', cote: 951, nationalite:'USA' },
{ footballer: 'Marcel', cote: 935, nationalite:'ESP' },
{ footballer: 'Stian', cote: 923, nationalite:'NOR' },
{ footballer: 'Martin', cote: 923, nationalite:'USA' },
{ footballer: 'Pierre', cote: 918, nationalite:'ESP' },
]
}
}
}).$mount('#tableau');
footballer.blade.php
<tableau
v-bind:titre="title"
:rows="gridData"
:columns="gridColumns "
:filter-key="searchQuery" >
</tableau>
TableauComponent
<template>
<div >
<h1 >{{titre}}</h1>
<table >
<thead>
<tr>
<th v-for="key in columns"
{{ key | capitalize }}
</th>
</tr>
</thead>
<tbody>
<tr v-for="entry in rows">
<td v-for="key in columns">
{{entry[key]}}
</td>
</tr>
</tbody>
</table>
</div>
</template>
<script>
export default {
name:'tableau',
props: {
rows: Array,
columns: Array,
titre: String
}
}
</script>
This works.
Then, here is what I would like: being able to put my values from the controller into footballer.blade.php, which is using TableauComponent.vue
FootballerController
public function footballer($id){
//process to get all this data in DB ($footballer, $gridData, $gridColumns, $title)
$footballer= (Footballer::select(SOME REQUEST)->where('id', '=', $id)->get())[0];
return view('footballers/footballer', ['footballer' => $footballer,
'gridData' => $gridData,
'gridColumns' => $gridColumns,
'title' => $title] );
}
And in footballer.blade.php
<tableau
v-bind:titre="{{ $title }}"
:rows="{{ $gridData }}"
:columns="{{ $gridColumns }}" >
</tableau>
Then in app.js I wouldn't need data anymore
const tableau = new Vue({
components:{tableau:Tableau
}
}).$mount('#tableau');
But this doesn't work and tells me "Property or method is not defined on the instance but referenced during render"
I don't manage at all and am worndering is I have the good way of doing: Should I not get my data in FootballerController? If not, where can I get it then?
Thanks a lot in advance.
When you use {{ value }} in both Blade & javascript framework at the same time. You need to use #{{ value }} to avoid collision between Blade & Vue.
try
<tableau
v-bind:titre="#{{ $title }}"
:rows="#{{ $gridData }}"
:columns="#{{ $gridColumns }}" >
</tableau>
Besides that, when you use :rows="value", the value must be javascript syntax, otherwise when rows="value", the value would be treated as string.
You might need to use json_encode to format your data from the Laravel, or use #json if you're using Laravel 5.5^.
Your are using ':' symbol before your attributes in your blade, which means 'v-bind' as the doc says : VueJS Shorthands.
So first, for assigning a String to a props, you don't need ':' before 'titre'.
Then, to solve your problem you could try to add a default value to your props, for example :
props: {
rows: {
default: []
},
columns: {
default: []
},
titre: {
default: ''
}
}
I didn't try but I think it should works.
Thanks a lot, indeed the php array to javascript array was the issue.
In the php controller, I parse my data into json
'gridData' =>json_encode($gridData),
In the php view footballer.blade.php
<tableau
titre="{{ $title }}"
rows="{{ $gridData }}">
</tableau>
And in my Vue view, I was getting an array, and changed the code for this:
rows: {
type: String,
default: ""
}
var rowsArray = JSON.parse(this.rows)
Now it seems like the data I get after my request isn't properly parsed, but that's another point :)

Prevent lazy loading in view

I have a JSON result from a query that looks like this:
{
"id":1,
"user_id":"1",
"message":"Hello, world",
"created_at":"2016-09-22 00:32:20",
"updated_at":"2016-09-22 00:32:20",
"stats": [
...
]
},
{
"id":2,
"user_id":"1",
"message":"Hello, world",
"created_at":"2016-09-22 00:32:20",
"updated_at":"2016-09-22 00:32:20",
},
{
... more results
}
Notice that sometimes the result has a stats property and sometimes it does not (despite every record having a stats relationship). Don't ask why, that's just how I have it set up in the backend.
I want to loop through these results in my view, like this:
#foreach ($posts as $post)
#if (isset($post->stats) && !empty($post->stats)
{{ $post->stats->total }}
#endif
#endforeach
However, for post id 2, the loop will also output the $post->stats->total value because it lazy loads the stats.
How can I prevent it from lazy loading the stats relationship?
That happens because you are accessing $post->stats. You can instead check if the stats relationship is loaded or not by using the relationLoaded() method defined in Illuminate\Database\Eloquent\Model:
#foreach ($posts as $post)
#if ($post->relationLoaded('stats'))
{{ $post->stats->total }}
#endif
#endforeach

Cannot display values when editing form in laravel 5

There is no output in the form when clicking a value. But I can see the values when using the return function. Here is my code:
ReportController
public function edit($id)
{
$crime_edit = CrimeReport::findOrFail($id);
$victim_info = VictimProfile::findOrFail($id);
return $victim_info;
//return $victim_info->firstname;
//return $victim_info;
$display_crime_type = CrimeType::lists('crime_type','id');
$display_crime_name = CrimeName::lists('crime_description','id');
return view('crimereports.edit',compact('crime_edit','victim_info','display_crime_name,'display_crime_type'));
}
edit view page
{!! Form::model($crime_edit,['method' =>'PATCH','route'=>'crime_reports.update',$crime_edit->id],'class'=>'form-horizontal']) !!}
<div class="form-group">
{!! Form::label('victim_name', 'Victim Name',['class'=>'col-md-3 control-label']) !!}
<div class="col-md-3">
{!! Form::text('victim_name', null, ['class' => 'form-control','placeholder' => 'Firstname']) !!}
</div>
<div class="col-md-2">
{!! Form::text('v_middle_name', null, ['class' => 'form-control','placeholder' => 'Middlename']) !!}
</div>
<div class="col-md-3">
{!! Form::text('v_last_name', null, ['class' => 'form-control','placeholder' => 'Last Name']) !!}
</div>
</div>
{!! Form::close() !!}
Am I missing something?
The null is the default value. I think Form::model is suppose to bind the values, but have you tried removing the null?
I don't use Form::model, but as a default value I always put old('field_name', $model->field_name). The old function will look into both GET and POST and if a key matches that'll be shown. If that doesn't exist, it'll use the second value.
Based on your debug output statements ("return $victim_info;"), it looks like you are trying to bind the form to the $crime_edit model while accessing the values from the $victim_info model. You can not bind a form to two different models at once, so if the blank victim name fields are not attributes of the $crime_edit model, your current implementation will not work.
You will need to either explicitly add $victim_info->victim_name, etc. in place of the 'null' values, or bind the form to the $victim_info model instead of the $crime_edit model.
If victim_name, v_middle_name, and v_last_name are attributes of the $crime_edit model, then I have no idea.

Submit form, add input to URL

I have a regular form with a single input:
{{ Form::open(array('id' => 'form_search')) }}
<div class="form-group">
{{ Form::text('search', '', array('class' => 'form-control', 'placeholder' => 'Search...')) }}
</div>
{{ Form::close() }}
When the form is submitted, I want it to redirect to a page showing the results by the following URL:
http://www.website.com/search/<QUERY_HERE>
For example, if someone typed john in the form input and submitted the form, the URL redirected to would look like:
http://www.website.com/search/john
How can I do this?
In your routes.php
//Handle form submit
Route::get('search', 'YourSearchController#yourSearchFunction');
//Return results
Route::get('search/{search}', 'YourSearchController#yourSearchResults');
Then add the route to your form:
{{Form::open(['route' => 'search'])}}
Then in yourSearchController:
function yourSearchFunction() {
$search = Input::only(['search']);
return Redirect::to('search/'.$search);
}
Then also in yourSearchController:
function yourSearchResults($search) {
return View::make('results')->with(compact('search'));
}

Resources