Laravel上传至Telegram的图片损坏且仅41字节,如何修复?
问题修复方案
你的问题核心是Http::attach的用法错误:该方法的第二个参数需要传入文件的内容(字符串/资源流),而不是文件的URL。你传入本地URL后,Laravel会把这个URL字符串直接作为文件内容上传,所以文件大小只有URL本身的字节数(约41字节),导致图片损坏。
修复步骤
1. 正确读取本地文件内容
根据你的文件存储位置,选择以下方式之一读取文件:
- 如果文件在Laravel的
storage/app目录下,使用Storage类:
use Illuminate\Support\Facades\Storage; // 假设文件路径是 storage/app/images/document.png $fileContent = Storage::get('images/document.png'); // 或者获取文件资源流(更适合大文件) $fileStream = Storage::readStream('images/document.png');
- 如果文件在项目根目录或其他位置,使用绝对路径读取:
// 替换为你的文件绝对路径 $filePath = '/var/www/html/your-project/public/images/document.png'; $fileContent = file_get_contents($filePath); // 或者资源流 $fileStream = fopen($filePath, 'r');
2. 修正Http请求代码
将读取到的文件内容/资源流传入Http::attach:
// 使用文件内容的示例 $response = Http::attach( 'document', $fileContent, 'document.png' )->post(self::telegramApiUrl.$this->telegramBotToken.'/sendDocument', [ 'chat_id' => $this->channelUserId, 'reply_to_message_id' => $replyId ]); // 使用资源流的示例 $response = Http::attach( 'document', $fileStream, 'document.png' )->post(self::telegramApiUrl.$this->telegramBotToken.'/sendDocument', [ 'chat_id' => $this->channelUserId, 'reply_to_message_id' => $replyId ]);
3. 额外检查项
- 确保Apache的运行用户(通常是www-data)拥有该文件的读取权限,可通过
chmod或chown调整权限。 - 用
file_exists($filePath)或Storage::exists('images/document.png')验证文件是否存在,避免读取空内容。 - 如果你使用
laravel-notification-channels/telegram扩展,也可以直接用其内置的附件方法,更简洁:
use NotificationChannels\Telegram\TelegramFile; // 在通知类的toTelegram方法中 return TelegramFile::create() ->chatId($this->channelUserId) ->document($filePath) // 直接传入文件绝对路径 ->replyToMessageId($replyId);
内容的提问来源于stack exchange,提问作者mstdmstd
相关产品推荐
相关产品推荐

