Access javascript data from Java

Hi guys,
I’m very new to maven, vaadin and java applications in general, so I hoped you could help me with this as I’m not sure what’s the best way to go about it.
Basically I have a maven project (java 7) which, using javascript, creates a popup window with a form inside, allows you to upload a file, display its content in a textarea and send it (the content of the file as a string) to the server via an ajax request. That was the easy part.
What I want to do now is to access that data sent through ajax (the string containing the data of the uploaded file) in Java because I need to run it through some validation.
I had a good look around, including the book of vaadin, and the net in general and considering that I have never done this before, it seems that one way could be to have a connector, but it looks a little too complicated and also it appears - from what I understand from the book of vaadin https://vaadin.com/docs/-/part/framework/gwt/gwt-overview.html - that I won’t be able to implement that in my project given the structure I have - which is different from what’s in there.
So, my question to you guys is, given the project I have (just a normal maven project) what would be the easiest way for me to access this data from Java?
Here is some code from the project, to put things into context:

import javax.servlet.annotation.WebServlet;
import com.vaadin.annotations.Theme;
import com.vaadin.annotations.VaadinServletConfiguration;
import com.vaadin.annotations.Widgetset;
import com.vaadin.server.VaadinRequest;
import com.vaadin.server.VaadinServlet;
import com.vaadin.ui.Button;
import com.vaadin.ui.Button.ClickEvent;
import com.vaadin.ui.JavaScript;
import com.vaadin.ui.Label;
import com.vaadin.ui.UI;
import com.vaadin.ui.VerticalLayout;
import com.vaadin.client.ui.*;

@Theme("mytheme")
@Widgetset("my.vaadin.apptest.MyAppWidgetset")
@com.vaadin.annotations.JavaScript({"https://ajax.googleapis.com/ajax/libs/jquery/1.12.2/jquery.min.js"

})
public class MyUI extends UI {
    @Override
    protected void init(VaadinRequest vaadinRequest) {
        final VerticalLayout layout = new VerticalLayout();
        layout.addStyleName("myLayout");//add class to main div        
        Label label = new Label("Hello Vaadin user. Use this application to upload files.");
        ...
        //HERE IS THE JAVASCRIPT CREATING AND INSTANTIATING THE POPUP AND THE AJAX CALL
        //CREATING POPUP
        JavaScript.getCurrent().execute(""
        +"var $HTMLpopup = $('<div class=\"popupContainer\">"
            +"<span class=\"cancelBtn big\"></span>"
            +"<div class=\"wrapper\">"
                +"<form action=\"\" id=\"fileForm\">"
                    +"<div class=\"mask\">"
                        +"<input type=\"file\" title=\" \"name=\"uploadFile\" class=\"uploadFile\" accept=\".mol,.sdf\">/*filters files to upload*/"
                        +"<span class=\"pseudoBtn\">Browse</span>"
                        +"<input type=\"text\" name=\"displayFile\" class=\"displayFile\" placeholder=\"no file loaded\">" 
                        +"<span class=\"cancelBtn small\"></span>"
                    +"</div>"
                    +"<textarea class=\"fileResult\"></textarea>"
                    +"<button type=\"submit\" class=\"submitBtn\">Upload</button>"
                    +"<div class=\"clear\"></div>"
                +"</form>"
            +"</div>"
        +"</div>');"
        //INSTANTIATING THE POPUP
        +"$('.popupTriggerBtn').click(function(){"
            +"/*console.log('button clicked!');*/"
            +"var $body = $('body');"
            +"$HTMLpopup.appendTo($body);"
        +"});"
        //HERE IS THE AJAX BIT
        +"var $submitBtn = $HTMLpopup.find('.submitBtn');"
        +"$submitBtn.click(function(e){"
            +"e.preventDefault();/*prevent submission*/"                    
            +"if(isFileUploadEmpty()){/*IF EMPTY*/"
                +"/*alert('submit clicked');*/"
                +"removeError();"
                +"showError('empty');"                        
            + "}"
            +"else{/*IF NOT EMPTY*/"
                +"/*AJAX OPS*/"
                +"if (window.XMLHttpRequest){/*XMLHttpRequest SUPPORT?*/"
                    +"console.log('XMLHttpRequest supported!');"
                    +"var postData = returnFileAsString();/*returns the file as a string*/;"                            
                    +"/*console.log('here is the file as a string ' + postData);*/"
                    +"$.ajax({"
                        +"type:'post',"
                        +"url:'http://localhost:8080/apptest/',"
                        +"data:postData,"
                        +"contentType: 'application/x-www-form-urlencoded',"
                        +"success: function(responseData, textStatus, jqXHR){"
                            +"/*alert('data saved');*/"
                            +"console.log('responseData is ' + responseData);"
                            +"console.log('text status is ' + textStatus);"
                            +"console.log('the data submitted is ' + postData );"
                        +"},"
                        +"error: function(jqXHR, textStatus, errorThrown){"
                            +"console.log(errorThrown);"
                            +"alert('an error has occurred!');"
                        +"}"    
                    +"});"
                +"}"
            +"}"
        +"});"        
    +"");
    //ADDING COMPONENTS
    layout.addComponents( label, button );
    layout.setMargin(true);
    layout.setSpacing(true);
    
    setContent(layout);
}

So, postData contains the string that I passed to the server and that I’d like to access in Java.
I came across this earlier on, which may or may not be another way to deal with it http://stackoverflow.com/questions/13861103/vaadin-with-ajax#13883449. What do you guys think?
Any help would be much appreciated, thanks

Hi,

The Vaadin way would be to use Vaadin components, like the file upload to handle file uploading and e.g. text area to show the content. See
http://demo.vaadin.com/sampler/#ui
for some demos of components. This will require an extra server roundtrip to show the file contents. Another way is to make custom component for this, but that was not an option you said. Custom components can be written in pure Javascript, so that might be an option
https://vaadin.com/docs/-/part/framework/gwt/gwt-javascript.html
. This way the clien-server communication infrastructure Vaadin provides can be utilised.

You could also add an extra Java (e.g. REST but non-Vaadin) service for handling the communication from your popup. There are several JSON librarys available, e.g. Jackson
https://github.com/FasterXML/jackson
.

Hi thanks. Let me explain a little better. Basically the way I have to do it to start with, is to use JS components as opposed to java components (eventually I will refactor it and replace js with java, but for now not an option), so for now the form, popup etc is in javascript.
My task is to be able to access the data sent via ajax from java because I need to run some validation. The way I was looking at was by using a connector to make sure that the said data (in my case it’s the string that is passed through ajax to the server, postData) can be accessed by the java part of my application, so yes this https://vaadin.com/docs/-/part/framework/gwt/gwt-javascript.html would be the way I thought I could go about it.
What I meant when I said “that’s this https://vaadin.com/docs/-/part/framework/gwt/gwt-overview.html wasn’t possible” was that, since in that link it says that I would have to have a different project structure from the one I have now, I thought, well that’s not it. But I was told that even with an ordinary maven project - which is what I have - it’s possible.
So, the first thing i’ve done was to remove all the above js that used to sit inside the .java file and moved it to an external js file, script.js, so that things are a little tidier. Now I will add a connector (to start with I will add it to script.js as I’ve never done it before so I just want to make sure it works) and in this connector I will pretty much do what the link says and we take it from there. I will post back when I have some more code.
thanks

Right, as I look more into this I get more confused. I’ve read posts, tutorials etc but none of them is clear enough for me to know exactly what I need to do - sorry, please bear with me as this is my first project in spring.
Let’s start from what I have first, again becuase I’ve updated my code quite a bit and summarize my needs again, I guess that will dictate the way I’ll want to go.
So far I have 2 java classes:
MyUI.java and FileUploader.java.
I also have some javascript that creates a popup and, through ajax, sends some information (string) to the server.
So, MyUI.java creates a button, then an object of type FileUploader wich is used to call a method inside the FileUploader class which then calls the js function in the script.js. Let’s have a look.
Class MyUI.java:

package my.vaadin.apptest; import com.vaadin.ui.AbstractJavaScriptComponent; import elemental.json.JsonObject; import javax.servlet.annotation.WebServlet; import com.vaadin.annotations.Theme; import com.vaadin.annotations.VaadinServletConfiguration; import com.vaadin.annotations.Widgetset; import com.vaadin.server.VaadinRequest; import com.vaadin.server.VaadinServlet; import com.vaadin.ui.Button; import com.vaadin.ui.Button.ClickEvent; import com.vaadin.ui.JavaScript; import com.vaadin.ui.Label; import com.vaadin.ui.UI; import com.vaadin.ui.VerticalLayout; import com.vaadin.client.ui.*; @Theme("mytheme") @Widgetset("my.vaadin.apptest.MyAppWidgetset") public class MyUI extends UI { @Override protected void init(VaadinRequest vaadinRequest) { final VerticalLayout layout = new VerticalLayout(); layout.addStyleName("myLayout");//add class to main div Label label = new Label("Hello Vaadin user. Use this application to upload files."); final FileUploader fileUploader = new FileUploader();//has to be final apparently final Button button = new Button("Open popup"); button.addClickListener(new Button.ClickListener(){ @Override public void buttonClick(ClickEvent event){ fileUploader.callScript(); } }); button.addStyleName("popupTriggerBtn");//add class to button layout.addComponents( label, button ); layout.setMargin(true); layout.setSpacing(true); setContent(layout); } @WebServlet(urlPatterns = "/*", name = "MyUIServlet", asyncSupported = true) @VaadinServletConfiguration(ui = MyUI.class, productionMode = false) public static class MyUIServlet extends VaadinServlet { } } Class FileUploader.java, just a method that calls the js function:

[code]
package my.vaadin.apptest;
import com.vaadin.annotations.*;
import com.vaadin.ui.AbstractJavaScriptComponent;
import com.vaadin.ui.JavaScript;
import elemental.json.JsonObject;
@com.vaadin.annotations.JavaScript({“https://ajax.googleapis.com/ajax/libs/jquery/1.12.2/jquery.min.js”, “script.js”
})

public class FileUploader extends AbstractJavaScriptComponent {
public void callScript(){//as usual, it needs a method!!
JavaScript.getCurrent().execute(“”
+“jsInit();”
+“”);

}    

}
[/code]So, from the server side,I need two things:
-know whether the ajax request was successful
-and if so, know the data that was sent through the ajax request and print it to the eclipse console
So, the way I’d like to go about this is to use a connector, something like here https://vaadin.com/docs/-/part/framework/gwt/gwt-javascript.html
So, what I think I need:
-There seems to be something called shared state which I need to implement: that means, presumably, creating another java class, FileUploaderState.java:

public class FileUploaderState extends JavaScriptComponentState { public String value; } This new class will sit with the other two presumably.
That done, in my FileUploader.java I can write:

@Override public FileUploaderState getState() { return (FileUploaderState) super.getState(); } After this, from the client side I need to
-create the connector: in my case

window.my_vaadin_apptest_FileUploader = function(){}; Is it correct so far?
What next?
thanks

Sorry for the delayed reply. It seems that you are on the right track. The recommended way to load you JS component is by the annotation “@JavaScript({“mylibrary.js”, “mycomponent-connector.js”})” on the FileUploader class where the arguments are the js files you use (see the link in my previous reply). After this you should be able to add on state change listeners in the client connector and also add repc calls from the client to the server and vice-versa.

Not a problem for the delay : - ), but I have to admit that my code has changed since last post.
Also, there are some constraints applied to my code, which perhaps goes against the “way-it-shoud-be-done”, and I fully appreciate that, but, hey, what can I do : -)? For instance, I’m not supposed to use the shared state, but an RPC call to pass the file string as a variable (which is sent to the server via ajax) from the js to the java side, and that really is all. The reason for that is that in the future I will use more and more RPC calls and I have to get used to them.

Happy to use the annotation, although I have to admit that I’ve seen this

JavaScript.getCurrent().execute("" done in many places.
Here is an update, just to put things into context:
-script.js, as above, contains all the code to get a popup + the form and the ajax call
-MyUI.java is still the same
-FileUploader.java largely the same with the addition of a constructor where Iuse registerRpc (sorry it still calls the javascript the old way, I haven’t amended it as yet).

package my.vaadin.apptest;
import com.vaadin.ui.AbstractJavaScriptComponent;
import com.vaadin.ui.JavaScript;
@com.vaadin.annotations.JavaScript({"https://ajax.googleapis.com/ajax/libs/jquery/1.12.2/jquery.min.js", "script.js"
})
/*THIS IS MY SERVER-SIDE COMPONENT */
public class FileUploader extends AbstractJavaScriptComponent {
    private static final long serialVersionUID = 2972063226748602140L;//must create it, otherwise it will create its own version
    //constructor
    public FileUploader(){
        registerRpc(new FileUploaderServerRpc() {
            @Override
            public void getFileData(String fileData) {

            }
        });
    }
    public void callScript(){//as usual, it needs a method!!
        JavaScript.getCurrent().execute(""
                +"jsInit();"
            +"");
    }//end of callScript()
    @Override
    public FileUploaderState getState() {
        return (FileUploaderState) super.getState();
    }
    public void setValue(String value) {
        getState().value = value;
    }
    public String getValue() {
        return getState().value;
    }
}

I’ve also added a FileUploaderServerRpc interface extending ServerRpc. In terms of RPC calls, I think I only need a call to send data from the clientside to the server side and not viceversa, unless you think I do of course, here is the code:

package my.vaadin.apptest; import com.vaadin.shared.communication.ServerRpc; public interface FileUploaderServerRpc extends ServerRpc { public void getFileData(String fileData);//abstract method with no body and must return void } So, in terms of classes and interfaces, is that it or do I need anything else? Sorry but I’m still struggling understanding the structure of the application as the vaadin tutorial are not very clear