我已经写了这样的代码,但是它给出了例外。实际上我想生成一个随机的value.save到数据库并将其返回给用户
import java.math.BigInteger;
import java.security.SecureRandom;
public static String recoverpassword(String uid,String ans) {
try {
verifyans.setString(1,uid);
verifyans.setString(2,ans);
ResultSet resultSet = verifyans.executeQuery();
if (resultSet.next()) {
SecureRandom random = new SecureRandom();
String newpass = new BigInteger(130, random).toString(32);
resetpass.setString(1,newpass);
resetpass.setString(2,uid);
resetpass.executeUpdate();
return newpass;
} else {
return "xxx";
}
} catch(Exception e) {
System.out.println("exception" +e);
e.printStackTrace();
return "xxx";
}
}
我得到空指针异常,如:
com.ibm.lims.Users@1d193c9]
exceptionjava.lang.NullPointerException
java.lang.NullPointerException
at org.tranql.connector.jdbc.ConnectionHandle.connectionError(ConnectionHandle.java:103)
at org.tranql.connector.jdbc.PreparedStatementHandle.executeUpdate(PreparedStatementHandle.java:105)
at com.ibm.lims.LimsHandler.recoverpassword(LimsHandler.java:940)
at org.apache.jsp.recoverpasswordresult_jsp._jspService(recoverpasswordresult_jsp.java:78)
at org.apache.jasper.runtime.HttpJspBase.service(HttpJspBase.java:70)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:806)
at org.apache.jasper.servlet.JspServletWrapper.service(JspServletWrapper.java:369)
at org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:342)
at org.apache.jasper.servlet.JspServlet.service(JspServlet.java:267)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:806)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:233)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191)
at org.apache.geronimo.tomcat.valve.DefaultSubjectValve.invoke(DefaultSubjectValve.java:56)
at org.apache.geronimo.tomcat.GeronimoStandardContext$SystemMethodValve.invoke(GeronimoStandardContext.java:406)
at org.apache.geronimo.tomcat.valve.GeronimoBeforeAfterValve.invoke(GeronimoBeforeAfterValve.java:47)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:128)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109)
at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:567)
at org.apache.geronimo.tomcat.valve.ThreadCleanerValve.invoke(ThreadCleanerValve.java:40)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:293)
at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:849)
at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:583)
at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:454)
at java.lang.Thread.run(Unknown Source)
嘿,我测试了删除那些securerandom类call.i的代码,只是在双引号中传递一个字符串值,如“sample”,并且它有效。表示问题在于securerandom类。我认为值在字符串值字段中以整数形式出现,因此数据库服务器正在发送异常。 plz给我一些代码来生成随机字符串 -
答案 0 :(得分:1)
在这里发挥作用有几个问题。
首先是NPE的根本原因:
java.lang.NullPointerException
at org.tranql.connector.jdbc.ConnectionHandle.connectionError(ConnectionHandle.java:103)
这显然是TranQL JDBC驱动程序中的一个错误。在ConnectionHandle#connectionError()
方法期间有一些意外的空指针,因此它无法处理实际的连接错误。要解决这个特定的问题(这样你就不会得到一个NPE,而是一个更清晰且特定于驱动程序的SQLException
),要么升级驱动程序,要么用更合适的替换它(我从未听说过) TranQL之前)。
关于整个问题的真正原因;从堆栈跟踪判断,看起来没有活动连接的方法。从非线程安全代码判断,看起来之前已经使用过preparedStatement,并且以某种方式隐式地从连接中关闭/分离。
至少它可以归结为你所拥有的非线程安全和非资源漏洞安全的JDBC代码。正常的JDBC习惯用法是,您应始终获取和关闭最短范围中的Connection
,PreparedStatement
和ResultSet
。因此,已经在同一个(非静态!)方法块内部。永远不应在线程之间共享语句和结果集。连接可以,但你不应该自己动手。为此使用合适的连接池API,例如C3P0。
这是一个根据理想的JDBC习语的例子:
public String recoverPassword(Long userId, String answer) throws SQLException {
Connection connection = null;
PreparedStatement verifyAnswer = null;
ResultSet resultSet = null;
String newPassword = null;
PreparedStatement resetPassword = null;
try {
connection = database.getConnection();
verifyAnswer = connection.prepareStatement(SQL_VERIFY_ANSWER);
verifyAnswer.setLong(1, userId);
verifyAnswer.setString(2, answer);
resultSet = statement.executeQuery();
if (resultSet.next()) {
SecureRandom random = new SecureRandom();
newPassword = new BigInteger(130, random).toString(32);
resetPassword = connection.prepareStatement(SQL_RESET_PASSWORD);
resetPassword.setString(1, newPassword);
resetPassword.setLong(2, userId);
resetPassword.executeUpdate();
}
} finally {
// Always free resources in reversed order.
if (resetPassword != null) try { resetPassword.close(); } catch (SQLException logOrIgnore) {}
if (resultSet != null) try { resultSet.close(); } catch (SQLException logOrIgnore) {}
if (verifyAnswer != null) try { verifyAnswer.close(); } catch (SQLException logOrIgnore) {}
if (connection != null) try { connection.close(); } catch (SQLException logOrIgnore) {}
}
return newPassword;
}
请注意,我暗示userId
是Long
。您真的不希望在代码和数据模型中都有String
ID。您可以找到有关编写可靠JDBC代码here的更多信息,提示和其他示例。
那说,堆栈跟踪的以下部分
at com.ibm.lims.LimsHandler.recoverpassword(LimsHandler.java:940)
at org.apache.jsp.recoverpasswordresult_jsp._jspService(recoverpasswordresult_jsp.java:78)
意味着您使用老式的scriptlet在JSP文件中编写原始Java代码。为了节省将来的维护和调试问题,我强烈建议您不要这样做,但只需使用Servlet类。
答案 1 :(得分:0)
您是否尝试使用调试程序逐步完成此操作?
从发布的代码看起来似乎uid在方法的顶部传入as null。
您也不应该将密码作为纯文本存储在数据库中,而应该使用密码的盐渍单向散列。
答案 2 :(得分:0)
您遇到的问题与随机数字无关。您可能会在您尝试执行的sql请求中查看数据库连接参数,但是请更具体地说“我正在获取NPE”不是一个问题:)