After the user submits a (uncomplete) form, I want the form to show the already entered data + an error message.
Using this code, the form is empty after submitting the form:
$request = $app['request'];
$form = $app['form.factory']->createBuilder('form')
->add('name', 'text', array( 'label' => 'Ihre Name:'))
->add('comment', 'text', array('constraints' => new Assert\Length(array('min' => 15))))
->getForm();
$twig_context = array('form' => $form->createView());
$form->handleRequest($request);
if ($form->isValid()) {
$data = $form->getData();
return 'valid!';
// Send form...
} else {
// display the form
return $app['twig']->render('contact.html.twig', $twig_context);
}
Twig-template:
{{ form_start(form) }}
{{ form_widget(form) }}
<div>
<input type="submit" value="Send" />
</div>
{{ form_end(form) }}
You should create the form view last, (could be right before you render your template). In your case, the view is created before the data from Request is applied.
This:
$twig_context = array('form' => $form->createView());
$form->handleRequest($request);
Should be:
$form->handleRequest($request);
And your render method should be:
return $app['twig']->render('contact.html.twig',
array(
'form' => $form->createView()
)
);
Related
I am trying to Import Excel Data in Laravel and Insert into Database. I am using maatwebsite/excel version 3 composer package and laravel version 5.8
Error screenshot:
https://imgur.com/a/2KXCE0g
Blade file: import.blade.php
<form action="{{ url('/import-excel/import') }}" method="POST" enctype="multipart/form-data">
{{ csrf_field() }}
<div class="form-group">
<label for="importFile">Select Import File</label>
<input type="file" name="select_file" class="form-controll">
</div>
<input type="submit" name="upload" class="btn btn-success" value="Import File">
</form>
Controller file: ImportExcelController.php
public function import(Request $request){
$this->validate($request, [
'select_file' => 'required|mimes:xls,xlsx'
]);
$path = $request->file('select_file')->getRealPath();
$data = Excel::import($path)->get();
if($data->count() > 0){
foreach($data->toArray() as $key => $value){
foreach($value as $row){
$insert_data[] = array(
'CustomerName' => $row['customer_name'],
'Gender' => $row['gender'],
'Address' => $row['address'],
'City' => $row['city'],
'PostalCode' => $row['postal_code'],
'Country' => $row['country'],
);
}
}
if(!empty($insert_data)){
DB::table('tbl_customer')->inset($insert_data);
}
}
return back()->with('success', 'Import data successfully!');
}
I have checked excel.php file are exits in config folder. provider and aliases added.
route
Route::get('/import-excel', 'ImportExcelController#index');
Route::post('/import-excel/import', 'ImportExcelController#import');
how to solve this please?
This is the method signature for the import method:
public function import($import, $filePath, string $disk = null, string $readerType = null);
Which means that the path is a second parameter, but you are missing the first one.
The first one should be an import class, you create one like this as an example
php artisan make:import UsersImport --model=User
Then to use it:
Excel::import(new UsersImport, $path);
You will need to let know the library how to map each row from the file into an object for your usage.
-- EDIT
So I would create a model, but you can do the same like this:
class CustomersImport implements ToCollection
{
public function collection(Collection $rows)
{
$data = [];
foreach ($rows as $row)
{
$data[] = array(
'CustomerName' => $row[0],
'Gender' => $row[1],
'Address' => $row[2],
'City' => $row[3],
'PostalCode' => $row[4],
'Country' => $row[5],
);
}
DB::table('tbl_customer')->insert($data);
}
}
So something like this, but debug what does the rows contains and make sure when you iterate you get the correct key to the correct column in your database.
I'm trying to do a form with symfony 4. It works fine. But I have a problem.
I have a field to write a comment. By default, it's not required.
However, I would like to change this using jquery.
This is what I tried to do.
Here, it's my twig:
<div class="information" id="informationForm">
{{ form_row(recordForm.category) }}
{{ form_row(recordForm.information) }}
{{ form_label(recordForm.comment) }}
{{ form_widget(recordForm.comment, {'attr': {'class': 'comment'}}) }}
{{ form_errors(recordForm.comment) }}
<button id="add_information_button" class="btn btn-primary">Ajouter un renseignement</button>
<button id="count_div" class="btn btn-primary">Compter</button>
<button class="remove_information_button btn btn-primary">Supprimer un renseignement</button>
</div>
Here it's the javascript:
$('.information')
.on("change", ".record_to_information_form_information", function (event) {
event.preventDefault();
var $commentState = $(this).find('option:selected').data('comment')
//Test: to know if i received the attribute
console.log($commentState)
if($commentState===false){
//the field isn't required
// {{ form_widget(recordForm.comment, {'attr': {'required': 'false'}}) }}
}else{
//the field is required
// {{ form_widget(recordForm.comment, {'attr': {'required': 'true'}}) }}
}
})
;
Do you have any suggestions?
You can toggle required property value from your jQuery code.
I assume that data-comment attribute has type boolean and it's always set, so your toggle statement can look as follows:
$('.information')
.on("change", ".record_to_information_form_information", function (event) {
event.preventDefault();
var $commentState = $(this).find('option:selected').data('comment');
//Test: to know if i received the attribute
console.log($commentState);
$('.comment').prop('required', $commentState);
});
If you need to do something else in your if-else statement, you can just leave your condition as you provided in sample:
if ($commentState === false) {
//the field isn't required
$('.comment').prop('required', false);
} else {
//the field is required
$('.comment').prop('required', true);
}
I have a dropdown list that should be filled from an excel file column
for now I am filling the list directly:
Formbuilder:
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('Author', ChoiceType::class, array(
'choices' => array(
'Author1' => 'Author1',
'Author2' => 'Author2',
'Author3' => 'Author3'
)))
;
}
twig
<div class="col-xs-9 col-sm-9 col-md-9 col-lg-9">
{{ form_widget(form.Author, {'attr': {'class' : 'form-control '}}) }}
</div>
is that doable from the form builder ?
You can use phpoffice/phpexcel to read your Excel files (it will be good to use service) : http://www.techchattr.com/how-to-read-excel-files-with-php
Add it to your FormBuilder definitions as params like :
$data = $options['data'];
Pass it as 'choices' of your field
Then, pass data as params of formbuilder like ($data contains infos from phpExcel) :
$form = $this->createForm(YourType::class, $entity, ['data' => $data]);
First data loading is fine but when i click on load more my second page data going inside even div only.
I am generating list like this:
<div class="odd">
<items>item1</items>
<items>item3</items>
<items>item5</items>
<items>item7</items>
</div>
<div class="even">
<items>item2</items>
<items>item4</items>
<items>item6</items>
<items>item8</items>
</div>
With this custom ListView class:
class ListViewOdd extends ListView
{
public function renderItems()
{
$models = $this->dataProvider->getModels();
$keys = $this->dataProvider->getKeys();
$rowsOdd = $rowsEven = [];
foreach (array_values($models) as $index => $model) {
if ($index%2 == 0) {
$rowsOdd[] = $this->renderItem($model, $keys[$index], $index);
} else {
$rowsEven[] = $this->renderItem($model, $keys[$index], $index);
}
}
return '<div class="odd">'.implode($this->separator, $rowsOdd) . '</div><div class="even">'.implode($this->separator, $rowsOdd) .'</div>'; // replace <div> to Html::tag('div', ...)
}
}
echo ListViewOdd::widget([
'dataProvider' => $dataProvider,
'itemView' => '_post',
]);
But load more pagination not splitting data again into odd/even listing as my first data list.
i am not passing anything from controller and action i am using model to get data provider
<?php echo ListViewOdd::widget([
'dataProvider' => Posts::getCommonListData($industry,'user','engage',0),
'itemOptions' => ['class' => 'item post-item'],
'summary' => '',
'id' => 'my-listview-id',
'itemView' => '_Posts',
'viewParams' => [
'fullView' => true,
],
'pager' => [
'class' => \app\vendor\kop\y2sp\ScrollPager::className(),
//'negativeMargin' => '200',
'triggerText' => 'Load More',
//'triggerOffset' => 3,
'noneLeftText' => '',
],
]);
getting output like this
<div class="odd">
<items>item1</items>
<items>item3</items>
<items>item5</items>
<items>item7</items>
</div>
<div class="even">
<items>item2</items>
<items>item4</items>
<items>item6</items>
<items>item8</items>
<items>item9</items>
<items>item10</items>
<items>item11</items>
<items>item12</items>
</div>
after clicking loadmore its just loading all records inside even div and load more aoption also coming under even div
Change in method renderItems:
return '<div class="odd">'.implode($this->separator, $rowsOdd) . '</div><div class="even">'.implode($this->separator, $rowsEven) .'</div>';
Mistake is ''.implode($this->separator, $rowsOdd) .''.
Div is even, but data from $rowsOdd :)
I had a project with Symfony 2.0 and FOSUserBundle 1.2.0, and everything was working fine. When I upgraded to the latest Symfony 2.1 version and the latest FOSUserBundle from the master branch, after fixing lots of stuff, the labels are not being translated, i.e. "form.username".
I had the User Bundle overwritten by a custom bundle I made. I've overwritten the following stuff:
Controller
ChangePasswordController
GroupController
RegistrationController
UserController
Form
Type
ChangePasswordFormType
RegistrationFormType
Resources
config
routing.yml
views
ChangePassword
changePassword_content.html.twig
changePassword.html.twig
Form
form_group.html.twig
form_user.html.twig
Group
edit.html.twig
list.html.twig
new.html.twig
show.html.twig
Registration
checkEmail.html.twig
email.txt.twig
register_content.html.twig
register.html.twig
User
edit.html.twig
index.html.twig
show.html.twig
I also have a custom user and group entity, and my custom UserType and GroupType which I omitted in the previous tree.
The translation files where at app/Resources/translations/FOSUserBundle.en.yml
I also tryed copying them to my bundle, src/Acme/UserBundle/Resources/translations/FOSUserBundle.en.yml
None of them is working with symfony 2.1.
Of course I cleaned the cache, the production cache, and regenerated assets just in case and refreshed the browser... Everything several times and nothing.
I searched here and on Google and I can't find any clues, I tried some things but without success.
I will copy the contents of some of the files below.
Acme/UserBundle/Controller/RegistrationController.php
<?php
namespace Acme\UserBundle\Controller;
use Symfony\Component\HttpFoundation\RedirectResponse;
class RegistrationController extends BaseController
{
public function registerAction()
{
$form = $this->container->get('fos_user.registration.form');
$formHandler = $this->container->get('fos_user.registration.form.handler');
$confirmationEnabled = $this->container->getParameter('fos_user.registration.confirmation.enabled');
$process = $formHandler->process($confirmationEnabled);
if ($process) {
$user = $form->getData();
$authUser = false;
if ($confirmationEnabled) {
$this->container->get('session')->set('fos_user_send_confirmation_email/email', $user->getEmail());
$route = 'fos_user_registration_check_email';
} else {
$authUser = true;
$route = 'AcmeUserBundle_admin_user_index';
}
$this->setFlash('fos_user_success', 'registration.flash.user_created');
$url = $this->container->get('router')->generate($route);
$response = new RedirectResponse($url);
if ($authUser) {
$this->authenticateUser($user, $response);
}
return $response;
}
return $this->container->get('templating')->renderResponse('FOSUserBundle:Registration:register.html.'.$this->getEngine(), array(
'form' => $form->createView(),
));
}
}
Acme/UserBundle/Form/Type/RegistrationFormType.php
<?php
namespace Acme\UserBundle\Form\Type;
use Doctrine\ORM\EntityManager;
class RegistrationFormType extends BaseType
{
private $entityManager;
public function __construct($class, EntityManager $entityManager)
{
parent::__construct($class);
$this->entityManager = $entityManager;
}
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('username', null, array('label' => 'form.username', 'translation_domain' => 'FOSUserBundle', 'error_bubbling' => true))
->add('nombre', 'text', array('error_bubbling' => true))
->add('apellido', 'text', array('error_bubbling' => true))
->add('email', 'email', array('label' => 'form.email', 'translation_domain' => 'FOSUserBundle', 'error_bubbling' => true))
->add('plainPassword', 'repeated', array(
'type' => 'password',
'options' => array('translation_domain' => 'FOSUserBundle'),
'first_options' => array('label' => 'form.password'),
'second_options' => array('label' => 'form.password_confirmation'),
'invalid_message' => 'fos_user.password.mismatch',
'error_bubbling' => true,
))
->add('groups', 'entity', array(
'class' => 'Acme\\UserBundle\\Entity\\Group',
'property' => 'name',
'label' => 'Grupos',
'empty_value' => 'Seleccione Grupos',
'multiple' => true,
'expanded' => true,
'required' => false,
));
}
public function getName()
{
return 'acme_user_registration';
}
}
Acme/Resources/views/Registration/register_content.html.twig
<form action="{{ path('fos_user_registration_register') }}" {{ form_enctype(form) }} method="POST" class="fos_user_registration_register">
<div class="content no-padding" {{ block('container_attributes') }}>
{{ form_widget(form) }}
</div>
<div class="actions">
<div class="actions-left" style="margin-top: 8px;"></div>
<div class="actions-right">
<input type="submit" value="{{ 'registration.submit'|trans({}, 'FOSUserBundle') }}" />
</div>
</div>
Acme/Resources/views/Registration/register.html.twig
{% extends "AcmeAdminBundle:Base:base_auth.html.twig" %}
{% form_theme form 'AcmeUserBundle:Form:form_user.html.twig' %}
*[...] Here are stylesheets and JS[...]*
{% block main_content %}
<!-- Start of the main content -->
<div id="main_content">
<h2 class="grid_12">{% block title "Crear Usuario" %}</h2>
<div class="clean"></div>
<div class="grid_6">
<div class="box">
<div class="header">
<img src="{{ asset('bundles/acmeadmin/img/icons/packs/fugue/16x16/ui-text-field-format.png') }}" alt="" width="16"
height="16">
<h3>Información Básica</h3>
<span></span>
</div>
{% block fos_user_content %}
{% include "AcmeUserBundle:Registration:register_content.html.twig" %}
{% endblock fos_user_content %}
</div> <!-- End of .box -->
</div> <!-- End of .grid_6 -->
</div> <!-- End of #main_content -->
<div class="push clear"></div>
{% endblock main_content %}
If I disable my bundle, removing
public function getParent()
{
return 'FOSUserBundle';
}
the labels appear translated as expected. I don't know what else to do. Any Suggestions?