登录表单 Java MySQL 在 intellij 中失败



我已经制作了一个与MySQL连接连接的javaFx登录表单工作正常,但是当我尝试登录时,我得到了错误的名称和密码,我将提供我的代码和MySQL的屏幕截图,因此任何试图提供帮助的人都不会感到困惑

package sample;
import javafx.application.Application;
import javafx.geometry.Insets;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.control.*;
import javafx.scene.layout.BorderPane;
import javafx.scene.layout.HBox;
import javafx.scene.layout.VBox;
import javafx.scene.paint.Color;
import javafx.scene.shape.Rectangle;
import javafx.scene.text.Font;
import javafx.stage.Stage;

import java.sql.*;
import java.util.logging.Level;
import java.util.logging.Logger;
public class DataBaseProject1 extends Application {
Connection conn;
PreparedStatement pst = null;
ResultSet rs = null;
@Override
public void start(Stage primaryStage) throws Exception
{
//GUIS a = new GUIS();
//a.createConnection();
//a.display();
DataBaseProject1 d = new DataBaseProject1();
d.createConnection();
primaryStage.setTitle("Retrive Database Values Into CheckBox");
//primaryStage.getIcons().add(new Image("file:user-icon.png"));
BorderPane layout = new BorderPane();
Scene newscene = new Scene(layout, 1200, 700, Color.rgb(0, 0, 0, 0));
Group root = new Group();
Scene scene = new Scene(root, 320, 200, Color.rgb(0, 0, 0, 0));
scene.getStylesheets().add(getClass().getResource("Style.css").toExternalForm());
Color foreground = Color.rgb(255, 255, 255, 0.9);
//Rectangila Background
Rectangle background = new Rectangle(320, 250);
background.setX(0);
background.setY(0);
background.setArcHeight(15);
background.setArcWidth(15);
background.setFill(Color.rgb(0 ,0 , 0, 0.55));
background.setStroke(foreground);
background.setStrokeWidth(1.5);
VBox vbox = new VBox(5);
vbox.setPadding(new Insets(10,0,0,10));
Label label = new Label("Label");
//label.setTextFill(Color.WHITESMOKE);
label.setFont(new Font("SanSerif", 20));
TextField username = new TextField();
username.setFont(Font.font("SanSerif", 20));
username.setPromptText("Username");
username.getStyleClass().add("field-background");
PasswordField password =new PasswordField();
password.setFont(Font.font("SanSerif", 20));
password.setPromptText("Password");
password.getStyleClass().add("field-background");
Button btn = new Button("Login");
btn.setFont(Font.font("SanSerif", 15));
btn.setOnAction(e ->{
try{
String user = username.getText();
String pass = password.getText();
String query = "SELECT * FROM userdatabasetable Where UserName = " + "'" + user + "'" + " AND Password = " + "'" +pass + "'" + " ";
rs = pst.executeQuery(query);
if(rs.next()){
label.setText("Login Successful");
primaryStage.setScene(newscene);
primaryStage.show();
}else{
label.setText("Login Failed");
}
username.clear();
password.clear();
pst.close();
rs.close();
}catch(Exception e1){
label.setText("SQL Error");
System.out.println("Wrong UserName Or Password");
//System.err.println(e1);
}
});
vbox.getChildren().addAll(label, username, password, btn);
root.getChildren().addAll(background, vbox);
primaryStage.setScene(scene);
primaryStage.show();
}
public static void main(String[] args)
{
launch(args);
}
Connection createConnection ()
{
try
{
//Class.forName("com.mysql.jdbc.Driver");
Class.forName("com.mysql.cj.jdbc.Driver");
Connection con = DriverManager.getConnection("jdbc:mysql://localhost:3306/UserDataBase","yusof","1234");
System.out.println("DataBase Connected Successfully");
//con.close();
}
catch (ClassNotFoundException | SQLException ex)
{
Logger.getLogger(DataBaseProject1.class.getName()).log(Level.SEVERE, null, ex);
}
return null;
}
}

输出:

数据库连接成功 错误的用户名或密码

MySQL 的屏幕截图:在此处输入图像描述

您没有初始化 PreparedStatement 变量,只是用空值声明PreparedStatement pst = null;

因此,当语句rs = pst.executeQuery(query);执行时,会抛出错误。 在您的 catch 块中,您只写了System.out.println("Wrong UserName Or Password");. 所以你收到错误"错误的用户名或密码">

但实际错误是您在执行查询之前没有初始化 PreparedStatementpst变量。

因此,初始化pst变量以解决您的问题

如果您想知道如何使用预准备语句,那么您可以从此处查看示例

我已经解决了您代码的所有问题,因此您只需复制并粘贴以下代码,希望对您有所帮助

package sample;
import javafx.application.Application;
import javafx.geometry.Insets;
import javafx.scene.Group;
import javafx.scene.Scene;
import javafx.scene.control.*;
import javafx.scene.layout.BorderPane;
import javafx.scene.layout.HBox;
import javafx.scene.layout.VBox;
import javafx.scene.paint.Color;
import javafx.scene.shape.Rectangle;
import javafx.scene.text.Font;
import javafx.stage.Stage;

import java.sql.*;
import java.util.logging.Level;
import java.util.logging.Logger;
public class DataBaseProject1 extends Application {
Connection conn;
PreparedStatement pst = null;
ResultSet rs = null;
@Override
public void start(Stage primaryStage) throws Exception
{
//GUIS a = new GUIS();
//a.createConnection();
//a.display();
DataBaseProject1 d = new DataBaseProject1();
d.createConnection();
primaryStage.setTitle("Retrive Database Values Into CheckBox");
//primaryStage.getIcons().add(new Image("file:user-icon.png"));
BorderPane layout = new BorderPane();
Scene newscene = new Scene(layout, 1200, 700, Color.rgb(0, 0, 0, 0));
Group root = new Group();
Scene scene = new Scene(root, 320, 200, Color.rgb(0, 0, 0, 0));
scene.getStylesheets().add(getClass().getResource("Style.css").toExternalForm());
Color foreground = Color.rgb(255, 255, 255, 0.9);
//Rectangila Background
Rectangle background = new Rectangle(320, 250);
background.setX(0);
background.setY(0);
background.setArcHeight(15);
background.setArcWidth(15);
background.setFill(Color.rgb(0 ,0 , 0, 0.55));
background.setStroke(foreground);
background.setStrokeWidth(1.5);
VBox vbox = new VBox(5);
vbox.setPadding(new Insets(10,0,0,10));
Label label = new Label("Label");
//label.setTextFill(Color.WHITESMOKE);
label.setFont(new Font("SanSerif", 20));
TextField username = new TextField();
username.setFont(Font.font("SanSerif", 20));
username.setPromptText("Username");
username.getStyleClass().add("field-background");
PasswordField password =new PasswordField();
password.setFont(Font.font("SanSerif", 20));
password.setPromptText("Password");
password.getStyleClass().add("field-background");
Button btn = new Button("Login");
btn.setFont(Font.font("SanSerif", 15));
btn.setOnAction(e ->{
try{
String user = username.getText();
String pass = password.getText();
String query = "SELECT * FROM userdatabasetable Where UserName = " + "'" + user + "'" + " AND Password = " + "'" +pass + "'" + " ";
d.pst=d.conn.prepareStatement(query);
rs = d.pst.executeQuery(query);
if(rs.next()){
label.setText("Login Successful");
primaryStage.setScene(newscene);
primaryStage.show();
}else{
label.setText("Login Failed");
}
username.clear();
password.clear();
d.pst.close();
rs.close();
}catch(Exception e1){
label.setText("SQL Error");
System.out.println("Wrong UserName Or Password");
//System.err.println(e1);
// e1.printStackTrace();
}
});
vbox.getChildren().addAll(label, username, password, btn);
root.getChildren().addAll(background, vbox);
primaryStage.setScene(scene);
primaryStage.show();
}
public static void main(String[] args)
{
launch(args);
}
Connection createConnection ()
{
try
{
//Class.forName("com.mysql.jdbc.Driver");
Class.forName("com.mysql.cj.jdbc.Driver");
conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/UserDataBase","yusof","1234");
System.out.println("DataBase Connected Successfully");
//con.close();
}
catch (ClassNotFoundException | SQLException ex)
{
Logger.getLogger(DataBaseProject1.class.getName()).log(Level.SEVERE, null, ex);
}
return null;
}
}

我相信你还有很长的路要走。您不仅缺少访问视图和数据库之间的基本逻辑分离,而且还:

  1. 您这里有一个可怕的SQL注入漏洞:String query = "SELECT * FROM userdatabasetable Where UserName = " + "'" + user + "'" + " AND Password = " + "'" +pass + "'" + " ";
  2. 您没有使用 scrypt、bcrypt 或类似方法对数据库中的密码进行哈希处理。
  3. 正如其他人提到的,您的错误处理非常糟糕。

对不起,这些严厉的话,但第 1 点和第 2 点是二十一世纪的致命罪过。请使用 https://cheatsheetseries.owasp.org/cheatsheets/SQL_Injection_Prevention_Cheat_Sheet.html 和 https://cheatsheetseries.owasp.org/cheatsheets/Password_Storage_Cheat_Sheet.html 修复它们。

另外,请在漏洞修复后更新您的代码,这样我们就不会有易受攻击的代码示例供某人复制和重用。

最新更新