Laravel-excel: La fila inicial (2) está más allá de la fila más alta (1)

Creado en 12 nov. 2018  ·  25Comentarios  ·  Fuente: Maatwebsite/Laravel-Excel

Versiones

Versión PHP: 7.2
Laravel versión: 5.7
Versión del paquete: 3.1

Descripción

Recibo el error: 'La fila de inicio (2) está más allá de la fila más alta (1)' de /Users/administrator/Sites/blog/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/RowIterator.php

La hoja de cálculo tiene encabezados en la primera fila y es una sola hoja. La segunda fila está en blanco, pero ¿no debería estar bien? No estoy seguro de cómo dar cuenta de este escenario. Cualquier ayuda es apreciada. Gracias.

Aplicación\Importaciones\PoliciesImport.php

<?php

namespace App\Imports;

use App\Policy;
use Maatwebsite\Excel\Concerns\ToModel;
use Maatwebsite\Excel\Concerns\WithValidation;
use Maatwebsite\Excel\Concerns\WithHeadingRow;
use Maatwebsite\Excel\Concerns\Importable;
use Maatwebsite\Excel\Concerns\WithMultipleSheets;
use Auth;


class PoliciesImport implements ToModel, WithValidation, WithHeadingRow, WithMultipleSheets
{

    use Importable;

    /**
    * <strong i="14">@param</strong> array $row
    *
    * <strong i="15">@return</strong> \Illuminate\Database\Eloquent\Model|null
    */
    public function model(array $row)
    {
        return new Policy([
          'user_id'     => Auth::user()->id,
          'policy_name' => $row['name'],
          'phone'       => $row['phone'],
          'street'      => $row['address'],
          'city'        => $row['city'],
          'state'       => $row['state'],
          'postal_code' => $row['postal_code'],
        ]);
    }

    public function sheets(): array
    {
        return [
            // Select by sheet index
            0 => new PoliciesImport(),
        ];
    }

    public function rules(): array
    {
        return [
            'policy_name' => 'required|string',
             '*.policy_name' => 'required|string',
        ];
    }

}

Controlador de políticas.php

public function import(Request $request)
  {
    if ($request->hasFile('file')) {

      // validate incoming request
      $this->validate($request, [
        'file' => 'required|file|mimes:xls,xlsx,csv|max:10240', //max 10Mb
      ]);

          if ($request->file('file')->isValid()) {

              $file = $request->file('file');
              $path = $file->store('uploads/policy');
              $fileHeaders = current((new HeadingRowImport)->toArray($path)[0]);
              $validHeaders = [
                'name','phone','address','state','city','postal_code'
              ];
              sort($fileHeaders);
              sort($validHeaders);

              // Check the File Headers
              if ($fileHeaders == $validHeaders) {
                  // Import the saved excel file
                  (new PoliciesImport)->import($path);
              }

              Storage::delete($path);
          }
      }

      return back();

  }

Comentario más útil

tengo el mismo error!

¡pero después de quitar la hoja 2, 3 resuelto!

para esta situación, necesita definir el índice de la hoja por

    public function sheets(): array
    {
        return [
            // Select by sheet index
            0 => new pricelist_items(),
        ];
    }

Todos 25 comentarios

¿Puedes publicar el stacktrace completo? Es difícil ver ahora qué importación lo causa.

screen shot 2018-11-12 at 8 02 38 am 2

/Usuarios/administrador/Sitios/blog/vendedor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/RowIterator.php

     *
     * <strong i="8">@param</strong> int $startRow The row number at which to start iterating
     *
     * <strong i="9">@throws</strong> PhpSpreadsheetException
     *
     * <strong i="10">@return</strong> RowIterator
     */
    public function resetStart($startRow = 1)
    {
        if ($startRow > $this->subject->getHighestRow()) {
            throw new PhpSpreadsheetException("Start row ({$startRow}) is beyond highest row ({$this->subject->getHighestRow()})");
        }

        $this->startRow = $startRow;
        if ($this->endRow < $this->startRow) {
            $this->endRow = $this->startRow;
        }
        $this->seek($startRow);

        return $this;
    }

    /**
     * (Re)Set the end row.
     *

Lo siento por eso. ¿Esto ayuda?

¡Gracias!

¡Teniendo el mismo problema aquí!

De acuerdo con el seguimiento de la pila, su archivo solo tiene 1 fila (la fila del encabezado), cuando intenta importar cada fila, PhpSpreadsheet se queja de que no hay una segunda fila (y no hay filas más allá de la segunda fila)

@patrickbrouwers Para mi caso, definitivamente hay filas y valores más allá de la fila 1. Parece que tengo que asegurarme de implementar AMBAS preocupaciones WithChunkReading y WithCustomChunkSize para superar el problema. Habiendo dicho eso, también creé un nuevo archivo de Excel y copié los valores del archivo anterior.

Parece que podría haber algún problema con su archivo, si funciona después de copiar los valores a un nuevo archivo.
En caso de que sea un CSV, ¿tal vez no esté usando el delimitador correcto?

Sí. Muy posible. Volveré aquí si vuelve a aparecer, ya que pronto procesaré algunos archivos diferentes. Todos son archivos XLSX.

¡Claro, avísame!

@patrickbrouwers sí, esto es cierto. Estoy tratando de evitar un error del servidor en este caso, y estoy luchando por detectarlo y detener la ejecución del método de modelo de importación.

¿Estoy en el camino correcto usando RegistersEventListeners en App\Imports\PoliciesImport.php? Descubrí cómo obtener la fila más alta, pero no puedo descifrar cómo pasar este valor o adónde ir desde aquí.

    public static function beforeImport(BeforeImport $event)
    {
        $worksheet = $event->reader->getActiveSheet();
        $highestRow = $worksheet->getHighestRow(); // e.g. 10

        dd($highestRow);
    }

@abbylovesdon lo mejor es lanzar una excepción antes de Importar e intentar atraparla en el controlador. Puede pasar la fila más alta a través de la excepción.

@patrickbrouwers ¡ Muchas gracias por tu ayuda! Soy nuevo en PHP/Laravel/Este paquete, así que si alguien más está en mi lugar, esto es lo que hice:

En mi clase de importación: App\Imports\PoliciesImport.php

<?php

namespace App\Imports;

use App\Policy;
use Auth;
use Maatwebsite\Excel\Concerns\ToModel;
use Maatwebsite\Excel\Validators\Failure;
use Maatwebsite\Excel\Validators\ValidationException;
use Maatwebsite\Excel\Concerns\WithValidation;
use Maatwebsite\Excel\Concerns\WithHeadingRow;
use Maatwebsite\Excel\Concerns\Importable;
use Maatwebsite\Excel\Concerns\WithEvents;
use Maatwebsite\Excel\Concerns\RegistersEventListeners;
use Maatwebsite\Excel\Events\BeforeImport;
use Maatwebsite\Excel\Concerns\WithMultipleSheets;

class PoliciesImport implements ToModel, WithValidation, WithHeadingRow, WithMultipleSheets, WithEvents
{
    use Importable, RegistersEventListeners;

    public static function beforeImport(BeforeImport $event)
    {
        $worksheet = $event->reader->getActiveSheet();
        $highestRow = $worksheet->getHighestRow(); // e.g. 10

        if ($highestRow < 2) {
            $error = \Illuminate\Validation\ValidationException::withMessages([]);
            $failure = new Failure(1, 'rows', [0 => 'Now enough rows!']);
            $failures = [0 => $failure];
            throw new ValidationException($error, $failures);
        }
    }

    /**
    * <strong i="8">@param</strong> array $row
    *
    * <strong i="9">@return</strong> \Illuminate\Database\Eloquent\Model|null
    */
    public function model(array $row)
    {
        return new Policy([
          'user_id'     => Auth::user()->id,
          'policy_name' => $row['name'],
          'phone'       => $row['phone'],
          'street'      => $row['address'],
          'city'        => $row['city'],
          'state'       => $row['state'],
          'postal_code' => $row['postal_code'],
        ]);
    }

    public function sheets(): array
    {
        return [
            // Select by sheet index
            0 => new PoliciesImport(),
        ];
    }

    public function rules(): array
    {
        return [
            'name' => 'required|string',
             '*.name' => 'required|string',
        ];
    }

}

Ahora en mi controlador puedo usar:

                  try {
                        (new PoliciesImport)->import($path);
                  } catch (\Exception $e) {
                        $failures = $e->failures();
                        dd($failures[0]);
                  }

¡Teniendo el mismo problema aquí! :((

¡Teniendo el mismo problema aquí! :((

En caso de que no pueda solucionar el problema con las sugerencias y los ejemplos anteriores, le pediría que abra un nuevo problema con la plantilla de problema. ¡Gracias!

tengo el mismo error!

¡pero después de quitar la hoja 2, 3 resuelto!

para esta situación, necesita definir el índice de la hoja por

    public function sheets(): array
    {
        return [
            // Select by sheet index
            0 => new pricelist_items(),
        ];
    }

Me sucedió el mismo caso, pero me di cuenta de que se debe a que existían varias hojas en un archivo de Excel

Acabo de tener el mismo problema. Después de cierta frustración, mi sospecha subyacente resultó ser cierta. Estaba siendo causado por una división en la hoja de cálculo. Después de 'desdividir' la primera fila, funcionó.
image

De acuerdo con el seguimiento de la pila, su archivo solo tiene 1 fila (la fila del encabezado), cuando intenta importar cada fila, PhpSpreadsheet se queja de que no hay una segunda fila (y no hay filas más allá de la segunda fila)

Cómo manejar si Excel solo tiene una fila de encabezado. quiero mostrar el mensaje de error adecuado al cliente

Hola, sé que este hilo ya está cerrado, pero tengo el mismo problema aquí y nada en este hilo me ayuda con mi problema.

Estoy cargando filas de 10k al mismo tiempo y recibí este error Start row (2) is beyond highest row (1) . Pero cuando lo divido en 5k, funciona como magia.

Qué es lo que parece ser el problema aquí?
¡Gracias por adelantado!

Hola, sé que este hilo ya está cerrado, pero tengo el mismo problema aquí y nada en este hilo me ayuda con mi problema.

Estoy cargando filas de 10k al mismo tiempo y recibí este error Start row (2) is beyond highest row (1) . Pero cuando lo divido en 5k, funciona como magia.

Qué es lo que parece ser el problema aquí?
¡Gracias por adelantado!

Tal vez un error en el archivo original que resuelve dividiéndolo. También podría ser un problema de rendimiento, pero es difícil saberlo sin ver su código y las especificaciones de su servidor. Supongo que es un error de archivo.

Me acaba de pasar esto. Ocurre cuando el archivo es más grande que la directiva 'upload_max_filesize' de PHP. Usé fragmentación de 500 para un tamaño de archivo de 5 mb con 40 000 filas, mientras que mi máximo 'upload_max_filesize' en AWS AMI fue de 2 MB. ¿Puedo sugerir a los autores que implementen la verificación del tamaño máximo de carga e impriman este error en lugar de confundir Start row (2) is beyond highest row (1) . Cuando aumenté el límite 'upload_max_filesize', el error desapareció y la carga del archivo fue un éxito.

Lo más probable es que haya más razones por las que phpspreadsheet puede arrojar ese error. Siempre puedes intentar un PR allí.

@GlennM gracias por la respuesta!
He creado una solución alternativa y ya se adapta a las necesidades de mi proyecto por ahora. Veré su sugerencia si tuviera este problema en el futuro.

@patrickbrouwers Para mi caso, definitivamente hay filas y valores más allá de la fila 1. Parece que tengo que asegurarme de implementar AMBAS preocupaciones WithChunkReading y WithCustomChunkSize para superar el problema. Habiendo dicho eso, también creé un nuevo archivo de Excel y copié los valores del archivo anterior.

me ayuda todavía tengo el mismo problema

eliminar hojas de trabajo están vacías

eliminar hojas de trabajo están vacías

Este fue mi caso, si su archivo tiene hojas de trabajo vacías y usa "WithHeadingRow", aparece este problema.

¿Fue útil esta página
0 / 5 - 0 calificaciones