How to POST an object to controller - spring

I'm having a difficulty passing my 'product' object to the controller. How can I do it? I'm not getting errors. The problem is that the 'product' object is null on my controller.
html:
<section th:each="menu : ${allMenus}">
<button
<h1 th:text="${menu.name}"></h1>
</button>
<div>
<div th:each="product : ${menu.productList}">
<a data-toggle="modal" th:href="'#' + ${product.name} + 'Modal'">
h5 th:text="${product.name}"></h5>
<small th:text="${product.price} + '$'"></small>
<p th:text="${product.description}"></p>
</a>
<div th:replace="/productModal :: productModal(product=${product})"></div>
</div>
</section>
Modal:
<div th:fragment="productModal(product)">
<div role="document">
<form method="post" th:action="#{/addItemToCart}">
<div th:each="topping : ${product.toppings}">
<input type="checkbox" th:id="${topping} + ${product.id}" name="checkedToppings" th:value="${topping}" />
<label th:for="${topping} + ${product.id}" th:text="${topping}"></label>
</div>
<div>
<button type="submit">Add to Shopping Cart</button>
</div>
</form>
</div>
</div>
controller:
#RequestMapping(value="/addItemToCart", method=RequestMethod.POST)
public String addItemToCart(#ModelAttribute("product") Product product, #RequestParam("checkedToppings") List<String> toppings)
{
//product is null;
//checkedToppings are retrieved correctly
return "redirect:/menu";
}

Short answer:
you don't post objects to controllers using HTML.
Details:
You will never be able to post a "product" object to your controller from an HTML page.
Instead,
you should send identifying information about the desired "product" to the controller,
perhaps a product-id or some other product-unique-identity-blammy.
Response to options in comments:
Hackers love hidden fields and JavaScript;
I recommend against using those for this situation.
I believe that you only have one option: identifying info.
This does not need to be a "real" product number.
You can generate a UUID and store a map in the choose one: (Servlet Session, Database, Application Session, somewhere else on the server) that maps from the UUID to the desired product.

Related

Cannot find parent element in DOM tree containing attribute: [wire:id]

I am laravel developer and developing a real time chat room using liveware , i am trying to open chat when i click to user but unfortunatly i am getting error https://flareapp.io/share/OmVDe437#F47 please help me how can resolved that ? thank u.
I am also getting error in console.
app\Http\Livewire\Messaging.php
public $selectedConservation;
public function mount(){
$this->selectedConservation = Conservation::query()
->where('sender_id',Auth::user()->id)
->orwhere('reciever_id',Auth::user()->id)
->first();
}
public function viewMessages($conservationsId){
$this->selectedConservation =
Conservation::findorFail($conservationsId);
}
public function render()
{
$conservation = Conservation::query()
->where('sender_id',Auth::user()->id)
->orwhere('reciever_id',Auth::user()->id)
->get();
return view('livewire.messaging',[
'conservation' => $conservation,
]);
}
resources\views\livewire\messaging.blade.php
#foreach ($conservation as $conservations)
<a href="#" wire:click.prevent="viewMessages({{ $conservations->id}} )">
<div class="user-card rounded bg-dark bg-opacity-10 mb-1">
<div class="mx-2">
<div class="d-flex pt-3">
<img class="rounded-circle" width="48px" height="48px" src="{{Config('wfh.file').$conservations->reciever->avator}}" alt="">
<div class="notification-text ms-3 w-100">
<span class="username fw-bold">{{$conservations->reciever->full_name}}</span>
<span class="float-end small"></span>
<p class="mt-1 text-muted">You: </p>
</div>
</div>
</div>
</div>
</a>
#endforeach
Check out the documentation on Dom Diffing Issues. It looks like you need to add a wire:key="{{ $conversations->id }}" attribute into your a tag so that Livewire can track changes to the list of conversations.

How to return view in controller?

I need to pull in data to my view but this doesn't work:
return view ('sub-domain', ['worker' => $worker ]);
Here is my code:
public function aerospace(Request $request , Worker $worker ){
$worker = $worker->newQuery();
if ($request->has('profession')) {
$worker->where('profession', $request->input('profession'));
}
if ($request->has('state')) {
$worker->where('state', $request->input('state'));
}
if ($request->has('local_govt')) {
$worker->where('local_govt', $request->input('local_govt'));
}
return $worker->get();
The above code brings out an array of data from the database which I can then filter with "domain/sub-domain?state=xyz"
Now when I try to pass in the data into my views using
return view ('sub-domain', ['worker' => $worker ]);
The page is loaded but no $worker data is loaded on the page. How can I pull the data? Here is my view file
<div class="row">
<form method="GET" action="">
Profession:<input type="text" name="profession"> State:<input type="text" name="state"> Local Govt:<input type="text" name="local_govt">
<button type="submit">Filter</button>
</form>
</div>
<div class="row">
#foreach ($worker as $worker)
<div class="col-lg-3 col-md-6">
<div class="member">
<div class="pic"><img src="avatar/{{$worker->avatar}}" alt=""></div>
<div class="details">
<h4>{{$worker->name}} {{$worker->l_name}}</h4>
<span>{{$worker->profession}}</span><br>{{ $worker->state }}
</div>
</div>
</div> #endforeach
</div>
I want to filter data by certain parameters, if there's a better way to do that please do let me know. But first I need the data to display.
You are returning a query instance, not a collection or singular model. That's why the get() method works. So first do:
$worker = $worker->get();

Laravel applying search filers

I have a page which has a search box(input text) which takes a place name as input and returns all the nearby dealers.
I also happen to have filters (checkboxes) for all the brand
<div class="col-sm-12 col-md-12">
{!! Form::checkbox('filters',$bike_oem, false,['style'=>'padding-right:5px;'] ) !!} <span style="padding-left:5px;"></span>{{ $bike_oem }}
</div>
How do I implement get the value of filter in my controller ?
<div class="col-sm-12 col-md-12">
<input style="padding-right:5px;" name="Hyundai " type="checkbox" value="Y"> <span style="padding-left:5px;"></span>Hyundai
</div>
This is how each filter appears in the page. Is the code correct to fetch the value in controller ? Please suggest
You can get the value of checkbox in this way also(in controller)
public function myFunction(Request $request){
if (isset($request['Hyundai']) && ($request['Hyundai'] == "on")) {
$value = "Y";
}
}

Hibernate Validator retrieve error messages without using Spring Framework

I am currently using hibernate-distribution-3.6.4.Final. New to Hibernate Validator.
Problem:
How should I retrieve error messages I got from adding annotations to databean/formbean? I know in Spring that everyone seems to use messages.properties file from the classpath?
But how about pure hibernate 3, is there any file like that or what should i do instead? (Didn't find good answers online...)
Hope this will help. Source is : Mastering Spring MVC
You will need to add a few more things for validation to work. First, the controller needs to say that it wants a valid model on form submission. Adding the javax.validation.Valid as wel as
import org.hibernate.validator.constraints.Email;
import org.hibernate.validator.constraints.NotEmpty;
annotation to the parameter representing the form does just that:
#RequestMapping(value = "/profile", method = RequestMethod.POST)
public String saveProfile(#Valid ProfileForm profileForm,
BindingResult bindingResult) {
if (bindingResult.hasErrors()) {
return "profile/profilePage";
}
System.out.println("save ok" + profileForm);
return "redirect:/profile";
}
Note that you do not redirect the user if the form contains any errors. This will allow you to display them on the same web page. Speaking of which, you need to add a place on the web page where those errors will be displayed.
Add these lines in profilePage.html:
<form th:action="#{/profile}" th:object="${profileForm}"
....">
<div class="row">
<div class="input-field col s6">
<input th:field="${profileForm.twitterHandle}"
id="twitterHandle" type="text" th:errorclass="invalid"/>
<label for="twitterHandle">Twitter handle</label>
<div th:errors="*{twitterHandle}" class="redtext">
Error</div>
</div>
<div class="input-field col s6">
<input th:field="${profileForm.email}" id="email"
type="text" th:errorclass="invalid"/>
<label for="email">Email</label>
<div th:errors="*{email}" class="red-text">Error</div>
</div>
</div>
<div class="row">
<div class="input-field col s6">
<input th:field="${profileForm.birthDate}"
id="birthDate" type="text" th:errorclass="invalid" th:placeholder="${
dateFormat}"/>
<label for="birthDate">Birth Date</label>
<div th:errors="*{birthDate}" class="red-text">Error</
div>
</div>
</div>
<div class="row s12">
<button class="btn indigo waves-effect waves-light"
type="submit" name="save">Submit
<i class="mdi-content-send right"></i>
</button>
</div>
</form>
Yes Indeed, Spring Boot takes care of creating a message source bean for us.
The default location for this message source is in
src/main/resources/messages.
properties.
Create such a bundle, and add the following text:
Size.profileForm.twitterHandle=Please type in your twitter user name
Email.profileForm.email=Please specify a valid email address
NotEmpty.profileForm.email=Please specify your email address
PastLocalDate.profileForm.birthDate=Please specify a real birth date
NotNull.profileForm.birthDate=Please specify your birth date
typeMismatch.birthDate = Invalid birth date format
.

Refresh g:each tag via AJAX call in Grails

I have a statistical panel which displays the last registered users. I want to implement a AJAX call to upload the panel without having to reload the full page.
I have the following code in my view:
<g:each in="${lastUsers}" var="user">
<div class="mt-comments">
<div class="mt-comment">
<div class="mt-comment-img">
<g:if test="${user?.avatar}">
<img src="${createLink(controller:'controllerUser',
action:'image', id: user?.id)}" />
</g:if>
<g:else>
<img class="img-circle"
src="${resource(dir: 'img/profile', file: 'user_profile.png')}"/>
</g:else>
</div>
<div class="mt-comment-body">
<div class="mt-comment-info">
<span class="mt-comment-author">${user?.username}</span>
<span class="mt-comment-date">
<g:formatDate date="${user?.dateCreated}"/>
</span>
</div>
<div class="mt-comment-text">${user?.email}</div>
<div class="mt-comment-details">
<g:if test="${user?.enabled}">
<span class="mt-comment-status label label-sm label-success circle">
</g:if>
<g:else>
<span class="mt-comment-status label label-sm label-info circle">
</g:else>
<g:formatBoolean boolean="${user?.enabled}"/>
</span>
<ul class="mt-comment-actions">
<li>
<g:link controller="user" action="edit" id="${user?.id}">Edit</g:link>
</li>
</ul>
</div>
</div>
</div>
</div>
</g:each>
Also, I have a button when it is clicked calls the AJAX function. The Ajax function receives the data successful in JSON format. From there, I don't know upload my g:each tag.
I have tried the remoteFunction of Grails to use the upload attribute, but an error appears: No javascript provider is configured and I have searched the solution but anything works me.
The AJAX call:
$('.button').click(function() {
$.ajax({
url: URL,
success: function(data) {
console.log(data[index]);
console.log(val.username);
console.log(val.dateCreated);
console.log(val.email);
console.log(val.enabled);
console.log(val.avatar);
console.log(val.id);
},
error: function(){
},
});
Thanks for helping me.
Instead of Using JSON Data, You can do this using grails templates and jQuery load method. Here is a quick POC.
Template (_userComments.gsp)
This will act as a reusable view which can be called via AJAX or can be included directly in other views.
<g:each in="${lastUsers}" var="user">
<div class="mt-comments">
.....
</div>
</g:each>
View (main.gsp)
Our Main View.
<div class="userComments">
<!-- When the Page is Loaded, We need render this without an Ajax Call -->
<g:render template="userComments" model="['lastUsers':lastUsers]"/>
</div>
Javascript
$('.button').click(function() {
$( ".userComments" ).load( "user/userComments" );
});
Controller
We are defining two methods one for the main view and one for the ajax call.
def index() {
def lastUsers = User.list();
render(view:'main', model: [lastUsers: lastUsers])
}
// Ajax Call
def userComments() {
def lastUsers = User.list(); // what ever your fetch logic is
render(template:'userComments', model: [lastUsers: lastUsers])
}

Resources