Friday, January 19, 2024

Var type in Java - Local Variable Type Inference

Java 10 introduced a new feature called local variable type inference where the type of the variable is inferred from the variable initializer. For this a new reserved type name “var” is added in Java to define and initialize local variables. Note that “var” is not a reserved keyword Java 10 onward it is a reserved type name so no worries if you already have an existing variable named var.


Type inference in Java- How it helps

Java is a static typed language that means any variable that is used must be defined with appropriate type. Consider the following statements-

int i = 10;
String s = “Hello”;
List<String> names = new ArrayList<String>();
Person p = new Person();

You have to declare the variable with its type before initializing it, that seems simple but at the same time it can be argued that in these statements type of the variable can easily be inferred from the context. s has to be of type String and names hold an ArrayList reference. That’s what local variable type inference does using the “var” type.

Java 10 onward, these statements can be written as follows using the var type.

var s = "test";
var names = new ArrayList<String>();

You can check whether the correct type in inferred by the compiler or not.

System.out.println("Type of s- " + s.getClass().getName());
System.out.println("Type of ArrayList- " + names.getClass().getName());

Output

Type of s- java.lang.String
Type of ArrayList- java.util.ArrayList

As you can see type is correctly inferred.

The main benefit of using var type is the increased readability. From the above two statements that point may not be that clear but consider the scenario where you have generics parameterized by further generic types. For example you have a HashMap that stores ArrayLists.

Map<String, List<String>> mapValues = new HashMap<String, List<String>>();

And then you have to iterate this HashMap of ArrayList using the entry set.

for(Map.Entry<String, List<String>> entry : mapValues.entrySet()){
  for(String s : entry.getValue()){
    System.out.println("Value - " + s);
  }
}

That’s a lot of angular brackets! Same thing can be written in a simpler form using local variable type inference.

var mapValues = new HashMap<String, List<String>>();

While iterating-

for(var entry : mapValues.entrySet()){
  for(String s : entry.getValue()){
    System.out.println("Value - " + s);
  }
}

Does var make Java dynamically typed

Though var type brings the convenience of not forced to give the exact type of the variable but it doesn’t make it dynamic by any means. Once a variable is declared using var type, variable is bound to the inferred type never to be changed again.

For example consider the following statement-

var s = "Hello";

Type of s is inferred as String by the compiler and this type can't be changed. If you try to assign an int value to variable s-

s = 7; 

you will get a compile time error "Type mismatch: cannot convert from int to String".

Restrictions with local variable type inference

1. You cannot use local variable type inference with fields and in method signatures. It’s only for local variables.

public void doCalculation(var i) {
  ..
  ..
}

Such method signature will give you compile time error “'var' is not allowed here”.

2. A var variable cannot be initialized to null.

var s = null; 

The above statement will result in a compile time error “Cannot infer type for local variable initialized to 'null'”.

3. You cannot use local variable declarations without an explicit initialization. Since the type of the variable is inferred from the value assigned to it so initialization is necessary, you cannot just use the var syntax to declare a variable without a value.

var s;

The above statement will result in a compile time error “Cannot use 'var' on variable without initializer”.

4. You cannot use var with lambda expressions because they require an explicit target-type.

var x = (a, b) -> a+b;

Above lambda expression results in compile time error “Lambda expression needs an explicit target-type”.

5. var doesn’t work well with polymorphic code. Consider the scenario where you have a Parent class named Parent and two child classes Child1 and Child2 then, because of run-time polymorphism the following statements are perfectly fine-

Parent p = new Child1();
p = new Child2();

Parent class can store reference of both Child1 and Child2. But with var if you have a statement as following-

var p = new Child1(); 

Compiler has no way of knowing whether you intended p to be of type Parent or Child1. Since type of var is inferred to be the type of the initializer so here p will be considered to be of type Child1. That means following assignment results in error.

p = new Child2(); // Type mismatch: cannot convert from Child1 to Child2

That's all for this topic Var type in Java - Local Variable Type Inference. If you have any doubt or any suggestions to make please drop a comment. Thanks!

>>>Return to Java Advanced Tutorial Page


Related Topics

  1. JShell in Java With Examples
  2. Private Methods in Java Interface
  3. String join() Method And StringJoiner Class in Java
  4. New Date And Time API in Java 8
  5. Java Stream API Tutorial

You may also like-

  1. Method Reference in Java
  2. String Pool in Java
  3. Switch Expressions in Java 12
  4. Connection Pooling Using Apache DBCP in Java
  5. Named Tuple in Python
  6. Angular - Call One Service From Another
  7. Spring Boot Hello World Web Application Example
  8. Using Avro File With Hadoop MapReduce

Thursday, January 18, 2024

Display Time in 24 Hours Format in Java

In this article we’ll see a Java program to display time in 24 hour format. The pattern specified in SimpleDateFormat or DateFormatter class (Java 8 onward) for time determines whether time is shown in 12 hour format or 24 hour format. For 24 hour format you will have to use HH for hour not hh.

Time in 24 hour format using DateFormatter

LocalTime time = LocalTime.now();
// Pattern for 24 hrs
DateTimeFormatter pattern = DateTimeFormatter.ofPattern("HH:mm:ss");
System.out.println("Time (24 Hour format) - " + time.format(pattern));

Output

Time (24 Hour format) – 16:43:45

Time in 24 hour format using SimpleDateFormat

Date date = new Date();
// Pattern for 24 Hrs.
SimpleDateFormat sdf = new SimpleDateFormat("HH:mm:ss");
System.out.println("Time (24 Hour format) - " + sdf.format(date));

Output

Time (24 Hour format) – 16:45:30

That's all for this topic Display Time in 24 Hours Format in Java. If you have any doubt or any suggestions to make please drop a comment. Thanks!

>>>Return to Java Programs Page


Related Topics

  1. How to Format Time in AM-PM Format - Java Program
  2. Create Date Object in Java With Date and Time Values
  3. Java Program to Get Current Date and Time
  4. How to Convert Date And Time Between Different Time-Zones in Java
  5. Difference Between Two Dates in Java

You may also like-

  1. Ternary Search Program in Java
  2. Count Number of Times Each Character Appears in a String Java Program
  3. How to Convert a File to Byte Array
  4. Setting And Getting Thread Name And Thread ID in Java
  5. Java Lambda Expression as Method Parameter
  6. Interface Default Methods in Java
  7. Service in Angular With Examples
  8. Spring NamedParameterJdbcTemplate Insert, Update And Delete Example

Wednesday, January 17, 2024

Create Date Object in Java With Date and Time Values

There are scenarios when you may want to create a date object with specific values meaning you should be able to pass date values like year, month, day and time values like hour, minute, second too if required. In this post we’ll see how to create such a date object with values in Java.

In new data and time API from Java 8 you can create date object using one of the following classes as per your requirements.

  • LocalDate- to create Date object with date values.
  • LocalTime- to create Date object with time values.
  • LocalDateTime- To create Date object with both date and time values.
  • ZonedDateTime- To create Date object with both date and time with a time-zone.

If you still want to use one of the java.util classes then you can also get a Date object with values using GregorianCalendar class which is a concrete subclass of Calendar.

1. Create date object using LocalDate in Java

You can use of() static method of LocalDate class to obtain an instance of java.time.LocalDate from the passed year, month and day.

LocalDate date = LocalDate.of(2020, 6, 17);
System.out.println("Date- " + date); // 2020-06-17

You can also use enum java.time.Month to specify month.

LocalDate date = LocalDate.of(2020, Month.JUNE, 17);

2. Create date object using LocalTime

If you want only time values then use of() method of java.time.LocalTime
LocalTime time = LocalTime.of(17, 12, 17);
System.out.println("Time- " + time); // 17:12:17

3. Create datetime object using java.time.LocalDateTime

If you have to pass both date and time values then use java.time.LocalDateTime class.

LocalDateTime dateTime = LocalDateTime.of(2020, Month.JUNE, 17, 17, 12, 17);
System.out.println("Date- " + dateTime); // 2020-06-17T17:12:17

4. Date object using ZonedDateTime

Along with date and time if you want time-zone information then use ZonedDateTime. You need to set the required zone id, for that you can use ZoneId.of() method.

ZonedDateTime zonedDateTime = ZonedDateTime.of(LocalDateTime.of(2020, Month.JUNE, 17, 17, 12, 17), ZoneId.of("Asia/Tokyo"));
System.out.println("Date- " + zonedDateTime); // Date- 2020-06-17T17:12:17+09:00[Asia/Tokyo]

Creating Date object using Java GregorianCalendar

In GregorianCalendar class there are different constructors to create a java.util.Date object passing only year, month, day values or passing both date and time values. There is also a constructor to pass timezone to get time value in the passed time zone.

  • GregorianCalendar(int year, int month, int dayOfMonth)- Constructs a GregorianCalendar with the passed year, month, day in the default time zone with the default locale.
  • GregorianCalendar(int year, int month, int dayOfMonth, int hourOfDay, int minute)- Constructs a GregorianCalendar with the passed year, month, day, hour, minute for the default time zone with the default locale.
  • GregorianCalendar(int year, int month, int dayOfMonth, int hourOfDay, int minute, int second)- Constructs a GregorianCalendar with the passed year, month, day, hour, minute, second for the default time zone with the default locale.
  • GregorianCalendar(TimeZone zone, Locale aLocale)- Constructs a GregorianCalendar based on the current time in the given time zone with the given locale.
Calendar cal = new GregorianCalendar(2020, Calendar.JUNE, 17, 17, 45, 17);
SimpleDateFormat sdf = new SimpleDateFormat("dd-MM-yyyy HH:mm:ss a");
System.out.println("Date- " + sdf.format(cal.getTime()));//17-06-2020 17:45:17 PM

With time-zone information, note that day time saving is not taken into consideration by GregorianCalendar.

Calendar cal = new GregorianCalendar(TimeZone.getTimeZone("America/Los_Angeles"), Locale.US);
cal.set(2020, Calendar.JUNE, 17, 17, 45, 17);
SimpleDateFormat sdf = new SimpleDateFormat("HH:mm:ss a", Locale.US);
System.out.println("Time- " + sdf.format(cal.getTime()));

That's all for this topic Create Date Object in Java With Date and Time Values. If you have any doubt or any suggestions to make please drop a comment. Thanks!

>>>Return to Java Programs Page


Related Topics

  1. Java Program to Get Current Date and Time
  2. Difference Between Two Dates - Java Program
  3. How to find last modified date of a file in Java
  4. How to Format Date in Java Using SimpleDateFormat
  5. How to Convert a File to Byte Array

You may also like-

  1. Find The Maximum Element in Each Row of a Matrix - Java Program
  2. How to Reverse a Linked List in Java
  3. Connection Interface in Java-JDBC
  4. Var type in Java - Local Variable Type Inference
  5. registerShutdownHook() Method in Spring Framework
  6. Angular Custom Two-Way Data Binding
  7. Spring Web Reactive - Spring WebFlux Example Using Functional Programming
  8. Python Program to Display Prime Numbers

Tuesday, January 16, 2024

JShell in Java With Examples

Many programming languages like Python. Scala provide an interactive command line tool where you can type a statement and immediately see the result. In Java such a tool was missing till Java 8. Finally in Java 9, the Java Shell Tool or JShell in short is added which is an interactive tool for learning the Java programming language, prototyping Java code, testing the parts of the code.

JShell is a Read-Evaluate-Print Loop (REPL) which-

  • Reads the entered statements, declarations and expressions.
  • Evaluates them
  • Immediately show the result (Print them)
  • Goes back to command line (Loop)

How JShell is useful

Since Java is object oriented programming language so it requires the complete setup of declaring a class and having at least main method for even a simple program like printing “Hello World”.

Another scenario is trying to test a part of the code before integrating it with the application.

Without JShell these scenarios would involve-

  • Write a complete program in IDE.
  • Compile the program
  • Fix compile time errors, if any.
  • Run the program.
  • Figure out logical errors or runtime errors
  • Fix those errors
  • Repeat the process.

JShell helps you try out code and easily explore options as you develop your program. Rather than going through the whole process as mentioned above you can test individual statements or small portions, try out different variations of a method and experiment with unfamiliar APIs within the JShell session.

For example suppose you have just upgraded to Java 12 from Java 8 and want to try out new String methods like repeat() or isBlank() added in Java 11. Rather than directly using in your code you can start a JShell session and practice there to get used with these methods and then use it properly in your application.

jshell> String str = "test";
str ==> "test"
|  created variable str : String

jshell> str.repeat(5);
$2 ==> "testtesttesttesttest"
|  created scratch variable $2 : String

jshell> System.out.println(str.is)
isBlank()   isEmpty()
jshell> System.out.println(str.isBlank());
false

Note that JShell provides code completion using Tab key.

How to start and stop JShell

Prerequisite for using JShell is that you have JDK 9 or above installed. Also set the Path to Java installation directory so that you are not restricted to start JShell only from the Java installation directory.

To start JShell, enter the jshell command on the command line.

F:\NETJS>jshell
|  Welcome to JShell -- Version 12.0.1

To start JShell in verbose mode use the -v option

F:\NETJS>jshell -v
|  Welcome to JShell -- Version 12.0.1
|  For an introduction type: /help intro

To exit JShell, enter /exit.

jshell> /exit
|  Goodbye

Print Hello World in JShell

In the section “How JShell is useful” I mentioned how you have to go through the process of creating a class and have a main method even for printing a statement, not anymore with JShell!

jshell> System.out.println("Hello World")
Hello World

Note that statement is not terminated with a semicolon. JShell automatically adds terminating semicolons to the end of a complete snippet if not entered.

Declaring variables in JShell

JShell accepts variable declarations, method and class definitions, imports and expressions. Let's start with variable declaration using JShell.

Declaring a string-

jshell> String s = "JShell";
s ==> "JShell"
|  created variable s : String

Declaring a double variable-

jshell> double d = 1.45
d ==> 1.45
|  created variable d : double

A variable once declared is retained thought out the lifetime of the JShell session. After declaring String variable we declared another variable but String s is retained, if I print s I still get the value.

jshell> System.out.println(s)
JShell

Changing type of variable

You can change the type of a variable in JShell even in incompatible ways. For example with in the same session of JShell type of s can be changed from String to int.

jshell> int s = 7
s ==> 7
|  replaced variable s : int
|    update overwrote variable s : String

jshell> System.out.println(s)
7

Scratch variables in JShell

When an expression is entered that is not assigned to a named variable, a scratch variable is created so that the value can be referenced later. Scratch variable name start with a '$' sign.

jshell> 1 + 3
$3 ==> 4
|  created scratch variable $3 : int

jshell> System.out.println($3);
4

Creating methods in JShell

You can create a method in JShell and invoke it from JShell too.

Creating method-

jshell> double multiply(int a, int b){
   ...> return a * b;
   ...> }
|  created method multiply(int,int)

Invoking method-

jshell> System.out.println(multiply(91, 23));
2093.0

Creating Classes in JShell

You can also create a class in JShell.

jshell> class HelloWorld{
   ...> void display(){
   ...> System.out.println("Hello World");
   ...> }
   ...> }
|  created class HelloWorld

From the JShell itself you can create instance of the class and execute its methods.

jshell> new HelloWorld().display();
Hello World

Forward References in JShell

JShell accepts method definitions that reference methods, variables, or classes that aren’t yet defined. Note that you won't be able to execute a method until all the forward references are defined. For example you have defined a method to calculate area of the circle which refernces yet to be defined variable and method.

jshell> double area(double radius){
   ...> return PI * square(radius);
   ...> }
|  created method area(double), however, it cannot be invoked until variable PI, and method square(double) are declared

As you can see JShell warns you that the method has forward references that need to be defined. If you try to execute area() method without doing that you will get an error.

jshell> System.out.print(area(5));
|  attempted to call method area(double) which cannot be invoked until variable PI, and method square(double) are declared. 

Defining all the required elements and then executing method.

jshell> double PI = 3.1415926535
PI ==> 3.1415926535
|  created variable PI : double

jshell> double square(double d){
   ...> return d * d;
   ...> }
|  created method square(double)
|    update modified method area(double)

jshell> System.out.print(area(5));
78.5398163375

Exception handling in JShell

JShell also has full exception handling support and prints the stack trace in case of exception.

jshell> int divide(int x, int y) {
   ...> return x/y;
   ...> }
|  created method divide(int,int)

jshell> divide(5, 0)
|  Exception java.lang.ArithmeticException: / by zero
|        at divide (#18:2)
|        at (#19:1)

JShell Commands

JShell has a set of commands to control the environment and display information within a session. Any JShell command starts with a leading forward slash (/) which distinguishes it from snippets. Here is a list of some of the JShell commands and how to use them.

/vars command

List the declared variables and their values.

jshell> /vars
|    String $2 = "testtesttesttesttest"
|    String str = "test"
|    double d = 1.45
|    int s = 7
|    double PI = 3.1415926535
|    int $19 = 0

/methods Command

List the declared methods and their signatures.

jshell> /methods
|    double multiply(int,int)
|    double area(double)
|    double square(double)
|    int divide(int,int)

/list Command

List the source code you have typed.

jshell> /list

   2 : str.repeat(5);
   3 : System.out.println(str.isBlank());
   4 : System.out.println("Hello World")
   5 : String str = "test";
   7 : double d = 1.45;
   8 : System.out.println(s)
   9 : int s = 7;
  10 : System.out.println(s)
  11 : double multiply(int a, int b){
       return a * b;
       }
  12 : System.out.println(multiply(91, 23));
  13 : double area(double radius){
       return PI * square(radius);
       }
  14 : System.out.print(area(5));
  15 : double PI = 3.1415926535;
  16 : double square(double d){
       return d * d;
       }
  17 : System.out.print(area(5));
  18 : int divide(int x, int y) {
       return x/y;
       }
  19 : divide(5, 0)

Getting list of available commands

You can get the list of available JShell commands by typing forward slash (/) accompanied by tab.

jshell> /
/!          /?          /drop       /edit       /env        /exit       /help
/history    /imports    /list       /methods    /open       /reload     /reset
/save       /set        /types      /vars
<press tab again to see synopsis>

/help Commamd

Gives information about JShell commands and how to use JShell tool.

For example getting help about /imports command.

jshell> /help /imports
|
|                                  /imports
|                                  ========
|
|  List the current active imports.  This will include imports from
|  startup snippets.

/imports Command

List the imported items. JShell imports few packages by default so you will get some values when using this command even if you don’t import any package yourself.

jshell> /import
|    import java.io.*
|    import java.math.*
|    import java.net.*
|    import java.nio.file.*
|    import java.util.*
|    import java.util.concurrent.*
|    import java.util.function.*
|    import java.util.prefs.*
|    import java.util.regex.*
|    import java.util.stream.*

That's all for this topic JShell in Java With Examples. If you have any doubt or any suggestions to make please drop a comment. Thanks!

>>>Return to Java Basics Tutorial Page


Related Topics

  1. Private Methods in Java Interface
  2. PermGen Space Removal in Java 8
  3. Optional Class in Java With Examples
  4. New Date And Time API in Java 8
  5. Core Java Basics Interview Questions And Answers

You may also like-

  1. serialVersionUID and versioning in Java Serialization
  2. BigDecimal in Java
  3. Parallel Stream in Java Stream API
  4. Busy Spinning in Multi-Threading
  5. Spring Email Scheduling Example Using Quartz Scheduler
  6. Accessing Characters in Python String
  7. Service in Angular With Examples
  8. Parquet File Format in Hadoop

Monday, January 15, 2024

Java Program to Get Current Date and Time

This article shows how to get current date and time in Java. In the new data and time API from Java 8 onward there are following classes that can be used for displaying either current date, current time or both.

  • java.time.LocalDate- To get current date.
  • java.time.LocalTime- To get current time.
  • java.time.LocalDateTime- To get both current date and time.
  • java.time.ZonedDateTime– To get both current date and time with time-zone information.

Other options, mostly applicable, if you are still not using Java 8 version or above are as follows.

  • By using java.util.Date class
  • By using java.util.Calendar class

1. Current date using LocalDate in Java

Using now() method of the LocalDate you can obtain the current date from the system clock in the default time-zone. For formatting the date in required format you can use DateTimeFormatter class also added in Java 8.

LocalDate currentDate = LocalDate.now();
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");
System.out.println(currentDate.format(formatter)); //2020-06-22

2. Current time using LocalTime in Java

Using now() method of the LocalTime class you can obtain the current time from the system clock in the default time-zone.

LocalTime currentTime = LocalTime.now();
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("hh:mm:ss");
System.out.println(currentTime.format(formatter)); //09:54:09

3. Current date and time using LocalDateTime in Java

Using now() method of LocalDateTime class you can get the current date-time from the system clock in the default time-zone.

LocalDateTime currentDateTime = LocalDateTime.now();
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ss");
System.out.println(currentDateTime.format(formatter)); //2020-06-22T09:58:46

4. Current date and time with zone information

By using ZonedDateTime you can get zone offset and time-zone information too.

ZonedDateTime currentDateTime = ZonedDateTime.now(ZoneId.of("America/Los_Angeles"));
DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ss z VV");
System.out.println(currentDateTime.format(formatter)); //2020-06-21T21:32:22 GMT-07:00 America/Los_Angeles

5. Getting Date and Time using java.util.Date

When a new Date object is created it is initialized to represent the time at which it was allocated.

Date date = new Date();
System.out.println("Date- " + date); // Date- Mon Jun 22 10:06:12 IST 2020

For formatting date you can use SimpleDateFormat class.

Date date = new Date();
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
System.out.println("Date- " + sdf.format(date)); // 2020-06-22 10:07:38

6. Getting Date and Time using java.util.Calendar

In Calendar class there is a getInstance() method that gives the current date and time.

Calendar calendar = Calendar.getInstance();
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
System.out.println("Date- " + sdf.format(calendar.getTime())); // 2020-06-22 10:10:34

That's all for this topic Java Program to Get Current Date and Time. If you have any doubt or any suggestions to make please drop a comment. Thanks!

>>>Return to Java Programs Page


Related Topics

  1. Create Date Object in Java With Date and Time Values
  2. How to Convert String to Date in Java
  3. How to Convert Date And Time Between Different Time-Zones in Java
  4. How to Compile Java Program at Runtime
  5. Converting double to int in Java

You may also like-

  1. Converting String to Enum Type in Java
  2. Invoking Getters And Setters Using Reflection in Java
  3. Connection Pooling Using C3P0 in Java
  4. final Vs finally Vs finalize in Java
  5. Map Operation in Java Stream API
  6. Spring MVC Redirect Example
  7. Spring Boot StandAlone (Console Based) Application Example
  8. Angular ngFor Directive With Examples

Sunday, January 14, 2024

Angular Example to Render Multiple Rows

In this Angular example we’ll see how to render multiple rows. There will be a UI for entering data and a submit button. After entering data when user clicks submit button the entered data is displayed below it. User can again enter the data and a new row will be displayed below the previously displayed data. This Angular example shows the usage of property binding, event binding, @Input decorator and ngFor directive.

Here is a screen shot which shows the final UI created using this Angular example for rendering multiple rows.

Angular example rendering rows


Angular example steps

  1. In your Angular project create a new folder User for keeping classes created for this example.
  2. Create a User class, it is a best practice to create a separate model bean class rather than keeping data in the Component class to reduce coupling.
  3. Create a new User component class that uses the User class to render data. In the example when data is entered using UI a new User class instance is created and data of the instance is rendered using User component. So every time data is entered and submit button is clicked a new User class instance is created and rendered as a new row.
  4. For storing multiple User instances an array of type User (User[]) is used.

Creating a User class

Create a Type script class user.model.ts to define a User class. If you are aware of MVC (Model View Controller) pattern then this class is the Model.

export class User {
  name : string;
  age : number;
  constructor(name: string, age : number) {
    this.name = name;
    this.age = age;
  }
}

Creating User component class

Create a Type script class user.component.ts

import { 
  Component,
  OnInit,
  Input
 } from '@angular/core';
import { User } from './user.model';
@Component({
  selector: 'app-user',
  templateUrl: './user.component.html'
})
export class UserComponent implements OnInit{
  @Input() user: User;
  constructor(){
  
  }
  ngOnInit(){
  }
}
  1. As you can see Component class uses User class to store instance data thus the import statement.
     import { User } from './user.model';
     
  2. @Input decorator marks a class field as an input property. The input property is bound to a DOM property in the template. During change detection, Angular automatically updates the data property with the DOM property's value. In our component we want to pass data to the user property thus it is decorated with @Input decorator. Because of using @Input with user property Angular uses user as an input binding.
    We’ll see a little later how property binding is done to bind a custom property to user instances. This custom property is then passed to the User component to display user data using input binding.

Creating template for displaying user data

Create user.component.html which is used to render user data. Bootstrap framework is used for styling.

<div class="container">
  <div class="row">
    <div class="col-xs-6 px-3">
      <label>Name: </label> {{ user.name }}      
    </div>
    <div class="col-xs-4">
      <label>Age: </label>{{ user.age }}
    </div>
  </div>
</div>

Changes in app module to register user component

If you have not created new component using Angular CLI then you need to manually import the component in app.module.ts file.

import { UserComponent } from './user/user.component';

Also add with in the declarations array in @NgModule decorator.

@NgModule({
  declarations: [
    AppComponent,
    UserComponent
    //HelloWorldComponent
  ],
..
..

Template for adding users

Add the following code in app.component.html

<form>
  <div class="form-group">
    <label for="name" class="col-sm-2 col-form-label">Name:</label>
    <div class="col-sm-10">
      <input class="form-control" placeholder="Enter name" id="name" #enteredname>
    </div>
  </div>
  <div class="form-group">
    <label for="age" class="col-sm-2 col-form-label">Age:</label>
    <div class="col-sm-10">
      <input class="form-control" placeholder="Enter age" id="age" #enteredage>
    </div>
  </div>
  <button (click)="addUser(enteredname, enteredage)" type="submit" class="btn btn-primary">Submit</button>
</form>

<app-user *ngFor="let user of users" [user]="user">
</app-user>

This template renders a form for adding users.

  1. In the template there are two input tags- one for entering user name and the other for age.
  2. #enteredname and #enteredage are local variables used with the tags. The input tags are assigned to these local variables.
  3. There is a submit button where we have also added an event (click) which calls the function addUser when the button is clicked. Note that function addUser is defined in AppComponent class.
  4. addUser() function takes two arguments. While calling the function the two variables #enteredname and #enteredage are passed.
  5. ngFor directive is used to iterate through the array of users and assign user instance to variable named user in each iteration.
  6. [user]="user" expression is the property binding. This binding is setting the user input (@Input() user: User in the user.component.ts) to the value of the variable user assigned here by ngFor.

app.component.ts

import { Component } from '@angular/core';
import { User } from './user/user.model';
@Component({
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css']
})
export class AppComponent {
  users: User[];
  constructor(){
    this.users = [];
  }
  addUser(name: HTMLInputElement, age: HTMLInputElement): boolean {
    //console.log(`user name: ${name.value}, age: ${age.value}`);
    // adding user instance to array
    this.users.push(new User(name.value, Number(age.value)));
    // resetting input elements
    name.value = '';
    age.value = '';
    return false;
  }
}

1. In the Component class User class is imported using this statement- import { User } from './user/user.model';

2. users: User[]; declares an array users of type User.

3. adduser() function which is called when the submit button is clicked is defined here. In the function, using the entered values a new User instance is created and added to the users array.

Build the code and access the URL http://localhost:4200/ which should render the screen to enter User data.

That's all for this topic Angular Example to Render Multiple Rows. If you have any doubt or any suggestions to make please drop a comment. Thanks!

>>>Return to Angular Tutorial Page


Related Topics

  1. Angular Disable Button Example
  2. Angular First App - Hello world Example
  3. Angular Project Structure With File Description
  4. How to Add Bootstrap to Angular Application
  5. Creating New Component in Angular

You may also like-

  1. Angular @Input and @Output Example
  2. Angular One-Way Data Binding Using String Interpolation
  3. Angular Application Bootstrap Process
  4. Angular - Call One Service From Another
  5. CallableStatement Interface in Java-JDBC
  6. Producer-Consumer Java Program Using wait notify
  7. Concatenating Lists in Python
  8. Java Collections Interview Questions And Answers

Saturday, January 13, 2024

Spring NamedParameterJdbcTemplate Insert, Update And Delete Example

In the post Spring JdbcTemplate Insert, Update And Delete Example we have already seen how JdbcTemplate can be used in Spring framework for data access. If you have noticed the examples there, indexed parameters are used with the place holder '?' in the SQL queries. With indexed parameter it is very important that you pass the parameters in the correct order in the query. Problem with indexed parameter is that any change in the query may require a change in order of the parameters too. If you want to avoid that another option is named parameters. As the name suggests here each parameter is given a name and you bind the parameters to the query using those names. This post shows how you can insert, update and delete using NamedParameterJdbcTemplate in Spring.

In this Spring NamedParameterJdbcTemplate example we'll see both options using XML configuration as well by using annotations.


NamedParameterJdbcTemplate in Spring

Spring framework provides NamedParameterJdbcTemplate class which adds support for programming JDBC statements using named parameters, as opposed to programming JDBC statements using only classic placeholder ('?') arguments.

Here one thing to note is NamedParameterJdbcTemplate class wraps a JdbcTemplate, and delegates to the wrapped JdbcTemplate to do much of its work.

Spring NamedParameterJdbcTemplate Example

In this example we'll see how to do DB insert, update and delete using NamedParameterJdbcTemplate in Spring. The example shows both the ways- using Spring XML configuration as well as using annotations for component scanning and autowiring.

Note that NamedParameterJdbcTemplate needs a DataSource in order to perform its management of fixed part like getting a DB connection, cleaning up resources. In this post Apache DBCP is used which provides pooled datasource and MYSQL is used as the back end.

Technologies used

  • Spring 5.0.4
  • Apache DBCP2
  • MYSQL 5.1.39
  • Java 8
  • Apache Maven 3.3.3

Maven Dependencies

If you are using maven then you can provide dependencies in your pom.xml.

With all the dependencies your pom.xml should look something like this-

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>org.netjs.prog</groupId> <artifactId>maven-spring</artifactId> <version>0.0.1-SNAPSHOT</version> <packaging>jar</packaging> <name>maven-spring</name> <url>http://maven.apache.org</url> <properties> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <spring.version>5.0.4.RELEASE</spring.version> </properties> <dependencies> <dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version>4.11</version> <scope>test</scope> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-core</artifactId> <version>${spring.version}</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-context</artifactId> <version>${spring.version}</version> </dependency> <dependency> <groupId>javax.inject</groupId> <artifactId>javax.inject</artifactId> <version>1</version> </dependency> <!-- Spring JDBC Support --> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-jdbc</artifactId> <version>${spring.version}</version> </dependency> <!-- MySQL Driver --> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>5.1.39</version> </dependency> <!-- Apache DBCP connection pool --> <dependency> <groupId>org.apache.commons</groupId> <artifactId>commons-dbcp2</artifactId> <version>2.1</version> </dependency> </dependencies> </project>

Alternatively you can download the jars and add them to the class path.

DB table used

For this example I have created a table called employee with the columns id, name and age in the MYSQL DB. Column id is configured as auto increment checked so no need to pass id from your query as DB will provide value for it.

CREATE TABLE `employee` (
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(35) DEFAULT NULL,
  `age` int(11) DEFAULT NULL,
  PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=8 DEFAULT CHARSET=utf8;

Configuring datasource dependency

First thing is to set up DataSource as a bean. I have used properties file to configure datasource where all the properties are there in the db.properties file.

<bean id="dataSource" class="org.apache.commons.dbcp2.BasicDataSource">
    <property name="driverClassName" value = "${db.driverClassName}" />
    <property name="url" value = "${db.url}" />
    <property name="username" value = "${db.username}" />
    <property name="password" value = "${db.password}" />
    <property name="initialSize" value = "${pool.initialSize}" />
</bean>

Where as db.properties file which is under the config folder has all the properties.

db.properties

db.driverClassName=com.mysql.jdbc.Driver
db.url=jdbc:mysql://localhost:3306/netjs
db.username=
db.password=
pool.initialSize=5

Description of the properties used here is as-

driver class name is the JDBC driver for the DB used. Since MYSQL is used here so the jdbc driver for the same (com.mysql.jdbc.Driver) is provided.

Url – You need to provide url to access your DB server. I have created a schema called netjs and DB is running on the same system so url is jdbc:mysql://localhost:3306/netjs.

Username and password for the DB.

IntialSize is the initial size of the connection pool. It is given as 5 so initially 5 connections will be created and stored in the pool.

To use properties file you need to put following configuration in your XML.

<context:property-placeholder location="classpath:config/db.properties" />

Spring NamedParameterJdbcTemplate configuration

DataSource bean has to be provided as a reference in NamedParameterJdbcTemplate.

<bean id="namedJdbcTemplate" class="org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate">  
    <constructor-arg ref="dataSource"></constructor-arg> 
</bean>

Java Classes

Since Spring always promotes to use interfaces and there is also a JEE design pattern for database layer called DAO which also says the same thing - Separate low level data access code from the business layers.

So we have a EmployeeDAO interface with insert, update and delete methods and its implementing class EmployeeDAOImpl. There is also a model class Employee with all the getters/setters.

Employee.java class

public class Employee {
 private int empId;
 private String empName;
 private int age;
 
 public int getEmpId() {
  return empId;
 }
 public void setEmpId(int empId) {
  this.empId = empId;
 }
 public String getEmpName() {
  return empName;
 }
 public void setEmpName(String empName) {
  this.empName = empName;
 }
 public int getAge() {
  return age;
 }
 public void setAge(int age) {
  this.age = age;
 }
}

EmployeeDAO interface

public interface EmployeeDAO {
 public int save(Employee employee);
 
 public void update(Employee employee);
 
 public void deleteEmpById(int empId);
}

EmployeeDAOImpl class

import java.util.HashMap;

import java.util.Map;
import org.netjs.dao.EmployeeDAO;
import org.netjs.model.Employee;
import org.springframework.jdbc.core.namedparam.MapSqlParameterSource;
import org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate;
import org.springframework.jdbc.core.namedparam.SqlParameterSource;

public class EmployeeDAOImpl implements EmployeeDAO {
  private NamedParameterJdbcTemplate namedJdbcTemplate; 
  
  final String INSERT_QUERY = "insert into employee (name, age) values (:name, :age)";
  final String UPDATE_QUERY = "update employee set age = :age where id = :id";
  final String DELETE_QUERY = "delete from employee where id = :id";
  
  public NamedParameterJdbcTemplate getNamedJdbcTemplate() {
    return namedJdbcTemplate;
  }

  public void setNamedJdbcTemplate(NamedParameterJdbcTemplate namedJdbcTemplate) {
    this.namedJdbcTemplate = namedJdbcTemplate;
  }

  @Override
  public int save(Employee employee) {
    // Creating map with all required params
    Map<String, Object> paramMap = new HashMap<String, Object>();
    paramMap.put("name", employee.getEmpName());
    paramMap.put("age", employee.getAge());
    // Passing map containing named params
    return namedJdbcTemplate.update(INSERT_QUERY, paramMap);  
  }

  @Override
  public void update(Employee employee) {
    // Adding params using MapSqlParameterSource class
    SqlParameterSource namedParameters = new MapSqlParameterSource().addValue("age", employee.getAge()).addValue("id", employee.getEmpId());
    int status = namedJdbcTemplate.update(UPDATE_QUERY, namedParameters); 
    if(status != 0){
      System.out.println("Employee data updated for ID " + employee.getEmpId());
    }else{
      System.out.println("No Employee found with ID " + employee.getEmpId());
    }
  }

  @Override
  public void deleteEmpById(int empId) {
    // Adding params using MapSqlParameterSource class
    SqlParameterSource namedParameters = new MapSqlParameterSource("id", empId);
    int status = namedJdbcTemplate.update(DELETE_QUERY, namedParameters);
    if(status != 0){
      System.out.println("Employee data deleted for ID " + empId);
    }else{
      System.out.println("No Employee found with ID " + empId);
    }
  }
}

This class contains namedJdbcTemplate property which will be wired by the Spring framework. In the save method named parameters are stored in a Map and that map is passed. In the update method another option MapSqlParameterSource class is used which has addValue method. Using the addValue method key, value pair is stored and later passed to the query.

Also notice how you are not writing any code for getting or closing connection, exception handling. All that fixed part is managed by the template class itself.
If there is any SQLException thrown that is also caught by JDBCTemplate and translated to one of the DataAccessException and rethrown.

Full XML Configuration

<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:context="http://www.springframework.org/schema/context" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd"> <!-- For reading properties files --> <context:property-placeholder location="classpath:config/db.properties" /> <bean id="namedJdbcTemplate" class="org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate"> <constructor-arg ref="dataSource"></constructor-arg> </bean> <bean id="employeeDAO" class="org.netjs.daoimpl.EmployeeDAOImpl"> <property name="namedJdbcTemplate" ref="namedJdbcTemplate"></property> </bean> <bean id="dataSource" class="org.apache.commons.dbcp2.BasicDataSource"> <property name="driverClassName" value = "${db.driverClassName}" /> <property name="url" value = "${db.url}" /> <property name="username" value = "${db.username}" /> <property name="password" value = "${db.password}" /> <property name="initialSize" value = "${pool.initialSize}" /> </bean> </beans>

Here note that in the bean definition for NamedParameterJdbcTemplate, data source property is passed as a constructor argument.

Test class

You can use the following code in order to test the insertion, update and deletion.

import org.netjs.dao.EmployeeDAO;
import org.netjs.model.Employee;
import org.springframework.context.support.ClassPathXmlApplicationContext;

public class App {
  public static void main(String[] args) {
    ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext
     ("appcontext.xml");
    
    EmployeeDAO dao=(EmployeeDAO)context.getBean("employeeDAO");  
    Employee emp = new Employee();
    emp.setEmpName("John");
    emp.setAge(25);
    int status = dao.save(emp);  
    System.out.println(status);  
    // For update
    emp.setEmpId(9);
    emp.setAge(25);
    dao.update(emp);
        
    // For delete
    dao.deleteEmpById(10);
  }
}

Spring NamedParameterJdbcTemplate with annotations

You can also use component scanning to automatically scan and wire the classes. For that you can use @Repository annotation with your DAO implementation classes and @Autowired annotation to automatically wire dependencies.

In that case your EmployeeDAOImpl will look like this -

import java.util.HashMap;
import java.util.Map;
import org.netjs.dao.EmployeeDAO;
import org.netjs.model.Employee;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.core.namedparam.MapSqlParameterSource;
import org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate;
import org.springframework.jdbc.core.namedparam.SqlParameterSource;
import org.springframework.stereotype.Repository;

@Repository
public class EmployeeDAOImpl implements EmployeeDAO {
  private NamedParameterJdbcTemplate namedJdbcTemplate; 

  final String INSERT_QUERY = "insert into employee (name, age) values (:name, :age)";
  final String UPDATE_QUERY = "update employee set age = :age where id = :id";
  final String DELETE_QUERY = "delete from employee where id = :id";

  @Autowired
  public EmployeeDAOImpl(NamedParameterJdbcTemplate namedJdbcTemplate){
    this.namedJdbcTemplate = namedJdbcTemplate;
  }
    
  @Override
  public int save(Employee employee) {
    // Creating map with all required params
    Map<String, Object> paramMap = new HashMap<String, Object>();
    paramMap.put("name", employee.getEmpName());
    paramMap.put("age", employee.getAge());
    // Passing map containing named params
    return namedJdbcTemplate.update(INSERT_QUERY, paramMap);  
  }

  @Override
  public void update(Employee employee) {
    // Adding params using MapSqlParameterSource class
    SqlParameterSource namedParameters = new MapSqlParameterSource().addValue("age", employee.getAge()).addValue("id", employee.getEmpId());
    int status = namedJdbcTemplate.update(UPDATE_QUERY, namedParameters); 
    if(status != 0){
      System.out.println("Employee data updated for ID " + employee.getEmpId());
    }else{
      System.out.println("No Employee found with ID " + employee.getEmpId());
    }
  }

  @Override
  public void deleteEmpById(int empId) {
    // Adding params using MapSqlParameterSource class
    SqlParameterSource namedParameters = new MapSqlParameterSource("id", empId);
    int status = namedJdbcTemplate.update(DELETE_QUERY, namedParameters);
    if(status != 0){
      System.out.println("Employee data deleted for ID " + empId);
    }else{
      System.out.println("No Employee found with ID " + empId);
    }
  }
}

XML Configuration

XML configuration will also change as you have to provide the base package to scan and you can also comment the bean definition for EmployeeDAO as it will be done automatically.

<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xmlns:context="http://www.springframework.org/schema/context" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-4.0.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd"> <context:component-scan base-package="org.netjs.daoimpl" /> <!-- For reading properties files --> <context:property-placeholder location="classpath:config/db.properties" /> <bean id="namedJdbcTemplate" class="org.springframework.jdbc.core.namedparam.NamedParameterJdbcTemplate"> <constructor-arg ref="dataSource"></constructor-arg> </bean> <!-- <bean id="employeeDAO" class="org.netjs.daoimpl.EmployeeDAOImpl"> <property name="namedJdbcTemplate" ref="namedJdbcTemplate"></property> </bean> --> <bean id="dataSource" class="org.apache.commons.dbcp2.BasicDataSource"> <property name="driverClassName" value = "${db.driverClassName}" /> <property name="url" value = "${db.url}" /> <property name="username" value = "${db.username}" /> <property name="password" value = "${db.password}" /> <property name="initialSize" value = "${pool.initialSize}" /> </bean> </beans>

Now at the time of running the program you can get the EmployeeDAOImpl bean like this-

EmployeeDAO dao=(EmployeeDAO)context.getBean("employeeDAOImpl");  

That's all for this topic Spring NamedParameterJdbcTemplate Insert, Update And Delete Example. If you have any doubt or any suggestions to make please drop a comment. Thanks!

>>>Return to Spring Tutorial Page


Related Topics

  1. Spring JdbcTemplate Select Query Example
  2. Spring NamedParameterJdbcTemplate Select Query Example
  3. Data access in Spring framework
  4. Spring Java Configuration Example Using @Configuration
  5. Spring Profiles With Examples

You may also like-

  1. Spring Setter Based Dependency Injection
  2. Injecting inner bean in Spring
  3. @Resource Annotation in Spring Autowiring
  4. TreeSet in Java With Examples
  5. How Linked List class works internally in Java
  6. Java ReentrantReadWriteLock With Examples
  7. Java Semaphore With Examples
  8. Java Stream API Tutorial

Angular @Input and @Output Example

In the post Angular Example to Render Multiple Rows we saw an example demonstrating the use of @Input decorator in Angular and property binding. In this post we’ll see an example showing the use of both @Input and @Output decorator in Angular.

@Input decorator marks a class field as an input property. The input property is bound to a DOM property in the template. During change detection, Angular automatically updates the data property with the DOM property's value. In our component we want to pass data to the user property thus it is decorated with @Input decorator.

@Output decorator with EvenEmitter is used to emit an event from the component. You’ll have more clarity as we progress through the example.

Steps in Angular @Input and @Output example

The requirement is to show a list of user names. When a user name is clicked details of that particular users are displayed. Screens for the example would be something like this-

First user names are displayed

Angular @Input and @Output decorator

Display user details for the selected User

Angular @Output with EvenEmitter

What is needed

  1. You need a model class for User fields.
  2. There will be one component for showing user names and another component for showing User details. So there will be two child component of app.component and the interaction from parent to child and vice versa will happen using @Input and @Output decorators.

Creating a User class

Create a Type script class user.model.ts to define a User class. If you are aware of MVC (Model View Controller) pattern then this class is the Model. There are 3 fields name, age and joinDate in the User class.

export class User {
  name : string;
  age : number;
  joinDate : Date;
  constructor(name: string, age : number, joinDate : Date) {
    this.name = name;
    this.age = age;
    this.joinDate  = joinDate;
  }
}

Creating user.component class

Create a Type script class user.component.ts with properties decorated with @Input and @Output decorators.

import { 
    Component,
    EventEmitter,
    Input, 
    Output
 } from '@angular/core';
import { User } from './user.model';
@Component({
  selector: 'app-user',
  templateUrl: './user.component.html'
})
export class UserComponent{
  @Input() user: User;
  @Output() onUserSelected: EventEmitter<User>;
  constructor(){
    this.onUserSelected = new EventEmitter();
  }
  userClicked() : void{
    this.onUserSelected.emit(this.user);
  }
}

In this component we want to get data in the user property thus it is decorated with @Input decorator. Because of using @Input decorator with user property Angular uses user as an input binding. So you can say that we’ll pass User instance from parent component app.component.ts to the child component user.component.ts and field marked with @Input decorator gets that user instance.

OnUserSelected property in user.component.ts is decorated with @Output decorator and of type EventEmitter<User> that means it will emit User instance (using emit function) which should be received by the parent component.

Creating user.component.html template

<div class="container">
  <div class="row">
    <div class="col-xs-6">
      <label>Name: </label><span (click)='userClicked()'> {{ user.name }}</span>
    </div>
  </div>
</div>

This template displays user names and you can see there is also an event binding for click event calling the userClicked() function in the .ts class when any user name is selected. In the user.component.ts class we have already seen with in the userClicked() function that particular user instance is emitted.

app.component.ts class

import { Component } from '@angular/core';
import { User } from './user/user.model';
@Component({
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css']
})
export class AppComponent {
  //username : String;
  users: User[];
  currentUser : User;
  constructor(){
    // Adding user instances in the users array
    this.users = [new User('Jack', 56, new Date('2005-03-25')),
                  new User('Lisa', 32, new Date('2012-05-09')),
                  new User('Jayesh', 28, new Date('2014-10-21'))] ;
  }

  showUser(user: User) : void {
    // Setting selected user to currentUser
    this.currentUser = user;
    //console.log('User: ', user );
  }

  // Function used to determine the selected user
  // so that its color can be changed 
  isSelected(user: User): boolean {
    if (!user || !this.currentUser) {
      return false;
    }
    return user.name === this.currentUser.name;
  }
}

In the class there is an array of type User, in the constructor user instances are created and stored in this array.

There is also a showUser(user: User) function, this is the method which stores the emitted user instance (from child component user.component).

isSelected() function determines which user name is selected, this helps in styling the selected user name.

app.component.html template

<div class="container">
  <h3>Click user name to see user details</h3>
  <app-user *ngFor="let user of users" 
      [user]="user"
      (onUserSelected)="showUser($event)"
      [class.alert-primary] = "isSelected(user)">
  </app-user>
</div>

<div class="container">
  <user-data *ngIf="currentUser" [user]="currentUser">
  </user-data>
</div>

ngFor iterates over the User array and each user instance is assigned to a user variable [user]="user", this expression also passes the value stored in user variable to the user property decorated with @Input decorator in user.component.ts class. Just keep in mind that the square brackets are used for input binding.

(onUserSelected)="showUser($event)" is for handling output. You have configured (onUserSelected) output to listen to the event and call function showUser() when data is emitted.

[class.alert-primary] = "isSelected(user)" is used to set css class conditionally based on the bollean values returned by the associated function. If isSelected() function returns true then the alert-primary (from Bootstrap) css class is added.

There is another div section in the template.

<div class="container">
    <user-data *ngIf="currentUser" [user]="currentUser">
    </user-data>
</div>

This is used for displaying user details. Using ngIf it is checked if currentUser has any value or not. If there is any assigned value then only it is assigned to the local variable user which also is an input binding for user property in userdata.component.

userdata.component.ts class

import { 
    Component,
    Input
 } from '@angular/core';
import { User } from './user.model';
@Component({
  selector: 'user-data',
  templateUrl: './userdata.component.html'
})
export class UserDataComponent{
    @Input() user: User;
    constructor(){
    }
}

As you can see in this type script class too there is a user property which is decorated using @Input decorator. This user property gets user data from the second div section of the app.component.html shown above.

userdata.component.html template

<div class="jumbotron">
  <div class="container">
    <h2>User Details</h2>
    <div class="row">
      <div class="col-xs-5 px-3">
        <label>Name: </label> {{ user.name }}      
      </div>
      <div class="col-xs-4 px-3">
        <label>Age: </label> {{ user.age }}
      </div>
      <div class="col-xs-4 px-3">
        <label>Joining Date: </label> {{ user.joinDate | date:'dd/MM/yyyy'}}
      </div>
    </div>
  </div>
</div>

This template shows user details for the selected user. Note that, for date, DatePipe is used to format the date.

Changes in app module to register created components

If you have not created new component using Angular CLI then you need to manually import the components in app.module.ts file.

Add import statements.

import { UserComponent } from './user/user.component';
import { UserDataComponent } from './user/userdata.component';

Add to declarations array within @NgModule decorator.

@NgModule({
  declarations: [
    AppComponent,
    UserComponent,
    UserDataComponent
  ],
  imports: [
 ..
 ..

That's all for this topic Angular @Input and @Output Example. If you have any doubt or any suggestions to make please drop a comment. Thanks!

>>>Return to Angular Tutorial Page


Related Topics

  1. Angular ngClass Directive With Examples
  2. Angular Custom Two-Way Data Binding
  3. Angular Project Structure With File Description
  4. Angular Application Bootstrap Process
  5. Creating New Component in Angular

You may also like-

  1. Angular First App - Hello world Example
  2. Angular One-Way Data Binding Using String Interpolation
  3. Injector Hierarchy and Service Instances in Angular
  4. Angular ngIf Directive With Examples
  5. Java String Interview Questions And Answers
  6. Can we Start The Same Thread Twice in Java
  7. BigDecimal in Java
  8. Sending Email Using Spring Framework Example

Friday, January 12, 2024

Autowiring in Spring Using XML Configuration

Spring framework provides an option to autowire the beans. In that case you don't need to explicitly wire the bean properties (using ref attribute) but Spring will do it automatically by using the "autowire" attribute.

In Spring you can autowire dependencies using XML configuration or use the annotations to autowire the dependencies. This post talks about autowiring in Spring using XML configuration.


Autowiring modes in Spring

Spring provides four kind of autowiring modes (updated as per Spring 4.x where autodetect option has been removed).

  • no- The traditional Spring default. No automagical wiring. Bean references must be defined in the XML file via the <ref/> element (or "ref" attribute). autowire=”default” is same as autowire=”no”

  • byName- Autowiring by name means properties of the autowired bean will be wired by searching for bean with same name/id in the configuration file. If such a bean is found it is injected, properties for which no matching bean is found will remain unwired which may later result in error.

  • byType- Autowiring by type means properties of the autowired bean will be wired by searching for bean whose type is compatible with the property's type. If such a bean is found it is injected, properties for which no matching bean is found will remain unwired which may later result in error.

  • constructor- In this case wiring will be done using the constructor of the autowired bean by looking for the bean whose type is compatible with the constructor argument.

  • autodetect- In case of autodetect auto wiring using constructor will be tried first, if default constructor only is there and autowiring using constructor can't be done then autowiring byType is used. Note that this option was available till Spring 3.x (deprecated) or older versions. In Spring 4.x it is removed and this option is not available anymore. In this post autodetect example is not there.

Autowiring in Spring - XML configuration

First thing to note here is that by default Spring doesn't autowire and you have to provide explicit wiring using ref attribute for the properties or for constructor-args which are to be dependency injected.

Let's see examples of autowiring using XML configuration in Spring with all the autowiring modes as stated above.

Autowiring in Spring using byName

When you are autowiring by name the auto wired bean will look for the bean with the same name/id in the configuration file.

Let's see it with an example-

Here we have a class PayServiceImpl which has a field payment of type IPayment which we have to autowire.

interface IPayService

public interface IPayService {
 void performPayment();
}

PayServiceImpl class

public class PayServiceImpl implements IPayService {
  private IPayment payment;
  private int amount;

  public void performPayment() {
    // calling payment class executePayment method
    payment.executePayment(amount);
  }

  public IPayment getPayment() {
    return payment;
  }


  public void setPayment(IPayment payment) {
    this.payment = payment;
  }

  public int getAmount() {
    return amount;
  }

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

interface IPayment

public interface IPayment {
 void executePayment(int amount);
}

CashPayment class

public class CashPayment implements IPayment{
 public void executePayment(int amount) {
  System.out.println("Perform Cash Payment for amount ... " + amount); 
 }
}

Configuration file

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:context="http://www.springframework.org/schema/context"
    xsi:schemaLocation="http://www.springframework.org/schema/beans 
    http://www.springframework.org/schema/beans/spring-beans-4.0.xsd">
 
 <!-- defining CashPayment bean -->
 <bean id="payment" class="org.netjs.springexp.prog.CashPayment" />
 
 <!-- Defining PayServiceImpl bean and injecting payment bean -->
 <bean id="payServiceBean" class="org.netjs.springexp.prog.PayServiceImpl" autowire="byName">
     <property name="amount" value="20" />
  </bean>
</beans>

Here notice that for the bean PayServiceImpl autowire=byName is used. In that case Spring will see that PayServiceImpl has one property named as payment so it will look for the bean with same name/id in the config file. Since there is a bean with id as payment so that bean will be injected.

You can run it using the following program-

public class App {
  public static void main(String[] args) {
    ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext
      ("appcontext.xml");
    IPayService bean = (IPayService) context.getBean("payServiceBean");
    bean.performPayment();
    context.close();
  }
}

Output

Perform Cash Payment for amount ... 20

Autowiring in Spring using byType

When you are autowring by type the property's type in auto wired bean will be used for searching the bean with the compatible type in the configuration file.

You can use the same example as above only change will be in the configuration file to change the autowire=byType.

<bean id="payServiceBean" class="org.netjs.springexp.prog.PayServiceImpl" autowire="byType">
     <property name="amount" value="20" />
</bean>

In the config file there is a bean of type Payment which matches the type of the payment field in the PayServiceImpl class. Thus autowiring by type will work.

Limitation with autowire="byType"

There is one problem with using autowiring as byType. What if there are more than one bean in the configuration file whose type is compatible with the autowired property. In that case Spring won't be able to decide which bean to use, it will throw an exception instead. To see an example of this problem you need to create one more class which implements IPayment interface. Let's say with CashPayment there is also an option for CreditPayment.

CreditPayment class

public class CreditPayment implements IPayment {
 public void executePayment(int amount) {
  System.out.println("Perform Credit Payment for amount ... " + amount);
 }
}

In the config file also the definition is added.

<!-- defining CreditPayment bean -->
<bean id="creditPayment" class="org.netjs.springexp.prog.CreditPayment" />

Now there are two beans of type IPayment in the config file. In that case if we run the program Spring won't be able to decide which one to inject either CashPayment or CreditPayment so it will throw UnsatisfiedDependencyException instead.

Output

org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 
'payServiceBean' defined in class path resource [appcontext.xml]: Unsatisfied dependency expressed 
through bean property 'payment': : No qualifying bean of type [org.netjs.springexp.prog.IPayment] is defined: 
expected single matching bean but found 2: payment,creditPayment; nested exception is 
org.springframework.beans.factory.NoUniqueBeanDefinitionException: No qualifying bean of type 
[org.netjs.springexp.prog.IPayment] is defined: expected single matching bean but found 2: payment,creditPayment
 at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireByType
 (AbstractAutowireCapableBeanFactory.java:1307)

Solving UnsatisfiedDependencyException with Spring autowiring

To overcome this problem there are two options-

  • primary candidate- Identify a primary candidate for auto wiring bean and set that as primary="true"
    <bean id="payment" class="org.netjs.springexp.prog.CashPayment" primary="true"/>
    
  • Exclude a bean from autowiring- You can exclude a bean from being autowired. For that set the autowire-candidate attribute of <bean> tag to false.
    <bean id="creditPayment" class="org.netjs.springexp.prog.CreditPayment" autowire-candidate="false" />
    

Autowiring in Spring by constructor

Autowiring by constructor is same like byType in this case type of the constructor argument in the auto wired bean is used to search the bean with the same type.

If you change the PayServiceImpl class to have a constructor which has a IPayment type as a parameter.

public class PayServiceImpl implements IPayService {
 private IPayment payment;
 private int amount;
 
 // Constructor
 PayServiceImpl(IPayment payment){
   this.payment = payment;
 }
  
 public void performPayment() {
  // calling payment class executePayment method
  payment.executePayment(amount);
 }

 public int getAmount() {
  return amount;
 }

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

And change the configuration file as-

<bean id="payServiceBean" class="org.netjs.springexp.prog.PayServiceImpl" autowire="constructor">
     <property name="amount" value="20" />
</bean>

default-autowire attribute

If you are using the same autowire attribute with most of the bean in your config file, you can define that autowire attribute as default for all the beans with in the config file. That can be done by adding a default-autowire attribute to the root </beans> element.

<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xmlns:context="http://www.springframework.org/schema/context"
    xsi:schemaLocation="http://www.springframework.org/schema/beans 
    http://www.springframework.org/schema/beans/spring-beans-4.0.xsd" default-autowire="byType">

Here default auto wiring is set to byType which means all the beans in this config file will use auto wiring as byType by default. Note that by default default-autowire is set to none.

You can still set autowire attribute for individual beans which will override the default-autowire attribute.

That's all for this topic Autowiring in Spring Using XML Configuration. If you have any doubt or any suggestions to make please drop a comment. Thanks!

>>>Return to Spring Tutorial Page


Related Topics

  1. Autowiring in Spring Using @Autowired and @Inject Annotations
  2. Spring Component Scan to Automatically Discover Beans
  3. Spring Java Configuration Example Using @Configuration
  4. @Conditional Annotation in Spring
  5. Circular Dependency in Spring Framework

You may also like-

  1. Injecting Inner Bean in Spring
  2. Data Access in Spring Framework
  3. Creating a Maven project in Eclipse
  4. static Keyword in Java With Examples
  5. Difference between ArrayList and LinkedList in Java
  6. LinkedHashSet in Java With Examples
  7. Lambda Expression Examples in Java
  8. Compress And Decompress File Using GZIP Format in Java