Что нового

_StringBetween работает только для одной переменной (не знаю, как объяснить)

louie1743shkirondo

Новичок
Сообщения
28
Репутация
0
Собственно, в переменную записываю значение response (ответ на запрос VK API), затем в response ищу сообщения и записываю их в массив.
Проблема встала тогда, когда мне понадобилось определять: прочитано сообщение или нет, то бишь искать значение read_state в response, которое представляет собой целое число (1 или 0).
Я применил _StringBetween для поиска этого самого значения, но скрипт мне постоянно ничего не выдаёт (Пустой ответ).
Не знаю, с чем это связанно, но могу догадываться, что из-за числового значения..
Сам скрипт:
Код:
#include <String.au3>
#include <Array.au3>
#include <File.au3>
#include <IE.au3>
#include <Array.au3>

HotKeySet("{ESC}", "Close")

Global $File = @ScriptDir & "\Messages.txt"
If Not FileExists($File) Then _FileCreate($File)
GLobal $FileOpen = FileOpen($File)

Global $Token = 'Токен'
Global $Shell = "https://api.vk.com/method/messages.get?count=200&access_token=" & $Token & "&v=5.53"

   $oHTTP = ObjCreate('WinHttp.WinHttpRequest.5.1')
   $oHTTP.Open('GET', $Shell)
   $oHTTP.SetRequestHeader("User-Agent", "Mozilla/5.0 (Windows NT 6.3; WOW64; rv:48.0) Gecko/20100101 Firefox/48.0")
   $oHTTP.Send('')
   $oHTTP.WaitForResponse
   $res = $oHTTP.ResponseText

   ConsoleWrite($res & @CRLF)

   $Domain = _StringBetween($res, 'read_state":', ',')                                  <===========================================
   $Text = _StringBetween($res, 'body":"', '"')
   ConsoleWrite(@CRLF & $Domain)
   Global $Count = UBound($Text)

   Global $FullMessages[250]       ; Вообще, максимум сообщений за раз - 200. Но в массиве у меня было 209, поэтому я перестраховался
   $b = 0

   For $i In $Text
	  FileWrite($File, $i & @LF & $Domain & @CRLF)
	  $FullMessages[$b] = $i
	  $b = $b + 1
   Next




Func Close()
   Exit
EndFunc

P.S.
Оптимизация и реализация каких-либо действий только приветствуется
 

ra4o

AutoIT Гуру
Сообщения
1,165
Репутация
246
Этот участок кода можно так :
Код:
Global $FullMessages[0]      
   $b = 0

   For $i In $Text
      FileWrite($File, $i & @LF & $Domain & @CRLF)
	  ReDim $FullMessages[$b+1]
      $FullMessages[$b] = $i
      $b += 1
   Next
 
Автор
L

louie1743shkirondo

Новичок
Сообщения
28
Репутация
0
Спасибо, я поправлю)

Ещё бы решить основную проблему... Прост, если я не буду знать, прочитано сообщение или нет, соответственно, не смогу ответить на него...
А есть какие-то другие варианты чтения между строк??
 
Автор
L

louie1743shkirondo

Новичок
Сообщения
28
Репутация
0
Если я внесу в цикл, то ничего же не изменится.. Просто переменная будет бесконечно иметь " "
Но я попробую)

*Так же я криворукий и не понял, куда пропало ваше предыдущие сообщение, перередактировал всё через одно место... Извиняюсь*
 

ra4o

AutoIT Гуру
Сообщения
1,165
Репутация
246
А есть какие-то другие варианты чтения между строк??
есть регулярные выражения
Код:
StringRegExp()

Если я внесу в цикл, то ничего же не изменится
Да, извините я не совсем вник ... пост свой предыдущий я сам удалил
Покажите то , что он в консоли пишет - переменную "$res"
 
Автор
L

louie1743shkirondo

Новичок
Сообщения
28
Репутация
0
Код:
$oState = StringRegExp($res, '"read_state":1')

Так инверсии не будет..
Немного ступил
 

Вложения

  • Безымянный.png
    Безымянный.png
    24.5 КБ · Просмотры: 20

firex

AutoIT Гуру
Сообщения
943
Репутация
208
louie1743shkirondo
Свой ответ (response) грузите в следующую функцию:
Код:
$oResp = _JsonLoad($res) ; <==

Func _JsonLoad($sJson)
    Local $oRes, $oSC = ObjCreate('ScriptControl')
    If Not IsObj($oSC) Then _
        Return SetError(1, 0, 0)
    ; *
    $oSC.Language = 'JavaScript'
    ; ---
    $sJson = StringRegExpReplace($sJson, '[\r\n]+', ' ')
    $sJson = StringReplace($sJson, "'", "\'")
    $oRes = $oSC.Eval('(' & $sJson & ')')
    If Not IsObj($oRes) Then  _
        Return SetError(2, 0, 0)
    ; ---
    Return $oRes
EndFunc

Значения ключей можно получать следующим образом:
Код:
$iCount = _JsonGet_s($oResp, 'response.count', 0)
If $iCount Then
	For $oItem In $oResp.response.items
		ConsoleWrite('id=' & $oItem.id & ' read_state=' & $oItem.read_state & @CRLF)
	Next
EndIf

Func _JsonGet_s(ByRef Const $Obj, $Key, $vDefault = '')
	Local $vRet
	; ---
	$vRet = Execute('$Obj.' & $Key)
	; ---
	Return (@error) ? $vDefault : $vRet
EndFunc

P.S. _JsonGet_s - ее либо использовать как можно чаще, либо не использовать вообще и вместо этого настроить AutoIt.Error callback.


Добавлено:
Сообщение автоматически объединено:

Да, и еще, vk на моей памяти отдает данные не в "ожидаемом" JSON формате. Не помню уже зависит ли это от используемой версии API, однако если _JsonLoad откажется обрабатывать ответ, то попробуйте следующий вариант:
Код:
Func _JsonLoad_vk($sJson)
    Local $oRes, $oSC = ObjCreate('ScriptControl')
    If Not IsObj($oSC) Then _
        Return SetError(1, 0, 0)
    ; *
    $oSC.Language = 'JavaScript'
    ; ---
    $sJson = StringRegExpReplace($sJson, '[\r\n]+', ' ')
	$sJson = StringRegExpReplace($sJson, "[^\\]'", '"')
	$sJson = StringStripWS($sJson, 3)
	If StringLeft($sJson, 1) <> '{' Then _
		$sJson = '{' & $sJson & '}'
	; *
    $oRes = $oSC.Eval('(' & $sJson & ')')
    If Not IsObj($oRes) Then  _
        Return SetError(2, 0, 0)
    ; ---
    Return $oRes
EndFunc
 
Автор
L

louie1743shkirondo

Новичок
Сообщения
28
Репутация
0
Спасибо... В этом надо будет покопаться, так как сходу такое без практического опыта не понять...
Благодарю ещё раз)


Добавлено:
Сообщение автоматически объединено:

Вообще, сложно выглядит, когда я не могу понять, как мне определять значение прочитано/не прочитано в каждом сообщение и запоминать его id, но это не к этой теме :rofl:
Но всё же постараюсь понять вашу задумку...
 
Верх