博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
Mysql根据内容查找在哪个表(Go版本)
阅读量:4218 次
发布时间:2019-05-26

本文共 5162 字,大约阅读时间需要 17 分钟。

Mysql根据内容查找在哪个表(Go版本)

前言

哈喽,大家好,我是星期八。

事情是这样婶的。

上次我们通过Python语言完成了Mysql根据内容查找在哪个表这个需求。

传送门:

但是都知道啊。Python是不太方便打包的。虽然可以。但是毕竟不是那么方便。

所以,思来想去,决定使用Go语言重构这个需求,并且打包成win64win32exe

项目说明

本项目已经上传gitee

地址:

在这里插入图片描述

下载下来可以发现是有mysql根据内容查询在哪个表这个文件夹的!

里面放的就是打包好的exe,可以直接使用!

在这里插入图片描述

由于小生不才,并没有学会Go GUI相关的知识,所以只能采用读取配置文件的方式进行一些设置!

打开my.ini文件,配置连接数据库相关信息要模糊搜索的内容,修改完记得保存!

在这里插入图片描述

然后,直接双击就好了,32位就双击32位的,64位的双击32和64都行!

在这里插入图片描述

这不,就拿到了数据,还匹配到了哪个字段!

代码解读

全局变量和导入包

import (	"database/sql"	"errors"	"fmt"	"github.com/go-ini/ini"	_ "github.com/go-sql-driver/mysql"	termbox "github.com/nsf/termbox-go"	"time")//全局变量var (	db        *sql.DB	ip        string	port      string	username  string	password  string	database  string	wait_time int	content   string)

读取ini文件,赋值给全局变量

读取ini文件这里用到的是github.com/go-ini/ini

安装命令

go get gopkg.in/ini.v1
func initIni() error {
cfg, err := ini.Load("my.ini") if err != nil {
return errors.New("ini文件读取失败") } ip = cfg.Section("mysql").Key("ip").String() port = cfg.Section("mysql").Key("port").String() username = cfg.Section("mysql").Key("username").String() password = cfg.Section("mysql").Key("password").String() database = cfg.Section("mysql").Key("database").String() content = cfg.Section("mysql").Key("content").String() wait_time, err = cfg.Section("mysql").Key("wait_time").Int() if err != nil {
return errors.New("wait_time参数不是整数") } return nil}

初始化Mysql连接

func initDB() (err error) {
var dsn = fmt.Sprintf("%s:%s@tcp(%s:%s)/%s", username, password, ip, port, database) //Open只会验证dsb的格式是否正确,不会验证是否连接成功,同理,密码是否正确也不知道 db, err = sql.Open("mysql", dsn) if err != nil {
return errors.New("格式错误") } // 此时尝试连接数据库,会判断用户,密码,ip地址,端口是否正确 err = db.Ping() if err != nil {
return errors.New("配置错误") } return nil}

根据数据库获取当前数据库下所有表

type Table struct {
//表名 TableName string}// 根据数据库获取当前数据库下所有表func DatabaseToTables() ([]Table, error) {
var sqlStr = "show TABLES;" rows, err := db.Query(sqlStr) if err != nil {
return nil, errors.New("查询失败") } defer rows.Close() var tables = make([]Table, 0, 100) for rows.Next() {
var table Table err = rows.Scan(&table.TableName) if err != nil {
return nil, errors.New("绑定数据失败") } tables = append(tables, table) } return tables, nil}

根据表名获取当前表所有字段

type Field struct {
//列名 ColumnName string}// 根据表名获取当前表所有字段func TableToFields(table string) ([]Field, error) {
var sqlStr = "select COLUMN_NAME from information_schema.COLUMNS where table_name = '%s';" sqlStr = fmt.Sprintf(sqlStr, table) rows, err := db.Query(sqlStr) if err != nil {
return nil, errors.New("查询失败") } defer rows.Close() var fields = make([]Field, 0, 100) for rows.Next() {
var field Field err = rows.Scan(&field.ColumnName) if err != nil {
return nil, errors.New("绑定数据失败") } fields = append(fields, field) } return fields, nil}

根据字段一一查询

func FieldSelect(table, field, content string) (map[string]string, error) {
//fmt.Println(table, field, content) var sqlStr = "SELECT * from %s where %s like '%%%s%%';" sqlStr = fmt.Sprintf(sqlStr, table, field, content) rows, err := db.Query(sqlStr) if err != nil {
return nil, errors.New("sql查询失败") } //函数结束释放链接 defer rows.Close() //sql转map result, err := ScanRow(rows) if err != nil {
return nil, err } return result, nil}//获取单个func ScanRow(rows *sql.Rows) (map[string]string, error) {
//读出查询出的列字段名 cols, _ := rows.Columns() //values是每个列的值,这里获取到byte里 values := make([][]byte, len(cols)) //query.Scan的参数,因为每次查询出来的列是不定长的,用len(cols)定住当次查询的长度 scans := make([]interface{
}, len(cols)) //让每一行数据都填充到[][]byte里面,狸猫换太子 for i := range values {
scans[i] = &values[i] } //获取单行必须Next() rows.Next() //传指针进去,但是不通过指针能获取值 err := rows.Scan(scans...) if err != nil {
return nil, errors.New("Scan失败") } row := make(map[string]string) for k, v := range values {
//cols[k]为字段名 key := cols[k] row[key] = string(v) } return row, nil}

暂停等待,不让cmd直接结束

func pause() {
fmt.Println("请按任意键继续...")Loop: for {
switch ev := termbox.PollEvent(); ev.Type {
case termbox.EventKey: break Loop } }}

main(主要逻辑)

func main() {
//初始化ini err := initIni() if err != nil {
fmt.Println("错误:", err) pause() return } //初始化mysql err = initDB() if err != nil {
fmt.Println("错误:", err) pause() return } //开始时间 begin_time := time.Now() // begin:主要逻辑,三层for循环 //根据数据库获取当前数据库下所有表 tables, err := DatabaseToTables() if err != nil {
fmt.Println("错误:", err) pause() return } for _, table := range tables {
fields, err := TableToFields(table.TableName) if err != nil {
fmt.Println("错误:", err) pause() return } for _, field := range fields {
_, err := FieldSelect(table.TableName, field.ColumnName, content) //err != nil表示查询失败,继续下次查询 if err != nil {
continue } //fmt.Println(row) fmt.Printf("表名:%s,列名:%s\n", table.TableName, field.ColumnName) //睡眠指定时间 time.Sleep(time.Millisecond * time.Duration(wait_time)) } } elapsed_time := time.Now().Sub(begin_time) fmt.Println("运行时间:", elapsed_time) //任意键结束 pause() //end:主要逻辑}

总结

本次是上次Python脚本的翻译版,但是在此基础之上,让程序变的更通用,直接是exe

源码在这,如果可以,还可以打包成Mac版,Linux版,只要你愿意,咋样都行!

相比之下,我现在开发项目更倾向Go!

如果在操作过程中有任何问题,记得下面留言,我们看到会第一时间解决问题。

乾坤未定,你我皆是黑马。

我是码农星期八,如果觉得还不错,记得动手点赞一下哈。

感谢你的观看。

转载地址:http://rmvmi.baihongyu.com/

你可能感兴趣的文章
struts+spring+hibernate的web应用<四> Web层代码编写(1)
查看>>
struts+spring+hibernate的web应用<四> Web层代码编写(2)
查看>>
struts+spring+hibernate分别用到了什么设计模式
查看>>
java scoket 编程实例
查看>>
Struts 1 和 Struts 2 的线程安全
查看>>
数据库视图作用
查看>>
数据库查询的5种视图以及作用
查看>>
为什么要使用Hibernate
查看>>
Hibernate工作原理及为什么要用?
查看>>
Hibernate如何调用存储过程
查看>>
Hibernate HQL 插入,查询,更新
查看>>
Hibernate的HQL查询语句对比Sql语句学习
查看>>
struts标签bean:cookie,bean:write,logic:page,logic:present,logic:iterate使用实例
查看>>
为什么要使用Spring
查看>>
Spring Ioc与工厂模式的区别
查看>>
AspectJ AOP实现
查看>>
Java工厂模式Ioc和AOP 框架设计
查看>>
Spring框架与AOP思想的研究与应用(1)
查看>>
Spring框架与AOP思想的研究与应用(2)
查看>>
一个简单的Spring的AOP例子
查看>>