created_at
no se importa en la base de datos. En cambio, veo 1970-01-01 en phpmyadmin
namespace App\Imports;
use App\NewsPost;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Collection;
use Maatwebsite\Excel\Concerns\ToCollection;
use Maatwebsite\Excel\Concerns\WithHeadingRow;
class NewsImport implements ToCollection, WithHeadingRow
{
public $rowCount = null;
public function collection(Collection $rows)
{
News::truncate();
foreach ($rows as $row)
{
if( !empty($row['category_id'])) {
NewsPost::create([
'category_id'=> $row['category_id'],
'title' => $row['title'],
'sef' => $row['sef'],
'introtext' => $row['introtext'],
'fulltext' => $row['fulltext'],
'image' => $row['image'],
'metatitle' => $row['metatitle'],
'metakey' => $row['metakey'],
'metadesc' => $row['metadesc'],
'hits' => $row['hits'],
'created_at' => $row['created_at'],
]);
}
}
$this->rowCount = $rows->count();
}
}
namespace App\Admin\Controllers;
use Illuminate\Support\Facades\DB;
use App\Imports\NewsPostImport;
use Maatwebsite\Excel\Facades\Excel;
class SeedController extends BaseAdminController
{
public function index(Content $content)
{
DB::statement('SET FOREIGN_KEY_CHECKS = 0');
Excel::import($newsPost = new NewsPostImport, 'import/news_posts.xlsm');
DB::statement('SET FOREIGN_KEY_CHECKS = 1');
return $content
->title('Import & Export')
->description('Laravel excel')
->withSuccess('Импорт завершен успешно',
'<p>Импортировано '. $newsPost->rowCount.' новостей</p>');
}
}
¿Se puede rellenar created_at en su modelo?
Si. Tengo todos los campos rellenables
Intente dd () y vea qué hay allí.
lo siento por el retraso. Estaba de vacaciones.
Puse dd aqui
if (empty($row['slug'])) {
News::create([
'category_id' => $row['category_id'],
'title' => $row['title'],
'slug' => Str::slug($row['title'], '-'),
'fulltext' => $row['fulltext'],
'image' => $row['image'],
'metatitle' => $row['metatitle'],
'metakey' => $row['metakey'],
'metadesc' => $row['metadesc'],
'hits' => $row['hits'],
'published_at' => $row['published_at'],
'created_at' => $row['created_at'],
'updated_at' => $row['updated_at'],
'deleted_at' => $row['deleted_at'],
]);
dd($row);
}
y veo una salida de fecha extraña en la página
Illuminate\Support\Collection {#1986 ▼
#items: array:14 [▼
"category_id" => 4
.......
"published_at" => null
"created_at" => 41767
]
}
en mi excel tengo cita asi
¿alguna idea?
Encontré un problema.
Pongo dd($row)
antes de News::create
y compruebo lo que viene de Excel.
Y vi 41767 de nuevo.
Luego voy a sobresalir y verifico el formato del campo
Al hacer eso, entendí que antes de importar todas las fechas en Excel se convierten en texto.
Así que convertí estos campos a texto manualmente, puse fechas dentro y ahora funciona.
Solo una vez pude realizar la importación con éxito y luego todavía tengo algunos problemas, que no puedo entender.
Es un dolor de cabeza importar dátiles. No puedo ver la regla, que funciona siempre.
Probé varias veces cómo debo mantener la fecha en Excel antes de la importación y no veo un comportamiento estable.
Hago que todos los campos de fecha tengan formato = texto en Excel.
Cuando pongo la fecha 08-05-2014
y el formato como texto.
De todos modos tengo un error durante la importación
Unexpected data found.
Unexpected data found.
Data missing
http://localhost.test/admin/seed
apuntando a \ vendor \ nesbot \ carbon \ src \ Carbon \ Traits \ Creator. php: 623
if (static::isStrictModeEnabled()) {
throw new InvalidArgumentException(implode(PHP_EOL, $lastErrors['errors']));
}
Pero cuando lo hago dd($row)
veo
"created_at" => "08-05-2014"
¿Qué está mal?
Parece que encontré una solución.
La única forma de trabajo es mantener la fecha 2014-05-08
en Excel y formatearla como texto.
Porque en este orden se almacena en MySQL = YYYY-MM-DD
Cualquiera de estos no funciona
08-05-2014 - orden incorrecta
08.05.2014 - delimitador incorrecto y orden incorrecto
2014.05.08 - delimitador incorrecto
Si los campos de fecha formateados como fecha en Excel, en mi caso, la fecha 2014-05-08 siempre se convertía a 41767 antes de la importación. No sé por qué.
Probé el convertidor de fecha a marca de tiempo y me da
2014-05-08 = 1399507200.
08-05-2014 = 1407182400
La única forma en que pude obtener 41767 es cuando probé en la fórmula de Excel =text(08.05.2014;0)
Así que supongo que Excel lo convierte.
Y se convierte incluso si ajusto el campo de fecha al formato AAAA-MM-DD.
Entonces, la única solución que funciona es el formato de texto con texto YYYY-MM-DD adentro.
Corrígeme si esta solución no es del todo correcta.
Tengo el mismo problema. Los campos de 'fecha' devuelven un número (¿una referencia, supongo?) Y no el valor.
Para obtener Carbon al tener la columna de fecha formateada como fecha: Carbon::instance(\PhpOffice\PhpSpreadsheet\Shared\Date:: excelToDateTimeObject($row['created_at']))
Funciona para campos no vacíos. Pero cuando el script de importación llega a un campo vacío, se detiene con el siguiente error.
Este problema aparece solo en Laravel 7. Con Laravel 6 no tengo este problema.
SQLSTATE[22007]: Invalid datetime format: 1292 Incorrect datetime value: '1970-01-01 00:00:00' for column 'published_at' at row 1 (SQL: insert into `news_posts` (`category_id`, `title`, `slug`, `fulltext`, `image`, `metatitle`, `metakey`, `metadesc`, `hits`, `is_published`, `published_at`, `created_at`, `updated_at`, `deleted_at`) values ...
¿Qué hacer?
La cláusula IF no es posible dentro de la importación
if (empty($row['published_at'])) {
'published_at' => $row['published_at'],
} else {
'published_at' => Carbon::instance(\PhpOffice\PhpSpreadsheet\Shared\Date::excelToDateTimeObject($row['published_at'])),
}
Da error syntax error, unexpected 'if' (T_IF), expecting ']'
Ponlo en una variable temporal
¿Qué quiere decir con "variable temporal"?
Encontré una solución aceptable
foreach ($rows as $row)
{
if (!empty($row['category_id'])) {
$slug = empty($row['slug']) ? Str::slug($row['title'], '-') : $row['slug'];
$published_at = empty($row['published_at']) ? $row['published_at'] : Carbon::instance(\PhpOffice\PhpSpreadsheet\Shared\Date::excelToDateTimeObject($row['published_at']));
$created_at = empty($row['created_at']) ? $row['created_at'] : Carbon::instance(\PhpOffice\PhpSpreadsheet\Shared\Date::excelToDateTimeObject($row['created_at']));
$updated_at = empty($row['updated_at']) ? $row['updated_at'] : Carbon::instance(\PhpOffice\PhpSpreadsheet\Shared\Date::excelToDateTimeObject($row['updated_at']));
$deleted_at = empty($row['deleted_at']) ? $row['deleted_at'] : Carbon::instance(\PhpOffice\PhpSpreadsheet\Shared\Date::excelToDateTimeObject($row['deleted_at']));
NewsPost::create([
'category_id' => $row['category_id'],
'title' => $row['title'],
'slug' => $slug,
'fulltext' => $row['fulltext'],
'image' => $row['image'],
'metatitle' => $row['metatitle'],
'metakey' => $row['metakey'],
'metadesc' => $row['metadesc'],
'hits' => $row['hits'],
'is_published' => $row['is_published'],
'published_at' => $published_at,
'created_at' => $created_at,
'updated_at' => $updated_at,
'deleted_at' => $deleted_at,
]);
}
}
Comentario más útil
Para obtener Carbon al tener la columna de fecha formateada como fecha:
Carbon::instance(\PhpOffice\PhpSpreadsheet\Shared\Date:: excelToDateTimeObject($row['created_at']))