- ubuntu12.04环境下使用kvm ioctl接口实现最简单的虚拟机
- Ubuntu 通过无线网络安装Ubuntu Server启动系统后连接无线网络的方法
- 在Ubuntu上搭建网桥的方法
- ubuntu 虚拟机上网方式及相关配置详解
CFSDN坚持开源创造价值,我们致力于搭建一个资源共享平台,让每一个IT人在这里找到属于你的精彩世界.
这篇CFSDN的博客文章PHP抓取远程图片(含不带后缀的)教程详解由作者收集整理,如果你对这篇文章有兴趣,记得点赞哟.
1、创建项目 。
作为演示,我们在www根目录创建项目grabimg,创建一个类GrabImage.php和一个index.php.
2、编写类代码 。
我们定义一个和文件名相同的类:GrabImage 。
1
2
3
|
class
GrabImage{
}
|
3、属性 。
接下来定义几个需要使用的属性.
1、首先定义一个需要抓取的图片地址:$img_url 。
2、再定义一个$file_name用来存储文件的名称,但是不携带拓展名,因为可能涉及到拓展名更换,所以这里拆开定义 。
3、紧接着就是拓展名$extension 。
4、然后我们定义一个$file_dir,该属性的作用是,远程图片抓取到本地后所存储的目录,一般相对于PHP入口文件所在的位置作为起始。但是该路径一般不保存到数据库.
5、最后我们定义一个$save_dir,顾名思义,该路径是用来直接保存的数据库的目录。这里说明下,我们不直接存储文件保存路径到数据库,一般是为了之后如果系统迁移,方便更换路径做准备。我们这里的$save_dir一般为日期 + 文件名,如果需要使用时候取出,在前方拼上所需要的路径.
4、方法 。
属性弄完了,接下来我们正式开始抓取工作.
首先我们定义一个对外开放的方法getInstances用来获取一些数据,比如抓取图片地址,和本地保存路径。同时将其放入属性中.
1
2
3
4
5
6
|
public
function
getInstances(
$img_url
,
$base_dir
)
{
$this
->img_url =
$img_url
;
$this
->save_dir =
date
(
"Ym"
).
'/'
.
date
(
"d"
).
'/'
;
// 比如:201610/19/
$this
->file_dir =
$base_dir
.
'/'
.
$this
->save_dir.
'/'
;
// 比如:./uploads/image/2016/10/19/
}
|
图片保存路径拼接完成,下面我们要注意一个问题,目录是否存在。日期在一天天走,但是目录并不会自动创建。所以,在保存图片之前,首先需要检查一下,如果当前目录不存在我们需要即时创建.
我们创建设置目录方法setDir。属性我们设置了private,安全 。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
|
/**
* 检查图片需要保持的目录是否存在
* 如果不存在,则立即创建一个目录
* @return bool
*/
private
function
setDir()
{
if
(!
file_exists
(
$this
->file_dir))
{
mkdir
(
$this
->file_dir,0777,TRUE);
}
$this
->file_name = uniqid().rand(10000,99999);
// 文件名,这里只是演示,实际项目中请使用自己的唯一文件名生成方法
return
true;
}
|
接下来就是抓取核心代码 。
第一步,解决一个问题,我们需要抓取的图片可能没有后缀名。按照传统的抓取方法,先抓取图片,然后截取后缀名的方案不可行.
我们必须通过其它方法来获得图片类型。办法就是从文件流信息中获取文件头信息,从而判断文件mime信息,就可以知道文件后缀名.
为了方便,先定义一个mime和文件拓展名映射.
1
2
3
4
5
6
7
|
$mimes
=
array
(
'image/bmp'
=>
'bmp'
,
'image/gif'
=>
'gif'
,
'image/jpeg'
=>
'jpg'
,
'image/png'
=>
'png'
,
'image/x-icon'
=>
'ico'
);
|
这样,当我获取了类型是image/gif的时候,我就可以知道是.gif图片了.
利用php函数get_headers,获取文件流头信息。当其值不为false时候我们将其赋值给变量$headers 。
取出Content-Type的值即为mime的值.
1
2
3
4
|
if
((
$headers
=get_headers(
$this
->img_url, 1))!==false){
// 获取响应的类型
$type
=
$headers
[
'Content-Type'
];
}
|
使用上面我们定义的映射表,我们可以很轻松的获取后缀名.
1
|
$this
->extension=
$mimes
[
$type
];
|
当然上面获取的$type,可能不存在我们的映射表中,说明这种类型文件并不是我们想要的,直接抛弃就好了,不用管它.
下面的步骤就和传统抓取文件一样.
1
2
3
4
5
6
7
8
|
$file_path
=
$this
->file_dir.
$this
->file_name.
"."
.
$this
->extension;
// 获取数据并保存
$contents
=
file_get_contents
(
$this
->img_url);
if
(
file_put_contents
(
$file_path
,
$contents
))
{
// 这里返回出去的值是直接保存到数据库的路径 + 文件名,形如:201610/19/57feefd7e2a7aY5p7LsPqaI-lY1BF.jpg
return
$this
->save_dir.
$this
->file_name.
"."
.
$this
->extension;
}
|
首先获取本地保图片存完整路径$file_path,接下来使用file_get_contents抓取数据,然后使用file_put_contents保存到刚刚的文件路径.
最后我们返回一个可以直接保存到数据库中的路径,而不是文件存储路径.
该抓取方法完整版是:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
|
private
function
getRemoteImg()
{
// mime 和 扩展名 的映射
$mimes
=
array
(
'image/bmp'
=>
'bmp'
,
'image/gif'
=>
'gif'
,
'image/jpeg'
=>
'jpg'
,
'image/png'
=>
'png'
,
'image/x-icon'
=>
'ico'
);
// 获取响应头
if
((
$headers
=get_headers(
$this
->img_url, 1))!==false)
{
// 获取响应的类型
$type
=
$headers
[
'Content-Type'
];
// 如果符合我们要的类型
if
(isset(
$mimes
[
$type
]))
{
$this
->extension=
$mimes
[
$type
];
$file_path
=
$this
->file_dir.
$this
->file_name.
"."
.
$this
->extension;
// 获取数据并保存
$contents
=
file_get_contents
(
$this
->img_url);
if
(
file_put_contents
(
$file_path
,
$contents
))
{
// 这里返回出去的值是直接保存到数据库的路径 + 文件名,形如:201610/19/57feefd7e2a7aY5p7LsPqaI-lY1BF.jpg
return
$this
->save_dir.
$this
->file_name.
"."
.
$this
->extension;
}
}
}
return
false;
}
|
最后,为了简单,我们想在其他地方只要调用其中一个方法就可以完成抓取。所以,我们将抓取动作直接放入到getInstances中,在配置完路径后,直接抓取,所以,在初始化配置方法getInstances里新增代码.
1
2
3
4
5
6
7
8
|
if
(
$this
->setDir())
{
return
$this
->getRemoteImg();
}
else
{
return
false;
}
|
测试 。
我们去刚刚创建的index.php文件内试试.
1
2
3
4
5
6
7
|
<?php
require_once
'GrabImage.php'
;
$object
=
new
GrabImage();
$img_url
=
"http://www.bidianer.com/img/icon_mugs.jpg"
; // 需要抓取的远程图片
$base_dir
=
"./uploads/image"
;
// 本地保存的路径
echo
$object
->getInstances(
$img_url
,
$base_dir
);
?>
|
的确抓取过来了 。
完整代码 。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
|
<?php
/**
* 抓取远程图片到本地,可以抓取不带有后缀的图片
* @author YanYing <yanyinghq@163.com>
* @link bidianer.com
*/
class
GrabImage{
/**
* @var string 需要抓取的远程图片的地址
* 例如:http://www.bidianer.com/img/icon_mugs.jpg
* 有一些远程文件路径可能不带拓展名
* 形如:http://www.xxx.com/img/icon_mugs/q/0
*/
private
$img_url
;
/**
* @var string 需要保存的文件名称
* 抓取到本地的文件名会重新生成名称
* 但是,不带拓展名
* 例如:57feefd7e2a7aY5p7LsPqaI-lY1BF
*/
private
$file_name
;
/**
* @var string 文件的拓展名
* 这里直接使用远程图片拓展名
* 对于没有拓展名的远程图片,会从文件流中获取
* 例如:.jpg
*/
private
$extension
;
/**
* @var string 文件保存在本地的目录
* 这里的路径是PHP保存文件的路径
* 一般相对于入口文件保存的路径
* 比如:./uploads/image/201610/19/
* 但是该路径一般不直接存储到数据库
*/
private
$file_dir
;
/**
* @var string 数据库保存的文件目录
* 这个路径是直接保存到数据库的图片路径
* 一般直接保存日期 + 文件名,需要使用的时候拼上前面路径
* 这样做的目的是为了迁移系统时候方便更换路径
* 例如:201610/19/
*/
private
$save_dir
;
/**
* @param string $img_url 需要抓取的图片地址
* @param string $base_dir 本地保存的路径,比如:./uploads/image,最后不带斜杠"/"
* @return bool|int
*/
public
function
getInstances(
$img_url
,
$base_dir
)
{
$this
->img_url =
$img_url
;
$this
->save_dir =
date
(
"Ym"
).
'/'
.
date
(
"d"
).
'/'
;
// 比如:201610/19/
$this
->file_dir =
$base_dir
.
'/'
.
$this
->save_dir.
'/'
;
// 比如:./uploads/image/2016/10/19/
return
$this
->start();
}
/**
* 开始抓取图片
*/
private
function
start()
{
if
(
$this
->setDir())
{
return
$this
->getRemoteImg();
}
else
{
return
false;
}
}
/**
* 检查图片需要保持的目录是否存在
* 如果不存在,则立即创建一个目录
* @return bool
*/
private
function
setDir()
{
if
(!
file_exists
(
$this
->file_dir))
{
mkdir
(
$this
->file_dir,0777,TRUE);
}
$this
->file_name = uniqid().rand(10000,99999);
// 文件名,这里只是演示,实际项目中请使用自己的唯一文件名生成方法
return
true;
}
/**
* 抓取远程图片核心方法,可以同时抓取有后缀名的图片和没有后缀名的图片
*
* @return bool|int
*/
private
function
getRemoteImg()
{
// mime 和 扩展名 的映射
$mimes
=
array
(
'image/bmp'
=>
'bmp'
,
'image/gif'
=>
'gif'
,
'image/jpeg'
=>
'jpg'
,
'image/png'
=>
'png'
,
'image/x-icon'
=>
'ico'
);
// 获取响应头
if
((
$headers
=get_headers(
$this
->img_url, 1))!==false)
{
// 获取响应的类型
$type
=
$headers
[
'Content-Type'
];
// 如果符合我们要的类型
if
(isset(
$mimes
[
$type
]))
{
$this
->extension=
$mimes
[
$type
];
$file_path
=
$this
->file_dir.
$this
->file_name.
"."
.
$this
->extension;
// 获取数据并保存
$contents
=
file_get_contents
(
$this
->img_url);
if
(
file_put_contents
(
$file_path
,
$contents
))
{
// 这里返回出去的值是直接保存到数据库的路径 + 文件名,形如:201610/19/57feefd7e2a7aY5p7LsPqaI-lY1BF.jpg
return
$this
->save_dir.
$this
->file_name.
"."
.
$this
->extension;
}
}
}
return
false;
}
}
|
总结 。
以上就是这篇文章的全部内容了,希望能对大家学习或者使用PHP能有所帮助,如果有疑问大家可以留言交流.
最后此篇关于PHP抓取远程图片(含不带后缀的)教程详解的文章就讲到这里了,如果你想了解更多关于PHP抓取远程图片(含不带后缀的)教程详解的内容请搜索CFSDN的文章或继续浏览相关文章,希望大家以后支持我的博客! 。
如本answer所述,如果浏览器不支持 e,可以设置后备游标。 G。 光标:抓取;。我现在的问题是获取这些图像。在我的驱动器上本地搜索“.cur”只给了我系统光标,其中 grab.cur 和 grab
以下代码在计算机上运行以从 Instagram 帐户中抓取数据。当我尝试在 VPS 服务器上使用它时,我被重定向到 Instagram 登录页面,因此脚本不起作用。 为什么当我在电脑上或服务器上时,I
我在使用 Ruby 和 Mechanize 将 POST 查询传递到站点的网站上。访问站点的查询基于 firebug,如下所示 param.PrdNo=-1¶m.Type=Prop¶m
我正在尝试抓取一个具有多个页面结果的网站,例如“1、2、3、4、5...”。 每个分页号都是到另一个页面的链接,我需要抓取每个页面。 到目前为止,我想出了这个: while lien = page.l
我正在使用 HtmlAgilityPack 在 C# Asp.Net 中执行 Scraping,到目前为止,我在从多个 Web 执行 Scratch 时没有遇到问题,但是,尝试弹出以下代码时出现错误
如果我有一个 css 文件做这样的事情 #foo:after{content:"bar;} ,有没有办法用 javascript 获取 :after 的内容?获取父元素的内容只返回 #foo 元素的内
问题是这样的: 我有一个 Web 应用程序 - 一个经常更改的通知系统 - 在一系列本地计算机上运行。该应用程序每隔几秒刷新一次以显示新信息。计算机仅显示信息,没有键盘或任何输入设备。 问题是,如果与
我想制作一个程序来模拟用户浏览网站和点击链接。必须启用 Cookie 和 javascript。我已经在 python 中成功地做到了这一点,但我想把它写成一种可编译的语言(python ide 不会
我制作了这个小机器人,它通过搜索参数列表进行处理。它工作正常,直到页面上有几个结果: product_prices_euros 给出了一半为空的项目列表。因此,当我与 product_prices_c
我需要找到一个单词的匹配项,例如: 在网上找到所有单词“学习”https://www.georgetown.edu/(结果:4个字)(您可以看到它按CTRL + F并搜索) 我有我的 Python 代
有一个站点\资源提供一些一般统计信息以及搜索工具的界面。这种搜索操作成本高昂,因此我想限制频繁且连续(即自动)的搜索请求(来自人,而不是来自搜索引擎)。 我相信有很多现有的技术和框架可以执行一些情报抓
这并不是真正的抓取,我只是想在网页中找到类具有特定值的 URL。例如: 我想获取 href 值。关于如何做到这一点的任何想法?也许正则表达式?你能发布一些示例代码吗?我猜 html 抓取库,比如 B
我正在使用 scrapy。 我正在使用的网站具有无限滚动功能。 该网站有很多帖子,但我只抓取了 13 个。 如何抓取剩余的帖子? 这是我的代码: class exampleSpider(scrapy.
我正在尝试从这个 website 中抓取图像和新闻 url .我定义的标签是 root_tag=["div", {"class":"ngp_col ngp_col-bottom-gutter-2 ng
关闭。这个问题需要更多focused .它目前不接受答案。 想改进这个问题吗? 更新问题,使其只关注一个问题 editing this post . 关闭上个月。 Improve this ques
我在几个文件夹中有数千个 html 文件,我想从评论中提取数据并将其放入 csv 文件中。这将允许我为项目格式化和清理它。例如,我在这个文件夹中有 640 个 html 文件: D:\My Web S
我在编写用于抓取网页的实用程序时遇到了一个问题。 我正在发送 POST 请求来检索数据,我模仿我正在抓取的网络行为(根据使用 fiddler 收集的信息)。 我已经能够自动替换我的 POST 中除 V
对于 Googlebot 的 AJAX 抓取,我在我的网站中使用“_escaped_fragment_”参数。 现在我查看了 Yandex 对我网站的搜索结果。 我看到搜索结果中不存在 AJAX 响应
我正在尝试抓取网站的所有结果页面,它可以工作,但有时脚本会停止并显示此错误: 502 => Net::HTTPBadGateway for https://website.com/id/12/ --
我是一个学习网络爬虫的初学者,由于某种原因我无法爬网this地点。当我在 Chrome 中检查它时,代码看起来不错,但是当我用 BeautifulSoup 阅读它时,它不再是可刮的。汤提到“谷歌分析”
我是一名优秀的程序员,十分优秀!