将数据导出为 CSV 时处理一对多关系


Handling One to Many relations when Exporting Data into CSV

我有一个数据库,其中包含 11 个表 9 个表,其中与用户信息表具有一对多关系。

用户表:

ID , Name , Age , phone , . .......

基于ID的关系是与表格,例如

User_cars
ID,User_ID(fk),Make , Model , .....

我需要能够做的是将此数据以 CSV 文件的形式呈现在数据库中。由于存在一对多关系,因此在行重复时,简单连接不起作用。(客户端不可呈现格式:S)

我使用 Yii 作为 Web 应用程序,需要一些扩展,可以以某种可读的方式呈现它。

或者也许PHP脚本也可以完成任务。

您可以通过以下两种方式之一处理它:

1. 使用GROUP_CONCAT(如评论中@Dave所述 - 这是链接:MYSQL PHP API - 显示和从另一个表中获取行中的多行)。但是有一个缺点,GROUP_CONCAT有一个限制(默认情况下为 1024 个字符),您可以使用服务器变量 group_concat_max_len 进行更改,但您可能无法访问这样做。

这看起来很像这样:

ID | Name | Car Model           | Year
1    John   BMW, Audi, Renault    1999, 2000, 2003
2    David  Mercedes, Ford        2000, 2005

如果每个用户有 30-40 个条目并且不可读,这可能会变得非常复杂。

2.第二种选择是将其导出为以下格式(不难做到,您只需遍历用户拥有的所有汽车,但仅在第一次迭代中写入用户)。


ID | Name | Car Model | Year
1    John   BMW         1999
            Audi        2000
            Renault     2003
2    David .....

下面是一些示例代码(我使用了很多具有暗示性名称的编造方法)。

$csvArray = array();
foreach ($users as $user) {
    $cars = $user->getCars(); //random method name. Grabs an array with the cars this user has :)

    $firstIteration = 1;
    foreach ($cars as $car) {
         if ($firstIteration == 1) { // we only set the CSV row the first time we iterate through cars
             $csvSingle['ID'] = $user->getId(); // more random method names
             $csvSingle['Name'] = $user->getName();
             $firstIteration = 0;
         }
        $csvSingle['car_model'] = $car->getCarModel();
        $csvSingle['car_year'] = $car->getCarYear();
        $csvArray[] = $csvSingle; // now we add the single row to the big CSV array.
    }
}
fputcsv($handle, $csvArray); // $handle is the file you export to

我喜欢@"Vlad Preda"的第一个变体,在您的控制器或组件中导出,您可以使用这样的东西:

  1. 获取有车用户(且汽车必须填写用户模型关系)

    $users = User::model()->with('cars')->findAll();

  2. 然后

    foreach ($users as $user) {

    $csvOneUser = array('id'=>$user->

    id, "name"=>$user->name);

    如果 (!$user->汽车) {

    $csvAll[] = $csvOneUser;
    continue;
    

    }

    foreach ($user->汽车作为$car) {

    $car_attributes = $car->getAttributes();
    foreach ($car_attributes as $k=>$v) {
      $csvOneUser[$k][] = $v;
    }
    

    }

    }