Funny coincidence, I just created the solution for your problem (but in PHPbut in PHP). The common thing here is the one-time use of a prepared statement, the difference is in the query string and arguments, so what you need is a function that accepts a query string, an argument determining what execution function to use (executeQuery() or executeUpdate()) and the parameters for the query:
// note: QueryType is an enum you should define
public static ResultSet query(String sql, QueryType queryType, Object... queryArgs){
// ...
}
Include the try-catch blocks in this function too of course, and return null when according to queryType there should be no results.
Note: I have no experience with database interaction with Java, so if there are only 2 different statement execution functions then you can use a boolean argument instead of the enum QueryType.
Then your code could look like this:
public static boolean checkLogin(String username, String password) {
String sql = "select * from users where username = ? and password = ? ";
ResultSet result = query(sql, QueryType.RETURN_RESULT, username, password);
return result.next(); // true if User exists
}
A note about your query string: I find it more convenient to use CAPS for keywords and lowercase text for names, it highlights the structure of the query.