一、 要设置好IP地址
在Java中一般使用JDBC访问MySQL都是使用127.0.0.1或者localhost来代表本地地址,但是在Android中使用localhost代表的是手机本机IP地址,所以在访问是需要修改IP地址;
在打开CMD(win+R)输入ipconfig后回车,显示如下:
以太网适配器 SSTAP 1:
媒体状态 . . . . . . . . . . . . : 媒体已断开连接
连接特定的 DNS 后缀 . . . . . . . :
以太网适配器 VirtualBox Host-Only Network:
连接特定的 DNS 后缀 . . . . . . . :
本地链接 IPv6 地址. . . . . . . . : fe80::4099:6c06:65a:4884%15
IPv4 地址 . . . . . . . . . . . . : 192.168.56.1
子网掩码 . . . . . . . . . . . . : 255.255.255.0
默认网关. . . . . . . . . . . . . :
以太网适配器 VirtualBox Host-Only Network #2:
连接特定的 DNS 后缀 . . . . . . . :
本地链接 IPv6 地址. . . . . . . . : fe80::3c64:b170:10bf:605d%8
IPv4 地址 . . . . . . . . . . . . : 192.168.251.2
子网掩码 . . . . . . . . . . . . : 255.255.255.0
默认网关. . . . . . . . . . . . . :
无线局域网适配器 本地连接* 1:
媒体状态 . . . . . . . . . . . . : 媒体已断开连接
连接特定的 DNS 后缀 . . . . . . . :
无线局域网适配器 本地连接* 2:
连接特定的 DNS 后缀 . . . . . . . :
本地链接 IPv6 地址. . . . . . . . : fe80::a89e:772:c850:8422%20
IPv4 地址 . . . . . . . . . . . . : 192.168.137.1
子网掩码 . . . . . . . . . . . . : 255.255.255.0
默认网关. . . . . . . . . . . . . :
以太网适配器 VMware Network Adapter VMnet8:
连接特定的 DNS 后缀 . . . . . . . :
本地链接 IPv6 地址. . . . . . . . : fe80::2d9e:45e7:a8:35e1%21
IPv4 地址 . . . . . . . . . . . . : 192.168.64.1
子网掩码 . . . . . . . . . . . . : 255.255.255.0
默认网关. . . . . . . . . . . . . :
以太网适配器 VMware Network Adapter VMnet1:
连接特定的 DNS 后缀 . . . . . . . :
本地链接 IPv6 地址. . . . . . . . : fe80::1e3:965e:ed9e:85a0%3
IPv4 地址 . . . . . . . . . . . . : 192.168.174.1
子网掩码 . . . . . . . . . . . . : 255.255.255.0
默认网关. . . . . . . . . . . . . :
无线局域网适配器 WLAN:
连接特定的 DNS 后缀 . . . . . . . : lan
本地链接 IPv6 地址. . . . . . . . : fe80::ace0:8e4a:46ba:ed3c%16
IPv4 地址 . . . . . . . . . . . . : 192.168.1.129
子网掩码 . . . . . . . . . . . . : 255.255.255.0
默认网关. . . . . . . . . . . . . : 192.168.1.1
1.AVD
对于AVD(即AndroidStudio自带的模拟器),可以将IP地址改为10.0.2.2(即运行的PC本地地址)或者直接改为本机地址,即上面的ipconfig查询的最后一项<无线局域网适配器 WLAN>中的IPv4地址,如上所示为192.168.1.129,代码部分如下
final String DB_URL = "jdbc:mysql://10.0.2.2:3306/meeting?useSSL=false"
final String DB_URL = "jdbc:mysql://192.168.1.129:3306/meeting?useSSL=false"
2.Genymotion
对于Genymotion模拟器,它是运行在虚拟机Oracle VM VirtualBox之上的,所以要访问本地服务器时,应该IP地址设置为ipconfig查询结果中的<以太网适配器 VirtualBox Host-Only Network #2>中的IPv4地址,如上面查询结果所示,本人例子中使用的IP地址是192.168.251.2,
final String DB_URL = "jdbc:mysql://192.168.251.2:3306/meeting?useSSL=false"
3.真机
真机测试时,相对于模拟器多了一些其他步骤,在这里先将IP地址的设置,其他步骤请在下文查找,程序要在真机测试时,需将代码中要访问的数据库的IP地址设为数据库所在主机的IP地址,即上面ipconfig查询结果中的<无线局域网适配器 WLAN>中的IPv4地址,如上面所示,此处为192.168.1.129
final String DB_URL = "jdbc:mysql://192.168.1.129:3306/meeting?useSSL=false"
关于JDBC连接MySQL的IP地址设置的介绍就先这样,接下来是访问数据库的用户设置。因为MySQL的root用户不允许远程访问,所以我们应该创建一个新用户
二、创建数据库新用户并授权允许远程访问
CMD登入MySQL(mysql -uroot -ppassword),然后执行以下步骤
//创建新用户,可以远程访问
//%表示任意IP地址,也可以自己制定,password设置此新用户登录时应该输入的密码
create user newuser@'%' identified by 'password';
//授予新用户对指定数据库的全部表或者某张表的操作权限
//DataBase替换成自己制定的数据库名字,Table替换成要访问的指定数据库的指定表
//要是要设置允许访问全部数据库的全部表,则将DataBase.Table改为 *.*
GRANT ALL PRIVILEGES ON DataBase.Table TO newuser@"%" IDENTIFIED BY "password";
设置后访问数据库的用户账号后,就该动手编程通过JDBC连接MySQL,来访问数据库,但是Android访问数据库需要在子线程中执行,所以在访问时应该创建新线程
三、在新线程中连接数据库获取信息(贴代码)
1.导入jar包,将下载的mysql-connector-java-XX.XX.XX-bin.jar(XX.XX.XX代表版本号)复制到工程的/app/libs或/app/src/main/libs(没有的话可以自己建一个)目录下,然后点击该jar包右键点击Add As Library.. 然后按提示再Syns一下,如果没报错就是成功添加了。
2.连接数据库,下面我提一个我在练习的时候写的代码展示一下,可以参考改成自己需要的,将‘Android’改成自己创建的用户名,将‘android’改成自己创建的用户的密码,
public class UserDataSource implements UserDataBase {
String TABLE_NAME = "user";
DatabaseHelper databaseHelper ;
SQLiteDatabase sqLiteDatabase;
BasePresenter basePresenter;
final String DB_URL = "jdbc:mysql://192.168.1.129:3306/meeting?useSSL=false";//数据库地址,10.10.2.2在虚拟机中,指本机ip;若是真机测试,则需要改为真是ip
final String DB_USER="Android";
final String DB_PASSWORD="android";
public UserDataSource(Context context,BasePresenter basePresenter){
databaseHelper = new DatabaseHelper (context);
this.basePresenter = basePresenter;
}
@Override
//改为连接数据库查找信息
public void getUserData(final String nameOrPhoneOrMail, final String password){
Thread loginThread = new Thread() {
@Override
public void run() {
try {
Class.forName("com.mysql.jdbc.Driver");
Connection conn = DriverManager.getConnection(DB_URL,DB_USER,DB_PASSWORD);
Statement stat = conn.createStatement();
//查找数据语句
String exe_query = "SELECT * FROM " + TABLE_NAME + " WHERE username = '" + nameOrPhoneOrMail +
"' OR phone = '" + nameOrPhoneOrMail + "' OR mail = '" + nameOrPhoneOrMail+"'";
ResultSet resultSet = stat.executeQuery(exe_query);
resultSet.last();
if (resultSet.getRow() == 1) {
resultSet.first();
if (password.equals(resultSet.getString("password"))) {//密码正确
// basePresenter.setResult(1);
basePresenter.setResult(1);
User user = new User();
user.setId(resultSet.getInt("u_id"));
user.setUserName(resultSet.getString("username"));
user.setPhone(resultSet.getString("phone"));
user.setMail(resultSet.getString("mail"));
user.setCredit(resultSet.getInt("credit"));
basePresenter.setSuccessLoginUser(user);//成功登录后返回用户具体信息
} else {
basePresenter.setResult(0);//密码错误
}
} else {//该用户未注册
basePresenter.setResult(0);
}
stat.close();
conn.close();
} catch (
Exception e) {
e.printStackTrace();
}
}
};
loginThread.start();
try {
loginThread.join();//使线程顺序执行
}catch (InterruptedException e){
e.printStackTrace();
}
}
@Override
//改为将用户信息存储到MySQL数据库
public void saveUserData(final User register){
Thread registThread = new Thread(){
@Override
public void run(){
try{
Class.forName("com.mysql.jdbc.Driver");
Connection conn = DriverManager.getConnection(DB_URL,DB_USER,DB_PASSWORD);
Statement stat = conn.createStatement();
//查询数据语句:注册之前要先查看该用户名或者
ResultSet resultSet;
String query_username = "SELECT * FROM " + TABLE_NAME + " WHERE username = '" + register.getUserName() +"'" ;
String query_phone = "SELECT * FROM " + TABLE_NAME + " WHERE phone = '" + register.getPhone() +"'" ;
String query_mail = "SELECT * FROM " + TABLE_NAME + " WHERE mail = '" + register.getMail()+"'" ;
resultSet = stat.executeQuery(query_username);
resultSet.last();
if(resultSet.getRow() != 0){//查询到有同样的用户名
basePresenter.setResult(2);
return;
}
resultSet = stat.executeQuery(query_phone);
resultSet.last();
if(resultSet.getRow() != 0){//查询到有同样的手机号
basePresenter.setResult(3);
return;
}
resultSet = stat.executeQuery(query_mail);
resultSet.last();
if(resultSet.getRow() != 0){//查询到有同样的手机号
basePresenter.setResult(4);
return;
}
//插入数据语句
String exe_insert = "INSERT INTO "+TABLE_NAME+
" VALUES(NULL,'"+register.getUserName()+"','"+register.getPhone()+"','"+register.getMail()+"','"+register.getPassword()+"',"+register.getCredit()+")";
int exe_result = stat.executeUpdate(exe_insert);//返回1:添加成功;返回其他:添加失败;
if (exe_result == 1){
basePresenter.setResult(1);
}else{
basePresenter.setResult(0);
}
stat.close();
conn.close();
}catch (Exception e){
e.printStackTrace();
}
}
};
registThread.start();
try {
registThread.join();
}catch (InterruptedException e){
e.printStackTrace();
}
}
}
四、 关闭防火墙(真机测试)
本文主要是针对连接本地数据库的Android程序的真机测试,所以以下两个步骤是真机测试所必须的,如果是AVD或者Genymotion那么完成上面步骤之后就可以运行尝试了。
在进行真机测试时,应先关闭本地的防火墙(win10) 设置-->更新与安全-->Windows安全中心-->防火墙与网络保护(或者其他已知的关闭方法)
五 、连接电脑热点(真机测试)
在进行真机测试时,如果要访问本地服务,还需保证真机与本地处于同一网络,较容易的方法就是代开电脑的移动热点,然后手机连接热点既可,然后运行程序就可以在真机上愉快地访问数据库了(或者尝试其他已知方法);
因为我是新手,暂时还没接触到http+webserver(应该是这个)来访问数据,所以只能做个简单的,通过jdbc直接访问MySQL来获取数据,但是网上说这种方法是不安全的,不建议的,但是我个人认为对于新手来说,这也可以算是一个学习的过程,所以整理了一下在连接MySQL过程中看的很多教程,使之成为一篇较完整的教程,可以方便像我一样的新手。