The project managers at JAMK University of Applied Sciences wanted to investigate the possibility of other ways of accessing the data collected by Mango. The Spring framework consists of several well-defined modules built on top of the core container. Fortunately, with the arrival of the latest version of Mango (1.7.0), a very simple mobile WatchList has appeared in the program.
It is a very simplified version of the original WatchList page and was written with mobile devices in mind. However, it lacks many of the functionalities that the project managers at JAMK University of Applied Sciences needed, and therefore there was a need for someone to implement these requirements. The task of the author of this thesis was to find out how Mango works under the covers, to document it and, if possible, to make some minor changes to the system.
For example, an image of a thermometer can show the operator the temperature of the room in which one of the sensors is located. Instructions can be found on the Mango homepage. http://mango.serotoninsoftware.com/download.jsp), solutions to common installation problems are in the forum. http://mango.serotoninsoftware.com/forum).
Compilation
The absolute path of the directory (relative to Tomcat's . webapps directory) where the compiled Mango will be placed. Download axis-ant.jar (for example from the apache.org website or from your Eclipse distribution) and place it in $MANGO_HOME/lib. This is just a test file, which unfortunately didn't compile and fixing it would take a lot of time.
After making all these changes, issuing an ant and ant reload command should run smoothly.
Software components used
According to Mango's author, the reason for using such an outdated version is that updating to a newer one would be a difficult and tedious task. Additionally, newer versions of Dojo are not on par with the features of this older version, according to one user's insightful comment (Dojo Update 2009).
The MVC architecture
Request processing in Spring MVC
ModelAndView object consists of two other objects: a Map instance with name-value pairs containing the model data and a logical name of a display component. Like handler assignments, one can also find several view resolvers, each with a different strategy to convert a logical view name into a real one. This resolver does nothing but glue together the prefix property, the logical view name, and the suffix property.
The DispatcherServlet passes the model data to the view implementation (usually a JSP file) and the view layer will render a page to the user using the given data.
Handler mappings
Controllers
Although AbstractCommandController is not used in Mango, it is a fairly important type of controller, because CommandControllers (such as . AbstractCommandController and BaseCommandController) automatically bind request parameters to a so-called command object. But before the handle() method is called, any parameters found in the request object are matched against properties in the command object. If a match is found, then the value of the parameter is bound to the object's property.
20 (ie binds the input variables to a command object) and either returns a success page or redisplays the form (if an error occurred). CommandControllers and FormControllers all have a Command object associated with them, whose properties are automatically bound, in a two-way fashion. When a form is submitted (meaning a POST request) or a GET request arrives with additional parameters, the properties of the command object are populated with the values of the corresponding request parameters, and then the command object is processed by the controller.
When rendering a form, a similar binding occurs, only in the other way: the values of the form's input fields are filled by the values of the command object, so when a form has to be rendered due to errors, the fields will be filled again with their previous values entered by the user. If there happens to be an input field with the name "user.firstName" and with the value "Adam", then the org.springframework.validation.DataBinder class translates it into a getUser().setFirstName("Adam") method call on the command object. Additional information (for example, a list of all the countries in the world, ready to be fed into an HTML selection box) for the form to be displayed can be provided by overriding the referenceData() method, as in
On success, it is redirected to the page defined by the successView property in the context configuration file (in Mango's case, this is the war/WEB-.INF/springDispatcher-servlet.xml file). The form to be displayed is defined by the formView property in the same XML file. The command object can also be declaratively set in the same XML using the Name command and the Class command.
Thus, LoginController (which extends SimpleFormController) first displays that JSP page which has the logical name login defined by the formView.
Views
After a successful submission, it displays a JSP page that is looked up by decoding the logical name specified by the successUrl property. To avoid the dreaded double-submit error (when the user reloads the form a second time), it's best to use the Redirect After Submission pattern. It's basically a SimpleFormController, the only difference is that the view name is not set through the springDispatcher servlet.xml file, but by a query string passed to the getSuccessRedirectView() method.
The InternalResourceViewResolver then “simply sends the request to the JSP to perform the actual rendering” (Walls 2008, 536). The model data (which is part of the ModelAndView object) is passed to the JSP, in which the input fields are bound to the properties of the command object, respectively.
Ajax with DWR
The DWRServlet, configured in web.xml, is responsible for creating the JavaScript versions of the original Java classes. Each file under the /dwr path is served by the DWRServlet, so if a request arrives at the server with the path /dwr/interface/MiscDwr.js, the servlet dynamically creates the MiscDwr.js file, which contains all the exposed methods of the MiscDwr Java class . MiscDwr.doLongPoll(mango.header.longPoll.pollCB) JavaScript method calls are routed to the original MiscDwr Java object.
The result of the call is a Map
Analysis of a request
DispatcherServlet reads the file war/WEB-INF/springDispatcher-servlet.xml and searches for handler mappings. This configuration property is specified in the springDispatcher-servlet.xml file, and in this case its value is publicView. The GetViewName() call returns the value of the publicView configuration property set in the springDispatcher-servlet.xml file.
The DispatcherServlet consults the only configured view resolver (the . InternalResourceViewResolver object) and creates the path /WEB-INF/jsp/publicView.jsp. In the example used now, the one and only ViewComponent that is in the requested anonymous view is a virtual DataPoint that randomly generates numbers.
Tables visualized
Data access layer
A peculiarity of Mango is that in many cases Java objects are included in the database as they are, that is, without storing an object's attributes in specific columns of the database. Point values are represented by com.serotonin.mango.rt.dataImage.PointValueTime objects and stored in the pointValues and pointValueAnnotations tables using a com.serotonin.mango.db.dao.PointValueDao object. To illustrate the above mechanism, here is an interactive session with the built-in Derby database.
Clicking on the image takes the user to webcam_live_feed.htm for the corresponding image. This webcam_live_feed.htm contains nothing but the code listed in the "Webcam live feed code" box when you edit the DataSource (see Figure 10). By modifying the page that renders this "webcam live feed code", one can allow users to upload arbitrary images, effectively changing the URL attribute of the DataPoint.
For this source code to work, a line must be added to the controller that renders it. Now the rendered JSP will contain the pointId of the DataPoint whose URL will be changed. 38 The form is submitted to the URL fileUpload.htm (see example 22) which is handled by the ImageUploaderController.
It makes a MultipartHttpServletRequest (that is, uploads a file), saves the file to the directory specified by the uploadDirectory variable, then changes the DataPoint URL to point to this newly uploaded image, and finally renders. When the author of Manga decided to store data by directly serializing Java objects into a BLOB column, he may have thought that this way would use different types. Fortunately, Mango offers - in addition to Java serialization - the ability to export data in JSON format.
A possible solution could be to write a controller that can export arbitrary Java objects to JSON format on the fly. Aside from the previously mentioned hurdle, Mango has proven to be a highly configurable system. After spending the time it deserves to be fully explored, one can customize the software to his or her very own needs.
The task
Implementation
Although this solution may have made his life easier, it definitely does not make the task of using data collected by an external, possibly non-Java, application any easier.