Thursday, 8 November 2012

Showing tool-tip on a component in Wicket

Few days back I was working on an application which was using Apache Wicket and there was a requirement to show tool-tip on a component. After googling it for hours I found this really easy solution for my requirement. 

The following code snippet shows how you can add a tool tip on a Label component.

...
Label lbl = new Label("myLable", "My Label Value");
lbl.add(new AttributeModifier("title", true, new Model<String>("My Tool-Tip"))); 
...

Thursday, 18 October 2012

Enabling HTTPS request on Tomcat Server


Enabling HTTPS Request on Tomcat

If you are developing a web application which is handling some sensitive data then you may want to use a secure medium for transferring the sensitive data between the web browser and your web server. SSL or Secure Socket Layer is an easy way to offer security to your users. SSL allows web browsers and web servers to encrypt all information and communicate it over a secured connection. 

Hypertext Transfer Protocol Secure (HTTPS) is a widely used communication protocol for secure communication over the Internet. It is simply layering of HTTP over SSL protocol. When we say we are using HTTPS for secure connection, we mean to say that the information (request) is first encrypted using SSL and transmitted using HTTP protocol and then the receiver decrypts it using SSL.

Apache Tomcat fully supports the SSL protocol and provides document on how to configure Tomcat to use SSL , but somehow I found it a little confusing for first time users. So here I am writing it in a simpler way to help you out :)

You need to follow these simple steps to enable HTTPS request in Tomcat server

Step 1 – Create a Keystore

A “keystore” is a repository of security certificates used by SSL protocol for encryption. We will use “keytool” command to create a “Keystore”
<JAVA_HOME>\bin>keytool -genkey -alias tomcat -keyalg RSA

The above command will prompt you for a password and an array of general questions required in generating the keystore & certificate. On successful execution a new file, in the home directory of the current user, named ".keystore" will be created. 

Note: Your keystore password and private key (tomcat) password should be the same.

Step 2 – Edit Tomcat Configuration File (server.xml)

Open <TOMCAT_HOME>\conf\server.xml file and search for the following text
<Connector port="8443" protocol="HTTP/1.1"
By default this entry is commented, you are supposed to just un-comment this entry and make following additional changes
  • Change protocol value from “HTTP/1.1” to “org.apache.coyote.http11.Http11Protocol” 
  • Add keystoreFile="your_keystore_path" keystorePass="your_password" to the entry
After making above change your entry should look somewhat like this
<Connector port="8443" protocol="org.apache.coyote.http11.Http11Protocol" SSLEnabled="true" maxThreads="150" scheme="https" secure="true"keystoreFile="C:\Users\dev\.keystore" keystorePass="changeit"clientAuth="false" sslProtocol="TLS" />
Step 3 – Just save the file and restart your server.

Now you can access https://localhost:8443/

NOTE: If you are using Tomcat with Eclipse IDE then probably you may be required to delete the existing tomcat server instance from IDE and add it again 

Thursday, 26 July 2012

An introduction to XML

What is XML?

XML, or eXtensible Markup Language was created by the World Wide Web Consortium (W3C) to overcome the limitations of HTML. While the HTML tags tell a browser how to display this information, the tags don't tell the browser what the information is. With XML, you can assign some meaning to the tags in the document, which can be processed by the machine.


A simple XML File
<?xml version="1.0" encoding="UTF-8"?>
<blog>
<post id="1" value="post1">
<title>Serialization in Java</title>
<author>Dev</author>
<date>05/06/2012</date>
<url>http://techiesinsight.blogspot.in/2012/06/serialization-in-java.html</url>
</post>
<post id="2" value="post2">
<title>serialVersionUId in Java Object Serialization</title>
<author>Dev</author>
<date>07/06/2012</date>
<url>http://techiesinsight.blogspot.in/2012/06/significance-of-serialverionuid-in-java.html</url>
</post>
<post id="3" value="post3">
<title>Serializable vs Externizable</title>
<author>Dev</author>
<date>09/07/2012</date>
<url>http://techiesinsight.blogspot.in/2012/07/serializable-vs-externizable.html</url>
</post>
</blog>

A little bit of XML terminology

  • XML Declaration: XML declaration is recommended but not mandatory
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
The  version is the version of XML usedThe encoding is the character set used in this document. If no encoding is specified, the XML parser assumes that the characters are in the  UTF-8; standalone, which can be either yes or no, defines whether this document can be processed without reading any other files.
  • Tag: is the text between the left angle bracket (<) and the right angle bracket (>). There are starting tags <post>ending tags </post> and self-closing tags <publishedOn date="20-07-2012"/>
  • Element: is the starting tag, the ending tag, and everything in between.  <post id=14> <title>An Introduction to XML</title> ... </post>
  • Root Element: is the first element in your XML file which encloses all the other elements of your XML. Each XML document has exactly one root element aka document element. In above example <blog> is the root element
  • Attribute: is a name-value pair inside the starting tag of an element. In above example,   id="1" value="post1"  
  • Comments: can appear anywhere in the document;  A comment begins with <!-- and ends with -->
  • Processing Instructions (PI): gives command or information to an application that is processing the XML. 
<? target instruction ?>
where the target is the name of application that is excepted to do the processing and instruction is the command or information for the application
NOTE: The XML Declaration at the beginning of an XML document is not a processing instruction
  • Entities: are the alias for a piece of information. The XML spec also defines five entities you can use in place of various special characters. The entities are:
    • &lt; for the less-than sign
    • &gt; for the greater-than sign
    • &quot; for a double-quote
    • &apos; for a single quote (or apostrophe)
    • &amp; for an ampersand.
<!ENTITY name "definition">

<!ENTITY blogurl "http://techiesinsight.blogspot.in">
Anywhere the XML processor finds the string &blogurl;, it replaces the entity with the string http://techiesinsight.blogspot.in

XML document rules

  • Root Element is mandatory. Every XML document must contain only one root element
  • Elements can't overlap - If you begin a <tag2> element inside <tag1>, then <tag2> must end before <tag1>
  • End tags are required or a tag should be self-closing tag
  • Elements are case sensitive - In XML  <blog> and <Blog> are not the same.  If you try to end an <blog> element with a </Blog> tag, you'll get an error.
  • Attributes must have values enclosed within quotation mark.
  • Element Names must follow the following naming convention
    • it can contain any letter or number or special characters
    • cannot contain spaces
    • must not begin with a number or any special character
    • cannot start with xml
  • XML declaration should be the first line in the document, if at all present
  • You should avoid having empty lines in the begging of the document, because few XML parsing API does not excepts such files   

XML Advantages:

  • Easy Information Exchange - XML allows easy sharing of data between different applications  - even if these applications are written in different languages and reside on different platforms.
  • XML enables smart code - XML's rigid set of rules helps make documents more readable to both humans and machines. XML document syntax contains a fairly small set of rules, making it possible for developers to get started right away.  
  • Self-describing dataEvery important piece of information (as well as the relationships between the pieces) can be identified easily.
  • Openness - it allow users to define their own DTDs; these set of tags can be used by the applications very easily
  • Unicode Support enables a wide variety of characters to be represented and communicated.

XML Disadvantages:

  • XML syntax is redundant, this may affect application efficiency through higher storage, transmission and processing costs
  • You cannot have a single generic application for processing different XMLs

Tuesday, 24 July 2012

Annotations in Java

Annotations are the tags that can be inserted into a Java programs so that they can be processed by the tools. In the Java programming language, an annotation is used like a modifier, and it is placed before the annotated item, without a semicolon. The name of each annotation is preceded by an @ symbol. 
For Example:
@Override 
public boolean equals(Object obj){
 ... 

Annotation Syntax

An annotation is defined by an annotation interface: 

public @interface AnnotationName
 //element declarations 
 type elementName()
 type elementName() default value
 . . . 
One of the following type can be used for annotation fields:
  • All primitives (boolean, char, short, int, long, double)
  • String
  • Class
  • Enum
  • Array of any of above types

Meta-Annotations

Meta annotations are annotations that are used to annotate annotations. There are four meta-annotation types that come standard with Java 5: 
@Documented: is a marker annotation. Annotation declaration (of the @documented annotation type) will be included in the documentation generated using Javadoc or similar tools.
@Inherited:  indicates that an annotation type is inherited by subclasses of annotated class. 
@Inherited
public @interface InheritedAnno {
}


@InheritedAnno
@SuppressWaring("unchecked")
public class SuperClass { ... }


public class SubClass extends SuperClass {... } 

In above example the SuperClass is explicitly annotated with @InheritedAnno and @SuppressWarning. SubClass has not been explicitly marked with any annotation, however it automatically inherits @InheritedAnno because of the @Inherited meta-annotation.


@Retention: indicates how long the annotations are to be retained. If no retention policy is defined, it defaults to RetentionPolicy.CLASS 

Retention Policies for the @Retention Annotation
Retention Policy Description
SOURCE Annotations are not included in class files. Annotations like @Deprecated, @SuppressWarning and @Override are used by the compiler at compile time to validate source code. 
CLASS
Annotations are included in class files, but the virtual machine need not load them. These are parsed by the application servers and other software tools at the time of deployment to generate XMLs, bolierplate code etc.
RUNTIME
Annotations are included in class files and loaded by the virtual machine. You could make your code to behave in a particular way whenever it is called. This can be achieved by the use of reflection API.



@Target: describes the program element on which an annotation is applicable. If no target is defined the annotation can be used on any program element. If target is defined the compiler will enforce specific usage restriction. 


Element Types for the @Target Annotation
Element TypesDescription
CONSTRUCTORAnnotation can be applied to constructors
FIELDAnnotation can be applied to class fields or global variables
LOCAL VARIABLESAnnotation can be applied to local variables
LOCAL VARIABLESAnnotation can be applied to local variables
METHODAnnotation can be applied to any method declaration
PACKAGEAnnotation can be applied to package declaration
PARAMETERAnnotation can be applied to method parameters
TYPEAnnotation can be applied to Class, interface and Enum declaration


User Defined Annotation (Custom Annotation)

package learn.java.annotation;


import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;


@Retention(RetentionPolicy.RUNTIME)
@Target(value={ElementType.METHOD, ElementType.LOCAL_VARIABLE, ElementType.TYPEElementType.FIELD})
public @interface CustomAnnotation {
int id() default 0;
String value() default "";
}


Annotated Class
Following code snippet shows the various formats in which an annotation can be annotated.
package learn.java.annotation;


@CustomAnnotation(id=111, value="Annotation on Class")
public class AnnotatedClass {
//The order of the elements does not matter
@CustomAnnotation(value="Annotation on globalVar1", id=222)
private int globalVar1;
//If element value is not specified, the default value is used
@CustomAnnotation(value="Annotation on globalVar2")
private float globalVar2;
//Single valued Annotation
@CustomAnnotation("Annotation on globalVar3")
private int globalVar3;
//Marker Annotation
@CustomAnnotation
private int globalVar4;

@CustomAnnotation(id=123)
public void annotatedMethod(){
System.out.println("Annotated method");
}
}

Making use of Reflection API

package learn.java.annotation;

import java.lang.annotation.Annotation;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;

public class CustomAnnotationParser {
public static void main(String[] args) {
parseAnnotatedClass();
}
public static void parseAnnotatedClass(){
Class<AnnotatedClass> c = AnnotatedClass.class;


//Fetches Class Level Annotation information
if(c.isAnnotationPresent(CustomAnnotation.class)){
CustomAnnotation anno = c.getAnnotation(CustomAnnotation.class);
System.out.println("Id: "+anno.id());
System.out.println("Value: "+anno.value());
}
System.out.println("==================================");
 
             //Retrieves all the methods defined in the Class
Method[] methods = c.getDeclaredMethods();
for(Method m : methods){
System.out.println("Method Name = "+m.getName());
 
  //Checks is CustomAnnotation is Present on the current method
if(m.isAnnotationPresent(CustomAnnotation.class)){
CustomAnnotation mAnno = m.getAnnotation(CustomAnnotation.class);
System.out.println("Id: "+mAnno.id());
System.out.println("Value: "+mAnno.value());
}
}
System.out.println("========================================");
  //Retrieves all the global variables/fields defined in the Class
Field[] fields = c.getDeclaredFields();
for(Field f : fields){
System.out.println("Field Name = "+f.getName());
  if(field.isAnnotationPresent(CustomAnnotation.class)){
CustomAnnotation fAnno = f.getAnnotation(CustomAnnotation.class);
System.out.println("Id: "+fieldAnno.id());
System.out.println("Value: "+fieldAnno.value());
}
else{
System.out.println(field.getName()+" is not annotated");
}
System.out.println("==============================");
}
}
}
The above class make use of Java Reflection API to parse the AnnotatedClass and prints the annotated elements values. 

Monday, 9 July 2012

Serializable vs Externizable

Serialization vs Externalization


Serializable
Externizable
Serializable is a marker interface (an interface with no methods) Unlike Serializable, Externizable is a standard interface with two methods defined to be implemented by the implementing class.
Serailization is a recursive process, all non-transient variables and super classes in the object hierarchy will be serialized causing an unnecessary overhead User defines what should be serialized and what should not. Hence it is more optimized. Should be preferred for "Fat Objects" 
Serialization uses reflection mechanism for marshalling and un marshalling the objects.  Marshalling/Unmarshalling process is user defined.
During de-serialization no constructor is called, hence initialization done in constructor will be skipped.  During de-serialization default constructor is invoked
A default construtor definition is not mandatory when parameterized constructor(s) are defined An explicit default constructor definition is mandatory, when parameterized constructor(s) is defined. Throws an exception if no default construtor in such cases.
While flattening an Object implementing Serializable requires more space on disk as it store additional inforamation(field names, types super classes info and other metadata) along with the field values An object implementing Externizable, will take lesser disk space while persiting it.
The default serialization mechanism adapts to class changes due to the fact that metadata is automatically extracted from the class definitions Externalization isn't very flexible and requires you to rewrite your readExternal and writeExternal code whenever you change your class definitions.
Implicitly serialize super class. If you are subclassing your externalizable class, you have to invoke your superclass’s implementation. So this causes overhead

Friday, 29 June 2012

The Externalizable Interface

Before you start exploring Externalization in Java, I would recommend you to gather some knowledge of Serialization in Java because Externalizable is an alternative to Serializable interface.


Externalizable interface allows you to customize how serialization is done. By implementing Externalizable you are controlling what gets serialized and what does not get serialized. Externalizable interface  extends Serializable interface and defines two methods to be overridden by the implementing class. 
  1. public void readExternal(ObjectInput in) throws IOException, ClassNotFoundException
  2. public void writeExternal(ObjectOutput out) throws IOException
Java class implementing Externalizable interface


package learn.java.serialization;


import java.io.Externalizable;
import java.io.IOException;
import java.io.ObjectInput;
import java.io.ObjectOutput;
import java.util.Date;


public class ExternalizableObject implements Externalizable{
   private String name;
   private  Date dob;
   private  int age;

public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Date getDob() {
return dob;
}
public void setDob(Date dob) {
this.dob = dob;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
@Override
public void readExternal(ObjectInput in) throws IOException, ClassNotFoundException {
name = (String) in.readObject();
age = in.readInt();
}
  @Override
public void writeExternal(ObjectOutput out) throws IOException {
out.writeObject(name);
out.writeInt(age);
}
}



As you have noticed we are not serializing/de-serializing dob variable in the overriding methods. Now, in the following code snippet we will try to serialize/deserialize the above class instance.

public static void main(String[] args) {
   ExternalizableObject externalizableObject = new ExternalizableObject();
   externalizableObject.setAge(26);
   externalizableObject.setDob(new Date("20/09/1985"));
   externalizableObject.setName("dev");
   externalizeObject(externalizableObject);

   ExternalizableObject deserializedObj = deserializeExternalizeObject();
   System.out.println("Name: "+ deserializedObj .getName());
   System.out.println("DOB: "+ deserializedObj.getDob());
   System.out.println("Age: "+ deserializedObj.getAge());
}


private static void externalizeObject(ExternalizableObject obj){
   try {
      FileOutputStream fos = new FileOutputStream("C:/temp/test.txt");
      ObjectOutputStream out = new ObjectOutputStream(fos);
      out.writeObject( obj ); //writeExternal() of ExternalizableObject is invoked
      out.close();
   } catch (IOException e) {
      e.printStackTrace();
   }
}

private static ExternalizableObject deserializeExternalizeObject(){
   ExternalizableObject obj = null;


   try {
      FileInputStream fis = new FileInputStream(new File("C:/temp/test.txt"));
      ObjectInputStream in = new ObjectInputStream(fis);
      obj = (ExternalizableObject) in.readObject(); //readExternal() of ExternalizableObject is invoked
   } catch (Exception e) {
      e.printStackTrace();
   } 
   return externalizableObject;
}


During the Serialization process JVM first checks if the object implements Externizable interface, it invokes writeExternal method to serialize the object otherwise the object is serialized using ObjectOutputStream.


While reconstructing the serialized object, an instance is created first using the public no-arg constructor, then the readExternal method is called. If the class only have parameterized constructor(s) defined,  than java.io.InvalidClassException: no valid constructor Exception is thrown.


If a class inherits some class implementing the Externalizable interface, it must override writeExternal() and readExternal() methods to serialize or deserialize this class in order to correctly save and restore the object.

Wednesday, 27 June 2012

How to scale image using Java

In this post we will see how can we scale an image to a desired dimension. 


In the following code snippet the scaleImage method is responsible for scaling the source image to the given height & width. Instead of overwriting the original file the code creates a new file for the scaled image version.



public static String  scaleImage(String imgSrc, int width, int height, String dest){
 try{
File f = new File(imgSrc);

//Reads the Image from the given URL
BufferedImage img = ImageIO.read(f);

//Scales the BufferedImage to the desired dimensions
   Image scaledImg = img.getScaledInstance(width, height, Image.SCALE_AREA_AVERAGING);
   
   //'coz the Image object cannot be written to disk directly 
   //We have to recreate a new BufferedImage instance from the scaled Image instance
   BufferedImage biScaledImg = toBufferedImage(scaledImg, BufferedImage.TYPE_INT_RGB);
     
   //Writes the file on to the disk at the given destination
   ImageIO.write(biScaledImg, "jpeg", new File(dest));
}
catch(IOException e){
return "Exception occurred while scaling the Image. Exception: "+e.getMessage();
}

return dest;
}


/**
* Method to create BufferedImage Instance from given Image Object
*/
private static BufferedImage toBufferedImage(Image image, int type) {
   int w = image.getWidth(null);
   int h = image.getHeight(null);
   BufferedImage result = new BufferedImage(w, h, type);
   Graphics2D g = result.createGraphics();
   g.drawImage(image, 0, 0, null);
   g.dispose();
   return result;
}



You can download the complete source code from here


It should be noted that if the new height & width is greater than the source image height & width then the resultant image will be a pixelated image.

Friday, 22 June 2012

How to delete Solr Index

To delete all documents from my Solr index, we have to issue an update request with the  stream.body parameter set to <delete><query>*:*</query></delete>, as with the following URL: 


http://<host>:<port>/solr/update?stream.body=<delete><query>*:*</query></delete>&commit=true


Just replace the placeholder with the correct details. If executed successfully the it will return a response with status = 0 and query execution time.

<response>

<lst name="responseHeader">
<int name="status">0</int>
<int name="QTime">3693</int>
</lst>
</response>



If you want to remove indexes of a particular field then specify the field name in the delete query
<delete><query>desc:*</query></delete>


You can also delete a wrongly indexed value from a particular field, just by adding the value in the delete query
<delete><query>desc:wrold</query></delete>

Using Solr Spellchecker from Java

Continuing from my prevoius post Implementing Spellchecker in Solr , we'll now see how to use SorlJ API to fetch spellcheck suggestions through a Java program.


public static Map<String, List<String>> getSuggestions(String queryStr){
if (queryStr != null &&  !queryStr.isEmpty()) {

try {

SolrServer server = new HttpSolrServer("http://localhost:8983/solr");


   ModifiableSolrParams params = new ModifiableSolrParams();
   params.set("qt", "/spell");
   params.set("q", queryStr);
   params.set("spellcheck", "true");
   params.set("spellcheck.collate", "true");


   QueryResponse response = server.query(params);
   System.out.println("response = " + response);

   if(response != null){
      SpellCheckResponse scr = response.getSpellCheckResponse();
    if(scr != null){
    List<Suggestion> suggLst = scr.getSuggestions();
    for(Suggestion sugg : suggLst){
    System.out.println("Suggestion for token"+sugg.getToken()+" are: ");
System.out.println(sugg.getAlternatives());
}
             System.out.println("Collated Result: "+scr.getAlternatives());
    }
   }
}
catch(Exception e){
e.printStackTrace();
}
}
return suggestionsMap;
}


You can download a copy of complete Java Program from here.


To run the above program you will need the following jar files

  • apache-solr-solrj-3.6.0.jar (I am using Solr 3.6.0)
  • httpclient-4.jar
  • httpcore-4.jar
  • httpmime-4.1.2.jar
  • slf4j-log4j12-1.0.jar
  • commons-logging.jar
  • log4j.jar