为了账号安全,请及时绑定邮箱和手机立即绑定

从 SQL 查询中获取表名

从 SQL 查询中获取表名

Go
不负相思意 2023-06-01 15:05:43
我正在使用golang SQL 解析器从实际的 SQL 查询字符串中获取查询相关信息。我可以使用以下代码找到查询类型:queryType := sqlparser.StmtType(sqlparser.Preview(sql)) fmt.Println(queryType)但我不确定如何从 sql 查询中获取实际的表名。文档也不清楚。我从解析函数中得到的唯一信息是一条语句有人可以指导我如何使用 golang sqlparser 获取此信息吗?
查看完整描述

3 回答

?
烙印99

TA贡献1829条经验 获得超13个赞

Statement要获取所有表名,您必须将它们从返回的 by中拉出Parse,可能使用反射。如果您运行以下代码:


stmt, _ := sqlparser.Parse("insert into my_table set my_column=1")

fmt.Printf("%#v\n", stmt)

你得到输出(为了便于阅读而缩进):


&sqlparser.Insert{

    Action:"insert", 

    Comments:sqlparser.Comments(nil), 

    Ignore:"", 

    Table:sqlparser.TableName{

        Name:sqlparser.TableIdent{v:"my_table"}, 

        Qualifier:sqlparser.TableIdent{v:""}

    }, 

    Partitions:sqlparser.Partitions(nil), 

    Columns:sqlparser.Columns{sqlparser.ColIdent{_:[0]struct { _ []uint8 }{}, val:"my_column", lowered:""}}, 

    Rows:sqlparser.Values{sqlparser.ValTuple{(*sqlparser.SQLVal)(0xc00000a0c0)}}, 

    OnDup:sqlparser.OnDup(nil)

}

如您所见,它包含一个类型的(子)字段TableIdent,其中包含语句中请求的表。


查看完整回答
反对 回复 2023-06-01
?
qq_遁去的一_1

TA贡献1725条经验 获得超7个赞

原始片段还返回了表的别名。例如


select * from my_table as mt join other_table using(my_key)

original snippet returns: [my_table, mt, other_table]

new snippet returns:      [my_table, other_table]

rob74 的原始片段:play.golang.org/p/B31wr2w1AL8


package main


import (

    "fmt"

    "github.com/xwb1989/sqlparser"

    "reflect"

)


func main() {

    stmt, _ := sqlparser.Parse("select * from my_table as mt join other_table using(my_key)")

    var tables []string

    tables = getTableNames(reflect.Indirect(reflect.ValueOf(stmt)), tables, 0, false)

    fmt.Printf("%s", tables)

}


func getTableNames(v reflect.Value, tables []string, level int, isTable bool) []string {

    switch v.Kind() {

    case reflect.Struct:

        if v.Type().Name() == "TableIdent" {

            // if this is a TableIdent struct, extract the table name

            tableName := v.FieldByName("v").String()

            if tableName != "" && isTable{

                tables = append(tables, tableName)

            }

        } else {

            // otherwise enumerate all fields of the struct and process further

            for i := 0; i < v.NumField(); i++ {

                tables = getTableNames(reflect.Indirect(v.Field(i)), tables, level+1, isTable)

            }

        }

    case reflect.Array, reflect.Slice:

        for i := 0; i < v.Len(); i++ {

            // enumerate all elements of an array/slice and process further

            tables = getTableNames(reflect.Indirect(v.Index(i)), tables, level+1, isTable)

        }

    case reflect.Interface:

        if v.Type().Name() == "SimpleTableExpr" {

            isTable = true

        }

        // get the actual object that satisfies an interface and process further

        tables = getTableNames(reflect.Indirect(reflect.ValueOf(v.Interface())), tables, level+1, isTable)

    }


    return tables

}


查看完整回答
反对 回复 2023-06-01
?
白衣染霜花

TA贡献1796条经验 获得超10个赞

我为 SQL 查询编写了一些字符串操作库来获取表名:


queryString := sqlstr.NewQueryString(`SELECT column_name(s)

FROM table1

LEFT JOIN table2

ON table1.column_name = table2.column_name;`)


tableNames := queryString.TableNames()


fmt.Println(tableNames)


// Output:

// [table1 table2]


查看完整回答
反对 回复 2023-06-01
  • 3 回答
  • 0 关注
  • 267 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信