r - 检查R中是否存在URL
问题描述
我想遍历一个 URL 列表,我想知道这些 URL 是否存在。
RCurl
提供url.exists()
功能。但是,输出似乎不正确,因为例如它说 amazon.com 未注册(这样做是因为url.exists()
-function 不返回 200 范围内的值,对于 amazon.com它是 405(“方法不允许”)。
我也试过HEAD()
并由包GET()
提供。httr
但有时我会在这里收到错误消息,例如超时或 URL 未注册。
错误消息如下所示:
Error in curl::curl_fetch_memory(url, handle = handle) :
Timeout was reached: Connection timed out after 10000 milliseconds
Error in curl::curl_fetch_memory(url, handle = handle) :
Could not resolve host: afsadadssadasf.com
当我收到这样的错误时,整个 for 循环都会停止。是否可以继续 for 循环?我试过tryCatch()
了,但据我所知,这只有在问题出在数据框本身时才有帮助。
解决方案
pingr::ping()
仅使用在健全的组织网络上被阻止的 ICMP,因为攻击者使用 ICMP 作为泄露数据并与命令和控制服务器通信的一种方式。
pingr::ping_port()
不使用 HTTPHost:
标头,因此 IP 地址可能会响应,但目标虚拟 Web 主机可能未在其上运行,并且它肯定不会验证目标 URL 中是否存在路径。
当只有非 200:299 范围的 HTTP 状态代码时,您应该澄清您想要发生的事情。下面做一个假设。
注意:您以亚马逊为例,我希望这是第一个“想到”的网站,因为刮取亚马逊是不道德的和犯罪的,如果您实际上是我的代码,我将不胜感激只是一个厚颜无耻的内容窃贼。如果您正在窃取内容,那么您不太可能在这方面处于领先地位,但是在外部机会您既在窃取又有良心,请让我知道,以便我可以删除此答案,以便至少其他内容窃贼可以'不要使用它。
这是一个用于检查 URL 的独立函数:
#' @param x a single URL
#' @param non_2xx_return_value what to do if the site exists but the
#' HTTP status code is not in the `2xx` range. Default is to return `FALSE`.
#' @param quiet if not `FALSE`, then every time the `non_2xx_return_value` condition
#' arises a warning message will be displayed. Default is `FALSE`.
#' @param ... other params (`timeout()` would be a good one) passed directly
#' to `httr::HEAD()` and/or `httr::GET()`
url_exists <- function(x, non_2xx_return_value = FALSE, quiet = FALSE,...) {
suppressPackageStartupMessages({
require("httr", quietly = FALSE, warn.conflicts = FALSE)
})
# you don't need thse two functions if you're alread using `purrr`
# but `purrr` is a heavyweight compiled pacakge that introduces
# many other "tidyverse" dependencies and this doesnt.
capture_error <- function(code, otherwise = NULL, quiet = TRUE) {
tryCatch(
list(result = code, error = NULL),
error = function(e) {
if (!quiet)
message("Error: ", e$message)
list(result = otherwise, error = e)
},
interrupt = function(e) {
stop("Terminated by user", call. = FALSE)
}
)
}
safely <- function(.f, otherwise = NULL, quiet = TRUE) {
function(...) capture_error(.f(...), otherwise, quiet)
}
sHEAD <- safely(httr::HEAD)
sGET <- safely(httr::GET)
# Try HEAD first since it's lightweight
res <- sHEAD(x, ...)
if (is.null(res$result) ||
((httr::status_code(res$result) %/% 200) != 1)) {
res <- sGET(x, ...)
if (is.null(res$result)) return(NA) # or whatever you want to return on "hard" errors
if (((httr::status_code(res$result) %/% 200) != 1)) {
if (!quiet) warning(sprintf("Requests for [%s] responded but without an HTTP status code in the 200-299 range", x))
return(non_2xx_return_value)
}
return(TRUE)
} else {
return(TRUE)
}
}
搏一搏:
c(
"http://content.thief/",
"http://rud.is/this/path/does/not_exist",
"https://www.amazon.com/s/ref=nb_sb_noss_2?url=search-alias%3Daps&field-keywords=content+theft",
"https://www.google.com/search?num=100&source=hp&ei=xGzMW5TZK6G8ggegv5_QAw&q=don%27t+be+a+content+thief&btnK=Google+Search&oq=don%27t+be+a+content+thief&gs_l=psy-ab.3...934.6243..7114...2.0..0.134.2747.26j6....2..0....1..gws-wiz.....0..0j35i39j0i131j0i20i264j0i131i20i264j0i22i30j0i22i10i30j33i22i29i30j33i160.mY7wCTYy-v0",
"https://rud.is/b/2018/10/10/geojson-version-of-cbc-quebec-ridings-hex-cartograms-with-example-usage-in-r/"
) -> some_urls
data.frame(
exists = sapply(some_urls, url_exists, USE.NAMES = FALSE),
some_urls,
stringsAsFactors = FALSE
) %>% dplyr::tbl_df() %>% print()
## A tibble: 5 x 2
## exists some_urls
## <lgl> <chr>
## 1 NA http://content.thief/
## 2 FALSE http://rud.is/this/path/does/not_exist
## 3 TRUE https://www.amazon.com/s/ref=nb_sb_noss_2?url=search-alias%3Daps&field-keywords=con…
## 4 TRUE https://www.google.com/search?num=100&source=hp&ei=xGzMW5TZK6G8ggegv5_QAw&q=don%27t…
## 5 TRUE https://rud.is/b/2018/10/10/geojson-version-of-cbc-quebec-ridings-hex-cartograms-wi…
## Warning message:
## In FUN(X[[i]], ...) :
## Requests for [http://rud.is/this/path/does/not_exist] responded but without an HTTP status code in the 200-299 range
推荐阅读
- mysql - 如何根据 MySQL 中的最大日期仅选择左表的一条记录?
- javascript - 带有动态条目的 Webpack
- go - 通过 TCP 读取字节并在 Go 中编码为 ISO-8859-9
- security - PingFederate OpenId/OAUTH2.0 与 Weblogic 10.3.6 集成
- c# - 仅数字 0-9 的正则表达式 c# 接受特殊字符 \n 符号
- c# - 循环遍历列表框项目并针对每个项目触发操作
- microsoft-graph-api - 什么是“Microsoft Graph API”的 $Filter 查询中“替换多个 OR 语句”的“替代运算符”
- swift - 使用 firebase ios 电子邮件登录
- ruby-on-rails - 从 init.d 服务脚本启动 rails 并加载正确版本的 ruby
- reactjs - 如何正确地将基于类的组件中的状态转换为使用 Hooks?