We are using wicket 6.
Both Session and Component classes have error() method to display an error. However in both cases these methods are final.
Is there any other universal way to add postfix to any error message? (we are looking to add error id)
Edit:
We have hundreds of files of code which already uses error() method from both Session and Component, so massive refactoring is not an option.
You can add arbitrary message objects to a Wicket component:
component.error(new ErrorCode(code));
With a custom FeedbackPanel you can then display the error code as needed:
protected Component newMessageDisplayComponent(String id, FeedbackMessage message)
{
Serializable rawMessage = message.getMessage();
if (rawMessage instanceof ErrorCode) {
// create custom component to display a text and/or code
...
} else {
return super.newMessageDisplayComponent(id, message);
}
}
Related
I am trying to redirect request if authorization is failed for it. I have following code:
class ValidateRequest extends Request{
public function authorize(){
// some logic here...
return false;
}
public function rules(){ /* ... */}
public function failedAuthorization() {
return redirect('safepage');
}
}
By default I am redirected to the 403 error page, but I would like to specify some specific route. I noticed that method failedAuthorization() is run, but redirect() method does not work...
Previously this code worked well with Laravel 5.1 but I used forbiddenResponse() method to redirect wrong request. How can I fix it with new LTS version?
Looks like it is impossible to redirect() directly from the custom ValidateRequest class. The only solution that I found is create custom exception and than handle it in the Handler class. So, now it works with following code:
Update: The method redirectTo() was updated to make solution work on Laravel 6.x and higher
app/Requests/ValidateRequest.php
class ValidateRequest extends Request{
public function authorize(){
// some logic here...
return false;
}
public function rules(){
return [];
}
public function failedAuthorization() {
$exception = new NotAuthorizedException('This action is unauthorized.', 403);
throw $exception->redirectTo("safepage");
}
}
app/Exceptions/NotAuthorizedException.php
<?php
namespace App\Exceptions;
use Exception;
class NotAuthorizedException extends Exception
{
protected $route;
public function redirectTo($route) {
$this->route = $route;
abort(Redirect::to($route));
}
public function route() {
return $this->route;
}
}
and app/Exceptions/Handler.php
...
public function render($request, Exception $exception){
...
if($exception instanceof NotAuthorizedException){
return redirect($exception->route());
}
...
}
So, it works, but much more slower than I expected... Simple measuring shows that handling and redirecting take 2.1 s, but with Laravel 5.1 the same action (and the same code) takes only 0.3 s
Adding NotAuthorizedException::class to the $dontReport property does not help at all...
Update
It runs much more faster with php 7.2, it takes 0.7 s
If you are revisiting this thread because in 2021 you are looking to redirect after failed authorization here's what you can do:
You cannot redirect from the failedAuthorization() method because it is expected to throw an exception (check the method in the base FormRequest class that you extend), the side effect of changing the return type is the $request hitting the controller instead of being handled on FormRequest authorization level.
You do not need to create a custom exception class, neither meddle with the Laravel core files like editing the render() of app/Exceptions/Handler.php, which will pick up the exception you threw and by default render the bland 403 page.
All you need to do is throw new HttpResponseException()
In the Laravel reference API we can see its job is to "Create a new HTTP response exception instance." and that is exactly what we want, right?
So we need to pass this Exception a $response. We can pass a redirect or JSON response!
Redirecting:
protected function failedAuthorization()
{
throw new HttpResponseException(response()->redirectToRoute('postOverview')
->with(['error' => 'This action is not authorized!']));
}
So we are creating a new instance of the HttpResponseException and we use the response() helper, which has this super helpful redirectToRoute('routeName') method, which we can further chain with the well known with() method and pass an error message to display on the front-end.
JSON:
Inspired by this topic
throw new HttpResponseException(response()->json(['error' => 'Unauthorized action!'], 403));
Thats'it.
You don't have to make ANY checks for validation or authorization in your controller, everything is done in the background before it hits the controller. You can test this by putting a dd('reached controller'); at the top of your controller method and it shouln't get trigered.
This way you keep your controller thin and separate concerns :)
Sidenote:
forbiddenResponse() has been replaced after lara 5.4 with failedAuthorization()
You can do through a middleware/policy i think. I don't know if you can do it from the validation.
You can override the function from FormRequest like this below:
/**
* Handle a failed authorization attempt.
*
* #return void
*
* #throws \Illuminate\Auth\Access\AuthorizationException
*/
protected function failedAuthorization()
{
throw new AuthorizationException('This action is unauthorized.');
}
And redirect where you want.
I am trying parse a HL7 REF I12 message with local customization(NZ).
When I tried using the GenericParser, I keep getting Validation exceptions.
For example for the segment below, I keep get the output
ca.uhn.hl7v2.validation.ValidationException: Validation failed:
Primitive value '(08)569-7555' requires to be empty or a US phone
number
PRD|PP|See T Tan^""^""^^""|""^^^^""^New Zealand||(08)569-7555||14134^NZMC
My question is:
Is there a way to avoid the validation by using the conformance class
generator
Is it possible to create own validation classes using
CustomModelClasses?
In either case, is there any example code for that or tutorial example documentation?
If disabling validation altogether is an option for your application, then you can set the validation context to use NoValidation.
See this thread in the hapi developers mailing list: http://sourceforge.net/p/hl7api/mailman/message/31244500/
Here is an example of how to disable validation:
HapiContext context = new DefaultHapiContext();
context.setValidationContext(new NoValidation());
GenericParser parser = context.getGenericParser();
String message = ...
try {
parser.parse(message);
} catch (Exception e) {
e.printStackTrace();
}
If you still require validation, but just want to change the validator for specific rules, then you'll have to create your own implementation of ValidationContext. This would be done by sub classing ca.uhn.hl7v2.validation.builder.support.NoValidationBuilder and overriding the configure method and use this to instantiate an instance of ValidationContextImpl.
For an example of how to implement the configure method in your subclass of NoValidationBuilder, see the source code for ca.uhn.hl7v2.validation.builder.support.DefaultValidationBuilder. This is the default validation context that is generating the error message you're seeing. To make it easier for you, I'm including the class listing here:
public class DefaultValidationBuilder extends DefaultValidationWithoutTNBuilder {
#Override
protected void configure() {
super.configure();
forAllVersions()
.primitive("TN")
.refersToSection("Version 2.4 Section 2.9.45")
.is(emptyOr(usPhoneNumber()));
}
}
Notice this is the implementation of the usPhoneNumber method defined in BuilderSupport:
public Predicate usPhoneNumber() {
return matches("(\\d{1,2} )?(\\(\\d{3}\\))?\\d{3}-\\d{4}(X\\d{1,5})?(B\\d{1,5})?(C.*)?",
"a US phone number");
}
in my application wicket is the client server and I am having a problem,I have two scenarios where the wicket asks from the server for info
read
read after update
i need to distinguish between the two cases , i want somethnig like
READ_OR_READ_AFTER_UPDATE paramter = READ_OR_READ_AFTER_UPDATE.READ;
ajaxRequestTarget.add(compToRender,parmeter);
is there a way to send the component value and treat the value inserted in prior call inside this component getModel , or before render...
You can check whether the current request is Ajax by:
if (RequestCycle.get().find(AjaxRequestTarget.class) != null) { Ajax } else {non-Ajax}
I dont know if i understand you correctly. Maybe this is what you want:
In your component set a variable for this
public Boolean isUpdated = Boolean.FALSE;
In your method where you perform the "update" set this variable to Boolean.TRUE;
In your components onConfigure() method overide and perform what you want:
#Override
protected void onConfigure() {
super.onConfigure();
if (isUpdated){
//do this
} else {
//do that
}
}
Is there a simple way in Symfony 1.4 to know whether a submitted form had any errors inside the form class? I'm familiar with the $form['some_field']->hasErrors() for templates but in this case I'd like to run a post-validator only if the form didn't have any errors with the standard validators. I'm basically after something like:
public function configure() {
// widgets
// standard validators
if (!this->hasErrors()) {
// run post-validator
}
}
The API documentation is as cryptic as usual. Thanks in advance.
Since the validation is perfom on the bind call, I don't see other place to post validate on error than in the bind function. So, in your form class:
public function bind(array $taintedValues = null, array $taintedFiles = null)
{
parent::bind($taintedValues, $taintedFiles);
if ($this->hasErrors())
{
// do post validate
// you can access values from your form using $taintedValues
}
}
But you will have to manually call the validator instead of just define a new one (since the bind process has already been done).
How do I define my own feedback messages in Wicket?
For example: if I give an incorrect username, I want to get an error message like "The user name in incorrect, try to login again." instead of using the default error message.
What would an example be like?
You can display your own error messages using error() and warn() and info(). If you want to show errors dependent on validators or the required flag you can define a properties file with the same name as the class which contains a mapping of field -> message. For example:
Index.java
Form form = new Form("myform");
form.add(new TextField("name").setRequired(true));
form.add(new PasswordTextField("password").setRequired(true));
form.add(new TextField("phonenumber").setRequired(true));
Index.properties
Required=Provide a ${label} or else...
All required fields
myform.name.Required=You have to provide a name
The field name in the form myform when it is required.
password.Required=You have to provide a password
Any field with the name password when it is required.
phonenumber.Required=A telephone number is obligatory.
Any field with the name phonenumber when it is required.
This shows a variety of ways of setting a feedback message for specific components.
You can also put the properties files next to the following component level (in order of importance, top highest):
Page Class
Component Class
Your Application Class
Wickets Application Class
Hope that helps
#user1090145: I've used overloaded Component's error() method in Validator's class:
private void error(IValidatable<String> validatable, String errorKey) {
ValidationError error = new ValidationError();
error.addMessageKey(errorKey);
validatable.error(error);
}
and invoked it in validate() by
error(validatable, "your-form.field.text-id");
Properties your-form.field.text-id must be defined in YourPage.properties
Sources:
Create custom validator in Wicket and
Form validation messages
you should set Feed back message to Session
message = "message";
Session.get().getFeedbackMessages().success(null, message);
You can use an anonymous IValidationError class and the messageSource.getMessage method to get a custom message from your property file:
error(new IValidationError() {
#Override
public Serializable getErrorMessage(IErrorMessageSource messageSource) {
//create a list of the arguments that you will use in your message string
Map<String, Object> vars = new HashMap<String, Object>();
vars.put("invalidUsername", getInvalidUsernameInput());
//get the message string from the property file
return messageSource.getMessage("mysettings.invalid_username", vars);
}
});
Sample property file:
mysettings.invalid_username=The user name "${invalidUsername}" is incorrect.