Interview question
What is the difference between Statement, PreparedStatement, and CallableStatement? Statement, PreparedStatement, और CallableStatement में क्या अंतर है?
Answer
| Interface | Purpose | SQL injection safe? | Performance |
|---|---|---|---|
| Statement | Static SQL queries, no parameters | No - vulnerable if concatenating input | Compiled every execution |
| PreparedStatement | Parameterized SQL with placeholders (?) | Yes - parameters are never treated as SQL | Precompiled, faster on repeated execution |
| CallableStatement | Executing stored procedures | Yes (same as PreparedStatement) | Precompiled |
// Statement - VULNERABLE to SQL injection if using user input
Statement stmt = conn.createStatement();
String email = userInput; // e.g. "' OR '1'='1"
ResultSet rs = stmt.executeQuery('SELECT * FROM users WHERE email = \'' + email + '\'');
// A malicious input can alter the query logic entirely - NEVER do this
// PreparedStatement - SAFE, parameters bound separately from SQL
String sql = 'SELECT * FROM users WHERE email = ?';
PreparedStatement pstmt = conn.prepareStatement(sql);
pstmt.setString(1, email); // treated strictly as data, never as SQL code
ResultSet rs2 = pstmt.executeQuery();
// PreparedStatement for INSERT/UPDATE
PreparedStatement insertStmt = conn.prepareStatement(
'INSERT INTO users (name, email) VALUES (?, ?)');
insertStmt.setString(1, 'John');
insertStmt.setString(2, 'john@example.com');
insertStmt.executeUpdate();
// CallableStatement - for calling a stored procedure
CallableStatement cstmt = conn.prepareCall('{call getUserById(?)}');
cstmt.setInt(1, 5);
ResultSet rs3 = cstmt.executeQuery();
// Stored procedure with an OUT parameter
CallableStatement cstmt2 = conn.prepareCall('{call getUserCount(?)}');
cstmt2.registerOutParameter(1, java.sql.Types.INTEGER);
cstmt2.execute();
int count = cstmt2.getInt(1);| Interface | उद्देश्य | SQL injection safe? | Performance |
|---|---|---|---|
| Statement | Static SQL, parameters नहीं | नहीं | हर बार compile |
| PreparedStatement | Parameterized SQL (?) | हाँ | Precompiled, तेज़ |
| CallableStatement | Stored procedures | हाँ | Precompiled |
// Statement - SQL injection के लिए VULNERABLE
Statement stmt = conn.createStatement();
String email = userInput;
ResultSet rs = stmt.executeQuery('SELECT * FROM users WHERE email = \'' + email + '\'');
// कभी न करें
// PreparedStatement - SAFE
String sql = 'SELECT * FROM users WHERE email = ?';
PreparedStatement pstmt = conn.prepareStatement(sql);
pstmt.setString(1, email);
ResultSet rs2 = pstmt.executeQuery();
PreparedStatement insertStmt = conn.prepareStatement(
'INSERT INTO users (name, email) VALUES (?, ?)');
insertStmt.setString(1, 'John');
insertStmt.setString(2, 'john@example.com');
insertStmt.executeUpdate();
// CallableStatement - stored procedure के लिए
CallableStatement cstmt = conn.prepareCall('{call getUserById(?)}');
cstmt.setInt(1, 5);
ResultSet rs3 = cstmt.executeQuery();Was this answer clear?