Вы не должны создавать глобальную переменную response
.Вместо этого добавьте его в форму let
, чтобы он был локальным по отношению к defun
.См. Также https://www.gnu.org/software/emacs/manual/html_node/elisp/Local-Variables.html
Более конкретно, url-retrieve
- это асинхронная функция: код, который пытается установить response
, еще не будет иметь буфера для работы, когда url-retrieve
завершит оценку (будетпродолжить в фоновом режиме и в конечном итоге вызвать его обратный вызов в lambda
, но нет никакой гарантии, что это произойдет во время выполнения вашей формы).Простое, но немного неуклюжее решение состоит в том, чтобы переключиться на url-retrieve-synchronously
и жить с тем фактом, что это может занять некоторое время.
Вы также должны позаботиться о том, чтобы не загромождать буфер пользователя, его положение в этом буфере,или история матчей регулярных выражений.
С этими исправлениями также вполне естественно выделить response
полностью.
(defun get-ip ()
(let ((url-request-method "GET")
(url-request-extra-headers
'(("Authorization" . "token xxxxxxxxx")
("Accept" . "application/vnd.github.v3.raw"))))
(save-match-data
(save-current-buffer
(set-buffer
(url-retrieve-synchronously "http://www.google.com/" 'silent))
(goto-char (point-min))
(if (search-forward-regexp "\\([0-9]*\\.[0-9]*\\.[0-9]*\\.[0-9]*\\)" nil t)
(match-string 0) "")))))