master
xzk 2 months ago
parent f601e0874b
commit aa5a45fddd

@ -33,6 +33,9 @@
<connection id="5a7f45ca-8eb4-45e2-b6e9-260baed6fedc" />
<connection id="9606bbe3-974e-4ddd-b9d9-242662729730" />
</component>
<component name="DBNavigator.Project.ExecutionManager">
<retain-sticky-names value="false" />
</component>
<component name="DBNavigator.Project.ObjectQuickFilterManager">
<last-used-operator value="EQUAL" />
<filters />

Binary file not shown.

@ -2,6 +2,10 @@ import java.sql.*;
import org.junit.Test;
import java.sql.*;
import org.junit.Test;
public class DML {
// 使用相对路径
@ -91,4 +95,33 @@ public class DML {
} //删除指定数据表
@Test
public void createGoodsTable() {
try (Connection conn = DriverManager.getConnection(URL);
Statement stmt = conn.createStatement()) {
// 创建货物信息表
String sql = "CREATE TABLE IF NOT EXISTS goods (" +
"id TEXT PRIMARY KEY NOT NULL," +
"name TEXT NOT NULL," +
"specification TEXT," +
"unit TEXT," +
"price REAL," +
"category TEXT," +
"quantity INTEGER," +
"remark TEXT," +
"inbound_time TIMESTAMP," +
"operator TEXT," +
"supplier TEXT" +
");";
stmt.execute(sql);
System.out.println("货物信息表创建成功");
} catch (Exception e) {
e.printStackTrace();
}
}
}

@ -1,6 +1,7 @@
package model;
import java.sql.*;
import java.time.format.DateTimeFormatter;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
@ -37,7 +38,7 @@ public class DataManager {
private void loadDataFromDatabase() {
String url = "jdbc:sqlite:db/dbuml.db3";
try (Connection conn = DriverManager.getConnection(url)) {
// 加载商品数据
loadGoods(conn);
@ -51,42 +52,45 @@ public class DataManager {
}
private void loadGoods(Connection conn) throws SQLException {
String sql = "SELECT * FROM goods";
String sql = "SELECT * FROM inbound_records";
try (Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery(sql)) {
while (rs.next()) {
String id = rs.getString("id");
String name = rs.getString("name");
String specification = rs.getString("specification");
String unit = rs.getString("unit");
double price = rs.getDouble("price");
String category = rs.getString("category");
String id = rs.getString("goods_id");
String name = rs.getString("goods_id"); // Assuming goods_id is also the name in inbound_records
String specification = ""; // Not available in inbound_records
String unit = ""; // Not available in inbound_records
double price = 0; // Not available in inbound_records
String category = ""; // Not available in inbound_records
String remark = rs.getString("remark");
Goods goods = new Goods(id, name, specification, unit, price, category, 0, remark);
Goods goods = new Goods(id, name, 0, remark);
goodsMap.put(id, goods);
}
}
}
private void loadSuppliers(Connection conn) throws SQLException {
String sql = "SELECT supplier_name FROM suppliers";
String sql = "SELECT supplier FROM inbound_records";
try (Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery(sql)) {
while (rs.next()) {
suppliers.add(rs.getString("supplier_name"));
String supplier = rs.getString("supplier");
if (!suppliers.contains(supplier)) {
suppliers.add(supplier);
}
}
}
}
private void loadInventory(Connection conn) throws SQLException {
String sql = "SELECT goods_id, quantity FROM inventory";
String sql = "SELECT goods_id, SUM(quantity) as total_quantity FROM inbound_records GROUP BY goods_id";
try (Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery(sql)) {
while (rs.next()) {
String goodsId = rs.getString("goods_id");
int quantity = rs.getInt("quantity");
inventory.put(goodsId, quantity);
int totalQuantity = rs.getInt("total_quantity");
inventory.put(goodsId, totalQuantity);
}
}
}
@ -104,20 +108,19 @@ public class DataManager {
try (Connection conn = DriverManager.getConnection(url);
Statement stmt = conn.createStatement()) {
// 使用与InboundView相同的表结构
String sql = "SELECT " +
" goods_id, " +
" goods_id as goods_name, " + // 因为InboundView中使用goods_id存储的是货物名称
" SUM(quantity) as total_quantity, " +
" GROUP_CONCAT(DISTINCT supplier) as supplier, " +
" CASE " +
" WHEN SUM(quantity) < 10 THEN '库存偏低' " +
" ELSE '库存正常' " +
" END as remark " +
"FROM warehouse " +
"GROUP BY goods_id " +
"ORDER BY goods_id";
" goods_id, " +
" goods_id as goods_name, " +
" SUM(quantity) as total_quantity, " +
" GROUP_CONCAT(DISTINCT supplier) as supplier, " +
" CASE " +
" WHEN SUM(quantity) < 10 THEN '库存偏低' " +
" ELSE '库存正常' " +
" END as remark " +
"FROM warehouse " +
"GROUP BY goods_id " +
"ORDER BY goods_id";
ResultSet rs = stmt.executeQuery(sql);
while (rs.next()) {
@ -163,8 +166,8 @@ public class DataManager {
public void addOperationLog(String operationType, String operationTarget, String operator, String details) {
String id = "LOG" + System.currentTimeMillis();
OperationLog log = new OperationLog(id, operationType, operationTarget,
operator, LocalDateTime.now(), details);
OperationLog log = new OperationLog(id, operationType, operationTarget,
operator, LocalDateTime.now(), details);
operationLogs.add(log);
}
@ -174,17 +177,80 @@ public class DataManager {
public List<OperationLog> getFilteredOperationLogs(LocalDateTime startDate, LocalDateTime endDate, String operationType) {
return operationLogs.stream()
.filter(log -> {
boolean timeMatch = true;
if (startDate != null && endDate != null) {
timeMatch = !log.getOperationTime().isBefore(startDate) &&
!log.getOperationTime().isAfter(endDate);
}
boolean typeMatch = "全部".equals(operationType) ||
operationType.equals(log.getOperationType());
return timeMatch && typeMatch;
})
.collect(Collectors.toList());
.filter(log -> {
boolean timeMatch = true;
if (startDate != null && endDate != null) {
timeMatch = !log.getOperationTime().isBefore(startDate) &&
!log.getOperationTime().isAfter(endDate);
}
boolean typeMatch = "全部".equals(operationType) ||
operationType.equals(log.getOperationType());
return timeMatch && typeMatch;
})
.collect(Collectors.toList());
}
public void addGoodsToDatabase(Goods goods) {
String url = "jdbc:sqlite:db/dbuml.db3";
String sql = "INSERT INTO warehouse (id, goods_id, quantity, supplier, inbound_time, operator, remark) " +
"VALUES (?, ?, ?, ?, ?, ?, ?)";
try (Connection conn = DriverManager.getConnection(url);
PreparedStatement pstmt = conn.prepareStatement(sql)) {
// Generate a unique ID for each record
String recordId = "REC" + System.currentTimeMillis();
pstmt.setString(1, recordId);
pstmt.setString(2, goods.getId());
pstmt.setInt(3, goods.getQuantity());
pstmt.setString(4, goods.getSupplier());
// Format LocalDateTime to ISO_LOCAL_DATE_TIME format
DateTimeFormatter formatter = DateTimeFormatter.ISO_LOCAL_DATE_TIME;
String inboundTimeString = goods.getInboundTime().format(formatter);
pstmt.setString(5, inboundTimeString);
pstmt.setString(6, goods.getOperator());
pstmt.setString(7, goods.getRemark());
pstmt.executeUpdate();
// Synchronize memory data
addGoods(goods);
// Add operation log
addOperationLog("新增", goods.getId(), "当前用户", "新增货物: " + goods.getName());
} catch (SQLException e) {
e.printStackTrace();
showAlert("错误", "添加货物失败:" + e.getMessage());
}
}
public void updateGoodsInDatabase(Goods goods) {
String url = "jdbc:sqlite:db/dbuml.db3";
String sql = "UPDATE warehouse SET quantity = ?, supplier = ?, inbound_time = ?, operator = ?, remark = ? WHERE goods_id = ? ORDER BY inbound_time DESC LIMIT 1";
try (Connection conn = DriverManager.getConnection(url);
PreparedStatement pstmt = conn.prepareStatement(sql)) {
pstmt.setInt(1, goods.getQuantity());
pstmt.setString(2, goods.getSupplier());
pstmt.setString(3, goods.getInboundTime().toString());
pstmt.setString(4, goods.getOperator());
pstmt.setString(5, goods.getRemark());
pstmt.setString(6, goods.getId());
pstmt.executeUpdate();
addOperationLog("更新", goods.getId(), "当前用户", "更新货物: " + goods.getName());
} catch (SQLException e) {
e.printStackTrace();
showAlert("错误", "更新货物失败:" + e.getMessage());
}
}
private void showAlert(String , String s) {
}
public List<String> getAllCategories() {

@ -1,6 +1,10 @@
package model;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
public class Goods {
private String id;
@ -53,6 +57,48 @@ public class Goods {
this.supplier = "";
}
public static void insertIntoDatabase(Connection conn, Goods goods) throws SQLException {
String sql = "INSERT INTO goods (id, name, specification, unit, price, category, quantity, remark, inbound_time, operator, supplier) " +
"VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)";
try (PreparedStatement pstmt = conn.prepareStatement(sql)) {
try {
pstmt.setString(1, goods.getId());
} catch (SQLException e) {
throw new RuntimeException(e);
}
pstmt.setString(2, goods.getName());
pstmt.setString(3, goods.getSpecification());
pstmt.setString(4, goods.getUnit());
pstmt.setDouble(5, goods.getPrice());
pstmt.setString(6, goods.getCategory());
pstmt.setInt(7, goods.getQuantity());
pstmt.setString(8, goods.getRemark());
pstmt.setString(9, goods.getInboundTime() != null ? goods.getInboundTime().format(DateTimeFormatter.ISO_LOCAL_DATE_TIME) : null);
pstmt.setString(10, goods.getOperator());
pstmt.setString(11, goods.getSupplier());
pstmt.executeUpdate();
}
}
public static void updateInDatabase(Connection conn, Goods goods) throws SQLException {
String sql = "UPDATE goods SET name = ?, specification = ?, unit = ?, price = ?, category = ?, " +
"quantity = ?, remark = ?, inbound_time = ?, operator = ?, supplier = ? WHERE id = ?";
try (PreparedStatement pstmt = conn.prepareStatement(sql)) {
pstmt.setString(1, goods.getName());
pstmt.setString(2, goods.getSpecification());
pstmt.setString(3, goods.getUnit());
pstmt.setDouble(4, goods.getPrice());
pstmt.setString(5, goods.getCategory());
pstmt.setInt(6, goods.getQuantity());
pstmt.setString(7, goods.getRemark());
pstmt.setString(8, goods.getInboundTime() != null ? goods.getInboundTime().format(DateTimeFormatter.ISO_LOCAL_DATE_TIME) : null);
pstmt.setString(9, goods.getOperator());
pstmt.setString(10, goods.getSupplier());
pstmt.setString(11, goods.getId());
pstmt.executeUpdate();
}
}
// Getters and Setters
public String getId() { return id; }
public void setId(String id) { this.id = id; }

@ -8,20 +8,20 @@ import javafx.scene.layout.*;
import javafx.scene.control.cell.PropertyValueFactory;
import model.DataManager;
import model.Goods;
import model.InventoryManager;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.Statement;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.ArrayList;
import java.util.List;
public class GoodsManagementView extends BorderPane {
private TextField idField;
private TextField nameField;
private TextField specificationField;
private TextField unitField;
private TextField priceField;
private TextField categoryField;
private TextField quantityField;
private TableView<Goods> tableView;
@ -64,31 +64,17 @@ public class GoodsManagementView extends BorderPane {
Label idLabel = new Label("货物ID");
idField = new TextField();
idField.setPromptText("请输入货物ID");
idField.setEditable(false); // ID 不可编辑
Label nameLabel = new Label("货物名称:");
nameField = new TextField();
nameField.setPromptText("请输入货物名称");
Label specificationLabel = new Label("规格:");
specificationField = new TextField();
specificationField.setPromptText("请输入规格");
Label unitLabel = new Label("单位:");
unitField = new TextField();
unitField.setPromptText("请输入单位");
Label priceLabel = new Label("价格:");
priceField = new TextField();
priceField.setPromptText("请输入价格");
Label categoryLabel = new Label("类别:");
categoryField = new TextField();
categoryField.setPromptText("请输入类别");
basicInfo.addRow(0, idLabel, idField, nameLabel, nameField);
basicInfo.addRow(1, specificationLabel, specificationField, unitLabel, unitField);
basicInfo.addRow(2, priceLabel, priceField, categoryLabel, categoryField);
basicInfo.addRow(1, priceLabel, priceField);
// 库存信息
GridPane stockInfo = new GridPane();
@ -106,12 +92,8 @@ public class GoodsManagementView extends BorderPane {
column1.setMinWidth(80);
ColumnConstraints column2 = new ColumnConstraints();
column2.setMinWidth(200);
ColumnConstraints column3 = new ColumnConstraints();
column3.setMinWidth(80);
ColumnConstraints column4 = new ColumnConstraints();
column4.setMinWidth(200);
basicInfo.getColumnConstraints().addAll(column1, column2, column3, column4);
basicInfo.getColumnConstraints().addAll(column1, column2);
stockInfo.getColumnConstraints().addAll(column1, column2);
// 操作按钮
@ -140,18 +122,9 @@ public class GoodsManagementView extends BorderPane {
TableColumn<Goods, String> nameCol = new TableColumn<>("货物名称");
nameCol.setCellValueFactory(new PropertyValueFactory<>("name"));
TableColumn<Goods, String> specificationCol = new TableColumn<>("规格");
specificationCol.setCellValueFactory(new PropertyValueFactory<>("specification"));
TableColumn<Goods, String> unitCol = new TableColumn<>("单位");
unitCol.setCellValueFactory(new PropertyValueFactory<>("unit"));
TableColumn<Goods, Double> priceCol = new TableColumn<>("价格");
priceCol.setCellValueFactory(new PropertyValueFactory<>("price"));
TableColumn<Goods, String> categoryCol = new TableColumn<>("类别");
categoryCol.setCellValueFactory(new PropertyValueFactory<>("category"));
TableColumn<Goods, Integer> quantityCol = new TableColumn<>("数量");
quantityCol.setCellValueFactory(new PropertyValueFactory<>("quantity"));
@ -168,14 +141,37 @@ public class GoodsManagementView extends BorderPane {
TableColumn<Goods, String> remarkCol = new TableColumn<>("备注");
remarkCol.setCellValueFactory(new PropertyValueFactory<>("remark"));
table.getColumns().addAll(idCol, nameCol, specificationCol, unitCol, priceCol, categoryCol, quantityCol,
table.getColumns().addAll(idCol, nameCol, priceCol, quantityCol,
inboundTimeCol, operatorCol, supplierCol, remarkCol);
return table;
}
private void loadGoodsData() {
List<Goods> goodsList = DataManager.getInstance().getAllGoods();
String url = "jdbc:sqlite:db/dbuml.db3";
List<Goods> goodsList = new ArrayList<>();
try (Connection conn = DriverManager.getConnection(url)) {
String sql = "SELECT goods_id, SUM(quantity) as total_quantity, supplier, inbound_time, operator, remark FROM warehouse GROUP BY goods_id";
try (Statement stmt = conn.createStatement();
ResultSet rs = stmt.executeQuery(sql)) {
while (rs.next()) {
Goods goods = new Goods(
rs.getString("goods_id"),
rs.getString("goods_id"), // Assuming goods_id is also the name in inbound_records
rs.getInt("total_quantity"),
rs.getString("remark")
);
goods.setInboundTime(LocalDateTime.parse(rs.getString("inbound_time")));
goods.setOperator(rs.getString("operator"));
goods.setSupplier(rs.getString("supplier"));
goodsList.add(goods);
}
}
} catch (Exception e) {
e.printStackTrace();
showAlert("错误", "加载货物信息失败:" + e.getMessage());
}
tableView.setItems(FXCollections.observableArrayList(goodsList));
}
@ -183,16 +179,12 @@ public class GoodsManagementView extends BorderPane {
try {
String id = idField.getText().trim();
String name = nameField.getText().trim();
String specification = specificationField.getText().trim();
String unit = unitField.getText().trim();
String priceText = priceField.getText().trim();
String category = categoryField.getText().trim();
String quantityText = quantityField.getText().trim();
// 输入验证
if (id.isEmpty() || name.isEmpty() || specification.isEmpty() || unit.isEmpty() ||
priceText.isEmpty() || category.isEmpty() || quantityText.isEmpty()) {
showAlert("错误", "请填写完整的货物信息!");
if (id.isEmpty() || name.isEmpty() || priceText.isEmpty() || quantityText.isEmpty()) {
showAlert("错误", "请填写货物ID、名称、价格和数量");
return;
}
@ -223,20 +215,24 @@ public class GoodsManagementView extends BorderPane {
// 查找货物对象
Goods existingGoods = DataManager.getInstance().getGoods(id);
if (existingGoods == null) {
showAlert("错误", "货物ID不存在");
return;
// 插入新货物
Goods newGoods = new Goods(id, name, "", "", price, "", quantity, "");
newGoods.setInboundTime(LocalDateTime.now());
newGoods.setOperator("当前用户");
DataManager.getInstance().addGoodsToDatabase(newGoods);
} else {
// 更新现有货物
existingGoods.setName(name);
existingGoods.setSpecification("");
existingGoods.setUnit("");
existingGoods.setPrice(price);
existingGoods.setCategory("");
existingGoods.setQuantity(quantity);
DataManager.getInstance().updateGoodsInDatabase(existingGoods);
}
// 更新货物对象
existingGoods.setName(name);
existingGoods.setSpecification(specification);
existingGoods.setUnit(unit);
existingGoods.setPrice(price);
existingGoods.setCategory(category);
existingGoods.setQuantity(quantity);
// 更新表格
tableView.refresh();
loadGoodsData();
// 清空输入
handleClear();
@ -245,26 +241,21 @@ public class GoodsManagementView extends BorderPane {
} catch (Exception e) {
showAlert("错误", "保存失败:" + e.getMessage());
e.printStackTrace(); // 添加堆栈跟踪以便调试
}
}
private void handleClear() {
idField.clear();
nameField.clear();
specificationField.clear();
unitField.clear();
priceField.clear();
categoryField.clear();
quantityField.clear();
}
private void fillFields(Goods goods) {
idField.setText(goods.getId());
nameField.setText(goods.getName());
specificationField.setText(goods.getSpecification());
unitField.setText(goods.getUnit());
priceField.setText(String.valueOf(goods.getPrice()));
categoryField.setText(goods.getCategory());
quantityField.setText(String.valueOf(goods.getQuantity()));
}

@ -12,8 +12,33 @@
<orderEntry type="module-library" exported="">
<library name="JUnit4">
<CLASSES>
<root url="jar://$MODULE_DIR$/lib/junit-4.13.1.jar!/" />
<root url="jar://$MODULE_DIR$/lib/hamcrest-core-1.3.jar!/" />
<root url="jar://$MAVEN_REPOSITORY$/junit/junit/4.13.1/junit-4.13.1.jar!/" />
<root url="jar://$MAVEN_REPOSITORY$/org/hamcrest/hamcrest-core/1.3/hamcrest-core-1.3.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES />
</library>
</orderEntry>
<orderEntry type="module-library" exported="">
<library name="JUnit5.8.1">
<CLASSES>
<root url="jar://$MAVEN_REPOSITORY$/org/junit/jupiter/junit-jupiter/5.8.1/junit-jupiter-5.8.1.jar!/" />
<root url="jar://$MAVEN_REPOSITORY$/org/junit/jupiter/junit-jupiter-api/5.8.1/junit-jupiter-api-5.8.1.jar!/" />
<root url="jar://$MAVEN_REPOSITORY$/org/opentest4j/opentest4j/1.2.0/opentest4j-1.2.0.jar!/" />
<root url="jar://$MAVEN_REPOSITORY$/org/junit/platform/junit-platform-commons/1.8.1/junit-platform-commons-1.8.1.jar!/" />
<root url="jar://$MAVEN_REPOSITORY$/org/apiguardian/apiguardian-api/1.1.2/apiguardian-api-1.1.2.jar!/" />
<root url="jar://$MAVEN_REPOSITORY$/org/junit/jupiter/junit-jupiter-params/5.8.1/junit-jupiter-params-5.8.1.jar!/" />
<root url="jar://$MAVEN_REPOSITORY$/org/junit/jupiter/junit-jupiter-engine/5.8.1/junit-jupiter-engine-5.8.1.jar!/" />
<root url="jar://$MAVEN_REPOSITORY$/org/junit/platform/junit-platform-engine/1.8.1/junit-platform-engine-1.8.1.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES />
</library>
</orderEntry>
<orderEntry type="module-library" exported="">
<library>
<CLASSES>
<root url="jar://$MODULE_DIR$/libs/sqlite-jdbc-3.31.1.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES />

Loading…
Cancel
Save