I created a Servlet call ShippingDetailsServlet.java and deployed it. I need to submit a HTML form to it. I am not sure what path I should put in the form action. Below is the form.
<form action="/services/mycompany/ShippingDetailsServlet" method="post">
Country: <input type="text" name="country" value="au"><br>
Quantity: <input type="text" name="quantity" value="1">
<cq:include path="./submit" resourceType="foundation/components/form/submit" />
Please let me know what path should I give for the form action so that it can be submitted to the Servlet.
Below is the Servlet.
package mycompany.servlets;
import org.apache.felix.scr.annotations.Properties;
import org.apache.felix.scr.annotations.Property;
import org.apache.felix.scr.annotations.sling.SlingServlet;
import org.apache.sling.api.SlingHttpServletRequest;
import org.apache.sling.api.SlingHttpServletResponse;
import org.apache.sling.api.servlets.SlingAllMethodsServlet;
import javax.servlet.ServletException;
import java.io.IOException;
import java.io.PrintWriter;
#SlingServlet(
paths={"/services/mycompany/"}
)
#Properties({
#Property(name="service.pid", value="mycompany.ShippingDetailsServlet",propertyPrivate=false),
#Property(name="service.description",value="Shipping details servlet", propertyPrivate=false),
#Property(name="service.vendor",value="mycompany", propertyPrivate=false)
})
public class ShippingDetailsServlet extends SlingAllMethodsServlet
{
#Override
protected void doGet(SlingHttpServletRequest request, SlingHttpServletResponse response) throws ServletException, IOException
{
//Do something fun here
}
#Override
protected void doPost(SlingHttpServletRequest request, SlingHttpServletResponse response) throws ServletException, IOException
{
//Do something fun here
PrintWriter out = response.getWriter();
out.println("Hello");
}
}
That is not necessarily true. You can deploy servlets on custom paths, but in order to do so you need to modify the "Apache Sling Servlet/Script Resolver and Error Handler" and add the custom path to the "Execution Paths" section.
Also, if this form is going to be deployed to your publish instance, you may want to use a custom path other than /bin/ because CQ has a lot of admin servlets registered under /bin and exposing them to the public may present a security concern.
By default, servlets can be deployed only below the /bin path. Don't put trailing / to the paths and don't add any additional properties. Eg. use following annotation:
#SlingServlet(paths={"/bin/services/mycompany"})
public class ShippingDetailsServlet extends SlingAllMethodsServlet
Path in the form should be the same as in #SlingServlet:
<form action="/bin/services/mycompany" method="post">
And if you really want to create servlet outside the /bin, you need to add appropriate path to the Execution Paths property in Apache Sling Servlet/Script Resolver and Error Handler configuration page in the /system/console/configMgr console.
Got the answer to my question from the forums.adobe.com
Answer is as below.
if you have annotated your servlet like this:
#SlingServlet(methods = { "POST" }, paths = "/apps/mycompany/servlets/GenericServlet")
the form shoud post to the same same url as in paths, that is "/apps/mycompany/servlets/GenericServlet"
so if you would change you "paths" line in the servlet to "/services/mycompany/ShippingDetailsServlet"
the form would post to that one.
Related
I have created a RotatingImagesComponent and allocating banners to that component.
As per requirement , need to allow maximum 6 banners in RotatingImagesComponent.
Can someone please let me know how to achieve this ?
Do I need to create CMS restriction in this case ?
Thanks..
Hi Below are the steps to Restrict Banner Numbers.
1 Extend RotatingImagesComponent to create custom one.
<relation code="SimpleResponsiveBannerComponentToTestRotatingImagesComponent" localized="false">
<deployment table="BannerToTestRotImgRel" typecode="25003"/>
<sourceElement qualifier="rotatingComponent" type="TestRotatingImagesComponent" cardinality="many"/>
<targetElement qualifier="simpleResponsiveBanners" type="SimpleResponsiveBannerComponent" cardinality="many" collectiontype="list" ordered="true"/>
</relation>
<itemtype code="TestRotatingImagesComponent" extends="RotatingImagesComponent" jaloclass="com.company.testcore.jalo.components.TestRotatingImagesComponent">
<description>Image carousel</description>
</itemtype>
2 Create new controller to set banneers based on your custom logic.
package com.company.teststorefront.controllers.cms;
import static java.util.stream.Collectors.toList;
import de.hybris.platform.acceleratorcms.model.components.SimpleResponsiveBannerComponentModel;
import java.util.List;
import javax.servlet.http.HttpServletRequest;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import com.company.testcore.model.components.TestRotatingImagesComponentModel;
import com.company.teststorefront.controllers.ControllerConstants;
/**
* Controller for the TestRotatingImagesComponent{#link TestRotatingImagesComponentModel}
*/
#Controller("TestRotatingImagesComponentController")
#RequestMapping(value = ControllerConstants.Actions.Cms.TestRotatingImagesComponent)
public class TestRotatingImagesComponentController
extends AbstractAcceleratorCMSComponentController<TestRotatingImagesComponentModel> {
private static final String IMAGE_CAROUSEL_BANNERS_ATTRIBUTE = "imageCarouselBanners";
private static final int BANNERS_MAX_SIZE = 5;
#Override
protected void fillModel(HttpServletRequest request, Model model, TestRotatingImagesComponentModel component) {
//#formatter:off
List<SimpleResponsiveBannerComponentModel> limitedBannerList = component.getSimpleResponsiveBanners().stream()
.limit(BANNERS_MAX_SIZE)
.collect(toList());
//#formatter:on
model.addAttribute(IMAGE_CAROUSEL_BANNERS_ATTRIBUTE, limitedBannerList);
}
}
3 create testRotatingImagesComponent.jsp and have logic to render banners.
<%# page trimDirectiveWhitespaces="true" %>
<%# taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<%# taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions"%>
<%# taglib prefix="ycommerce" uri="http://hybris.com/tld/ycommercetags" %>
<%# taglib prefix="image" tagdir="/WEB-INF/tags/responsive/image"%>
<div class="owl-carousel js-owl-carousel js-owl-banner carousel-banner" data-autoplayspeed = "${component.timeout}">
<c:forEach items="${imageCarouselBanners}" var="banner" varStatus="status">
<c:if test="${ycommerce:evaluateRestrictions(banner)}">
<c:url value="${banner.urlLink}" var="encodedUrl" />
<div class="carousel__item">
<a tabindex="-1" href="${encodedUrl}"<c:if test="${banner.urlLink}"> target="_blank"</c:if>>
<image:damImgModel damAsset="${banner.media}" cssClass="carousel-banner__image"/>
</a>
</div>
</c:if>
</c:forEach>
</div>
4 control this variable BANNERS_MAX_SIZE dynamically by adding in properties and use configurationService.
I think what you need in an interceptor
Create interceptor that implements PrepareInterceptor
public class RotatingImagesComponentInterceptor implements PrepareInterceptor<RotatingImagesComponentModel> {
....
#Override
public void onPrepare(RotatingImagesComponentModel model, InterceptorContext ctx) throws InterceptorException {
if (CollectionsUtils.isNotEmpty(model.getBanners()) && model.getBanners().size() > 6)
throw new InterceptorException("Only 6 banners are allowed");
}
}
From reusabilty point of view, I want to create a component for an interface. So I use it with different concrete objects.
For example, the interface is like this
interface ICalculation
{
double Calculate();
}
and the Test component is
<button #onclick="(() => SetResult())">Set</button>
#result
#code{
double result;
ICalculation Calculation;
void SetResult()
{
result = Calculation.Calculate();
}
}
so some where else in another component/page I have some thing like this
<Test inject CalculationA />
<Test inject CalculationB />
So I want to inject Different Calculations into different instances of this component. How can i get this?
I thought using dependency injection of net core, but that is for to inject one object for an interface.
Why important? It helps me to override requests to api, for example, admin and user have different requests but they see the same page structure.
In the Test component you would make it a normal parameter:
[Parameter]
public ICalculation Calculator { get; set; }
and then in 'some where else'
#inject CalculationA CalculationA
#inject CalculationB CalculationB
<Test Calculator="CalculationA" />
<Test Calculator="CalculationB" />
Or replace those '#inject` lines with normal instantiations (2x) because with multiple implementations you can't do DI on the interface anyway.
So I am trying to create this web application that uses java and trying to connect the html to java via httpservlet As a trial I am just trying to get some sample data passed to and from the html to java and vise versa. The issue I am having is when I run the html form, which works fine and I try to press the search button after adding the values I want, it goes to the 404 Not Found page. I tried to make sure that the compiled servlet class file resides in its package structure in /WEB-INF/classes folder. I also have a package. I am using tomcat to build and compile the app but I am getting "The origin server did not find a current representation for the target resource or is not willing to disclose that one exists." when I try to run "http://localhost:8080/". I have tried using #WebServlet, "action" in html and adding a jsp file. I have included images of the folder structure, web page and error.
I have no idea what I am doing wrong, would really love some help##
##
Folder Structure
Error
Web page
Java
#WebServlet("/servlet")
public class page extends HttpServlet {
#Override
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws IOException {
String accountid = request.getParameter("Accountid");
String marketid = request.getParameter("Marketid");
response.setContentType("text/html");
PrintWriter writer = response.getWriter();
writer.println("<html>");
writer.println("<head>");
writer.println("<title> Incidents search result </title>");
writer.println("<head>");
writer.println("<body>");
writer.println("<h1>" + accountid + marketid + "</h1>");
writer.println("</body>");
writer.println("</html>");
}
HTML
<form name="getInput" action="${com.example.page.java}/servlet" method="post">
<p>Account id: <input type="text" name="Accountid"></p>
<p>Market id: <input type="text" name="Marketid"></p>
<input type="submit" value="Submit">
</form>
web.xml
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee
http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"
id="WebApp_ID" version="3.1"
>
<!-- Invoke 'Generate' action to add tags or functions -->
<servlet>
<servlet-name>Servlet</servlet-name>
<servlet-class>com.example.page</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>Servlet</servlet-name>
<url-pattern>/servlet</url-pattern>
</servlet-mapping>
<welcome-file-list>
<welcome-file>index.jsp</welcome-file>
<welcome-file>getInputs.html</welcome-file>
</welcome-file-list>
</web-app>
jsp
<%# page contentType="text/html;charset=UTF-8" language="java" %>
Same as the html
Edit: I have tried using Servlet returns “HTTP Status 404 The requested resource (/servlet) is not available” but it didn't seem to work, as I have shown in the code and folder structure and am also using tomcat plus have tried all the different ways of writing 'action=...' in html.
Edit: This is the new error that I am getting
New Error
I think the problem is with action path provided in HTML remove ${com.incidents.cashout.CurlExecutor.java} & try it might work. Find - out path by sysouts .
I need to access httpServletRequest in the validate method of spring webflow. Please help me how to do this.
My webflow for view state is:
<var name="search" class="com.test.form.Search"/>
...................
<view-state id="search" model="search" view="searchPage">
<transition on="submit" to="searchAction">
</transition>
</view-state>
...............
validate method in search model class is:
public void validateLoanSearch(ValidationContext context) {
//I need to get a httpServletRequest here...
}
In action/controller class I can get it thru RequestContext but ValidationContext gives only the messageContext. Any idea? Please help.
I got the solution.
In the bean class or validator class inside the validate method use this:
RequestContext rc = RequestContextHolder.getRequestContext();
RequestContextHolder is becoming available inside the validate method.
I'm trying to learn how to use custom events in Flex.
I'm following Oliver Merk's tutorial found here: blog
The custom event works if I implement it using MXML in the main app. But, if I use actionscript, then I get error 1119: Access of possibly undefined property ADD_PRODUCT through a reference with static type Class.
My Event:
In the events subdirectory, I've got:
package events {
import flash.events.Event;
public class AddProductEvent extends Event {
public var productName:String;
public function AddProductEvent( type:String, productName:String ) {
super( type );
this.productName = productName;
}
override public function clone():Event {
return new AddProductEvent( type, productName );
}
}
}
In the component, I've got a radioButtonGroup
<mx:RadioButtonGroup id="choicesRadioButtonGroup" itemClick="onButtonClick()"/>
private function onButtonClick():void {
var myEventObj:Event = new AddProductEvent("addProduct", "Flex T-shirt");
dispatchEvent(myEventObj);
}
This is the metadata in the component and the import statement:
<mx:Metadata>
[Event (name="addProduct", type="events.AddProductEvent")]
</mx:Metadata>
import events.AddProductEvent;
In the main app, I've got:
import events.AddProductEvent;
private function onAddProduct( event:AddProductEvent ):void {
mx.controls.Alert.show('Attached data was ' + event.productName);
}
If I implement the component in the main app like this:
<visualcomponent:PopWindow addProduct="onAddProduct(event)" />
then everything works.
If I implement the component in the main app in actionscript like this, then I get an error:
public function clickHandler2(event:MouseEvent):void {
if(event.currentTarget.selected){popWindow = new PopWindow;
queryBuilder(event.currentTarget);
PopUpManager.addPopUp(popWindow, my_view, false);
PopUpManager.centerPopUp(popWindow);
popWindow.addEventListener(AddProductEvent.ADD_PRODUCT, onAddProduct);}
}
I get the error on the addEventListener line. What am I doing wrong? Any advice?
Thank you.
-Laxmidi
Your AddProductEvent class doesn't seem to expose a public static string called ADD_PRODUCT which has the value "addProduct" which is what it looks like you are trying to do.