How to hide Url values in Play Scala? - scala

How to hide the values in the URL? In routes:
GET /admin/:userId com.example.sample.getUser(userId: Int)
When getUser action is requested, URL returns in the format as shown below:
http://localhost:9000/admin/0
I don't want to view the userId in the URL.

This is common GET vs POST difference. In GET request params are sent within the URL, in POST are not.
If you need to avoid params in the URL just use a HTML form with hidden field instead of a tag to send the requests and in your controller fetch the POST arguments, dummy HTML sample:
<form action="/admin/" method="POST">
<input type="hidden" name="userId" value="#userId" >
<input type="submit" value="#userName" >
</form>
It will give you submit button with name of the user as a label, you can use CSS to give it feel and look of common link.
Note that's invalid REST pattern, as POST shouldn't be used to showing data, you don't mention what is the purpose of this, so maybe you should rethink your needs.
Maybe you can also just make usage of parameters with default or fixed values:
check the docs for more options

Related

Gorilla CSRF - Forbidden - CSRF token invalid - fails when there are two forms

I'm adding in CSRF token validation and I'm running into a problem where I have two forms on a page and one of them will submit successfully and the other will not. I'm not doing AJAX requests, I'm simply using hidden input fields. If I submit the form when it is the only one on the page, it submits without issue. If I submit it on a page with more than one form, it fails.
Below is the template code for my two forms
{{if .IsAuthenticated}}
<form action='/admin/logout' method='POST'>
<button>Logout</button>
{{.CsrfField}}
</form>
{{end}}
<form action='/admin/stuff/create' method='POST'>
{{with .Form}}
<div>
<label>Title:</label>
<input type='text' name='title' value='{{.Get "title"}}'>
</div>
<div>
<input type='submit' value='Publish stuff'>
</div>
{{end}}
{{.CsrfField}}
</form>
And this is what the generated HTML looks like. Both appear to be valid.
When I click the "Logout" button though, I get the Forbidden - CSRF token invalid error, but clicking the create input value in the second form always works.
The logout button is correctly validated when I attempt to use it on the home page which is "/admin/" but it does not work on any of the other pages "/admin/snippet/:id" or "/admin/snippet/create". The Logout button is part of a base template, so it appears on every page, so there shouldn't be anything different in how it appears on any page.
I've read other SO posts about multiple forms & CSRF tokens on a page and I understand there should be no issue with multiple forms with the same information as long as you have each one in it's own form, it should be fine. So I am not sure where I am going wrong.
I found the issue. Currently the way that gorilla/csrf works, it does not like creating the masked token from one path and then sending that token off to another path. So in my situation, going from /admin/snippet/create to /admin/logout threw an error because it was expecting the path for the token to be /admin/snippet/<something> and so it threw an error.
This issue has been addressed in this PR: https://github.com/gorilla/csrf/pull/147 and essentially the solution is to set the default path yourself to something which all of your routes will contain, so in my case that was /admin
This is what my CSRF declaration looks like now in main.go
var csrfMiddleWare = csrf.Protect(
[]byte("<put your 32 character key here>"),
csrf.Path("/admin"),
csrf.Secure(false),
)
A note, if you had this issue and then apply this fix and it doesn't resolve the problem, trying testing in a separate browser as there may be some caching issues.

Dynamically loading content through Groovy server page upon form submit

I have a Groovy project (vanilla; no Grails) with an index.gsp that takes form input from the user and sends it in a POST request to a Groovy script. The form is set up like this:
<form action="somewhere" method="POST" enctype="multipart/form-data">
// some other inputs
<input type="submit"/>
</form>
Is there any way (ideally not using Javascript) to dynamically load content on the same page after the user submits? Redirecting to another GSP might also work. Just something simple, like a string containing whatever the user typed. It seems like Grails has plenty of options, but unfortunately I can't use it.
As you mentioned, Grails is capable of doing what you need without any complex code. Since you can't use it, you will have to use JQuery(Javascript) to make an AJAX call. AJAX is the he only way that I know to achive that.
Just make an AJAX call to your groovy script. JQuery.ajax has a success function to be called if the request succeeds. You can use it to update a hidden dive after the form. This success function has the data returned from the server as an argument, that data could be the string containing whatever the user typed. In that case just add the data to the hidden div and then make that div visible.
function onSucceed(data) {
$('#hiddenDivToUpdate').text(data);
$('#hiddenDivToUpdate').show();
}
You can learn about JQuery.ajax() in this link AJAX

How to add a contact form to a static web site?

I have a mostly "static" web site with no server-side code and just a little JavaScript. Now I would like to add a contact form. I do not care how I get the contact form data (so just writing this data to a text file in the server will be ok).
What is the simplest solution for this problem? How do people usually handle this?
I believe I can add some server-side code (PHP or something) to handle the form (and write the form data to a file, for instance) but I would prefer a client-side solution.
Use an external tool, they are commonly referred to as "formmailer". You basically submit the form to their server, and they send the form contents via mail to you.
If you don't want that, you have to do something server-sided: Storing data on the server, without having a server side program that accepts the data from the client, is just not possible.
You could install CouchDB and interface that from Javascript :) Everyone could use that then, too :)
The most easy PHP script that stores POST data on your harddisk:
<?php file_put_contents('/path/to/file', serialize($_POST) . "\n", FILE_APPEND); ?>
You can use Google Drive and create form with required fields. and embed code (which will be iframe) in your static web page.
You will be able to get submitted data in spreadsheet.
You can use qontacto . it is a free contact form you can add to any website. it forwards you the messages.
I set up the fwdform service for this exact need.
Just two simple steps to get your form forwarded to your email.
1.Register
Make an HTTP POST request to register your email.
$ curl --data "email=<your_email>" https://fwdform.herokuapp.com/register
Token: 780a8c9b-dc2d-4258-83af-4deefe446dee
2. Set up your form
<form action="https://fwdform.herokuapp.com/user/<token>" method="post">
Email: <input type="text" name="name"><br>
Name: <input type="text" name="email"><br>
Message: <textarea name="message" cols="40" rows="5"></textarea>
<input type="submit" value="Send Message">
</form>
With a couple of extra seconds you can spin up your own instance on Heroku.

generate querystring

I have created one jsp form which contains the username textfield. On the click of submit button it pass on to servlet and read parameter and display on the screen.
I want to generate a querystring of username with the url.
Can anyone tell me how can i do that??
The following example will add the username field in the querystring of the request URL.
<form action="servletURL">
<input type="text" name="username" />
<input type="submit" />
</form>
Note that there's no method. It defaults to GET already, which means that all form data is passed by URL.
If you still don't see the querystring in the request URL, then it means that your servlet is performing a redirect after submit.
response.sendRedirect("result.jsp");
The enduser will then see the redirected URL in browser address bar instead. If you don't include the querystring in the redirect URL, then the enduser will indeed not see it at all.
You should either be doing a forward() instead,
request.getRequestDispatcher("/WEB-INF/result.jsp").forward(request, response);
or append the query string yourself:
response.sendRedirect("result.jsp?" + request.getQueryString());

Does Alfresco Share provide any mecanism for Inter Dashlet Communication?

I am trying to figure out how to perform some inter dashlet communication with Alfresco Share.
Here a simple use case:
We do have 2 dashlets, let's call them A and B. I want to be able to fill in a field "name" (let's say with value "Toto") in A and click on submit button. After clicking on submit button in A. B should be updated with greeting like " Good Morning Toto".
Thank you for you answers.
Thanks for your answer. Can you elaborate a bit regarding "let dashlet_b.get.html.ftl post something to dashlet_a.post.html.ftl" ?
In dashlet_b.get.html.ftl you have something like that I guess :
<form id="..." action="" method="POST">
<input id="name" type="text" name="name" value=""/>
<input type="submit" id="send" value="Send" /></form>
When you submit the form it's gonna look for dashlet_b.post.js right ? How do you actually tell to send the form to dashlet_a.post.js ?
To create these dynamic dashlets it is not enough to use the server side dashlet webscript. You need javascript logic in the browser to notify the other dashlet of changes. This is how Alfresco usually does that:
Browser Javascript Dashlet A:
YAHOO.Bubbling.fire("interDashletMessage",
{
message: "Hello World."
});
Browser Javascript Dashlet B:
YAHOO.Bubbling.on("interDashletMessage", function(layer, args) {
var message = args[1].message;
alert(message); // or write it to the dashlets HTML content
});
This will send the message from dashlet A to dashlet B using a custom event called "interDashletMessage".
If your dashlet B only displays a few messages it could be enough to send the data over using the events. If it is more complex your dashlet A needs to post it's data to the repository first, then trigger the "refresh" event and have dashlet B refresh it's content from the repository. This will involve multiple webscripts you may need to write.
That's quite simple I guess.
Each Dashlet is in fact a webscript. So you can have multiple webscript for different usage. Like I've got dashlet_a.get.html.ftl and dashlet_a.post.html.ftl.
In fact these two are the same webscript, one just acts on a post and the other on get.
So what you could do, is let dashlet_b.get.html.ftl post something to dashlet_a.post.html.ftl. Hence you are submitting value(s) from b to a.
The next step is to refresh dashlet_a, one way is to do a full page refresh, but that's not nice.
Whats better is the following:
In dashlet_a.post.html.ftl you just set through YUI/JQuery the value of the field which is defined in dashlet_a.get.html.ftl.
Take a look how the default configurable dashlet do it, like the webview. If you put something in the config, the value directly is shown.