Saturday, March 21, 2020

Where and how to start for your system design

In this post, we are trying to cover where to start for your System Design even it is a very small system.

During initial few years of a developer,  they are involved in only coding of a small component or fixing a bug. Then all of a sudden you get assigned to design a complete system on your own.
Or you start looking out for a job and get stuck while attending your first few design interviews.

The mantra to overcome this challenge is very simple and you can follow below basic steps which you usually heard a lot of times from your seniors. Just try to remember Software Development Life Cycles...

Step 1: First step is to make the requirement clarifications. As a developer we get a bad habit of skipping the requirement which really blocks us sometime while coding. We need to go back to the PMs and leads to clarify different use cases for a same component. The reason of this is lacking the step for requirement clarification.

There are 2 types of requirement, one is functional clarification which tells you how to use your system? You can draw a flow chart of this functionalities.

The other requirement is to write the non functional requirement of the system. Few major things that drives the future of y0our project are:-

1. Availability
2. Number of user to be supported/Number of requests per second
3. Latency of each functionality
4. Sync vs Async
5. Storage/Compute/Network requirements
6. Redundancy/Failures to tolerate


Step 1.5: Yes usually we don't have a separate step for this but it is critical for the systems which is having a legacy system and you want to enhance some the features of it. In that case, it is very crucial for you to dive deep on the legacy system, understand how it works and then go for this implementation. If you avoid this step, then it may so happen that your system cause a regression and which impacts your overall project timeline.

Step 2: If all of the information required for your project is clear to you then you should move to this steps. Otherwise you should keep going to PMs, seniors to clarify on the requirement. You start with identifying the core components of your entire system. Don't focus on the integration at this point but make it as modular as you can. Try to use your flowchart come with the components.

One you are done with identifying all of your components, you try to use flow chart and start integrating with different components for each use cases.

While designing the components you can also keep in mind what minimal data are required to communicate with different components. Try to keep data locally with your component.

You should not think at all how different methods should be and how implementation can be done in this step. As a developer you try to think from that perspective and you start making mistakes there.

Step3: In this step you are allowed to think how each component can be designed. Since you have identified all your components and integration points you can use those integration points and how to implement those.

You need to keep in mind that, all parameters you are trying to  use, make it generic enough and so that it can extended anytime in future. it may look very ugly to keep one or two variables for a class but thats okay since it would enable to extend your component in future.







Sample Spring Project - How to add CSS and Image in Eclipse and Apache tomcat

We have found it very difficult to add an image or a css file for our sample Spring project. Below steps will give you how to achieve that.

1. Create a WebContent folder into your Eclipse project.
2. Under the WebContent folder, create Css folder and add your css file here
3. Under the WebContent folder,  create img folder and add your image.

The directory structure would look like below:

4. Change Deployment Assembly of the project to include WebContet folder as "/". You can go to this by "your-project"->Right click and go to Properties->Deployment Assembly


Friday, March 13, 2020

One of the correct Singleton Class implementation

Here is a correct way of implementation:
class Singleton {
 private volatile static Singleton _instance;//do not initialize here

 private Singleton() { //mark it private to prevent Singleton object to be instantiated from outside

 }
 
 public static Singleton getInstance() {
  if (_instance == null) { 
   synchronized (Singleton.class) { 
    if (_instance == null) { 
     _instance = new Singleton();
    }
   }
  }
 return _instance;
}

Common mistakes to avoid while coding in Java

During my development experience I have gone through multiple stages of exceptions and errors. I will list down all the mistakes I have done in my development experience from the beginning of my career. I think it will be very helpful to all of those who faced same kind of issues.

1. Use of integer, long, floats: While calculating some result with integer array and trying to get the sum, often it might happen that the result sum exceeded the integer.max_val. So in this case I recommend to use long.

we know if we do float operation with integer variable we might loose the decimal point value. hence we need to be very careful while doing such kind of computation.

2. NULL pointer exception: Handling null pointer exception is mandatory in 99% cases BUT we might miss some critical bugs in future if we use if-else blocks instead of assert statement. So recommended is to use assert statement if you don't want the value to be null.

3. Trying to overuse !StringUtils.isEmpty() kind of syntax. Its always better to use StringUtils.isNotEmpty() since it gives better readability. We often spend our time figuring out issues in code where we missed "!" before StringUtils.isEmpty().


Sample Spring-Hibernate-MySQL example for add, update, delete, list cards

Let's start with an example. Let's say we want to create page to add card to patients/students, update card details, delete a card and list all cards. In the following you can see the steps to do that.
  1. Create MySQL table for card
  2. Add a Hibernate Pojo/Model for Card
  3. Modify hibernate.cfg.xml to create a mapping of the POJO.
  4. Create CardDAO for the corresponding Card Pojo.
  5. Create Spring Controller
  6. Add CardDAO bean into root-context.xml
  7. Add the jsp files to add card to patients/students, update card details, delete a card and list all cards.
  8. Link the jsp with your existing webpage e.g. home page

Let us take a look at each step details.

Step 1

Create the table first. It can be skipped if you use below property in your hibernate.cfg.xml file.

<property name="hibernate.hbm2ddl.auto">update</property>

Step 2

Use below code snipped.

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
import javax.persistence.Transient;

@Entity
@Table(name="card_table")
public class Card {

@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name="cardID", unique = true, nullable = false)
    private long id;
@Column(name="card_no")
private String cardNo;
@Column(name="card_name")
private String cardName;
@Column(name="group_capacity")
private Long groupCapacity;
@Column(name="validity_year")
private Long validityInYears;
@Column(name="amount")
private Long amount;
@Column(name="title")
    private String title;
@Column(name="message")
    private String message;
@Column(name = "price")
private Float price;
@Transient
private int postedBy;
public int getPostedBy() {
return postedBy;
}

public void setPostedBy(int postedBy) {
this.postedBy = postedBy;
}

public Card() {
}
public Card(String cardNo, String cardName, Long groupCapacity, Long validityInYears, Long amount,
String title, String message, Float price) {
super();
this.cardNo = cardNo;
this.cardName = cardName;
this.groupCapacity = groupCapacity;
this.validityInYears = validityInYears;
this.amount = amount;
this.title = title;
this.message = message;
this.price = price;
}

public long getId() {
return id;
}

public void setId(long id) {
this.id = id;
}

public String getCardNo() {
return cardNo;
}

public void setCardNo(String cardNo) {
this.cardNo = cardNo;
}

public String getCardName() {
return cardName;
}

public void setCardName(String cardName) {
this.cardName = cardName;
}

public Long getGroupCapacity() {
return groupCapacity;
}

public void setGroupCapacity(Long groupCapacity) {
this.groupCapacity = groupCapacity;
}

public Long getValidityInYears() {
return validityInYears;
}

public void setValidityInYears(Long validityInYears) {
this.validityInYears = validityInYears;
}

public Long getAmount() {
return amount;
}

public void setAmount(Long amount) {
this.amount = amount;
}

public String getTitle() {
return title;
}

public void setTitle(String title) {
this.title = title;
}

public String getMessage() {
return message;
}

public void setMessage(String message) {
this.message = message;
}

public Float getPrice() {
return price;
}

public void setPrice(Float price) {
this.price = price;
}
}

Step 3

Add below mapping class into hibernate.cfg.xml

<mapping class="com.my.spring.pojo.Card"/>

Step 4

Create CardDAO for the corresponding Card Pojo.

import java.util.Collections;
import java.util.List;

import org.hibernate.HibernateException;
import org.hibernate.Query;

public class CardDAO extends DAO {

public Card create(Card card) {
try {
begin();            
getSession().save(card);     
commit();
return card;
catch (HibernateException e) {
return null;
finally {
rollback();
}
}

public Card update(Card card) {
try {
begin();
Card newCard = get(""+card.getId());//long to string
newCard.setTitle(card.getTitle());
newCard.setMessage(card.getMessage());
newCard.setPrice(card.getPrice());
getSession().saveOrUpdate(newCard);     
commit();
return newCard;
catch (HibernateException e) {
return null;
finally {
rollback();
}
}


public void delete(String cardId) {
try {
begin();
getSession().delete(get(cardId));
commit();
catch (HibernateException e) {

finally {
rollback();
}
}

public void delete(Card card) {
try {
begin();
getSession().delete(card);
commit();
catch (HibernateException e) {

finally {
rollback();
}
}

public List<Card> list() {

try {
begin();
Query q = getSession().createQuery("from Card");
List<Card> cards = q.list();
return cards;
catch (HibernateException e) {

}
return Collections.EMPTY_LIST;
}

public Card get(String id) {

try {
Query q = getSession().createQuery("from Card where id = :id");
q.setString("id"id);
Card card = (Card) q.uniqueResult();
return card;
catch (HibernateException e) {
}
return null;
}
}

Step 5

Create Spring Controller

@Controller
@RequestMapping("/card/*")
public class CardController {
@Autowired
@Qualifier("cardDao")
CardDAO cardDao;

                @RequestMapping(value = "/card/add", method = RequestMethod.POST)
public ModelAndView addCategory(@ModelAttribute("card") Card card, BindingResult resultthrows Exception {

Card persistentCard = cardDao.create(card);
return new ModelAndView("card-success""card"persistentCard);
}

@RequestMapping(value="/card/add", method = RequestMethod.GET)
public ModelAndView initializeForm(HttpServletRequest requestthrows Exception {
ModelAndView mv = new ModelAndView();
mv.addObject("card"new Card());
mv.setViewName("card-form");
return mv;
}

@RequestMapping(value = "/card/list", method = RequestMethod.GET)
public ModelAndView addCategory(HttpServletRequest requestthrows Exception {

ModelAndView mav = new ModelAndView("card-list");
List<Card> cards = cardDao.list();
mav.addObject("cards"cards);
return mav;

}

@RequestMapping(value = "/card/update", method = RequestMethod.POST)
public ModelAndView updateCategory(@ModelAttribute("card") Card card, BindingResult resultthrows Exception {

Card persistentCard = cardDao.update(card);
return new ModelAndView("card-success""card"persistentCard);
}

@RequestMapping(value="/card/update", method = RequestMethod.GET)
public ModelAndView initializeUpdateForm(HttpServletRequest request@RequestParam("id") String idthrows Exception {
ModelAndView mv = new ModelAndView();
mv.addObject("card"cardDao.get(id));
mv.setViewName("card-update-form");
return mv;
}

@RequestMapping(value="/card/delete", method = RequestMethod.POST)
public ModelAndView deleteCard(HttpServletRequest request@RequestParam("cardId") String cardIdthrows Exception {
cardDao.delete(cardId);
ModelAndView mav = new ModelAndView("card-list");
List<Card> cards = cardDao.list();
mav.addObject("cards"cards);
return mav;
}
}

Step 6

Add CardDAO bean into root-context.xml
<bean id="cartDao" class="com.my.spring.dao.CartDAO" ></bean>

Step 7

Add the jsp files to add card to patients/students, update card details, delete a card and list all cards.

Step 8

Link the jsp with your existing webpage e.g. home page