MySql数据库表数据合并同步

最近遇到一个项目,一个系统要部署在两个网络区里,由于安全限制,这两个区域A和B无法保持长链接,只能是Http协议,数据交互只能只能一方(A)请求另一方(B)被动响应,数据还要定时从A汇总到B,B区的数据是全量的,A区的数据只能是A区自身可见的数据。
实现思路:
由于mysql连接是长连接所以无法使用一个数据库,所以A和B区内各有一个数据结构完全相同的数据库存储,定时把A区数据发送到B区。
通过MySql Client提供的脚本mysqldump和mysql导出导入sql语句文件,实现将A区的增量修改数据(通过where条件)同步到B区的数据库中。
具体实现:
关键代码如下
public class ProcessUtil {

    /**
     * mysqldump导出表数据结构和全部数据
     * @param tableName
     */
    public static void dumpFull(String tableName,String fileDir){
        List<String> cmdList = new ArrayList<String>();
        cmdList.add(SynConstatns.mysqlBinDir+"mysqldump");

        cmdList.add("-u"+SynConstatns.userName);
        cmdList.add("-p"+SynConstatns.passwd);

        cmdList.add("--host");
        cmdList.add(SynConstatns.host);

        cmdList.add("--port");
        cmdList.add(SynConstatns.port);

//      cmdList.add("--no-create-info");
//      cmdList.add("--replace");
        cmdList.add("--complete-insert");

        cmdList.add(SynConstatns.schema);
        cmdList.add(tableName);
        cmdList.add("--result-file="+fileDir+File.separator+tableName+".sql");

        process(cmdList);
    }

    /**
     * mysqldump导出表的where条件数据
     * @param tableName
     * @param whereCondition
     */
    public static void dumpWhereData(String tableName,String whereCondition,String fileDir){
        List<String> cmdList = new ArrayList<String>();
        cmdList.add(SynConstatns.mysqlBinDir+"mysqldump");//程序中mysqldump的路径

        cmdList.add("-u"+SynConstatns.userName);
        cmdList.add("-p"+SynConstatns.passwd);

        cmdList.add("--host");
        cmdList.add(SynConstatns.host);

        cmdList.add("--port");
        cmdList.add(SynConstatns.port);

        cmdList.add("--no-create-info");//去掉删表、建表的语句
        cmdList.add("--replace");//之所以用replace生成的语句是replace into可以用于覆盖掉update操作
        cmdList.add("--complete-insert");

        cmdList.add(SynConstatns.schema);
        cmdList.add(tableName);
        cmdList.add("--where="+whereCondition);//表数据过滤条件
        cmdList.add("--result-file="+fileDir+File.separator+tableName+".sql");//sql文件保存路径

        process(cmdList);
    }

    /**
     * 导入执行sql文件
     * 
     * @param filePath
     */
    public static void importData(String filePath){
        List<String> cmdList = new ArrayList<String>();
        cmdList.add(SynConstatns.mysqlBinDir+"mysql");
        cmdList.add("-u"+SynConstatns.userName);
        cmdList.add("-p"+SynConstatns.passwd);
        cmdList.add("-h"+SynConstatns.host);
        cmdList.add("-P"+SynConstatns.port);
        cmdList.add(SynConstatns.schema);
        cmdList.add("--execute=source "+filePath); 
        process(cmdList);
    }

    /**
     * process执行
     * @param cmds
     */
    public static void process(List<String> cmds){
        ProcessBuilder builder = new ProcessBuilder();
        builder.redirectErrorStream(true);
        try {
            Process process = builder.command(cmds).start();
            InputStream is = process.getInputStream();
            BufferedReader br = new BufferedReader(new InputStreamReader(is, "utf8"));
            String tmp = br.readLine();
            do{
                System.out.println(tmp);
            }while((tmp =br.readLine())!=null);
            is.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

缺点:
只能记录insert和update操作的数据,不能记录生成删除操作的sql语句
建议对于删除操作可以不做物理删除,通过逻辑修改数据可见性的方式达到删除规避不能生成
或者创建一张删除记录表,对每张表加触发器,将删除数据的主键key和tablename记录,同步后进行关联删除记录,也可以实现删除记录的同步。
具体命令参数参考mysql官方文档
http://dev.mysql.com/doc/refman/5.7/en/mysql.html
http://dev.mysql.com/doc/refman/5.7/en/mysqldump.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值