2017 © Pedro Peláez
 

symfony-bundle csv-bundle

Symfony2 CSV Bundle

image

avro/csv-bundle

Symfony2 CSV Bundle

  • Friday, March 2, 2018
  • by jdewit
  • Repository
  • 6 Watchers
  • 23 Stars
  • 21,819 Installations
  • PHP
  • 1 Dependents
  • 0 Suggesters
  • 17 Forks
  • 11 Open issues
  • 8 Versions
  • 2 % Grown

The README.md

AvroCsvBundle Build Status

This bundle provides an easy way to upload data to your db using csv files with just a few configuration parameters., (*1)

Status

This bundle is under development and may break., (*2)

Limitations

This bundle uses php and Doctrine2 and is not your best bet for importing gargantuan csv files. Use your databases native importing & exporting solutions to skin that cat., (*3)

Features

  • Import data by csv file
  • Export data to csv file
  • A few services for reading/writing csv files

Supports

  • Doctrine ORM

Installation

This bundle is listed on packagist., (*4)

Simply add it to your apps composer.json file, (*5)

    "avro/csv-bundle": "^0.4.2"

Enable the bundle in config/bundles.php as well as the dependent AvroCaseBundle:, (*6)

    Avro\CsvBundle\AvroCsvBundle::class => ['all' => true],
    Avro\CaseBundle\AvroCaseBundle::class => ['all' => true],

Configuration

Add this required config, (*7)

# config/packages/avro_csv.yaml
avro_csv:
    db_driver: orm # supports orm
    batch_size: 15 # The batch size between flushing & clearing the doctrine object manager
    tmp_upload_dir: "%kernel.root_dir%/../web/uploads/tmp/" # The directory to upload the csv files to
    sample_count: 5 # The number of sample rows to show during mapping

Add routes to your config, (*8)

# config/routes/avro_csv.yaml
avro_csv:
    resource: "@AvroCsvBundle/Resources/config/routing.yml"

Add the entities/documents you want to implement importing/exporting for, (*9)

# config/packages/avro_csv.yaml
avro_csv:
    # 
    objects: # the entities/documents you want to be able to import/export data with 
        client:
            class: Avro\CrmBundle\Entity\Client # The entity/document class
            redirect_route: avro_crm_client_list # The route to redirect to after import
        invoice:
            class: Avro\CrmBundle\Entity\Invoice
            redirect_route: avro_crm_invoice_list

To exclude certain fields from being mapped, use the ImportExclude annotation like so., (*10)

namespace Avro\CrmBundle\Entity;

use Doctrine\ORM\Mapping as ORM;
use Avro\CsvBundle\Annotation\ImportExclude;

/**
 * Avro\CrmBundle\Entity\Client
 *
 * @ORM\Entity
 */
class Client
{
    /**
     * @var string
     *
     * @ORM\Column(type="string", length=100, nullable=true)
     * @ImportExclude
     */
    protected $password;

Importing

Implement importing for as many entities/documents as you like. All you have to do is add them to the objects node as mentioned previously., (*11)

Then just include a link to specific import page like so:, (*12)

<a href="{{ path('avro_csv_import_upload', {'alias': 'client'}) }}">Go to import page</a>

Replace "client" with whatever alias you called your entity/document in the config., (*13)

Views

The bundle comes with some basic twitter bootstrap views that you can override by extending the bundle., (*14)

Association mapping

An event is fired when importing an association field to allow implementing your own logic fitting, (*15)

Just create a custom listener in your app that listens for the AssociationFieldEvent::class event., (*16)

A simple implementation getting an associated entity by name could look like:, (*17)

namespace App\EventListener;

use Avro\CsvBundle\Event\AssociationFieldEvent;
use Doctrine\ORM\EntityManagerInterface;
use Doctrine\ORM\Mapping\ClassMetadataInfo;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;

/**
 * Csv import listener
 */
class ImportListener implements EventSubscriberInterface
{
    private $em;

    /**
     * @param EntityManagerInterface   $em      The entity manager
     */
    public function __construct(EntityManagerInterface $em)
    {
        $this->em = $em;
    }

    public static function getSubscribedEvents()
    {
        return [
            AssociationFieldEvent::class => 'importAssociation',
        ];
    }

    /**
     * Set the objects createdBy field
     *
     * @param AssociationFieldEvent $event
     */
    public function importAssociation(AssociationFieldEvent $event)
    {
        $association = $event->getAssociationMapping();
        switch ($association['type']) {
            case ClassMetadataInfo::ONE_TO_ONE:
            case ClassMetadataInfo::MANY_TO_ONE:
                $relation = $this->em->getRepository($association['targetEntity'])->findOneBy(
                    [
                        'name' => $event->getRow()[$event->getIndex()],
                    ]
                );
                if ($relation) {
                    $event->getObject()->{'set'.ucfirst($association['fieldName'])}($relation);
                }
                break;
        }
    }
}

Customizing each row

Want to customize certain fields on each row? No problem., (*18)

An event is fired when a row is added that you can tap into to customize each row of data., (*19)

Just create a custom listener in your app that listens for the RowAddedEvent::class event., (*20)

For example..., (*21)

namespace App\EventListener;

use Avro\CsvBundle\Event\RowAddedEvent;
use Doctrine\ORM\EntityManagerInterface;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\Security\Core\SecurityContextInterface;

/**
 * Csv import listener
 */
class ImportListener implements EventSubscriberInterface
{
    private $em;
    private $context;

    /**
     * @param EntityManagerInterface   $em      The entity manager
     * @param SecurityContextInterface $context The security context
     */
    public function __construct(EntityManagerInterface $em, SecurityContextInterface $context)
    {
        $this->em = $em;
        $this->context = $context;
    }

    public static function getSubscribedEvents()
    {
        return [
            RowAddedEvent::class => 'setCreatedBy',
        ];
    }

    /**
     * Set the objects createdBy field
     *
     * @param RowAddedEvent $event
     */
    public function setCreatedBy(RowAddedEvent $event)
    {
        $object = $event->getObject();

        $user = $this->context->getToken()->getUser();

        $object->setCreatedBy($user);
    }
}

Register your listener or use autowiring, (*22)

Exporting

This bundle provides some simple exporting functionality., (*23)

Navigating to "/export/your-alias" will export all of your data to a csv and allow you to download it from the browser., (*24)

You can customize the export query builder and the exported data by listening to the corresponding events (See events in the Avro\CsvBundle\Event namespace)., (*25)

If you want to customize data returned, just create your own controller action and grab the queryBuilder from the exporter and add your constraints before calling "getContent()"., (*26)

Ex., (*27)

namespace App\Controller;

use Avro\CsvBundle\Export\ExporterInterface;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpFoundation\Response;

class ExportController extends AbstractController
{
    /**
     * Export a db table.
     *
     * @param ExporterInterface $exporter The exporter
     * @param string            $alias    The objects alias
     *
     * @return Response
     */
    public function exportAction(ExporterInterface $exporter, string $alias): Response
    {
        $class = $this->getParameter(sprintf('avro_csv.objects.%s.class', $alias));

        $exporter->init($class);

        // customize the query
        $qb = $exporter->getQueryBuilder();
        $qb->where('o.fieldName =? 1')->setParameter(1, false);

        $content = $exporter->getContent();

        $response = new Response($content);
        $response->headers->set('Content-Type', 'application/csv');
        $response->headers->set('Content-Disposition', sprintf('attachment; filename="%s.csv"', $alias));

        return $response;
    }
}

Register your controller or use your already setup autowiring, (*28)

To Do:

  • Finish mongodb support

Acknowledgements

Thanks to jwage's EasyCSV for some ground work., (*29)

Feedback and pull requests are much appreciated!, (*30)

The Versions

21/01 2018

0.1.x-dev

0.1.9999999.9999999-dev http://github.com/jdewit/AvroCsvBundle

Symfony2 CSV Bundle

  Sources   Download

MIT

The Requires

 

The Development Requires

by Joris de Wit

csv export import

21/01 2018

v0.1.1

0.1.1.0 http://github.com/jdewit/AvroCsvBundle

Symfony2 CSV Bundle

  Sources   Download

MIT

The Requires

 

The Development Requires

by Joris de Wit

csv export import

18/01 2013

dev-develop

dev-develop http://github.com/jdewit/AvroCsvBundle

Symfony2 CSV Bundle

  Sources   Download

MIT

The Requires

 

The Development Requires

by Joris de Wit

csv export import

14/12 2012

v0.1.0

0.1.0.0 http://github.com/jdewit/AvroCsvBundle

Symfony2 CSV Bundle

  Sources   Download

MIT

The Requires

  • php >=5.3.2

 

by Joris de Wit

csv converter