如何将 PhpSpreadsheet 与 App Engine 和 Google 云存储一起使用

How to use PhpSpreadsheet with App Engine and Google Cloud Storage

几天来我一直在思考这个问题,觉得是时候问一下了。任务看起来很简单 - 使用 PhpSpreadsheet 将 Excel sheet 写入 Google Cloud Storage 存储桶。

目前我的想法是文件需要流式传输到存储桶。另一种选择似乎是在内存中生成文件,然后将其写入存储桶,我觉得这可能会占用大量资源。

我在标准环境和 PHP 7.4.

中使用 App Engine

为了测试它,我一直在使用最基本的代码来制作 sheet -

require 'vendor/autoload.php';    
use PhpOffice\PhpSpreadsheet\Spreadsheet;
use PhpOffice\PhpSpreadsheet\Writer\Xlsx;    
$spreadsheet = new Spreadsheet();
$sheet = $spreadsheet->getActiveSheet();
$sheet->setCellValue('A1', 'Hello World !');    
$writer = new Xlsx($spreadsheet);
$writer->save('hello world.xlsx');

然后我想结合对存储桶的基本写入 -

require 'vendor/autoload.php';
use Google\Cloud\Storage\StorageClient;

 /**
 * @param string $bucketName The name of your Cloud Storage bucket.
 * @param string $objectName The name of your Cloud Storage object.
 * @param string $source The path to the file to upload.
 */
function upload_object($bucketName, $objectName, $source)
{
    // $bucketName = 'my-bucket';
    // $objectName = 'my-object';
    // $source = '/path/to/your/file';

    $storage = new StorageClient();
    $file = fopen($source, 'r');
    $bucket = $storage->bucket($bucketName);
    $object = $bucket->upload($file, [
        'name' => $objectName
    ]);
}

这些基本上是来自 PhpSpreadsheet 和 Google 的代码示例。我已经让他们自己工作了。有没有人有关于让生成的 Excel sheet 最终进入 Cloud Storage 存储桶的想法?

// 添加于 2022-01-13 ///////////////////////////////////

经过一些评论后,我尝试了不同的选项并在下面列出了结果。我认为它正在接近,但还不完全是。

<?php
require 'vendor/autoload.php';

use PhpOffice\PhpSpreadsheet\Spreadsheet;
use PhpOffice\PhpSpreadsheet\Writer\Xlsx;
use Google\Cloud\Storage\StorageClient;

$bucketName = 'BUCKETNAME'; // Name of the GCS bucket
$objectName = 'new_file_name.xlsx'; // Name of the new file we are creating
$objectLocation = 'gs://'.$bucketName.'/'.$objectName; // Path of the new file

try {

    $storage = new StorageClient();
    $storage->registerStreamWrapper();

    $spreadsheet = new Spreadsheet();
    $sheet = $spreadsheet->getActiveSheet();
    $sheet->setCellValue('A1', 'Hello World !');
    $sheet->setCellValue('B1', 'Hello You !');

    $writer = new Xlsx($spreadsheet);
    
    // Trial 1
    // This displays "Could not open file "gs://BUCKETNAME/new_file_name.xlsx" for writing." in the browser window.
    $writer->save($objectLocation);

    // Trial 2
    // This creates an empty file in the GCS bucket and displays the XLSX file code on the screen
    //$file = fopen($writer->save('php://output'), 'r');
    //$bucket = $storage->bucket($bucketName);
    //$object = $bucket->upload($file, [
    //    'name' => $objectName
    //]);

    // Trial 3
    // This displays "Could not open file "new_file_name.xlsx" for writing." in the browser window.
    //$file = fopen($writer->save($objectName), 'r');
    //$bucket = $storage->bucket($bucketName);
    //$object = $bucket->upload($file, [
    //    'name' => $objectName
    //]);
}
catch (Exception $e) {
    echo $e->getMessage();
}

这是一个有效的示例代码:

<?php
require 'vendor/autoload.php';

use PhpOffice\PhpSpreadsheet\Spreadsheet;
use PhpOffice\PhpSpreadsheet\Writer\Xlsx;
use Google\Cloud\Storage\StorageClient;

$bucketName = 'BUCKET_NAME'; // Name of the GCS bucket
$objectName = 'FILENAME.xlsx'; // Name of the new file we are creating

try {
    $storage = new StorageClient();
    $storage->registerStreamWrapper();

    $spreadsheet = new Spreadsheet();
    $sheet = $spreadsheet->getActiveSheet();
    $sheet->setCellValue('A1', 'Hello World !');
    $sheet->setCellValue('B1', 'Hello You !');

    $writer = new Xlsx($spreadsheet);

    ob_start();
    $writer->save('php://output');
    $content = ob_get_contents();
    ob_end_clean();

    $bucket = $storage->bucket($bucketName);
    $object = $bucket->upload($content, [
        'name' => $objectName
    ]);
}
catch (Exception $e) {
    echo $e->getMessage();
}
?>

以下是 Google 云存储中包含内容的电子表格的屏幕截图:

在PHP中,有一个引用叫做PHP Output Control

我使用 ob_start() to create an output buffer and ob_end_clean() 删除了最顶层的输出缓冲区及其所有内容,而没有向浏览器发送任何内容。

我也使用php://output根据PHPSpreadsheet Documentation.

将文件临时存放在脚本的工作目录中