commit 3aeda46b0b780d1080fc1455ee1de19caeeaa26d
Author: frank <3224536684@qq.com>
Date: Wed Jun 28 00:54:18 2023 +0800
:sparkles: first commit
diff --git a/.gitignore b/.gitignore
new file mode 100644
index 0000000..a879ee7
--- /dev/null
+++ b/.gitignore
@@ -0,0 +1,39 @@
+target/
+!.mvn/wrapper/maven-wrapper.jar
+!**/src/main/**/target/
+!**/src/test/**/target/
+
+### IntelliJ IDEA ###
+.idea/
+.idea/modules.xml
+.idea/jarRepositories.xml
+.idea/compiler.xml
+.idea/libraries/
+*.iws
+*.iml
+*.ipr
+
+### Eclipse ###
+.apt_generated
+.classpath
+.factorypath
+.project
+.settings
+.springBeans
+.sts4-cache
+
+### NetBeans ###
+/nbproject/private/
+/nbbuild/
+/dist/
+/nbdist/
+/.nb-gradle/
+build/
+!**/src/main/**/build/
+!**/src/test/**/build/
+
+### VS Code ###
+.vscode/
+
+### Mac OS ###
+.DS_Store
\ No newline at end of file
diff --git a/pom.xml b/pom.xml
new file mode 100644
index 0000000..d7a78a7
--- /dev/null
+++ b/pom.xml
@@ -0,0 +1,80 @@
+
+
+ 4.0.0
+
+ net.javase.db
+ mysql-tool
+ 1.0.0
+
+
+ 8
+ 8
+ UTF-8
+ 8.0.30
+
+
+
+
+ junit
+ junit
+ 4.13.2
+ test
+
+
+ mysql
+ mysql-connector-java
+ ${mysql.version}
+ runtime
+
+
+ commons-beanutils
+ commons-beanutils
+ 1.9.4
+
+
+
+
+
+ mysql-tool
+
+
+ org.apache.maven.plugins
+ maven-compiler-plugin
+ 3.8.1
+
+ ${maven.compiler.source}
+ ${maven.compiler.target}
+
+
+
+ org.apache.maven.plugins
+ maven-javadoc-plugin
+ 3.1.1
+
+
+ package
+
+ jar
+
+
+
+
+
+ org.apache.maven.plugins
+ maven-source-plugin
+ 3.1.0
+
+
+ nexus-release
+ package
+
+ jar-no-fork
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/src/main/java/net/javase/db/annotation/Column.java b/src/main/java/net/javase/db/annotation/Column.java
new file mode 100644
index 0000000..73d8993
--- /dev/null
+++ b/src/main/java/net/javase/db/annotation/Column.java
@@ -0,0 +1,38 @@
+package net.javase.db.annotation;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+/**
+ * Column
+ *
+ * @author frank
+ */
+@Retention(RetentionPolicy.RUNTIME)
+@Target(ElementType.FIELD)
+public @interface Column {
+
+ /**
+ * column name
+ *
+ * @return column name
+ */
+ String name();
+
+ /**
+ * not null
+ *
+ * @return true | false
+ */
+ boolean notNull() default false;
+
+ /**
+ * default value
+ *
+ * @return default value
+ */
+ String defaultValue();
+
+}
diff --git a/src/main/java/net/javase/db/annotation/Entity.java b/src/main/java/net/javase/db/annotation/Entity.java
new file mode 100644
index 0000000..b3a0ac0
--- /dev/null
+++ b/src/main/java/net/javase/db/annotation/Entity.java
@@ -0,0 +1,24 @@
+package net.javase.db.annotation;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+/**
+ * 实体类注解
+ *
+ * @author frank
+ */
+@Retention(RetentionPolicy.RUNTIME)
+@Target(ElementType.TYPE)
+public @interface Entity {
+
+ /**
+ * 自定义表名
+ *
+ * @return table name
+ */
+ String table() default "";
+
+}
diff --git a/src/main/java/net/javase/db/annotation/Id.java b/src/main/java/net/javase/db/annotation/Id.java
new file mode 100644
index 0000000..dbd1656
--- /dev/null
+++ b/src/main/java/net/javase/db/annotation/Id.java
@@ -0,0 +1,17 @@
+package net.javase.db.annotation;
+
+import java.lang.annotation.ElementType;
+import java.lang.annotation.Retention;
+import java.lang.annotation.RetentionPolicy;
+import java.lang.annotation.Target;
+
+/**
+ * 主键注解
+ *
+ * @author frank
+ */
+@Retention(RetentionPolicy.RUNTIME)
+@Target(ElementType.FIELD)
+public @interface Id {
+
+}
diff --git a/src/main/java/net/javase/db/config/DbConfig.java b/src/main/java/net/javase/db/config/DbConfig.java
new file mode 100644
index 0000000..d09b434
--- /dev/null
+++ b/src/main/java/net/javase/db/config/DbConfig.java
@@ -0,0 +1,102 @@
+package net.javase.db.config;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.util.Properties;
+
+/**
+ * DbConfig
+ *
+ * @author Frank
+ */
+public class DbConfig {
+ private static final String FILE_NAME = "mysql.properties";
+
+ private static Properties p = null;
+
+ private static DbConfig dbConfig = null;
+
+ /**
+ * driver
+ */
+ private String driver;
+
+ /**
+ * url
+ */
+ private String url;
+
+ /**
+ * username
+ */
+ private String username;
+
+ /**
+ * password
+ */
+ private String password;
+
+ public DbConfig(String driver, String url, String username, String password) {
+ this.driver = driver;
+ this.url = url;
+ this.username = username;
+ this.password = password;
+ }
+
+ public String getUrl() {
+ return url;
+ }
+
+ public void setUrl(String url) {
+ this.url = url;
+ }
+
+ public String getUsername() {
+ return username;
+ }
+
+ public void setUsername(String username) {
+ this.username = username;
+ }
+
+ public String getPassword() {
+ return password;
+ }
+
+ public void setPassword(String password) {
+ this.password = password;
+ }
+
+ public String getDriver() {
+ return driver;
+ }
+
+ public void setDriver(String driver) {
+ this.driver = driver;
+ }
+
+ static {
+ InputStream inputStream = ClassLoader.getSystemResourceAsStream(FILE_NAME);
+ p = new Properties();
+ try {
+ p.load(inputStream);
+ } catch (IOException e) {
+ throw new RuntimeException(e);
+ }
+ }
+
+ /**
+ * 获取配置信息对象
+ */
+ public static DbConfig get() {
+ if (dbConfig == null) {
+ dbConfig = new DbConfig(
+ p.getProperty("driver"),
+ p.getProperty("url"),
+ p.getProperty("username"),
+ p.getProperty("password")
+ );
+ }
+ return dbConfig;
+ }
+}
diff --git a/src/main/java/net/javase/db/utils/BeanUtil.java b/src/main/java/net/javase/db/utils/BeanUtil.java
new file mode 100644
index 0000000..54732d8
--- /dev/null
+++ b/src/main/java/net/javase/db/utils/BeanUtil.java
@@ -0,0 +1,5 @@
+package net.javase.db.utils;
+
+public class BeanUtil {
+
+}
diff --git a/src/main/java/net/javase/db/utils/DbUtil.java b/src/main/java/net/javase/db/utils/DbUtil.java
new file mode 100644
index 0000000..596db0b
--- /dev/null
+++ b/src/main/java/net/javase/db/utils/DbUtil.java
@@ -0,0 +1,297 @@
+package net.javase.db.utils;
+
+import net.javase.db.annotation.Column;
+import net.javase.db.annotation.Entity;
+import net.javase.db.annotation.Id;
+import net.javase.db.config.DbConfig;
+
+import java.lang.reflect.Field;
+import java.lang.reflect.InvocationTargetException;
+import java.sql.*;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.apache.commons.beanutils.PropertyUtils;
+
+/**
+ * DbUtil
+ *
+ * @author Frank
+ */
+public class DbUtil {
+
+ private static Connection conn;
+
+ static {
+ try {
+ Class.forName(DbConfig.get().getDriver());
+ } catch (ClassNotFoundException e) {
+ e.printStackTrace();
+ }
+ }
+
+ /**
+ * 获取数据库连接对象
+ *
+ * @return {@link Connection}
+ */
+ public static Connection getConnection() {
+ // 获取连接并捕获异常
+ try {
+ if (conn == null || conn.isClosed())
+ conn = DriverManager.getConnection(
+ DbConfig.get().getUrl(),
+ DbConfig.get().getUsername(),
+ DbConfig.get().getPassword());
+ } catch (SQLException e) {
+ e.printStackTrace();
+ }
+ return conn;// 返回连接对象
+ }
+
+ /**
+ * 关闭数据库连接
+ *
+ * @param conn {@link Connection} 数据库连接
+ */
+ public static void closeConn(Connection conn) {
+ try {
+ if (conn != null && !conn.isClosed())
+ conn.close();
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ }
+
+ /**
+ * 关闭数据库连接。
+ *
+ * @param conn 数据库连接
+ * @param stmt Statement对象
+ * @param rs 结果集
+ */
+ public static void closeAll(Connection conn, Statement stmt, ResultSet rs) {
+ // 若结果集对象不为空,则关闭
+ try {
+ if (rs != null && !rs.isClosed())
+ rs.close();
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ // 若Statement对象不为空,则关闭
+ try {
+ if (stmt != null && !stmt.isClosed())
+ stmt.close();
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ // 若数据库连接对象不为空,则关闭
+ try {
+ if (conn != null && !conn.isClosed())
+ conn.close();
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ }
+
+ /**
+ * 增、删、改操作
+ *
+ * @param sql sql语句
+ * @param params 参数数组
+ * @return 执行结果
+ */
+ public static int executeUpdate(String sql, Object... params) {
+ int result = 0;
+ conn = getConnection();
+ PreparedStatement pstmt = null;
+ try {
+ pstmt = conn.prepareStatement(sql);
+ for (int i = 0; i < params.length; i++) {
+ pstmt.setObject(i + 1, params[i]);
+ }
+ result = pstmt.executeUpdate();
+ } catch (SQLException e) {
+ e.printStackTrace();
+ } finally {
+ closeAll(null, pstmt, null);
+ }
+ return result;
+ }
+
+ /**
+ * 查询操作
+ *
+ * @param sql sql语句
+ * @param params 参数数组
+ * @return 查询结果集
+ */
+ public static ResultSet executeQuery(String sql, Object... params) {
+ conn = getConnection();
+ PreparedStatement pstmt = null;
+ ResultSet rs = null;
+ try {
+ pstmt = conn.prepareStatement(sql);
+ for (int i = 0; i < params.length; i++) {
+ pstmt.setObject(i + 1, params[i]);
+ }
+ rs = pstmt.executeQuery();
+ } catch (SQLException e) {
+ e.printStackTrace();
+ }
+ return rs;
+ }
+
+ /**
+ * 查询实体列表
+ *
+ * @param T
+ * @param clazz entity class
+ * @param sql 查询sql
+ * @param params sql参数
+ * @return entity list
+ */
+ public static List selectList(Class clazz, String sql, Object... params) {
+ conn = getConnection();
+ PreparedStatement pstmt = null;
+ ResultSet rs = null;
+ List list = new ArrayList();
+ try {
+ pstmt = conn.prepareStatement(sql);
+ for (int i = 0; i < params.length; i++) {
+ pstmt.setObject(i + 1, params[i]);
+ }
+ rs = pstmt.executeQuery();
+ Map entityMateData = getMetaData(clazz);
+ ResultSetMetaData rsmd = rs.getMetaData();
+ int columnCount = rsmd.getColumnCount();
+ while (rs.next()) {
+ T obj = clazz.newInstance();
+ for (int i = 1; i <= columnCount; i++) {
+ String columnName = rsmd.getColumnName(i);
+ Object value = rs.getObject(i);
+ try {
+ if (entityMateData.get(columnName) != null) {
+ PropertyUtils.setProperty(obj, entityMateData.get(columnName), value);
+ }
+ } catch (InvocationTargetException e) {
+ e.printStackTrace();
+ } catch (NoSuchMethodException e) {
+ e.printStackTrace();
+ }
+ }
+ list.add(obj);
+ }
+ entityMateData = null;
+ } catch (SQLException | InstantiationException | IllegalAccessException e) {
+ throw new RuntimeException(e);
+ } finally {
+ closeAll(conn, pstmt, rs);
+ }
+ return list;
+ }
+
+ /**
+ * 获取entity对应的column对应关系
+ *
+ * @param T
+ * @param clazz entity class
+ * @return map
+ */
+ private static Map getMetaData(Class clazz) {
+ Map map = new HashMap<>();
+ Field[] fields = clazz.getDeclaredFields();
+ for (Field field : fields) {
+ Column c = field.getAnnotation(Column.class);
+ if (c != null) {
+ if (StrUtil.notBlank(c.name())) {
+ map.put(c.name(), field.getName());
+ }
+ }
+ map.put(field.getName(), field.getName());
+ }
+ return map;
+ }
+
+ /**
+ * 生成建表语句
+ *
+ * @param clazz 实体类
+ * @param underline 是否下划线命名
+ * @param 实体类
+ * @return sql
+ */
+ public static String createSchemaSql(Class clazz, boolean underline) {
+ String table = clazz.getSimpleName();
+ Entity e = clazz.getAnnotation(Entity.class);
+ if (e != null && !StrUtil.isBlank(e.table())) {
+ table = e.table();
+ } else {
+ table = StrUtil.camelToUnderscore(table);
+ }
+ StringBuilder sqlBuilder = new StringBuilder();
+ sqlBuilder.append("CREATE TABLE IF NOT EXISTS `").append(table).append("` (");
+ Field[] fields = clazz.getDeclaredFields();
+ for (Field field : fields) {
+ String columnName = field.getName();
+ String jdbcType = ""; // 类型
+ boolean notNull = false; // 是否为空
+ String defaultValue = ""; // 默认值
+ boolean isKey = false;
+
+ Id id = field.getAnnotation(Id.class);
+ if (id != null) {
+ isKey = true;
+ notNull = true;
+ }
+
+ Column c = field.getAnnotation(Column.class);
+ if (c != null) {
+ if (StrUtil.notBlank(c.name())) {
+ columnName = c.name();
+ }
+ notNull = c.notNull();
+ defaultValue = c.defaultValue();
+ }
+
+ Class> fieldType = field.getType();
+ if (String.class.equals(fieldType)) {
+ jdbcType = "VARCHAR(255)";
+ } else if (Integer.class.equals(fieldType) || int.class.equals(fieldType)) {
+ jdbcType = "INT";
+ } else if (Long.class.equals(fieldType) || long.class.equals(fieldType)) {
+ jdbcType = "BIGINT";
+ } else if (Boolean.class.equals(fieldType) || boolean.class.equals(fieldType)) {
+ jdbcType = "BOOLEAN";
+ } else if (Double.class.equals(fieldType) || double.class.equals(fieldType)) {
+ jdbcType = "DOUBLE";
+ } else if (Date.class.equals(fieldType) || java.util.Date.class.equals(fieldType)) {
+ jdbcType = "datetime";
+ } else if (Float.class.equals(fieldType) || float.class.equals(fieldType)) {
+ jdbcType = "float";
+ } else {
+ jdbcType = "VARCHAR(255)";
+ }
+
+ if (underline) {
+ columnName = StrUtil.camelToUnderscore(columnName);
+ }
+
+ sqlBuilder.append("`").append(columnName).append("` ")
+ .append(jdbcType).append(" ")
+ .append(notNull ? "NOT NULL" : "NULL").append(" ")
+ .append(StrUtil.notBlank(defaultValue) ? "DEFAULT '" + defaultValue + "'" : "").append(" ")
+ .append(isKey ? "PRIMARY KEY AUTO_INCREMENT" : "")
+ .append(",");
+ }
+ // 去掉最后一个逗号
+ if (fields.length > 0) {
+ sqlBuilder.deleteCharAt(sqlBuilder.length() - 1);
+ }
+
+ sqlBuilder.append(") ENGINE=InnoDB DEFAULT CHARSET=utf8;");
+ return sqlBuilder.toString();
+ }
+}
diff --git a/src/main/java/net/javase/db/utils/StrUtil.java b/src/main/java/net/javase/db/utils/StrUtil.java
new file mode 100644
index 0000000..8742cb4
--- /dev/null
+++ b/src/main/java/net/javase/db/utils/StrUtil.java
@@ -0,0 +1,86 @@
+package net.javase.db.utils;
+
+/**
+ * StrUtil
+ *
+ * @author Frank
+ */
+public class StrUtil {
+
+ /**
+ * 判断字符串是否为空
+ *
+ * @param str 字符串
+ * @return true | false
+ */
+ public static boolean isBlank(String str) {
+ return str == null || str.length() == 0 || str.trim().length() == 0;
+ }
+
+ /**
+ * 字符串是否不为null或者''
+ *
+ * @param str 字符串
+ * @return true | false
+ */
+ public static boolean notBlank(String str) {
+ return !isBlank(str);
+ }
+
+ /**
+ * 驼峰转下划线
+ *
+ * @param str 驼峰字符串
+ * @return 下划线字符串
+ */
+ public static String camelToUnderscore(String str) {
+ if (str == null || str.isEmpty()) {
+ return str;
+ }
+ StringBuilder result = new StringBuilder();
+ char[] chars = str.toCharArray();
+ for (int i = 0; i < chars.length; i++) {
+ char ch = chars[i];
+ if (i == 0) {
+ result.append(Character.toLowerCase(ch));
+ continue;
+ }
+ if (Character.isUpperCase(ch)) {
+ result.append("_").append(Character.toLowerCase(ch));
+ } else if (Character.isDigit(ch)) {
+ result.append("_").append(ch);
+ } else {
+ result.append(ch);
+ }
+ }
+ return result.toString();
+ }
+
+ /**
+ * 下划线转驼峰
+ *
+ * @param underLineStr 下划线字符串
+ * @return 驼峰字符串
+ */
+ public static String underlineToCamel(String underLineStr) {
+ StringBuilder result = new StringBuilder();
+ // 标记当前字符是否为下划线后的第一个字符
+ boolean flag = false;
+ // 遍历字符串,将下划线后的第一个字符转换成大写字母
+ for (int i = 0; i < underLineStr.length(); i++) {
+ char currentChar = underLineStr.charAt(i);
+ if (currentChar == '_') {
+ flag = true;
+ } else {
+ if (flag) {
+ result.append(Character.toUpperCase(currentChar));
+ flag = false;
+ } else {
+ result.append(Character.toLowerCase(currentChar));
+ }
+ }
+ }
+ return result.toString();
+ }
+
+}
diff --git a/src/test/java/net/javase/db/test/BankAccount.java b/src/test/java/net/javase/db/test/BankAccount.java
new file mode 100755
index 0000000..6775b57
--- /dev/null
+++ b/src/test/java/net/javase/db/test/BankAccount.java
@@ -0,0 +1,85 @@
+package net.javase.db.test;
+
+import net.javase.db.annotation.Entity;
+import net.javase.db.annotation.Id;
+
+import java.util.Date;
+
+/**
+ * BankAccount
+ * @author frank
+ */
+@Entity
+public class BankAccount {
+
+ @Id
+ private int id;
+
+ private String username;
+
+ private String realName;
+
+ private String password;
+
+ private String optPassword;
+
+ private String balance;
+
+ private Date createTime;
+
+ public int getId() {
+ return id;
+ }
+
+ public void setId(int id) {
+ this.id = id;
+ }
+
+ public String getUsername() {
+ return username;
+ }
+
+ public void setUsername(String username) {
+ this.username = username;
+ }
+
+ public String getRealName() {
+ return realName;
+ }
+
+ public void setRealName(String realName) {
+ this.realName = realName;
+ }
+
+ public String getPassword() {
+ return password;
+ }
+
+ public void setPassword(String password) {
+ this.password = password;
+ }
+
+ public String getOptPassword() {
+ return optPassword;
+ }
+
+ public void setOptPassword(String optPassword) {
+ this.optPassword = optPassword;
+ }
+
+ public String getBalance() {
+ return balance;
+ }
+
+ public void setBalance(String balance) {
+ this.balance = balance;
+ }
+
+ public Date getCreateTime() {
+ return createTime;
+ }
+
+ public void setCreateTime(Date createTime) {
+ this.createTime = createTime;
+ }
+}
diff --git a/src/test/java/net/javase/db/test/BankAccountLog.java b/src/test/java/net/javase/db/test/BankAccountLog.java
new file mode 100755
index 0000000..4f22faa
--- /dev/null
+++ b/src/test/java/net/javase/db/test/BankAccountLog.java
@@ -0,0 +1,86 @@
+package net.javase.db.test;
+
+import net.javase.db.annotation.Entity;
+import net.javase.db.annotation.Id;
+
+import java.util.Date;
+
+/**
+ * BankAccountLog
+ *
+ * @author frank
+ */
+@Entity
+public class BankAccountLog {
+
+ @Id
+ private int id;
+
+ private int accountId;
+
+ private String username;
+
+ private String optType;
+
+ private String optAmount;
+
+ private String desc;
+
+ private Date createTime;
+
+ public int getId() {
+ return id;
+ }
+
+ public void setId(int id) {
+ this.id = id;
+ }
+
+ public int getAccountId() {
+ return accountId;
+ }
+
+ public void setAccountId(int accountId) {
+ this.accountId = accountId;
+ }
+
+ public String getUsername() {
+ return username;
+ }
+
+ public void setUsername(String username) {
+ this.username = username;
+ }
+
+ public String getOptType() {
+ return optType;
+ }
+
+ public void setOptType(String optType) {
+ this.optType = optType;
+ }
+
+ public String getOptAmount() {
+ return optAmount;
+ }
+
+ public void setOptAmount(String optAmount) {
+ this.optAmount = optAmount;
+ }
+
+ public String getDesc() {
+ return desc;
+ }
+
+ public void setDesc(String desc) {
+ this.desc = desc;
+ }
+
+ public Date getCreateTime() {
+ return createTime;
+ }
+
+ public void setCreateTime(Date createTime) {
+ this.createTime = createTime;
+ }
+}
diff --git a/src/test/java/net/javase/db/test/DbUtilTest.java b/src/test/java/net/javase/db/test/DbUtilTest.java
new file mode 100644
index 0000000..0f2b1d5
--- /dev/null
+++ b/src/test/java/net/javase/db/test/DbUtilTest.java
@@ -0,0 +1,28 @@
+package net.javase.db.test;
+
+import net.javase.db.utils.DbUtil;
+
+import java.util.List;
+
+import org.junit.Test;
+
+/**
+ * MainTest
+ *
+ * @author Frank
+ */
+public class DbUtilTest {
+
+ @Test
+ public void testCreateTableSql() {
+ System.out.println(DbUtil.createSchemaSql(BankAccount.class, true));
+ System.out.println("\n");
+ System.out.println(DbUtil.createSchemaSql(BankAccountLog.class, true));
+ }
+
+ @Test
+ public void testQueryList() {
+ List list = DbUtil.selectList(Product.class, "select * from sys_product");
+ list.forEach(item -> System.out.println(item));
+ }
+}
diff --git a/src/test/java/net/javase/db/test/Product.java b/src/test/java/net/javase/db/test/Product.java
new file mode 100644
index 0000000..b50a4d7
--- /dev/null
+++ b/src/test/java/net/javase/db/test/Product.java
@@ -0,0 +1,52 @@
+package net.javase.db.test;
+
+public class Product {
+
+ private Integer pid;
+
+ private String pname;
+
+ private Double pprice;
+
+ private Integer stock;
+
+ public String getPname() {
+ return pname;
+ }
+
+ public void setPname(String pname) {
+ this.pname = pname;
+ }
+
+ public Integer getPid() {
+ return pid;
+ }
+
+ public void setPid(Integer pid) {
+ this.pid = pid;
+ }
+
+ public Double getPprice() {
+ return pprice;
+ }
+
+ public void setPprice(Double pprice) {
+ this.pprice = pprice;
+ }
+
+ public Integer getStock() {
+ return stock;
+ }
+
+ public void setStock(Integer stock) {
+ this.stock = stock;
+ }
+
+ @Override
+ public String toString() {
+ return "Product [pid=" + pid + ", pname=" + pname + ", pprice=" + pprice + ", stock=" + stock + "]";
+ }
+
+
+
+}
diff --git a/src/test/resources/mysql.properties b/src/test/resources/mysql.properties
new file mode 100644
index 0000000..1f34a23
--- /dev/null
+++ b/src/test/resources/mysql.properties
@@ -0,0 +1,4 @@
+driver=com.mysql.cj.jdbc.Driver
+url=jdbc:mysql://localhost:3306/demo?characterEncoding=utf-8&serverTimezone=GMT%2b8
+username=root
+password=root
\ No newline at end of file