So far, I hadn´t understood that interfaces can be used as data types in java. I discovered it while learning depency injection.
An interface in java is a valid referenca data type. If you want to use an interface as reference variabile, make sure your class implements it!
Here is the interface for any liquid container:
public interface LiquidContainer {
void fill(int ml);
void empty();
void wash();
void drink();
}
The class Glass implements the developed interfaced:
import static java.lang.System.out;
public class Glass implements LiquidContainer{
@Override
public void fill(int ml) {
out.println("Glass filled with "+ml+"!");
}
@Override
public void empty() {
out.println("Your glass is now empty.");
}
@Override
public void wash() {
out.println("the glass has been washed.");
}
@Override
public void drink() {
out.println("you have drunk from a Glass.");
}
}
Mug is another class implementing the interface:
import static java.lang.System.out;
public class Mug implements LiquidContainer {
@Override
public void fill(int ml) {
out.println("Mug filled with "+ml+"!");
}
@Override
public void empty() {
out.println("Your Mug is now empty");
}
@Override
public void wash() {
out.println("Your mug has been washed.");
}
@Override
public void drink() {
out.println("You have drunk from a mug.");
}
}
Then we can define two classes: Superman and Batman mugs extending Mug, without specifying what they implement:
import static java.lang.System.out;
public class SupermanMug extends Mug{
LiquidContainer liquidContainer;
@Override
public void fill(int ml) {
out.println("Superman Mug filled with "+ml+"!");
}
@Override
public void empty() {
out.println("superman Mug is now empty.");
}
@Override
public void wash() {
out.println("Superman Mug has been washed.");
}
@Override
public void drink() {
out.println("you have drunk from a Superman Mug!");
}
}
And finally a Breakfast class:
public class Breakfast {
LiquidContainer lc;
static void drinkFromObject(LiquidContainer lc){
lc.drink();
}
public static void main(String args[]){
SupermanMug sm=new SupermanMug();
BatmanMug bm=new BatmanMug();
Glass glass=new Glass();
Mug mug=new Mug();
drinkFromObject(glass);
drinkFromObject(mug);
drinkFromObject(sm);
drinkFromObject(bm);
}
}
The “drinkFromObject” methods work for any liquid container objects, no matter what the class inheritance is, because it takes an interface (LiquidContainer) as reference data type parameter. The resulte is:
you have drunk from a Glass.
You have drunk from a mug.
you have drunk from a Superman Mug!
you have drunk from a Batman Mug!
Subtle, isn´t it?
This tutorial tells you how to make a custom jquery paginator in your liferay portlet.
This example is about photoalbums, but the page can contain whatever in the <div “image”>
The jquery file is specified in header-portlet tag in the liferay-portlet.xml :
<header-portlet-javascript>/js/jquery-1.8.3.js </header-portlet-javascript>
or in the jsp directly (as you can see below)
The code in the ViewPhotos.jsp is:
<script type="text/javascript" src="${renderRequest.contextPath}/js/jquery-1.8.3.js"></script>
images = ImageLocalServiceUtil.getAllImagesbyAlbumId(albumId);
String albumName= (String) request.getAttribute("albumName");
%>
<div id="<portlet:namespace/><br />"><span style="color: blue;">Photogallery DEMO Version 0.X </span>
<script type="text/javascript">
var $jq = jQuery.noConflict(true);
$(document).ready(function(){
$('#content').Pagination();
}); </script>
<div id="wrapper-content">
<h2>Photo album Paginator</h2>
<div class="pagination">
<ul>
<li><a href="#" id="prev"><button>Previous</button></a>
<li><a href="#" id="next"><button>Next</button></a></li>
</ul>
</div>
<div id="content">
No images found.
<div class="image">
<img class="center" src="/<%=albumName=>/<%=path%>" alt="" width="40%" />
Image:
</div>
</div> <!-- content -->
</div> <!-- wrapper-content -->
</div> <!-- portletnamespace -->
Remember to wrap it all with : <strong><div id=”<portlet:namespace/>”></strong>
In my demo the “albumName” folder specified in the image attribute src is set in the xml file:
/home/laura/project/liferay-portal-6.1.0-ce-ga1/tomcat-7.0.23/conf/Catalina/localhost/albumName.xml
The content of the xml file is something the following:
<?xml version=”1.0″ encoding=”UTF-8″?>
<Context path=”/albumName” docBase=”/home/laura/albums/albumName” reloadable=”true”/>
“albumName” might be something like “birthday_Party_Laura_2013”
the jquery plugin (that I’ve placed in the main.js file) is the following:
(function($) {
// Attach a new method to jQuery
$.fn.extend({
// PluginName - Pagination
Pagination : function(options) {
console.log("plugin");
// Set the default values, use comma to separate the settings,
// example:
var defaults = {
fadeSpeed : 100
};
// options can be extended when the plugin is invoked
var options = $.extend(defaults, options);
// Creating a reference to the object
var objContent = $(this);
// child div of the "content" one
var imageDivList = new Array();
var lastPage = 1;
var paginatedPages;
// initialization function
init = function() { // for each div
$('.image').each(function() {
imageDivList.push(this);
});
// objContent.children().hide();
$('.image').hide();
console.log($(imageDivList).length);
// show first page (lastPage=1)
showPage(lastPage);
// draw controls
showPagination($(imageDivList).length);
}; // end init function
// show page function
showPage = function(page) {
i = page - 1;
if (imageDivList[i]) {
console.log(i);
// hiding old page, display new one
$(imageDivList[lastPage]).fadeOut(options.fadeSpeed);
lastPage = i;
$(imageDivList[lastPage]).fadeIn(options.fadeSpeed);
}
};
// show pagination function (draw switching numbers)
showPagination = function(numPages) {
var pagins = '';
for ( var i = 1; i <= numPages; i++) {
pagins += '<li><a href="#" onclick="showPage(' + i
+ '); return false;"><button>' + i + '</button></a></li>';
} //
// after the firt element, with id="prev", append the list with
// the page number links
$('.pagination li:first-child').after(pagins);
};
// perform initialization
init();
// and binding 2 events - on clicking to Prev
$('.pagination #prev').click(function() {
showPage(lastPage);
});
// and Next
$('.pagination #next').click(function() {
showPage(lastPage + 2);
});
}
});
// pass jQuery to the function,
})(jQuery);
The css for the paginator buttons, that I have specified in the main.css file is:
ul, li {
list-style-type: none;
margin-left:40px;
}
.pagination {
clear: both;
padding:0;
/* width:250px; */
}
.pagination li {
float:left;
margin-left: 0 auto;
}
Lately I’ve purchased a virtual private server hosting (VPS) to deploy my liferay portal. I’ve been assigned a different port number… and I needed to understand the steps to make a ssh connection.
After some hours surfing the web and making experiment, I could make it. So now I’m posting this litte tutorial, for those that want to work by the linux shell B)
Firt of all you need to generate a public and private keys with a cryptographic algorithm:
ssh-keygen -t dsa
I’ve chosen the DSA (digital signature algorithm), but you can choose RSA, etc.
After entering the ssh-keygen command on the shell, under the folder ~/.ssh/ you will find the following files: id_dsa, id_dsa.pub, authorized_keys and known_hosts files.
Make sure that you have all the permissions on the folder and that you’re the only one that can read and write the authorized_keys file:
sudo chmod 600 ~/.ssh/authorized_keys
The system will add your host to the lists of the “known hosts”, when you try to login to the remote server for the first time.
Once your keys have been generated, you need to copy the public key in the “authorized_keys” file:
cp ~/.ssh/id_dsa.pub ~/.ssh/authorized_keys
Then you need to send your public key to the server. Let’s assume that our ssh port number is 12345:
scp -P 12345 ~/.ssh/id_dsa.pub username@remotehost:~/.ssh/authorized_keys
The shell will ask you a password:
username@remotehost's password: user's passowrd
Now that you’ve sent your public key to the server you can connect:
ssh -p 12345 username@remotehost
After this command you’ll be asked your passphrase password (that you set when you generate the public key),
so you can be authenticated with your private key.
That’s it!
This is a short but useful tutorial. I’ve googled for 3 hours before understanding how to access a tomcat folder location.
The following example should help you.
If you want to render images from a server location in Tomcat 7, you need to create a your-web-app/META-INF/context.xml file and specify a location:
<?xml version="1.0"?> <Context path="/images" docBase="/home/laura/gallery" reloadable="true"/>
Then in your .jsp file you will simply set the img tag like the following:
<img src="/images/picture.jpg" width="30%" />
Alternatively you can also set the context xml file in the /tomcat-7.0.23/conf/Catalina/localhost folder, by giving it the same name of the webapp, (that is yourWebApp.xml).
I prefer to place the file in the meta-inf folder of the project so I can control il in the IDE enviroment.
I’m doing this to make my development in local host, but in the future i will need it to access an externa image folder for a database.
Discussions are welcome
Hello, guys!
I’ve been struggling for a couple of days trying to make my seach container pagination works.
When you clicking on the next page and you need to use a form parameter value submitted to get the rows, you need to store it in the portlet preferences, otherwise you lose it in the page “refresh”.
I haven’t found a solution on the web so far, so I’m posting my code snippets… that WORKS lol:
but I’m using portlet preferences … check it out!
[b]action method in the controller:[/b]
public void searchVolume(ActionRequest request, ActionResponse response)
throws IOException, PortletException, PortalException,
SystemException, NoSuchVolumeException {
String volumeIdentifier = request.getParameter("volumeId");
long volumeId = (long) Integer.parseInt(volumeIdentifier);
long idVol = 0;
boolean found = false;
boolean emptyList = false;
List volume = new ArrayList();
volume = VolumeLocalServiceUtil.getAllVolumes();
List caseArchive = new ArrayList();
caseArchive = CaseArchiveLocalServiceUtil
.getAllCasesbyVolumeId(volumeId);
if (caseArchive.size() == 0) {
emptyList = true;
}
for (Volume itemVolume : volume) {
if (itemVolume.getVolumeId() == volumeId)
found = true;
}
if (found && emptyList) {
SessionMessages.add(request, "no-cases-found");
} else if (found && !emptyList) {
Volume vol = DBUtil.getVolumefromRequest(request);
idVol = vol.getVolumeId();
if (idVol == 1) {
System.out.println("Volume id iniziale: " + volumeId);
SessionErrors.add(request, "error-volume");
} else if (SearchValidator.volumeNotNull(idVol) && !(idVol == 1))
{
System.out.println("Volume id action : " + vol.getVolumeId());
response.setRenderParameter("volId", volumeIdentifier);
System.out.println("search volume clicked");
PortletPreferences prefs = request.getPreferences();
String volumeIdent = request.getParameter("volumeId");
if (volumeIdent != null) {
prefs.setValue("volumeIdPref", volumeIdent);
prefs.store();
}
VolumeLocalServiceUtil.clearService();
SessionMessages.add(request, "search-volume");
}
} else
SessionErrors.add(request, "error-volume");
response.setRenderParameter("jspPage", viewDatabaseJSP);
}
[b]JSP page[/b]:
CaseArchiveLocalServiceUtil.clearCache();
VolumeLocalServiceUtil.clearCache();
//RoiLocalServiceUtil.clearCache();
//ImageDBLocalServiceUtil.clearCache();
//DicomLocalServiceUtil.clearCache();
ImageTypeLocalServiceUtil.clearCache();
List volumes = VolumeLocalServiceUtil.getAllVolumes();
List cases = CaseArchiveLocalServiceUtil.getAllCases();
Long volumeIdentifier = 1L;
Collections.sort(volumes, new Comparator() {
public int compare(Volume o1, Volume o2) {
Volume p1 = (Volume) o1;
Volume p2 = (Volume) o2;
return p1.getVolumeName().compareToIgnoreCase(
p2.getVolumeName());
}
});
PortletURL portletURL = renderResponse.createRenderURL();
portletURL.setParameter("jspPage", "/html/admin/viewDatabase.jsp");
int selected = 0;
String volSel = null;
PortletPreferences prefs = renderRequest.getPreferences();
String volumeId = (String) prefs.getValue("volumeIdPref", "1");
%>
method="post">
1) {
volumeIdentifier = (long) Integer.parseInt(volumeId);
}
List tempResults = DBUtil
.getAllCasesOk(volumeIdentifier);
results = ListUtil.subList(tempResults,
searchContainer.getStart(),
searchContainer.getEnd());
total = tempResults.size();
pageContext.setAttribute("results", results);
pageContext.setAttribute("total", total);
portletURL.setParameter("cur",
searchContainer.getCurParam());
System.out.println("Cur PRINT:" + searchContainer.getCur());
%>
href="" name='view Case' />
<a href="<%=cancelURL%>">← Back to Menu</a>
In the example above, volumeId is the form action parameter (passed by the select option), while volumeIdPref is the portlet preferences parameter, which keeps the value while consulting the pages.
In the action method, that is invoked when submitting the form value, i’ve set a response parameter called volId which is used in the jsp to set the variable value when invoking the search-container result page “1″. The render parameter is null when visiting the other pages, but it can be retrieved by the portlet preferences value.
I hope this helps. Let me know if you have questions or suggestions.
Regards
Laura
To make a Liferay Service Builder with external database there are some rules to follow. This post will help you to get straight to the point.
Keep in mind that:
- You can’t deploy more than one portlet mapping column with the same entity name, otherwise you get a hot-Deployment error.
- the names of the portlet name, namespace and database must be distinct (ex. portlet=”imageview“, namespace=”mammography“, database=”dicomviewer“).
- when you add external jar, you must add them in the Tomcat/lib/ext
so liferay can find them in the global classpath.
The steps to make the service builder with the external database mapping are:
- make the service.xml file in the /docroot/WEB-INF/
- launch the build-service ant command
- add the ext-spring.xml file in the /docroot/WEB-INF/src/META-INF/ folder
- deploy the portlet.
The example below might be helpful.
—service.xml ————
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE service-builder PUBLIC "-//Liferay//DTD Service Builder 6.0.0//EN" "http://www.liferay.com/dtd/liferay-service-builder_6_0_0.dtd">
<service-builder package-path="it.dicom">
<author>Laura Liparulo</author>
<namespace>mammography</namespace>
<entity name="Volume" local-service="true" remote-service="true" table="volume"
data-source="mammographyDataSource" session-factory="mammographySessionFactory" tx-manager="mammographyTransactionManager">
<!-- PK Fields -->
<column name="volumeId" type="long" primary="true" />
<!-- Other Fields -->
<column name="volumeName" type="String" />
<!-- Relationships -->
<column name="caseVolume" type="Collection" entity="CaseArchive"
mapping-key="volumeId" />
<order by="asc">
<order-column name="volumeName" />
</order>
<finder name="Volume_Name" return-type="Collection">
<finder-column name="volumeName" />
</finder>
</entity>
<entity name="CaseArchive" local-service="true" remote-service="true" table="case_archive";
data-source="mammographyDataSource" session-factory="mammographySessionFactory" tx-manager="mammographyTransactionManager">
<!-- PK Fields -->
<column name="caseId" type="long" primary="true" />
<!-- Other Fields -->
<column name="caseName" type="String" />
<column name="volumeId" type="long" />
<column name="notes" type="String" />
<!-- Relationships -->
<column name="image_Case" type="Collection" entity="Image"
mapping-key="caseId" />
<order by="asc">
<order-column name="caseName" />
</order>
<finder name="Case_Name" return-type="Collection">
<finder-column name="caseName" />
</finder>
</entity>
</service-builder>
—ext-spring.xml ————
<?xml version="1.0"?>
<!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN"
"http://www.springframework.org/dtd/spring-beans.dtd">
<beans>
<bean
class="
org.springframework.beans.factory.config.PropertyPlaceholderConfigurer">
</bean>
<bean id="mammographyDataSourceTarget"
class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName" value="com.mysql.jdbc.Driver" />
<property name="url" value="jdbc:mysql://localhost:3306/dicomviewer" />
<property name="username" value="root" />
<property name="password" value="tigertailz" />
</bean>
<bean id="mammographyDataSource"
class="org.springframework.jdbc.datasource.LazyConnectionDataSourceProxy">
<property name="targetDataSource">
<ref bean="mammographyDataSourceTarget" />
</property>
</bean>
<bean id="mammographyHibernateSessionFactory"
class="com.liferay.portal.spring.hibernate.PortletHibernateConfiguration">
<property name="dataSource">
<ref bean="mammographyDataSource" />
</property>
</bean>
<bean id="mammographySessionFactory">
<property name="sessionFactoryImplementor">
<ref bean="mammographyHibernateSessionFactory" />
</property>
</bean>
<bean id="mammographyTransactionManager"
class="org.springframework.orm.hibernate3.HibernateTransactionManager">
<property name="dataSource">
<ref bean="mammographyDataSource" />
</property>
<property name="sessionFactory">
<ref bean="mammographyHibernateSessionFactory" />
</property>
</bean>
</beans>
Now you can make it fast as a shark!
To remove comments in the wordpress pages you have to comment you have to edit the file comments.php in the theme directory (the one you want to use).
You just need to add on the top of the file, as first line the following line:
<?php return false; ?>
That’s all.
Yeah, you have understood that this blog is powered by WordPress.
Surfing the web, I have found plugins and posts about removing items from the wordpress dashboard.
Loggin as administrator, i’ve tried a plugin called: “remove-posts-from-admin”, but that doesn’t remove the comments.
I’ve tried some code modifications suggested by other bloggers, so I’ve found a way to make it.
Nobody tells it straight. So here it is
. You have to modify a file in your theme folder:
/www/wp-content/themes/yourtheme/functions.php
To remove “posts” and “comments” simply add this code at the end of the file:
add_action( 'admin_menu', 'remove_links_menu' );
function remove_links_menu() {
remove_menu_page('index.php'); // Dashboard
// remove_menu_page('edit.php'); // Posts
// remove_menu_page('upload.php'); // Media
// remove_menu_page('link-manager.php'); // Links
// remove_menu_page('edit.php?post_type=page'); // Pages
remove_menu_page('edit-comments.php'); // Comments
// remove_menu_page('themes.php'); // Appearance
// remove_menu_page('plugins.php'); // Plugins
// remove_menu_page('users.php'); // Users
//remove_menu_page('tools.php'); // Tools
// remove_menu_page('options-general.php'); // Settings
}
?>
Another way is the following. This is a core modification and may cause incompatibility problems if you want to upgrade. Anyway it works:
You simply need to edit the file called menu.php in the wp-admin directory.
I’ve commented the “posts” and “comments” sections and moved Pages to the top (changed the number in the array, $menu[5] is now Posts) :
$menu[5] = array( __('Pages'), 'edit_pages', 'edit.php?post_type=page', '', 'menu-top menu-icon-page', 'menu-pages', 'div' );
$submenu['edit.php?post_type=page'][5] = array( __('All Pages'), 'edit_pages', 'edit.php?post_type=page' );
/* translators: add new page */
$submenu['edit.php?post_type=page'][10] = array( _x('Add New', 'page'), 'edit_pages', 'post-new.php?post_type=page' );
$i = 15;
foreach ( get_taxonomies( array(), 'objects' ) as $tax ) {
if ( ! $tax->show_ui || ! in_array('page', (array) $tax->object_type, true) )
continue;
$submenu['edit.php?post_type=page'][$i++] = array( esc_attr( $tax->labels->menu_name ), $tax->cap->manage_terms, 'edit-tags.php?taxonomy=' . $tax->name . '&post_type=page' );
}
unset($tax);
$awaiting_mod = wp_count_comments();
$awaiting_mod = $awaiting_mod->moderated;
To remove a section you must comment the piece of code, adding /* at the beginning and */ at the end. Like this:
POSTS:
/*$menu[5] = array( __('Posts'), 'edit_posts', 'edit.php', '', 'open-if-no-js menu-top menu-icon-post', 'menu-posts', 'div' );
$submenu['edit.php'][5] = array( __('All Posts'), 'edit_posts', 'edit.php' );
/* translators: add new post */ /*
$submenu['edit.php'][10] = array( _x('Add New', 'post'), 'edit_posts', 'post-new.php' );
$i = 15;
foreach ( get_taxonomies( array(), 'objects' ) as $tax ) {
if ( ! $tax->show_ui || ! in_array('post', (array) $tax->object_type, true) )
continue;
$submenu['edit.php'][$i++] = array( esc_attr( $tax->labels->menu_name ), $tax->cap->manage_terms, 'edit-tags.php?taxonomy=' . $tax->name );
}
unset($tax); */
COMMENTS:
/*$menu[25] = array( sprintf( __('Comments %s'), "" . number_format_i18n($awaiting_mod) . "" ), 'edit_posts', 'edit-comments.php', '', 'menu-top menu-icon-comments', 'menu-comments', 'div' );
unset($awaiting_mod);
$submenu[ 'edit-comments.php' ][0] = array( __('All Comments'), 'edit_posts', 'edit-comments.php' );
$_wp_last_object_menu = 25; // The index of the last top-level menu in the object menu group
*/
Easy, right?
Hi guys I’m posting you my Portlet method and edit.jsp.. it works fine
I’ve also included the upload progress bar
:kid::kid:
:kid:
[b]<%@ taglib uri="http://java.sun.com/portlet_2_0" prefix="portlet"%> <%@ taglib uri="http://liferay.com/tld/aui" prefix="aui"%> <%@ taglib uri="http://liferay.com/tld/ui" prefix="liferay-ui"%> <%@ page import="com.liferay.portal.kernel.util.ParamUtil"%> <%@ page import="com.liferay.portal.kernel.util.Validator"%> <%@ page import="javax.portlet.PortletPreferences"%> <%@ page import="com.liferay.util.PwdGenerator"%> <portlet:defineObjects /> <% String uploadProgressId = PwdGenerator.getPassword(PwdGenerator.KEY3, 4); PortletPreferences prefs = renderRequest.getPreferences(); %> <portlet:actionURL var="editCaseURL" name="uploadCase"> <portlet:param name="jspPage" value="/edit.jsp" /> </portlet:actionURL> <liferay-ui:success key="success" message=" YEAH. Case uploaded successfully!" /> <liferay-ui:error key="error" message="Sorry, an error prevented the upload. Please try again." /> <liferay-ui:upload-progress id="<%= uploadProgressId %>" message="uploading" redirect="<%= editCaseURL %>" /> <aui:form action="<%= editCaseURL %>" enctype="multipart/form-data" method="post" > <aui:input type="file" name="fileName" size="75"/> <input type="submit" value="<liferay-ui:message key="upload" />" onClick="<%= uploadProgressId %>.startProgress(); return true;"/> <!-- aui:button type="submit" value="Save" /--> </aui:form> <br /> <br /> <br /> <br /> <portlet:renderURL var="viewCaseURL"> <portlet:param name="jspPage" value="/view2.jsp" /> </portlet:renderURL> <aui:button onClick="<%=viewCaseURL%>" value="view Uploaded Case" />[/b]
this is the UPLOAD method:
[b] public void uploadCase(ActionRequest actionRequest,
ActionResponse actionRresponse) throws PortletException,
IOException {
String folder = getInitParameter("uploadFolder");
realPath = getPortletContext().getRealPath("/");
logger.info("RealPath" + realPath + " UploadFolder :" + folder);
try {
logger.info("Siamo nel try");
UploadPortletRequest uploadRequest = PortalUtil
.getUploadPortletRequest(actionRequest);
System.out.println("Size: "+uploadRequest.getSize("fileName"));
if (uploadRequest.getSize("fileName")==0) {
SessionErrors.add(actionRequest, "error");
}
String sourceFileName = uploadRequest.getFileName("fileName");
File file = uploadRequest.getFile("fileName");
logger.info("Nome file:" + uploadRequest.getFileName("fileName"));
File newFile = null;
newFile = new File(folder + sourceFileName);
logger.info("New file name: " + newFile.getName());
logger.info("New file path: " + newFile.getPath());
InputStream in = new BufferedInputStream(uploadRequest.getFileAsStream("fileName"));
FileInputStream fis = new FileInputStream(file);
FileOutputStream fos = new FileOutputStream(newFile);
byte[] bytes_ = FileUtil.getBytes(in);
int i = fis.read(bytes_);
while (i != -1) {
fos.write(bytes_, 0, i);
i = fis.read(bytes_);
}
fis.close();
fos.close();
Float size = (float) newFile.length();
System.out.println("file size bytes:" + size);
System.out.println("file size Mb:" + size / 1048576);
logger.info("File created: " + newFile.getName());
SessionMessages.add(actionRequest, "success");
} catch (FileNotFoundException e) {
System.out.println("File Not Found.");
e.printStackTrace();
SessionMessages.add(actionRequest, "error");
} catch (NullPointerException e) {
System.out.println("File Not Found");
e.printStackTrace();
SessionMessages.add(actionRequest, "error");
}
catch (IOException e1) {
System.out.println("Error Reading The File.");
SessionMessages.add(actionRequest, "error");
e1.printStackTrace();
}
}
[/b]
It works fine! the errors get properly notified when the file size exceeds 100 MB
I’m currently working on my Master degree thesis and I’m projecting a demo database about a Mammography archive. The purpose is providing an archive, whose clinical cases can be consulted on a portal page by a user interface.
I must create a database for a Liferay portal. Liferay is a very powerful opensouce CMS / web application framework written in Java that allows creating the database and the queries by an xml file.
Before developing the portlet I need to study the situation. I’m analyzing and evaluating the query formulations, as I will have to develop GUIs to consult the image (Echography) archive and upload new cases.
I’ve started with some sql scripts.
I’ve made a sql script to create and populate the Mammography database. Then I’ve made another script to add the archive zip file size of each clinical case and a stored procedure to update the volume table (grouping clinical cases of the same category) with the sum of the cases’ zip file size.
You can download the ER diagram clicking on the image above (powered by MySQLWorkbench!).
The script to create and populate the DB is:
/*Mammography demo database */
CREATE DATABASE `mammography`;
/* access database */
USE `mammography`;
CREATE TABLE scanner (
id_scanner INT(2) NOT NULL AUTO_INCREMENT PRIMARY KEY ,
scanner_type VARCHAR(100) NOT NULL
);
CREATE TABLE volume (
id_volume INT(10) NOT NULL AUTO_INCREMENT PRIMARY KEY,
volume_name VARCHAR(100) NOT NULL,
cases INT(10), /* filled by a query */
total_size VARCHAR(10), /*filled by a query calculating the Gb*/
id_scanner INT(2) NOT NULL,
bits INT(10) NOT NULL,
resolution VARCHAR(50) NOT NULL, /*es. 42 microon , might be calculated*/
overview TEXT,
FOREIGN KEY(id_scanner) REFERENCES scanner (id_scanner)
);
/* 1:N* - one volume - n cases*/
CREATE TABLE case_archive (
id_case INT(10) NOT NULL AUTO_INCREMENT PRIMARY KEY,
case_name VARCHAR(100) NOT NULL,
id_volume INT(10) NOT NULL REFERENCES volume(id_volume) ,
ics_version VARCHAR(50) NOT NULL,
date_case DATE NOT NULL,
age_patient INT(3) NOT NULL,
film VARCHAR(50) ,
film_type VARCHAR(50) ,
density INT(10) NOT NULL,
digitizer_dba INT(10) NOT NULL,
notes TEXT,
zip_folder_link TEXT NOT NULL,
FOREIGN KEY (id_volume) REFERENCES volume(id_volume)
);
/* 1 image type : N images*/
CREATE TABLE image_type (
id_image_type INT(2) NOT NULL AUTO_INCREMENT PRIMARY KEY,
image_type VARCHAR(100)
);
/* 1:N* - one case - n images*/
CREATE TABLE image (
id_image INT(10) NOT NULL AUTO_INCREMENT PRIMARY KEY,
id_case INT(10) NOT NULL,
image_name VARCHAR(150),
image_type INT(2) NOT NULL,
link TEXT NOT NULL,
bits_pixel INT(10) NOT NULL, /*might be null*/
resolution VARCHAR(50) NOT NULL,
left_cc_lines int(10) NOT NULL,
pixels_per_line INT(10) NOT NULL,
/* the following column might null in normal cases - demo:only 2 columns */
total_abnormality INT(10),
abnormality INT(2),
FOREIGN KEY (id_case) REFERENCES case_archive (id_case),
FOREIGN KEY(image_type) REFERENCES image_type (id_image_type)
);
/*————————————————————————————*/
/* 3 scanner types */
insert into scanner(scanner_type) values('DBA');
insert into scanner(scanner_type) values('HOWTECK');
insert into scanner(scanner_type) values('LUMISYS');
/* 2 Volumes, 2 Cases X Volume*/
insert into volume (volume_name, id_scanner, bits, resolution, overview) values ('normal_01', 1, 16,'42 microns', 'overview notes ');
insert into volume (volume_name, id_scanner, bits, resolution, overview) values ('cancer_01', 3, 12, '50 microns', 'overview notes');
/* Image type*/
insert into image_type(image_type) values('Left_cc 0');
insert into image_type(image_type) values('Right_cc 1');
insert into image_type(image_type) values(' Left_mcl 2');
insert into image_type(image_type) values(' Right_mcl 3');
/* 2 Cases*/
insert into case_archive (case_name, id_volume, ics_version, date_case, age_patient, density, digitizer_dba, notes, zip_folder_link) values ('A-0002-1', 1, 1.0,'2008-06-13', 63, 2, 21,'n/a','/home/laura/project/case/normal1_case0001.zip' );
insert into case_archive (case_name, id_volume, ics_version, date_case, age_patient, density, digitizer_dba, notes, zip_folder_link) values ('A-0002-1', 1, 1.0,'2007-04-23', 43, 3, 23,'n/a','/home/laura/project/case/normal1_case0002.zip' );
insert into case_archive (case_name, id_volume, ics_version, date_case, age_patient, density, digitizer_dba, notes, zip_folder_link) values ('A-0002-1', 2, 1.0,'2009-07-12', 56, 2, 20,'n/a','/home/laura/project/case/cancer1_case0001.zip' );
insert into case_archive (case_name, id_volume, ics_version, date_case, age_patient, density, digitizer_dba, notes, zip_folder_link) values ('A-0002-1', 2, 1.0,'2007-03-12', 48, 3, 19,'n/a','/home/laura/project/case/cancer1_case0002.zip' );
/* 2 images x case*/
insert into image(id_case, image_name, image_type, link, bits_pixel, resolution, left_cc_lines, pixels_per_line, total_abnormality, abnormality) values ( 1, 'A_0002_1.LEFT_CC.LJPEG',1,'/home/laura/Arbeitsfläche/Project/case/normal1_case0001/A_0002_1.LEFT_CC.LJPEG',16,42,4349, 1979, 234, 1);
insert into image(id_case, image_name, image_type, link, bits_pixel, resolution, left_cc_lines, pixels_per_line, total_abnormality, abnormality) values ( 1, 'A_0002_1.RIGHT_CC.LJPEG',2,'/home/laura/Arbeitsfläche/Project/case/normal1_case0001/A_0002_1.RIGHT_CC.LJPEG',12,32,4229, 1959, 214, 2);
insert into image(id_case, image_name, image_type, link, bits_pixel, resolution, left_cc_lines, pixels_per_line, total_abnormality, abnormality) values ( 2, 'A_0003_1.LEFT_CC.LJPEG',1,'/home/laura/Arbeitsfläche/Project/case/normal1_case0002/A_0003_1.LEFT_CC.LJPEG',24,62,2359, 1629, 267, 1);
insert into image(id_case, image_name, image_type, link, bits_pixel, resolution, left_cc_lines, pixels_per_line, total_abnormality, abnormality) values ( 2, 'A_0003_1.RIGHT_CC.LJPEG',2,'/home/laura/Arbeitsfläche/Project/case/normal1_case0002/A_0003_1.RIGHT_CC.LJPEG',16,42,4349, 1979, 234, 1);
insert into image(id_case, image_name, image_type, link, bits_pixel, resolution, left_cc_lines, pixels_per_line, total_abnormality, abnormality) values ( 3, 'C_0001_1.LEFT_MLO.LJPEG',3,'/home/laura/Arbeitsfläche/Project/case/cancer1_case0001/C_0001_1.LEFT_MLO.LJPEG',24,46,3649, 2979, 734, 5);
insert into image(id_case, image_name, image_type, link, bits_pixel, resolution, left_cc_lines, pixels_per_line, total_abnormality, abnormality) values ( 3, 'C_0001_1.RIGHT_MLO.LJPEG',4,'/home/laura/Arbeitsfläche/Project/case/cancer1_case0001/C_0001_1.RIGHT_MLO.LJPEG',32,47,7349, 1363, 734, 1);
insert into image(id_case, image_name, image_type, link, bits_pixel, resolution, left_cc_lines, pixels_per_line, total_abnormality, abnormality) values ( 4, 'C_0001_2.LEFT_MLO.LJPEG',3,'/home/laura/Arbeitsfläche/Project/case/cancer1_case0002/C_0002_1.LEFT_CC.LJPEG',32,92,3549, 3779, 374, 1);
insert into image(id_case, image_name, image_type, link, bits_pixel, resolution, left_cc_lines, pixels_per_line, total_abnormality, abnormality) values ( 4, 'A_0001_2.LEFT_CC.LJPEG',4,'/home/laura/Arbeitsfläche/Project/case/cancer1_case0002/C_0002_1.RIGHT_CC.LJPEG',16,42,4349, 1979, 234, 1);
————————————————————————-
Then I’ve considered adding columns:
ALTER TABLE volume ADD COLUMN total_size VARCHAR(10);
ALTER TABLE case_archive ADD COLUMN size_zip_MB FLOAT NOT NULL (10);
And populate them:
UPDATE case_archive SET size_zip_MB=200.1 where id_case=1;
UPDATE case_archive SET size_zip_MB=460.2 where id_case=2;
UPDATE case_archive SET size_zip_MB=2154.5 where id_case=3;
UPDATE case_archive SET size_zip_MB=225.3 where id_case=4;
To calculate the sum of the zip files’ size of the cases for each row of the volume table I’ve made the following procedure:
DELIMITER //
CREATE PROCEDURE volume_total_size()
BEGIN
DECLARE i int(10);
DECLARE l int(10);
SET i=0;
set l= (SELECT COUNT(*) from volume);
WHILE i<l DO
SET i=i+1;
UPDATE volume SET total_size= (select IF(sum(case_archive.size_zip_MB)>1024.0, CONCAT(TRUNCATE(sum(case_archive.size_zip_MB)/1024,1),'GB' ),
CONCAT(sum(case_archive.size_zip_MB),'MB')) as total_size
from case_archive
where id_volume=i)
where id_volume=i;
SELECT * FROM volume;
END;
To invoke procedure type in the console:
MySQL> call volume_total_size();
You can also copy the command in a new *.sql file and launch the script.
I’ve tested the whole “project” with MySQL 5.5.
I have decided to share this because I have spent several hours trying to understand how to update the volume table with the sum of the file size.
Notice that in the ‘case_archive‘ table the column ‘size_zip_MB‘ type is INT(10) and you have to insert the size in MB, while in ‘volume‘ the ‘total_size‘ column type is VARCHAR(10). MySQL 5.5 casts the column type automatically
