Board logo

標題: [發問] 圖形驗證(Captcha) 破解? [打印本頁]

作者: lalalada    時間: 2013-5-10 22:22     標題: 圖形驗證(Captcha) 破解?

證交所開放下載csv檔了~  http://bsr.twse.com.tw/bshtm/
想改寫之前的下載方式
本來是利用web查詢在另存成csv檔
但是效率很差

在證交所網站中
下載前必須輸入圖形驗證
而且每次會不同
想知道有沒有辦法在VBA上破解?
目前的想法有二
一是使用圖形辨識(OCR)
就網頁上的圖看起來還算工整
只是這麼做效率可能也不會太好(?) 還沒試過
第二個想法是利用網頁cookie
我猜輸入驗證碼之後會得到一組cookie作為鑰匙
利用VBA生成/保留那組cookie說不定可以一勞永逸?
不知道有沒有解法 感謝!!
作者: mark15jill    時間: 2013-5-16 15:44

證交所開放下載csv檔了~  http://bsr.twse.com.tw/bshtm/
想改寫之前的下載方式
本來是利用web查詢在另存 ...
lalalada 發表於 2013-5-10 22:22



    1.如果用OCR 辨識  會有幾個問題產生
      1-1 完整性 <英文、數字、文字>
      2-2 可辨識度 < 如 圖內 X、Y點,或 其他>

     2.如果用Cookie ,那 可以跟妳說..  基本上 此方法幾乎不可能...
         原因為何? 除非,妳有該網站所有圖形驗證的圖資 或  妳能辨識 圖形,否則 COOKIE 不會是固定的
         如果 今天A網站 的 圖形驗證的圖資有100種 , 基本上 就有可能有 100種COOKIE ...
作者: lalalada    時間: 2013-5-19 12:27

回復 2# mark15jill

感謝回覆!
那如果想使用OCR的話
在VBA內該怎麼引用呢?

辨識的話因為剛好網站只採用數字
而且底色單純也沒有太多變形處理
OCR辨識應該是可行的
由於少掉了對圖形的處理
說不定還是能比原本的作法快(?)

其實原本的作法除了繞路之外
速度慢的其中一個原因是因為它會擋大量連續連線要求
每五次必須等5秒左右
作者: mark15jill    時間: 2013-5-20 11:49

回復 3# lalalada


    抱歉 關於這部份小弟就無深入研究
作者: lalalada    時間: 2013-5-20 14:40

回復 4# mark15jill

還是很感謝你願意分享:)
最近比較忙
等我找到方法再po上來
作者: joey0415    時間: 2013-9-27 22:28

本帖最後由 joey0415 於 2013-9-27 22:29 編輯

回復 5# lalalada


    圖形部份,excel home藍天大有,不過我還不會用
http://club.excelhome.net/home.php?mod=space&uid=1666515&do=thread&view=me&from=space

每日券商我是下載csv

上市:每日約30分(網頁轉csv)
上櫃:每日5分(csv)

轉進資料庫另計

以上為vba

聽說用python可以多線下載會更快,不過我沒有用!
作者: GBKEE    時間: 2013-9-28 16:40

回復 5# lalalada
試試看
  1. Option Explicit
  2. Sub 證交所_買賣交易日報表()
  3.     Dim Stock_NO As String, Sh As Worksheet, URL As String, WB As Workbook
  4.     Do
  5.       Stock_NO = InputBox("股票號碼")
  6.       If Stock_NO = "" Then Exit Sub
  7.     Loop Until Len(Stock_NO) >= 4
  8.     Set Sh = ActiveWorkbook.Sheets.Add
  9.     Application.DisplayAlerts = False
  10.     On Error GoTo Er
  11.     Sh.Name = Stock_NO
  12.     Application.StatusBar = "下載資料中.... "
  13.     Application.ScreenUpdating = False
  14.     URL = "http://bsr.twse.com.tw/bshtm/bsContent.aspx?StartNumber=" & Stock_NO & "&FocusIndex=All_" & 報表頁數(Stock_NO)
  15.     Set WB = Workbooks.Open(URL)
  16.     With WB.Sheets(1)
  17.         If .UsedRange.Count = 1 Then GoTo xOUT         '股票沒有資料
  18.         .UsedRange.Columns("A:Q").ClearFormats
  19.         .UsedRange.Columns("B:H").Delete Shift:=xlToLeft
  20.         .UsedRange.Columns("B:B").SpecialCells(xlCellTypeBlanks).Offset(, -1).Delete xlShiftUp
  21.         .UsedRange.Columns("B:E").SpecialCells(xlCellTypeBlanks).Delete xlShiftUp
  22.         .UsedRange.Columns("F:J").SpecialCells(xlCellTypeBlanks).Delete xlShiftUp
  23.         .UsedRange.Columns("F:J").Cut .Cells(.Rows.Count, "A").End(xlUp).Offset(1)
  24.         .Rows("1:2").Delete
  25.         With .UsedRange
  26.             .Value = .Value
  27.             .Sort Key1:=.Range("A2"), Order1:=xlAscending, Header:=xlYes
  28.             .Offset(3).Replace "序", "=XXX", xlWhole
  29.             .SpecialCells(xlCellTypeFormulas, xlErrors).EntireRow.Delete
  30.         End With
  31.         .UsedRange.Copy Sh.[A1]
  32.         Sh.UsedRange.EntireColumn.AutoFit
  33.     End With
  34.     WB.Close False
  35.     Application.ScreenUpdating = True
  36.     Application.StatusBar = False
  37.     Exit Sub
  38. Er:
  39.     Sheets(Stock_NO).Delete
  40.     Resume
  41. xOUT:
  42.     WB.Close False
  43.     Sheets(Stock_NO).Delete
  44.     MsgBox "沒有股票 " & Stock_NO
  45.     Application.StatusBar = False
  46.     Application.ScreenUpdating = True
  47. End Sub
  48. Private Function 報表頁數(Sstock_N0 As String) As String
  49.     Dim element As Object
  50.     With CreateObject("InternetExplorer.Application")
  51.         .Navigate "http://bsr.twse.com.tw/bshtm/bsMenu.aspx"
  52.          Do While .Busy Or .ReadyState <> 4
  53.             DoEvents
  54.         Loop
  55.         .Document.getElementsByName("txtTASKNO")(0).Value = Sstock_N0
  56.         .Document.getElementsByName("btnOK")(0).Click
  57.          Do While .Busy Or .ReadyState <> 4
  58.             DoEvents
  59.         Loop
  60.        報表頁數 = .Document.getElementsByName("sp_ListCount")(0).innertext
  61.        .Quit
  62.     End With
  63. End Function
複製代碼

作者: HSIEN6001    時間: 2013-9-28 18:41

回復 7# GBKEE


    關於圖形驗證Captcha的方式,這是joey0415提供得[參考]來源
看不懂^_^!!          但跑驗證碼是正確的
  1. Public Declare Function GetClipboardData Lib "user32" (ByVal wFormat As Long) As Long
  2. Public Declare Function CloseClipboard Lib "user32" () As Long
  3. Public Declare Function OpenClipboard Lib "user32" (ByVal hwnd As Long) As Long
  4. Private Declare Function GlobalLock Lib "kernel32" (ByVal hMem As Long) As Long
  5. Private Declare Function GlobalSize Lib "kernel32" (ByVal hMem As Long) As Long
  6. Private Declare Function GlobalUnlock Lib "kernel32" (ByVal hMem As Long) As Long
  7. Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (Destination As Any, Source As Any, ByVal Length As Long)
  8. '剪貼版資料格式定義
  9. Private Const CF_DIB = 8

  10. Sub 驗證碼識別()
  11.     Dim a(1 To 4)
  12.     Dim img       '(驗證碼)圖片
  13.     Dim CtrlRange '非文本物件集合
  14.     Dim bytClipData()  As Byte '定義位元組陣列
  15.     Dim arr(0 To 1260)
  16.     Dim ts As Integer
  17.     On Error Resume Next
  18.     Set Regedit_XG = CreateObject("WScript.Shell")              '創建一個空的VBS"殼"
  19.     Jz = Regedit_XG.RegRead("HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Internet Settings\Zones\3\1407")                   '讀取註冊表"安全設置-Internet區域"中的"允許對剪貼板進行編程訪問"設置(3=禁用、0=啟用、1=提示)原始值
  20.     Regedit_XG.RegWrite "HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Internet Settings\Zones\3\1407", "0", "REG_DWORD"      '修改註冊表"安全設置-Internet區域"中的"允許對剪貼板進行編程訪問"設置(3=禁用、0=啟用、1=提示),使系統默認為"允許訪問剪貼板"
  21.     With CreateObject("InternetExplorer.application")           '創建一個空的ie
  22.         .Visible = True                                         '讓ie可見
  23.         .Navigate "http://119.145.135.38/fscx/web/loginForm.do" '導航到http://119.145.135.38/fscx/web/loginForm.do
  24.         Do Until .ReadyState = 4               '等待ie完畢載入
  25.             DoEvents
  26.         Loop
  27.         Set img = .Document.All.tags("img")(0) '指定(驗證碼)目標圖片
  28.         Set CtrlRange = .Document.body.createControlRange()  '創建非文本物件 ControlRange 集合
  29.         CtrlRange.Add img                      '向非文本物件 ControlRange 集合中添加 img 物件
  30.         CtrlRange.execCommand "Copy", True     '從 ControlRange 集合中copy img 物件(圖片)到剪貼板
  31.         Dim hMem As Long, lpData As Long
  32.         OpenClipboard 0&                       '打開粘貼板
  33.         hMem = GetClipboardData(8)             '獲得粘貼板資料,指定格式為:CF_DIB = 8
  34.         If CBool(hMem) Then
  35.             lpData = GlobalLock(hMem)          '鎖定記憶體物件hMen
  36.             lClipSize = GlobalSize(hMem)       '獲得粘貼板資料位元組數
  37.             If lpData <> 0 And lClipSize > 0 Then
  38.                 ReDim bytClipData(0 To lClipSize - 1) As Byte      '重新定義位元組陣列大小
  39.                 CopyMemory bytClipData(0), ByVal lpData, lClipSize '粘貼板轉化成位元組陣列
  40.             End If
  41.             GlobalUnlock hMem                  '解除鎖定記憶體物件hMen
  42.         End If
  43.         CloseClipboard                         '關閉粘貼板
  44.         For i = 1 To 1260                      '歸一化處理
  45.             ts = (Val(bytClipData((i - 1) * 3 + 40)) + Val(bytClipData((i - 1) * 3 + 41)) + Val(bytClipData((i - 1) * 3 + 42))) / 3 '40是圖片開始位元組
  46.             If ts > 150 Then
  47.                 ts = 0
  48.             Else
  49.                 ts = 1
  50.             End If
  51.             arr(i) = ts
  52.         Next i
  53.         For i = 1 To 4
  54.             a(i) = 0                                                          '0
  55.             If arr(13 * 60 + 8 + (i - 1) * 14) = 1 And arr(14 * 60 + 8 + (i - 1) * 14) = 1 Then a(i) = 1: GoTo 1 '16位色,所以乘以"3"RGB各占一位元組,60是寬,14是字間距,
  56.             If arr(4 * 60 + 6 + (i - 1) * 14) = 1 Then a(i) = 2: GoTo 1       '2
  57.             If arr(16 * 60 + 11 + (i - 1) * 14) = 0 Then a(i) = 3: GoTo 1     '3
  58.             If arr(7 * 60 + 5 + (i - 1) * 14) = 1 Then a(i) = 4: GoTo 1       '4
  59.             If arr(12 * 60 + 9 + (i - 1) * 14) = 1 Then a(i) = 5: GoTo 1      '5
  60.             If arr(9 * 60 + 8 + (i - 1) * 14) = 1 And arr(11 * 60 + 9 + (i - 1) * 14) = 1 Then a(i) = 6: GoTo 1  '6
  61.             If arr(16 * 60 + 13 + (i - 1) * 14) = 1 Then a(i) = 7: GoTo 1     '7
  62.             If arr(10 * 60 + 8 + (i - 1) * 14) = 1 And arr(11 * 60 + 8 + (i - 1) * 14) = 1 Then a(i) = 8: GoTo 1 '8
  63.             If arr(9 * 60 + 9 + (i - 1) * 14) = 1 Then a(i) = 9               '9
  64. 1:
  65.         Next i
  66.         Cells(1, 1) = a(1) & a(2) & a(3) & a(4)             '識別後的驗證碼
  67.         .Document.All.tags("INPUT")(0).Value = "1234567890" '填寫登錄名
  68.         .Document.All.tags("INPUT")(1).Value = "0987654321" '填寫密  碼
  69.         .Document.All.tags("INPUT")(2).Value = Cells(1, 1)  '填寫驗證碼
  70.         .Document.All.tags("img")(1).Click                  '點擊"登錄"按鈕
  71.         '.Quit                     '關閉ie
  72.         'MsgBox "OK"
  73.     End With
  74.     Regedit_XG.RegWrite "HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Internet Settings\Zones\3\1407", Jz, "REG_DWORD"      '恢復註冊表"安全設置-Internet區域"中的"允許對剪貼板進行編程訪問"設置(3=禁用、0=啟用、1=提示)原始值
  75.     Set Regedit_XG = Nothing      '釋放VBS"殼"
  76. End Sub
複製代碼

作者: HSIEN6001    時間: 2013-9-28 18:59

回復 7# GBKEE


    對不起!忘了附上URL
下載CSV相關位址:
(1)不知道用的上?!
http://bsr.twse.com.tw/bshtm/bsMenu.aspx?__EVENTTARGET=&__EVENTARGUMENT=&__VIEWSTATE=%2FwEPDwUKLTQzNzI3ODE3MQ9kFgICAQ9kFg4CBQ8WAh4JaW5uZXJodG1sBQoyMDEzLzA5LzI3ZAIGDxYCHwAFCDIwMTMwOTI3ZAIIDw8WBh4JRm9udF9Cb2xkZx4EXyFTQgKEEB4JRm9yZUNvbG9yCj1kZAIKD2QWAgIBDw9kFgIeB09uQ2xpY2sFHGphdmFzY3JpcHQ6YnV0Q2xlYXJfQ2xpY2soKTtkAgwPDxYGHwFoHwIChBAfAwpHZGQCDg8PFgIeB1Zpc2libGVoZGQCEA8PFgYfAWgfAgKEEB8DCkdkZGSiKU%2Fti2BvI3vsAvp%2BUySKAAAAAA%3D%3D&__EVENTVALIDATION=%2FwEWCQKGnJS3DwLjpuXcAwKN4Ij0CwLB5ZfoCQLjk6TKBwKY8en5CwLdkpmPAQL6n7vzCwLAhrvLBeRfGpOZWTxdVZsdlLXS6sgAAAAA&HiddenField_spDate=&HiddenField_page=PAGE_DownloadBS&txtTASKNO=%E8%AB%8B%E8%BC%B8%E5%85%A5%E8%82%A1%E7%A5%A8%E4%BB%A3%E7%A2%BC&hidTASKNO=&Button_DownloadBS=%3C%E4%B8%8B%E8%BC%89+CSV%3E

(2)Download
http://bsr.twse.com.tw/bshtm/bsDownload.aspx?__VIEWSTATE=%2FwEPDwUJNDA4NDA2OTYwZGSrd3Tlksjh9VIjA2KPwnxSAAAAAA%3D%3D&__EVENTVALIDATION=%2FwEWBgLgmuzfAwLPiaeCCQLNkNdZAs%2Bk8%2FwMAp%2BC7OYNAsyPx6EHbi4KW9bFIDAKFtSJoAwOXQAAAAA%3D&HiddenField_Download=&TextBox_Stkno=股票代號&TextBox_VerifyCode=驗證碼&Button_Download=%E4%B8%8B%E8%BC%89
作者: joey0415    時間: 2013-9-28 22:33

回復 9# HSIEN6001

不知HSIEN6001大

可以改成驗證台灣的嗎?

我自己試是不成功的,讀台灣驗證碼部份
作者: GBKEE    時間: 2013-9-29 07:45

回復 9# HSIEN6001
對圖形驗證沒研究,所以下載列印的檔案.
作者: HSIEN6001    時間: 2013-9-29 09:49

回復 10# joey0415


VBA我懂很少耶!!

測試心得   
(1)可以先導向http://bsr.twse.com.tw/bshtm/bsDownload.aspx?__VIEWSTATE=%2FwEPDwUJNDA4NDA2OTYwZGSrd3Tlksjh9VIjA2KPwnxSAAAAAA%3D%3D&__EVENTVALIDATION=%2FwEWBgLgmuzfAwLPiaeCCQLNkNdZAs%2Bk8%2FwMAp%2BC7OYNAsyPx6EHbi4KW9bFIDAKFtSJoAwOXQAAAAA%3D&HiddenField_Download=&TextBox_Stkno=股票代碼
(2)再輸入驗證碼 (這,我也不會 ^_^ ,抱歉!)
(3)其後,驗證碼正確後  if(document.getElementById('HiddenField_Download').value == 'OK')
好像還得回到 http://bsr.twse.com.tw/bshtm/ 才會完成 [下載]

好像是這樣 (搔頭傻笑
作者: lalalada    時間: 2013-10-1 00:11

回復 7# GBKEE

版主好~
這個應該是單一股票下載的版本
寫法跟我的差很多呢 學到不少@@
可是我實際跑的時候會出錯... Run-time error '91'
Object variable or With block variable not set
標黃色的是報表頁數function下的   報表頁數  .Document.getElementsByName("sp_ListCount")(0).innertext  這行
我晚點再來研究哪裡出了問題

下載方面我目前沒有問題
能夠下載全部上市櫃的資料了
主要是想增加速度
所以直觀想到的辦法一個是破解驗證碼直接下載csv
另外一個則是每下載幾個就換ip繞過時間鎖(這個應該不可行)
作者: lalalada    時間: 2013-10-1 00:14

回復 6# joey0415

你好~
我們方式應該是一樣的
是網路情況大概2000秒可以下載完(同時跑其他資料的下載)
想請問怎麼轉入資料庫呢?!
我在彙整資料上也遇到問題..."
作者: lalalada    時間: 2013-10-1 00:16

回復 8# HSIEN6001


感謝分享~
可是我剛剛測了一下...
這要怎麼用啊XD
作者: HSIEN6001    時間: 2013-10-1 10:36

本帖最後由 HSIEN6001 於 2013-10-1 10:41 編輯

回復 15# lalalada

試試這個!!藍天大寫的
[attach]16209[/attach]
各樣式驗證碼識別 : http://club.excelhome.net/thread-896161-1-1.html
藍天大的Blog http://blog.csdn.net/a814153a/article/details/9375971
liucqa : http://club.excelhome.net/thread-897117-1-1.html
參考 : http://bbs.csdn.net/topics/390090057
論文 : http://www.digitaltrends.com/web/stanford-researchers-crack-captcha-codes/
-----------------------------------
抱歉!!以上我是,有看沒有懂  ^^

僅以下測試,完成下載券商日報表,流程:
(1)導向 http://bsr.twse.com.tw/bshtm/bsDownload.aspx?__VIEWSTATE=%2FwEPDwUJNDA4NDA2OTYwZGSrd3Tlksjh9VIjA2KPwnxSAAAAAA%3D%3D&__EVENTVALIDATION=%2FwEWBgLgmuzfAwLPiaeCCQLNkNdZAs%2Bk8%2FwMAp%2BC7OYNAsyPx6EHbi4KW9bFIDAKFtSJoAwOXQAAAAA%3D&HiddenField_Download=&TextBox_Stkno=1101  '先指定股票代號
(2)券商日報表的驗證碼,[待高手解決囉!] http://bsr.twse.com.tw/bshtm/VerifyImage.aspx?tick=635162133074615000
(3)回到 http://bsr.twse.com.tw/bshtm/
(4).Document.getElementById("Button_DownloadBS").Click                    '點擊,"下載CSV"
作者: lalalada    時間: 2013-10-1 21:40

回復 16# HSIEN6001

好哦!!
謝謝版主分享
又多學了一課~




歡迎光臨 麻辣家族討論版版 (http://forum.twbts.com/)