Reputation: 565
I am creating android application which sending some data to database using Spring application also create by me.
Method which I am using to save data is this:
public void save(LinkedHashMap<String, Object> dataCollected) {
String sql = "INSERT INTO sys001.lm.bottle_neck_reject ("
+ "\n col_1, col_2, col_3, col_4,"
+ "\n col_5, col_6, col_7, col_8, col_9,"
+ "\n col_10, col_11, col_12,"
+ "\n col_13)"
+ "\n VALUES (?, ?, ?, ?,"
+ "\n ?, ?, ?, convert(datetime, ? + ' ' + ?, 103), ?,"
+ "\n ?, ?, ?, ?)";
dataCollected.forEach((key, value) -> {
System.out.println(key + " > " + value); // output: key_one > value_one
});
try(Connection conn = getConnection();
PreparedStatement saveStatement = conn.prepareStatement(sql)){
saveStatement.setString(1, (String) dataCollected.get("key_one"));
saveStatement.setString(2, "WH"); // this value are saved
saveStatement.setString(3, "PC"); // this value are saved
saveStatement.setString(4, (String) dataCollected.get("key_two"));
saveStatement.setString(5, "UN"); // this value are saved
saveStatement.setString(6, (String) dataCollected.get("key_three"));
saveStatement.setString(7, (String) dataCollected.get("key_four"));
saveStatement.setString(8, (String) dataCollected.get("date"));
saveStatement.setString(9, (String) dataCollected.get("time"));
saveStatement.setString(10, (String) dataCollected.get("key_five"));
saveStatement.setString(11, (String) dataCollected.get("key_six"));
saveStatement.setString(12, (String) dataCollected.get("key_seven"));
saveStatement.setString(13, (String) dataCollected.get("key_eight"));
saveStatement.setString(14, (String) dataCollected.get("key_nine"));
saveStatement.executeUpdate();
} catch (SQLException e) {
e.printStackTrace();
}
}
Problem is that when I am using this method in forEach
loop I can properly see and get key
and values
but when I am sending query to database, record is create but all values are null
except position 2, 3 and 5 ('WH', 'PC', 'UN') those are created properly.
Can anyone let me know what is wrong with my code? Or maybe is some other problem, not related to the code? I have no clue, any advice will be appreciated.
Upvotes: 0
Views: 881
Reputation: 103617
This code properly 'closes' the connection after executing the UPDATE call, which is why you're witnessing a new row.
The fact that you observe the values (almost) all being NULL can only mean one thing.
dataCollected.get("key_one")
is returning null. You're printing the values in the input map, and you do see 'key_one', however.
Perhaps the key is " key_one"
(note the space!), or otherwise something that looks (almost?) exactly like "key_one" but isn't equal to "key_one". There are symbols that look exactly like these letters in most fonts but aren't that letter. For example, the o
has a boatload of symbols that look very very similarly. There's also zero-width space characters and other creative whitespace that you won't see in a println statement.
Here's how to debug your code:
Use a breakpoint, or just add a sysout statement, to print, right at the very top of the method before you even open any db connections, the result of that get call: System.out.println(dataCollected.get("key_one"));
- that should be null, which indicates beyond any doubt that regardless of what you think you're seeing with that foreach loop to print keys, "key_one"
is not in that map.
Then, to see what key_one-esque key IS in the map, loop through each key in it and print the char values of each symbol:
public void debugString(String in) {
System.out.print(in);
System.out.print(": ");
for (char c : in.toCharArray()) {
System.out.print((int) c);
System.out.print(" ");
}
System.out.println();
}
... and then in your save method, at the top:
debugString("key_one"); // see what a 'real' key_one looks like
for (String key : dataCollected.keySet()) {
debugString(key); // now debug-print each key
}
Likely this will show the problem by giving a different sequence of numbers. Find the difference, grab an ascii chart or unicode table, and look up what's wonky.
For example, if the first print shows that the 4th number is 95
but the key has as 4th number 818
, then the key is using this alternate underscore character that will look exactly, or almost exactly, like an underscore, but it's not the same character, therefore, wouldn't be found by .get("key_one")
.
Perhaps that is an instance of some subclass of LinkedHashMap (or not java.util.LinkedHashMap
which is broken. Check by printing: System.out.println(dataCollected.getClass())
. This should print java.util.LinkedHashMap
- if it does not, this is worth investigating further.
It is possible, but tricky, to use hacks and reflection to make a string (which is normally immutable) contain different characters, which you'd witness when you try to print it. There's no reason to ever do such a thing except as an intentional exercise to mess up code. If that's the case, find the prankster and tell them to cut it out.
Upvotes: 2