在golang中显示数据库的结果

huangapple go评论82阅读模式
英文:

Displaying results from a database in golang

问题

我正在从一个表单中读取一个MySQL查询输入:

<h1>MySQL页面</h1>
<small>在这里执行查询和编辑数据库</small>
<form method="get" action="">
  <label for="sqlQuery">MySQL查询:</label>
  <input type="text" id="sqlQuery" name="sqlQuery">
  <button type="submit">执行查询</button>
</form>

之后,我想使用GoLang在同一页上显示结果,但它一直告诉我:

# command-line-arguments
./sql.go:128: 无法将结果(类型为sql.Result)转换为字符串类型

请记住,这是我写的第一个GoLang应用程序,如果这是一个简单的问题,我很抱歉,以下是GoLang代码:

func sqlQueryHandler(response http.ResponseWriter, request *http.Request){
  userName := getUserName(request)
  db, err := sql.Open("mysql", userName)
  fmt.Fprintf(response, sqlPage)
  sqlCommand := request.FormValue("sqlQuery")
  //fmt.Fprintf(response, sqlCommand)
  if err != nil {
    fmt.Fprintf(response, "\n\n在执行MySQL命令时发生错误:%s", err)
    panic(err)
  } else {
    data, err := db.Exec(sqlCommand)
    if err != nil {
      http.Redirect(response, request, "/error", 302)
    } else {
      // 在这里显示SQL查询的输出
    }
  }
}
英文:

I'm reading a MySQL query input from a form:

&lt;h1&gt;MySQL Page&lt;/h1&gt;
&lt;small&gt;Perform queries and edit the database from here&lt;/small&gt;
&lt;form method=&quot;get&quot; action=&quot;&quot;&gt;
  &lt;label for=&quot;sqlQuery&quot;&gt;MySQL Query:&lt;/label&gt;
  &lt;input type=&quot;text&quot; id=&quot;sqlQuery&quot; name=&quot;sqlQuery&quot;&gt;
  &lt;button type=&quot;submit&quot;&gt;Perform Query&lt;/button&gt;
&lt;/form&gt;

After that I want to display the results on the same page using GoLang, however it keeps telling me that:

# command-line-arguments
./sql.go:128: cannot convert results (type sql.Result) to type string

Please keep in mind, this is the first golang app I've ever written so I apologize if this is a simple issue, here is the golang code:

func sqlQueryHandler(response http.ResponseWriter, request *http.Request){
  userName := getUserName(request)
  db, err := sql.Open(&quot;mysql&quot;, userName)
  fmt.Fprintf(response, sqlPage)
  sqlCommand := request.FormValue(&quot;sqlQuery&quot;)
  //fmt.Fprintf(response, sqlCommand)
  if err != nil {
    fmt.Fprintf(response, &quot;\n\nAn error occured during your MySQL command: %s&quot;, err)
    panic(err)
  } else {
    data, err := db.Exec(sqlCommand)
    if err != nil {
      http.Redirect(response, request, &quot;/error&quot;, 302)
    } else {
      // display the output of the sql query here
    }
  }
}

答案1

得分: 2

根据你的代码,这里有一个示例:

func sqlQueryHandler(response http.ResponseWriter, request *http.Request) {
    var (
        userName   = getUserName(request)
        sqlCommand = request.FormValue("sqlQuery")
    )

    db, err := sql.Open("mysql", userName)
    if err != nil {
        fmt.Fprintf(response, "\n\n在执行MySQL命令时发生错误:%s", err)
        // 如果发生错误,你可以在这里停止执行,不需要else语句
        panic(err)
    }
    rows, err := db.Query(sqlCommand)
    if err != nil {
        http.Redirect(response, request, "/error", 302)
        // 返回,所以不需要else语句
        return
    }

    if err != nil {
        panic(err)
    }
    defer rows.Close()
    for rows.Next() {
        var (
            name string
            age  int
        )
        if err := rows.Scan(&name, &age); err != nil {
            panic(err)
        }
        fmt.Printf("%s is %d\n", name, age)
    }
    if err := rows.Err(); err != nil {
        panic(err)
    }
}

然而,这种方法存在几个问题:

  • 你从服务器外部传递了SQL语句。任何访问这个函数的人都可以读取你服务器上的所有数据。
  • Go语言的一个优点是它是一种强类型语言。但是在这里,你正在构建一个处理通用SQL查询的函数,这与“强类型语言”的范例相矛盾。你可以编写处理不同结构化数据的通用函数(比如json.Unmarshal()),但是特别是在编程Go语言的早期阶段,你不应该这样做。
英文:

Here an example based on your code:

func sqlQueryHandler(response http.ResponseWriter, request *http.Request) {
	var (
		userName   = getUserName(request)
		sqlCommand = request.FormValue(&quot;sqlQuery&quot;)
	)

	db, err := sql.Open(&quot;mysql&quot;, userName)
	if err != nil {
		fmt.Fprintf(response, &quot;\n\nAn error occured during your MySQL command: %s&quot;, err)
		// if you panic you stop here anyway. no else needed
		panic(err)
	}
	rows, err := db.Query(sqlCommand)
	if err != nil {
		http.Redirect(response, request, &quot;/error&quot;, 302)
		// return, so no else is needed
		return
	}

	if err != nil {
		panic(err)
	}
	defer rows.Close()
	for rows.Next() {
		var (
			name string
			age  int
		)
		if err := rows.Scan(&amp;name, &amp;age); err != nil {
			panic(err)
		}
		fmt.Printf(&quot;%s is %d\n&quot;, name, age)
	}
	if err := rows.Err(); err != nil {
		panic(err)
	}
}

There are several problems however with this approach:

  • You are passing the sql from outside the server. Anyone accessing this can read all the data from your server.
  • One of Go's strengths is being a typed language. Here you are building a general sql query function which contradicts the typed language paradigm. You can write general function dealing with differently structured data (like json.Unmarshal()) -- but especially early in programming go you shouldn't.

huangapple
  • 本文由 发表于 2017年8月18日 00:04:39
  • 转载请务必保留本文链接:https://go.coder-hub.com/45740042.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定