2016-09-20 49 views
0

我想學習如何避免SQL注入,並使用VBA通過ADO在VB中連接到一個MySQL數據庫。參數不添加到ADO字符串的INSERT語句VBA

我遇到的問題是,對於線

Set rs = cmd.Execute 

我碰到下面的錯誤,我一直沒能在兩天推測:「沒有一個或多個必需的參數給定值」。

而且肯定的是,打印帕拉姆字符串時,返回此:(我注意到在PARAMS的區別..不知道爲什麼它會出現)

INSERT INTO prm1=? VALUES prm2=?, prm3=?, prm4=?, prm5=?, prm6=?, prm7=?, prm8=?, prm9=?, prm10=?, prm11=?, prm12=?, prm13=?; 

這是我使用的澄清代碼:

Function addToServer(file As String, server As Integer, lastRow As Integer) 

Sheets("usage").Select 
Dim str As String 
Dim i As Integer 

Dim conn As ADODB.Connection 
Set conn = DBConnection 
Dim rs As ADODB.Recordset 
Set rs = New ADODB.Recordset 

Dim cmd As ADODB.Command 
Dim prm2 As ADODB.Parameter 
    Dim prm3 As ADODB.Parameter 
    Dim prm4 As ADODB.Parameter 
    Dim prm5 As ADODB.Parameter 
    Dim prm6 As ADODB.Parameter 
     Dim prm7 As ADODB.Parameter 
     Dim prm8 As ADODB.Parameter 
     Dim prm10 As ADODB.Parameter 
     Dim prm11 As ADODB.Parameter 
      Dim prm12 As ADODB.Parameter 
      Dim prm13 As ADODB.Parameter 
      Dim prm14 As ADODB.Parameter 
      Dim prm15 As ADODB.Parameter 

Set cmd = New ADODB.Command 
cmd.ActiveConnection = conn 

    With cmd 
     If server <> 0 Then 
      .CommandText = "INSERT INTO NLVMerlinResults (Year, Month, Day, Lab, Station, IP, thisWeek, Week1, Week2, Week3, Week4, Week5, WeeksInMonth, SumOverWeeks) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?);" 
     Else 
      .CommandText = "INSERT INTO STMerlinResults (Year, Month, Day, Lab, Station, IP, thisWeek, Week1, Week2, Week3, Week4, Week5, WeeksInMonth, SumOverWeeks) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?) ;" 
     End If 

     cmd.CommandType = adCmdText 

     Set prm2 = .CreateParameter(Name:="year", Type:=adInteger, size:=4) 
     .Parameters.Append prm2 
     Set prm3 = .CreateParameter(Name:="month", Type:=adSmallInt, size:=2) 
     .Parameters.Append prm3 
     Set prm4 = .CreateParameter(Name:="day", Type:=adSmallInt, size:=2) 
     .Parameters.Append prm4 
     Set prm5 = .CreateParameter(Name:="lab", Type:=adVarChar, size:=30) 
     .Parameters.Append prm5 
     Set prm6 = .CreateParameter(Name:="cell", Type:=adVarChar, size:=30) 
     .Parameters.Append prm6 
     Set prm7 = .CreateParameter(Name:="ip", Type:=adVarChar, size:=20) 
     .Parameters.Append prm7 
     Set prm8 = .CreateParameter(Name:="week", Type:=adSmallInt, size:=2) 
     .Parameters.Append prm8 
     Set prm9 = .CreateParameter(Name:="1", Type:=adVarChar, size:=10) 
     .Parameters.Append prm9 
     Set prm10 = .CreateParameter(Name:="2", Type:=adVarChar, size:=10) 
     .Parameters.Append prm10 
     Set prm11 = .CreateParameter(Name:="3", Type:=adVarChar, size:=10) 
     .Parameters.Append prm11 
     Set prm12 = .CreateParameter(Name:="4", Type:=adVarChar, size:=10) 
     .Parameters.Append prm12 
     Set prm13 = .CreateParameter(Name:="5", Type:=adVarChar, size:=10) 
     .Parameters.Append prm13 
     Set prm14 = .CreateParameter(Name:="weeksinmonth", Type:=adTinyInt, size:=1) 
     .Parameters.Append prm14 
     Set prm15 = .CreateParameter(Name:="total", Type:=adVarChar, size:=10) 
     .Parameters.Append prm15 

    Dim j As Integer 
    For i = 1 To lastRow 
     For j = 1 To 15 
      If (j = 1) Then 
       prm2.value = CLng(cells(i, j)) 
      ElseIf (j = 2) Then 
       prm3.value = CInt(cells(i, j)) 
      ElseIf (j = 3) Then 
       prm4.value = CInt(cells(i, j)) 
      ElseIf (j = 4) Then 
       prm5.value = CStr(cells(i, j)) 
      ElseIf (j = 5) Then 
       prm6.value = CStr(cells(i, j)) 
      ElseIf (j = 6) Then 
       prm7.value = CStr(cells(i, j)) 
      ElseIf (j = 7) Then 
       prm8.value = CInt(cells(i, j)) 
      ElseIf (j = 8) Then 
       If IsEmpty((cells(i, j))) Then 
        prm9.value = vbNullString 
       Else 
        prm9.value = CStr(cells(i, j)) 
       End If 
      ElseIf (j = 9) Then 
       If IsEmpty((cells(i, j))) Then 
        prm10.value = vbNullString 
       Else 
        prm10.value = CStr(cells(i, j)) 
       End If 
      ElseIf (j = 10) Then 
       If IsEmpty((cells(i, j))) Then 
        prm11.value = vbNullString 
       Else 
        prm11.value = CStr(cells(i, j)) 
       End If 
      ElseIf (j = 11) Then 
       If IsEmpty((cells(i, j))) Then 
        prm12.value = vbNullString 
       Else 
        prm12.value = CStr(cells(i, j)) 
       End If 
      ElseIf (j = 12) Then 
       If IsEmpty((cells(i, j))) Then 
        prm13.value = vbNullString 
       Else 
        prm13.value = CStr(cells(i, j)) 
       End If 
      ElseIf (j = 13) Then 
       prm14.value = CByte(cells(i, j)) 
      ElseIf (j = 14) Then 
       prm15.value = CStr(cells(i, j)) 
      End If 
     Next j 
      .Execute 
    Next i 

End With 
Set cmd = Nothing 
End Function 

我有兩種不同的方法,我使用上面顯示,但它似乎既不是兩項工作。有人能爲我能做些什麼提供幫助嗎?我嘗試從.CreateParameter函數中取出參數(http://www.w3schools.com/asp/met_comm_createparameter.asp表示它們是可選的),但那也沒用。

最佳,

阿什利

編輯::我已經在上面添加編輯。我嘗試了一個測試插入,它是成功的。

INSERT INTO `NLVMerlinResults` (Year, Month, Day, Lab, Station, IP, thisWeek, Week1, Week2, Week3, Week4, Week5, WeeksInMonth, SumOverWeeks) VALUES ("1", "2", "3", "4", "5", 1, 5, "5", "5", "6", 6, "5", "4", "5") 

雖然它的奇怪的是,它讓我進入整數和字符串時,DB只需要VARCHAR ...

+2

問題的至少一部分是你不能參數化一個表名:只有字段值。請參閱:http://stackoverflow.com/questions/11312737/can-i-parameterize-the-table-name-in-a-prepared-statement –

+0

'INSERT INTO SET'? – Comintern

+0

...並且您的插入語法看起來不對 –

回答

1

刪除「限定符=?」來自SQL語句。 ODBC參數與單個?規定,並在相同的順序,它們出現在語句中加入:

INSERT INTO `NLVMerlinResults` (Year, Month, Day, Lab, Station, IP, 
thisWeek, Week1, Week2, Week3, Week4, Week5, WeeksInMonth, SumOverWeeks) 
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?) 

OP編輯:在問題的講話中提供的功能代碼。

+0

這仍然是在同一個地方出錯,抱怨「沒有給出一個或多個必需參數的值」。 –

+0

@noc_coder - 將Set rs = cmd.Execute更改爲cmd.Execute,將cmd.CommandType = adCmdStoredProc更改爲cmd.CommandType = adCmdText。 – Comintern

+0

我在進行這些更改後使用了調試器,因爲excel只是在cmd.Execute上關閉。我打印每個參數,它們都用Debug.print打印出來。然而,整體而言,顯示爲...VALUES(?,?,?,?,?,?,?,?,?,?,?,?,?,?)。然後它就在那條線上關閉。 –