I've got a JSF page that allows users to upload images. I'd like to perform some validation on the uploaded file to ensure it's the correct size, dimensions, content type, etc. I've created a JSF Validator, and have tried specifying it both in the <s:fileUpload validator="XXX" /> attribute, as well as using the <f:validator /> tag. However, no matter what I try my validator is never called. Is there any way to validate a file upload in Seam? Would using <rich:fileUpload /> allow me to do validation on the uploaded file?
After a lot of trial and error, I've just decided to do a manual validation in my submit method. I haven't found a way to get a Validator object to work successfully.
You can try with a listener like (not sure if event has a cancel method to call if your constraint fails, but you can check):
public void listener(UploadEvent event) throws IOException {
UploadItem item = event.getUploadItem();
String name = "unnamed_attachment";
byte[] data = item.getData();
if (item.isFile()) {
name = FilenameUtils.getName(item.getFileName());
data = FileUtils.readFileToByteArray( item.getFile() );
}
debug("file uploaded '#0' : '#1'", name, item.getFileName());
And some constraints you can put in components.xml, like:
<web:multipart-filter create-temp-files="false"
max-request-size="5200000"
url-pattern="/*"/>
Related
I am using Liferay 6.2. I made a hook to add some extra fields in User-My Acccount page. On key press of these fields, an ajax call needs to be invoked. I read lifery service override and trying to follow the same approach: It works for updating user with new fields.
However, for ajax call, i need to override serve resource method somewhere. But i am not sure where exactly to call serve resource().
My approach is as follows:
In details.jsp
<portlet:resourceURL var ="userProfileURL"></portlet:resourceURL>
In js:
I call the ajax by using AUI io request: I pass mode as a parameter to check if it goes inside serveResource or not..
But before going to serve resource, it gives me an error saying userProfileURL is not defined. I have also included needed imports for it in jsp.
In userServiceImpl class that extends UserServiceWrapper, i tried to override serveResource:
public void serveResource(ResourceRequest resourceRequest, ResourceResponse resourceResponse) throws PortletException {
String mode = ParamUtil.getString(resourceRequest,"mode")
if(mode.equals("getData")
{
// do needed processings & return data
}
else {
// super.serveResource(resourceRequest, resourceResponse);
}
But i get an error that says:
The method serveResource(ResourceRequest, ResourceResponse) is undefined for the type UserServiceWrapper
Is there any way to make ajax calls in hooks for user account page or am i oveririding on the wrong place?
I'm using zf2 form object on the server and ajax code on the client to implement my registration form.
I post the form values in the ajax request, no problem, and the form gets them fine with
$form->setData($request->getPost());
After I validate the form and perform the registration on the server, I want to send the form back to the client, especially if there are errors, so I can show them to the user.
I'm looking for a standard way using zend or any plugin to serialise the form object into JSON format, so I can send it in the response to the AJAX call.
Any idea?
Well what you can do is run the validation on your form and after that you will return your form within a new JsonModel.
Here is a little example of how to handle your controller:
class RegistrationController extends AbstractActionController
{
public function RegisterAction()
{
$form = new RegisterForm();
$form->setInputFilter(new RegisterInputFilter());
if ($this->getRequest()->isPost()) {
$form->setData($this->getRequest()->getPost());
if($form->isValid()) {
// Handle your registration as the form is valid!
// return to some path after registration is complete.
// Show user he registered succesfully, etc. ;)
}
// Checks if the request is from JavaScript
if($this->getRequest()->isXmlHttpRequest()) {
return new JsonModel(array('registerForm' => $form));
}
}
return new ViewModel(array('registerForm' => $form));
}
}
Notice that the form object is holding all the invalid inputs including its message after validation.
I would take another approach just to completely render the ViewModel again so you can display the validation message much easier. On the side you could add Client Side (Javascript) validation as it's much more user-friendly, but that is just some fancy shizzle I would do ;) In case of rendering the ViewModel:
use Zend\View\Renderer\PhpRenderer;
if($this->getRequest()->isXmlHttpRequest()) {
$renderer = new PhpRenderer;
$registerViewModel = new ViewMOdel();
$registerViewModel->setTemplate('view/register.phtml');
return new JsonModel(array('registerViewModel' => $renderer->render($registerViewModel));
}
Note that not setting a template to your viewModel will result in ZF2 getting the default of the action (view/moduleName/registration/register.phtml) you are in! So in your case you don't need to use PhpRenderrer::setTemplate(). But I just hand it to you so you can change it if you are using any other file.
So now you will receive Json from our controller, in your javascript. Retrieve the new ViewModel from Json and remove the old ViewModel and replace it with the new. By removing the old, you also remove any Javascript that is bound to any element within the viewModel, so you might set the events on your body within your javascript or have it on your attributes in Form/RegistrationForm.
Hope this pushes you in the right direction.
Im building my own web service on the premise of 2-legged OAuth.
With each authenticated request there will be an included HMAC.
I know it could be done like this:
public ActionResult userInfoExample(string HMAC, string username)
{
MyMembership.checkHMAC(HMAC);
//get user
return View();
}
but that is fairly nasty, because HMAC needs to be included in the parameters for every action. Its weakly typed and crap.
I wanted to do something like this:
[AuthorizeHMAC]
public ActionResult userInfoExample(string username)
{
//get user
return View();
}
I found this, and it mentioned I should look at Custom Modal Binders, so then I found this and after reading it I am unsure how I could make that work.
My goal is to authenticate (/authorise) using a HMAC that (I assume) is placed in the URL parameters i.e.: http:// www.website.com/foo/bar?username=xxx&hmac=xxxxxxxxx
I would like to know if anyone has any references I can read or a direct solution.
I am also welcome to criticism on my fundamental understanding of API security, or how I am doing things, I am fairly new to this area of
Check out my code at
http://mvcsecurity.codeplex.com/
I do something similar to validate parameters on the page (it is not an HMAC though). Since you will be generating it on the View Im assuming (or passing it to the view) you can check it the same way a similar way I check it in my attribute.
From:
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
//The hidden form field that contains our hash - for ex. CustomerId is rendered as a hidden input id="_CustomerIdToken"
string encryptedPropertyName = string.Format("_{0}Token", _propertyName);
//grab the token
string hashToken = filterContext.HttpContext.Request.Form[encryptedPropertyName];
//The encrypted form data MUST be there. We do not allow empty strings otherwise this could give
//an attack vector in our filter as a means to bypass checks by simply passing in an empty validation token.
if (string.IsNullOrEmpty(hashToken))
{
throw new MissingFieldException(string.Format("The hidden form field named value {0} was missing. This is created by the Html.AntiModelInjection methods. Ensure the name used on your [ValidateAntiModelInjectionAttribute(\"!HERE!\")] matches the field name used in Html.AntiModelInjection method. If this attribute is used on a controller method that is meant for HttpGet, then the form value would not yet exist. This attribute is meant to be used on controller methods accessed via HttpPost.", encryptedPropertyName));
}
//Get the plain text value
string formValue = filterContext.HttpContext.Request.Form[_propertyName];
//Plain text must be available to compare.
if (string.IsNullOrEmpty(formValue))
{
throw new MissingFieldException(string.Format("The form value {0} was missing. If this attribute is used on a controller method that is meant for HttpGet, then the form value would not yet exist. This attribute is meant to be used on controller methods accessed via HttpPost.", _propertyName));
}
//We cannot encrypt the form value and compare to the previously encrypted form token.
//Each time you Encrypt() with the MachineKey class even using the same plain text, the end result is difference.
byte[] plainTextBytes = MachineKey.Decode(hashToken, MachineKeyProtection.Encryption);
string plainText = Encoding.Unicode.GetString(plainTextBytes);
//And compare
if (string.Compare(plainText, formValue , false, CultureInfo.InvariantCulture) != 0)
{
throw new HttpAntiModelInjectionException(string.Format("Failed security validation for {0}. It is possible the data was tampered with as the original value used to create the form field does not match the current property value for this field. Ensure if this is a web farm, the machine keys are the same.",_propertyName));
}
filterContext.HttpContext.Trace.Write("(Logging Filter)Action Executing: " +
filterContext.ActionDescriptor.ActionName);
base.OnActionExecuting(filterContext);
}
I am using the validation framework with Struts 1.1.When validation fails, the entire form is reset.
After much time scouring the net, I have gathered:
When a new request is received, the form object is created if it does not exist in the current scope (request or session).
Reset is called()
Form values are populated from the bean properties.
Validation starts if enabled
If validation fails, ActionErrors are returned and the request is directed to the URI given by the input attribute of the action tag in my struts-config.xml.
That's where I have the problem. If validation fails, and I set the input param to the same page, reset() gets called again but it does not use the bean values from when the form is initially loaded. So the user has to re-enter everything.
My action mapping class for this action looks like this:
<action
path="/edit/componentRelease"
type="org.twdata.struts.SpringAction"
name="edit/componentRelease"
scope="request"
input="/WEB-INF/jsp/edit/editComponentRelease.jsp"
parameter="edit/componentRelease"
validate="true"
>
<forward
name="edit/componentRelease"
path="/WEB-INF/jsp/edit/editComponentRelease.jsp"
redirect="false"
/>
</action>
The form used to display the bean starts with:
<html:form method="post" name="componentReleaseEditor" type="com.mx.releasemgr.forms.ComponentReleaseEditorForm" action="/edit/componentRelease">
the reset() is used to clear the values previously entered...if u debug it and see then u'll come to know. eg ur entering 1 in the form and say submit and again come on the same form and enter 2 and submit again now what reset will do is it will clear 1 and now 2, and thus u get 2 in ur validate() part.
#Override
public void reset(ActionMapping mapping, HttpServletRequest request) {
//If Clear button click will set date as today and clear all other value
//If Insert, update with validation as failure than not clear all value on the form, but only clear that wrong when validation (means skipp all value as true on the form and only clear value wrong)
String actionName = request.getParameter("method");
if(actionName!=null){
if (actionName.equals(Enums.ActionName.CLEAR.getActionName())) {
Date date = new Date();
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd");
this.setPublicationDay(dateFormat.format(date));
}
else{
request.setAttribute("book", this);
}
}
super.reset(mapping, request);
}
The solution is to move the display of the form to a different action than that used to forward. In my example, they are both the same.
I have a Spring configuration file with MANY entries such as the one below.
<mvc:view-controller path="/test/one" view-name="one.xml" />
<mvc:view-controller path="/test/two" view-name="two.xml" />
<mvc:view-controller path="/test/three" view-name="three.xml" />
Now I am integrating controller code and I am trying to avoid having to have a request mapping for every single page. Is there a way for Spring MVC to implicitly find the page with the view as specified in the controllers.xml.
So instead of returning a string as the View. I would like a method where I was returning void or just the model to the page and for it to find the page
#RequestMapping(value = "/test/one", method = RequestMethod.GET)
public String getOne(HttpServletRequest request, Model model) {
// Business Logic
return "one.xml" // would like to be able to return void here or just the mode
}
The idea of mvc:view-controller is precisely to avoid having to implement a controller whan its only job would be to dispatch to a view. Just having this tag in the XML is sufficient. You don't need a controller.
See http://static.springsource.org/spring/docs/current/spring-framework-reference/html/mvc.html#mvc-view-controller
If you have controller logic and thus need a controller, then the mvc:view-controller element should be removed, and be replaced by the actual controller, which dispatches to the appropriate view. You may avoid specifying a view name explicitely here using a RequestToViewNameTranslator, as explained here.