Heim > Artikel > Backend-Entwicklung > Analyse des Problems mit den Versionsunterschieden der Curl-Upload-Datei
=Nachdem das Front-End-Postformular die Datei hochgeladen hat, leitet das Back-End den Post nach Erhalt der Datei an den Bildserver weiter. Also habe ich Curl zum Hochladen verwendet und mit „@file path“ hochgeladen.
Der Code lautet wie folgt
<?php if($_FILES['video']['size']>0){ $data = array('video'=>$_FILES['video']['tmp_name']); $ch = curl_init(); $url="test.php"; // 设置URL和相应的选项 curl_setopt($ch, CURLOPT_URL, $url); //启用时会将头文件的信息作为数据流输出。 curl_setopt($ch, CURLOPT_HEADER, 0); //将curl_exec()获取的信息以字符串返回,而不是直接输出 curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_POST, 1); curl_setopt($ch, CURLOPT_POSTFIELDS, $data); $res = curl_exec($ch); // 抓取URL并把它传递给浏览器 curl_exec($ch); // 关闭cURL资源,并且释放系统资源 curl_close($ch); }
Die PHP-Version der Testmaschine ist 5.2. Es gibt keine Problem beim Brechen des Codes, aber beim Einfügen in die Zeile erhält die Variable $_FILES keinen Wert. Dann beobachte ich genau, ich habe $_POST['video']='@/tmp/phps12d63'; in $_POST erhalten. Die erste Reaktion ist, dass der Inhaltstyp nicht normal übertragen wird der hochgeladenen Datei sollte „Multipart/form-data“ lauten, in diesem Fall sollte sie „application/x-www-form-urlencoded“ lauten. Drucken Sie dann die Variable $_SERVER[‘HTTP_CONTENT_TYPE’] auf dem Bildserver aus und stellen Sie fest, dass es sich um „multipart/form-data“ handelt.
Bei einem Blick in das Handbuch habe ich festgestellt, dass der Content-Type-Header auf multipart/form-data gesetzt wird, wenn der übergebene Parameter von CURLOPT_POSTFIELDS ein Array ist.
Dann gibt es einen magischen Parameter CURLOPT_SAFE_UPLOAD, der in php5.5.0 hinzugefügt wurde. Der Standardwert ist false, 5.6.0 ist standardmäßig true,
CURLOPT_SAFE_UPLOAD
TRUE deaktiviert das Senden von Dateien mit dem @-Präfix in CURLOPT_POSTFIELDS. Dies bedeutet, dass @ sicher in Feldern verwendet werden kann. Verfügbar
CURLFile als Ersatz für das Hochladen.
Und CURLOPT_POSTFIELDS Parameterbeschreibung
CURLOPT_POSTFIELDS
Alle Daten werden über die Operation „POST“ im HTTP-Protokoll gesendet. Um eine Datei zu senden, stellen Sie dem Dateinamen ein @ voran und verwenden Sie den vollständigen Pfad. Der Dateityp kann im Format „;type=mimetype“ hinter dem Dateinamen angegeben werden. Dieser Parameter kann eine URL-codierte Zeichenfolge sein, ähnlich wie „para1=val1¶2=val2&...“, oder Sie können ein Array mit dem Feldnamen als Schlüssel und den Felddaten als Wert verwenden. Wenn value ein Array ist, wird der Content-Type-Header auf multipart/form-data gesetzt. Ab PHP 5.2.0 muss der Wert beim Übergeben von Dateien mit dem @-Präfix ein Array sein. Ab PHP 5.5.0 ist das @-Präfix veraltet und Dateien können über CURLFile gesendet werden. Setzen Sie CURLOPT_SAFE_UPLOAD auf TRUE, um das Senden von Dateien mit dem @-Präfix für zusätzliche Sicherheit zu deaktivieren.
Bei der Überprüfung der Version stellt sich heraus, dass die Testumgebung PHP5.3 und die Online-Testumgebung 5.6 ist, was bedeutet, dass CURLOPT_SAFE_UPLOAD standardmäßig auf true eingestellt ist, @-Upload deaktiviert ist und @ ein ist gewöhnliche Saite. Ab 5.5 wurde das @-Präfix zum Hochladen von Dateien abgeschafft. Versionen größer als 5.5 müssen mit CURLFile hochgeladen werden. Die endgültige kompatible Lösung verwendet das Präfix @, wenn es kleiner als 5.5 ist, und CURLFile, wenn es größer als 5.5 ist. Verwenden Sie zum Hochladen @, und Sie können zusätzliche Parameter hinzufügen Geben Sie
<?php //curl_file_create是函数的别名CURLFile::__construct() if (!function_exists('curl_file_create')) { function curl_file_create($filename, $mimetype = '', $postname = '') { return "@$filename;filename=" . ($postname ?: basename($filename)) . ($mimetype ? ";type=$mimetype" : ''); } }
Endcode ein. Zusammenfassend lässt sich sagen:
<?php if($_FILES['video']['size']>0){ $data = array('video'=>$_FILES['video']['tmp_name']); $ch = curl_init(); $url="test.php"; // 设置URL和相应的选项 curl_setopt($ch, CURLOPT_URL, $url); //启用时会将头文件的信息作为数据流输出。 curl_setopt($ch, CURLOPT_HEADER, 0); //将curl_exec()获取的信息以字符串返回,而不是直接输出 curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_POST, 1); $data['video']=curl_file_create($_FILES['video']['tmp_name'],'video/mp4',$_FILES['video']['name']); curl_setopt($ch, CURLOPT_POSTFIELDS, $data); $res = curl_exec($ch); // 抓取URL并把它传递给浏览器 curl_exec($ch); // 关闭cURL资源,并且释放系统资源 curl_close($ch); }
: Wenn Sie auf ein Problem stoßen, sollten Sie es zunächst ruhig analysieren und dann das Handbuch sorgfältig lesen.
Am Freitag ist ein Problem aufgetreten. Nachdem das Front-End-Postformular eine Datei hochgeladen hatte, leitete das Back-End den Post nach Erhalt der Datei an den Bildserver weiter. Also habe ich Curl zum Hochladen verwendet und mit „@file path“ hochgeladen.
Der Code lautet wie folgt
<?php if($_FILES['video']['size']>0){ $data = array('video'=>$_FILES['video']['tmp_name']); $ch = curl_init(); $url="test.php"; // 设置URL和相应的选项 curl_setopt($ch, CURLOPT_URL, $url); //启用时会将头文件的信息作为数据流输出。 curl_setopt($ch, CURLOPT_HEADER, 0); //将curl_exec()获取的信息以字符串返回,而不是直接输出 curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_POST, 1); curl_setopt($ch, CURLOPT_POSTFIELDS, $data); $res = curl_exec($ch); // 抓取URL并把它传递给浏览器 curl_exec($ch); // 关闭cURL资源,并且释放系统资源 curl_close($ch); }
Die PHP-Version der Testmaschine ist 5.2. Es gibt kein Problem, den Code zu knacken. aber wenn es online gestellt wird, $_FILES Die Variable kann keinen Wert empfangen. Dann beobachten Sie genau, dass ich $_POST['video']='@/tmp/phps12d63'; in $_POST erhalten habe. Die erste Reaktion ist, dass der Inhaltstyp nicht normal übertragen wird der hochgeladenen Datei sollte „Multipart/form-data“ lauten, in diesem Fall sollte sie „application/x-www-form-urlencoded“ lauten. Drucken Sie dann die Variable $_SERVER[‘HTTP_CONTENT_TYPE’] auf dem Bildserver aus und stellen Sie fest, dass es sich um „multipart/form-data“ handelt.
Beim Durchsehen des Handbuchs habe ich festgestellt, dass der Content-Type-Header auf multipart/form-data gesetzt wird, wenn der übergebene Parameter von CURLOPT_POSTFIELDS ein Array ist.
Dann gibt es einen magischen Parameter CURLOPT_SAFE_UPLOAD, der in php5.5.0 hinzugefügt wurde. Der Standardwert ist false, 5.6.0 ist standardmäßig true,
CURLOPT_SAFE_UPLOAD
TRUE deaktiviert das Senden von Dateien mit dem @-Präfix in CURLOPT_POSTFIELDS. Dies bedeutet, dass @ sicher in Feldern verwendet werden kann. Verfügbar
CURLFile als Ersatz für das Hochladen.
Und CURLOPT_POSTFIELDS Parameterbeschreibung
CURLOPT_POSTFIELDS
Alle Daten werden über die Operation „POST“ im HTTP-Protokoll gesendet. Um eine Datei zu senden, stellen Sie dem Dateinamen ein @ voran und geben Sie den vollständigen Pfad an. Der Dateityp kann im Format „;type=mimetype“ hinter dem Dateinamen angegeben werden. Dieser Parameter kann eine URL-codierte Zeichenfolge sein, ähnlich wie „para1=val1¶2=val2&...“, oder Sie können ein Array mit dem Feldnamen als Schlüssel und den Felddaten als Wert verwenden. Wenn value ein Array ist, wird der Content-Type-Header auf multipart/form-data gesetzt. Ab PHP 5.2.0 muss der Wert ein Array sein, wenn Dateien mit dem @-Präfix übergeben werden. Ab PHP 5.5.0 ist das @-Präfix veraltet und Dateien können über CURLFile gesendet werden. Setzen Sie CURLOPT_SAFE_UPLOAD auf TRUE, um das Senden von Dateien mit dem @-Präfix für zusätzliche Sicherheit zu deaktivieren.
查看版本,果然测试环境是php5.3,而线上测试环境是5.6,也是就是说CURLOPT_SAFE_UPLOAD默认为true,禁用了@ 上传,@就是普通字符串了。而从5.5开始@前缀上传文件已经被废弃。大于5.5版本需使用CURLFile 上传。最后兼容方案小于5.5使用@前缀,大于5.5使用CURLFile,在小于5.5的版本是用@上传还可以添加额外的参数;filename=文件名;type=mime类型
<?php //curl_file_create是函数的别名CURLFile::__construct() if (!function_exists('curl_file_create')) { function curl_file_create($filename, $mimetype = '', $postname = '') { return "@$filename;filename=" . ($postname ?: basename($filename)) . ($mimetype ? ";type=$mimetype" : ''); } }
最后代码为
<?php if($_FILES['video']['size']>0){ $data = array('video'=>$_FILES['video']['tmp_name']); $ch = curl_init(); $url="test.php"; // 设置URL和相应的选项 curl_setopt($ch, CURLOPT_URL, $url); //启用时会将头文件的信息作为数据流输出。 curl_setopt($ch, CURLOPT_HEADER, 0); //将curl_exec()获取的信息以字符串返回,而不是直接输出 curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_POST, 1); $data['video']=curl_file_create($_FILES['video']['tmp_name'],'video/mp4',$_FILES['video']['name']); curl_setopt($ch, CURLOPT_POSTFIELDS, $data); $res = curl_exec($ch); // 抓取URL并把它传递给浏览器 curl_exec($ch); // 关闭cURL资源,并且释放系统资源 curl_close($ch); }
相关推荐:
post - php curl上传文件如何像表单一样指定其name值
Das obige ist der detaillierte Inhalt vonAnalyse des Problems mit den Versionsunterschieden der Curl-Upload-Datei. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!