unable to render Zend_Form - zend-framework

i'm trying to render a login form using Zend_Form, i want it to be rendered calling www.site.com/login or www.site.com/account/login, but once i've done all the steps below and i try to call /login or /account/login from my browser i'm getting a HTTP 500 (Internal Server Error).. even if the rest of the site works perfectly. Please help me figure out where i'm wrong..
(note that I'm using Zend Framework 1.11)
(1) Create the model through ZF
zf create model FormLogin
(2) Edit the new created model in application/models/FormLogin.php
class Application_Model_FormLogin extends Zend_Form
{
public function __construct($options = null)
{
parent::__construct($options);
$this->setName('login');
$this->setMethod('post'); // GET O POST
$this->setAction('/account/login'); // form action=[..]
$email = new Zend_Form_Element_Text('email');
$email->setAttrib('size', 35);
$pswd = new Zend_Form_Element_Password('pswd');
$pswd->setAttrib('size', 35);
$submit = new Zend_Form_Element_Submit('submit'); // submit button
$this->setDecorators( array( array('ViewScript', array('viewScript' => '_form_login.phtml'))));
$this->addElements(array($email, $pswd, $submit));
}
}
(3) Add loginAction to the Account controller
class AccountController extends Zend_Controller_Action
{
public function init()
{
/* Initialize action controller here */
}
public function indexAction()
{
}
public function loginAction()
{
$form = new Application_Model_FormLogin();
$this->view->form = $form;
}
}
(4) Create the View at application/views/scripts/account/login.phtml
<?php echo $this->form; ?>
(5) Create the page application/views/scripts/_form_login.phtml called by setDecorators() at the point (2)
<form id="login" action="<?php echo $this->element->getAction(); ?>"
method="<?php echo $this->element->getMethod(); ?>">
<p>
E-mail Address<br />
<?php echo $this->element->email; ?>
</p>
<p>
Password<br />
<?php echo $this->element->pswd; ?>
</p>
<p>
<?php echo $this->element->submit; ?>
</p>
</form>
(6) And this is my Bootstrap.php
class Bootstrap extends Zend_Application_Bootstrap_Bootstrap
{
public function _initRoutes()
{
$frontController = Zend_Controller_Front::getInstance();
$router = $frontController->getRouter();
$route = new Zend_Controller_Router_Route_Static (
'login',
array('controller' => 'Account', 'action' => 'login')
);
$router->addRoute('login', $route);
$route = new Zend_Controller_Router_Route (
'games/asin/:asin/',
array('controller' => 'Games',
'action' => 'view',
'asin' => 'B000TG530M' // default value
)
);
$router->addRoute('game-asin-view', $route);
}
}

Change your class definition for Application_Model_FormLogin to the following:
<?php
class Application_Model_FormLogin extends Zend_Form
{
public function init()
{
$this->setName('login');
$this->setMethod('post'); // GET O POST
$this->setAction('/account/login'); // form action=[..]
$email = new Zend_Form_Element_Text('email');
$email->setAttrib('size', 35);
$pswd = new Zend_Form_Element_Password('pswd');
$pswd->setAttrib('size', 35);
$submit = new Zend_Form_Element_Submit('submit'); // submit button
$this->setDecorators( array( array('ViewScript', array('viewScript' => '_form_login.phtml'))));
$this->addElements(array($email, $pswd, $submit));
}
}
You should set your form up using the init() method rather than using __construct()
When you call parent::__construct($options); in the constructor for your Zend_Form, that ends up calling the form's init() method and then nothing after that is executed so your form initialization and element creation was never being called.
The 500 internal server was because you were calling parent::__construct() and your form had no init() method.

drew010 has a good point about setting up your form in init() rather then__construct().
I just spent hours fighting with the viewScript method and this is how I got it to work (so far).
$this->view->form = $form assigns to the view
then in your view you need to render the partial with something like <?php echo $this->render('_form_login.phtml')
if you use this method then you access your elements using <?php echo $this->form->email; ?>
Using this method I did not use the $this->setDecorators( array( array('ViewScript', array('viewScript' => '_form_login.phtml')))); line of code.
The proper way to do this uses the viewScript decorator, however I have not been able to make it work yet. I did find that using this decorator I had to access the elements using $this->element->elementname, but I could not find anyway to access the method or action. getMethod() and getAction() both returned errors.
[EDIT]
ok i got it to work:
Make your form as normal using init()
$form->setDecorators(array(
array('ViewScript', array('viewScript' => '_yourScript.phtml'))
)); I like to add this in the controller.
in your viewScript access the form object using $this->element instead of $this->form
assign your form to the view normally $this->view->form = $form
render the form normally <?php echo $this->form ?>
this is the example I got to work...finally
<form action="<?php echo $this->element->getAction() ?>"
method="<?php echo $this->element->getMethod() ?>">
<table>
<tr>
<td><?php echo $this->element->weekend->renderLabel() ?></td>
<td><?php echo $this->element->weekend->renderViewHelper() ?></td>
<td><?php echo $this->element->bidlocation->renderLabel() ?></td>
<td><?php echo $this->element->bidlocation->renderViewHelper() ?></td>
<td><?php echo $this->element->shift->renderLabel() ?></td>
<td><?php echo $this->element->shift->renderViewHelper() ?></td>
</tr>
<tr>
<td colspan="6"><?php echo $this->element->submit ?></td>
</tr>
</table>
</form>
I think my hoof-in-mouth is cured for the moment.

Related

cakephp3- unable to post form data to controller function

I have a contact us form and user enter data and submits it. This data needs to accessed in controller function so I can send a mail to admin informing about the user request recently received.
But when I press submit button, nothing happens. Form just reloads and the contactus form (view page) is shown to the users. I don't know why the data is not getting passed to the controller function.
I'mm new to CakePHP framework and I'm using CakePHP3 for development purposes.
Here is my form:
<?php echo $this->Form->create(null, ['url' => ['controller' => 'Pages', 'action' => 'contactus']]); ?>
<div class="col-md-6">
<?php echo $this->Form->input('fname', ['placeholder' => 'Your name.' , 'id' => 'fname', 'required' => 'required']); ?>
</div>
<div class="col-md-6">
<?php echo $this->Form->input('mail', ['placeholder' => 'Your email.' , 'id' => 'mail', 'required' => 'required']); ?>
</div>
<div class="col-md-6">
<?php echo $this->Form->input('subject', ['placeholder' => 'Write something.', 'id' => 'subject']); ?>
</div>
<div class="col-md-9">
<?php echo $this->Form->button(__('Submit')); ?>
</div>
<?php echo $this->Form->end(); ?>
And my controller function is:
public function contactus()
{
$pages ='';
if ($this->request->is('post'))
{
$pages = $this->request->data('Contact');
}
$this->set(compact('pages'));
$this->set('_serialize', ['pages']);
}
Can anyone tell me the mistakes I made?
I think your form is submitting but not through the post method. So I would like to say you that, please make the bellow changes before submitting the form.
$pages ='';
if ($this->request->is('post'))
{
echo "Request is post";die;
$pages = $this->request->data('Contact');
}else{
echo "request is not post";die;
}
$this->set(compact('pages'));
$this->set('_serialize', ['pages']);
Now check, which is printing in the display. Then I can help you further.
Remember: - fill the form, then after change the controller method, then press submit method.

Disable or change validation for embedded form fields in Symfony1 form

I am trying to cancel validation in embedded forms based on a value from main form.
By default, embedded forms fields have validator option set to 'required'=>true. So it gets validated like that. If user leave any field blank, the form does not pass validation and blank fields get marked in template (different style).
What I am trying to do is to change option:"required" to false for all fields in embedded form.
I tried to do that in post validator callback method, but it seems that it is not possible that way.
The main form code:
class TestForma extends sfForm
{
public function configure()
{
$this->setWidgets(array(
'validate_items' => new sfWidgetFormChoice(array(
'choices' => array('no' => 'No', 'yes' => 'Yes'),
'multiple' => false,'expanded'=>true,'default' => 'no')),
));
$this->setValidators(array('validate_items' => new sfValidatorPass()));
$this->widgetSchema->setNameFormat('testforma[%s]');
$subForm = new sfForm();
for ($i = 0; $i < 2; $i++)
{
$form = new ItemForma();
$subForm->embedForm($i, $form);
}
$this->embedForm('items', $subForm);
$this->validatorSchema->setPostValidator(
new sfValidatorCallback(array('callback' => array($this, 'postValidate')))
);
}
Post-validator code:
public function postValidate($validator,$values)
{
$validatorSchema = $this->getValidatorSchema();
if($values['validate_items']=='no')
{
$itemsValidatorSchema = $validatorSchema['items'];
$itemsFieldsValidatorSchemes = $itemsValidatorSchema->getFields();
foreach($itemsFieldsValidatorSchemes as $itemValidatorScheme)
{
$itemValidatorScheme['color']->setOption('required',false);
$itemValidatorScheme['shape']->setOption('required',false);
}
}
return $values;
}
Embedded form class:
class ItemForma extends sfForm
{
public function configure()
{
$this->setWidgets(array(
'color' => new sfWidgetFormInputText(),
'shape' => new sfWidgetFormInput(),
));
$this->setValidators(array(
'color' => new sfValidatorString(array('required'=>true)),
'shape' => new sfValidatorEmail(array('required'=>true)),
));
$this->widgetSchema->setNameFormat('items[%s]');
}
}
Template code:
<form action="<?php echo url_for('weather/formiranje')?>" method="post">
<?php
foreach($form->getErrorSchema()->getErrors() as $e)
{
echo $e->__toString();
}
?>
<table>
<tfoot>
<tr>
<td colspan="2">
<input type="submit" value="OK" />
</td>
</tr>
</tfoot>
<tbody>
<tr><th>Main form</th></tr>
<tr><td><?php echo $form['validate_items']->renderLabel() ?>
<span class="<?php echo $form['validate_items']->hasError() ? 'rowError' : ''?>">
<?php echo $form['validate_items'] ?></span>
</td></tr>
<tr><td> </td></tr>
<tr><th>Embedded forms</th></tr>
<?php
foreach($form['items'] as $item)
{
?>
<tr>
<td><span class="<?php echo $item['color']->hasError() ? 'rowError' : ''?>">
<?php echo $item['color']->renderLabel() ?>
<?php echo $item['color'] ?></span>
</td>
</tr>
<tr>
<td><span class="<?php echo $item['shape']->hasError() ? 'rowError' : ''?>">
<?php echo $item['shape']->renderLabel() ?>
<?php echo $item['shape'] ?></span>
</td></tr>
<?php
}
echo $form['_csrf_token'];
?>
</tbody>
</table>
</form>
The way you organised it won't work because the post validator is run after all the field validators, so they've already been checked and marked as failed. (because the fields were required).
You could try the same approach you have here but with setting a preValidator instead of a postValidator. I think it should work then.
If it still won't work as expected what I would do is to change the default settings on the embedded form's fields to 'required' = false and use the postValidator. In the validator you could check whether or not you need to validate the embedded fields. If you need to validate them you can check if their values are set and if not you can throw errors for those fields. (I hope this is explained clearly)
Another thing you could try is to re-run the validation for the chosen fields. So something like that in your postValidator:
$itemValidatorScheme['color']->setOption('required',false);
$itemValidatorScheme['color']->clean($values['name_of_the_field']);

jquery ajax in Zend framework

i am new to ZF i want to create ajax link that will go to "task" controller and "ajax" action
do something like this
$registry = Zend_Registry::getInstance();
$DB = $registry['DB'];
$sql = "SELECT * FROM task ORDER BY task_name ASC";
$result = $DB->fetchAll($sql);
than put the result in this div
<div id="container">container</div>
this is my view where i am doing this
<?php echo $this->jQuery()->enable(); ?>
<?php echo $this->jQuery()->uiEnable(); ?>
<div id="container">container</div>
<?php
echo $this->ajaxLink("Bring All Task","task/ajax",array('update' => '#container'));
?>
i dont know the syntax how i will do this , retouch my code if i am wrong i searched alot but all in vain plz explain me thanking you all in anticipation also refer me some nice links of zendx_jquery tutorial
This should work:
class IndexController extends Zend_Controller_Action
{
/**
* Homepage - display result of ajaxRequest
*/
public function indexAction()
{
}
/**
* Print result of database query
*/
public function ajaxAction()
{
// disable rendering of view and layout
$this->_helper->layout()->disableLayout();
$registry = Zend_Registry::getInstance();
$db = $registry['DB'];
// get select object to build query
$select = $db->select();
$select->from('task')->order('task_name ASC');
// echo result or what ever..
$this->view->tasks = $db->fetchAll($select);
}
}
// index.phtml (view)
<?php
echo $this->jQuery()->enable();
echo $this->jQuery()->uiEnable();
// create link to ajaxAction
$url = $this->url(array(
'controller' => 'index',
'action' => 'ajax',
));
?>
<div id="container">container</div>
<?php
echo $this->ajaxLink(
"Bring All Task", $url, array('update' => '#container')
);
?>
and in your ajax.phtml
<?php if ($this->tasks): ?>
<table>
<tr>
<th>task ID</th>
<th>task Name</th>
</tr>
<?php foreach($this->tasks as $task) : ?>
<tr>
<td><?php echo $task['task_id']; /* depending on your column names */ ?>
</td>
<td><?php echo $this->escape($task['task_name']); /* to replace " with " and so on */ ?>
</td>
</tr>
<?php endforeach; ?>
</table>
<?php else: ?>
No tasks in table.
<?php endif; ?>
regarding db you have to setup it first somewhere earlier in your code, for example front controller index.php or bootstrap.php, for example:
$db = Zend_Db::factory('Pdo_Mysql', array(
'host' => '127.0.0.1',
'username' => 'webuser',
'password' => 'xxxxxxxx',
'dbname' => 'test'
));
Zend_Registry::set('DB', $db);

zend paginator make other links and Action Calling concatinating with the URL

I am NEW to ZF .i used zend paginator in my first project .its working fine that is switching b/w pages with right result but the problem is that i have other links too in that view have a look to my view
<?php include "header.phtml"; ?>
<h1><?php echo $this->escape($this->title);?></h1>
<h2><?php echo $this->escape($this->description);?></h2>
Register
<table border="1" align="center">
<tr>
<th>User Name</th>
<th>First Name</th>
<th>Last Name</th>
<th>Action</th>
</tr>
<?php
foreach($this->paginator as $record){?>
<tr>
<td><?php echo $record->user_name;?></td>
<td><?php echo $record->first_name;?></td>
<td><?php echo $record->last_name;?></td>
<td>
Edit
|
Delete
</td>
</tr>
<?php } ?>
</table>
<?php echo $this->paginationControl($this->paginator, 'Sliding', 'pagination.phtml'); ?>
<?php include "footer.phtml"; ?>
as i said the pagination renders and working fine but when i click on these links
<a id="edit_link" href="edit/id/<?php echo $record->id;?>">Edit</a>
or
<a id="delete_link" href="del/id/<?php echo $record->id;?>">Delete</a>
or
Register
it is not calling the required action instead it make my url like this
(initial link) http://localhost/zend_login/web_root/index.php/task/list
after clicking any of the above link its like this
http://localhost/zend_login/web_root/index.php/task/list/page/edit/id/8
http://localhost/zend_login/web_root/index.php/task/list/page/edit/id/edit/id/23
http://localhost/zend_login/web_root/index.php/task/list/page/edit/id/edit/id/register http://localhost/zend_login/web_root/index.php/task/list/page/edit/id/edit/id/del/id/12
note its not happening when the page renders first time but when i click on any pagination link its doing so initialy its going to the reguired action and displaying a view...any help HERE IS THE ACTION
public function listAction(){
$registry = Zend_Registry::getInstance();
$DB = $registry['DB'];
$sql = "SELECT * FROM task ORDER BY task_name ASC";
$result = $DB->fetchAll($sql);
$page=$this->_getParam('page',1);
$paginator = Zend_Paginator::factory($result);
$paginator->setItemCountPerPage(3);
$paginator->setCurrentPageNumber($page);
$this->view->assign('title','Task List');
$this->view->assign('description','Below, are the Task:');
$this->view->paginator=$paginator;
}
Try:
// controller
$this->view->controllerName = $this->getRequest()->getControllerName();
// view script
Edit
|
Delete
or
Edit
|
Delete
Second example uses baseUrl() view helper that's using front controller's baseUrl setting. If you don't set baseUrl in your frontController it's trying to guess. As you're not using bootstrap functionality to set baseUrl you may do the following in index.php (not required):
$frontController = Zend_Controller_Front::getInstance();
$frontController->setBaseUrl('/');
Third possibility using url() view helper:
<a href="<?php echo $this->url(array(
'controller' => $controllerName,
'action' => 'edit',
'id' => $record_->id
)); ?>">Edit</a>
|
<a href="<?php echo $this->url(array(
'controller' => $controllerName,
'action' => 'del',
'id' => $record_->id
));?>">Delete</a>
add this in your action
$request = $this->getRequest();
$this->view->assign('url', $request->getBaseURL());
and replace your links in view with this
Add a Task
Edit
Delete

Zend Framework Custom Forms with viewScript

I am having some problems working out how to use custom forms in Zend Framework.
I have followed various guides but none seem to work. Nothing at all gets rendered.
Here is the bits of code that I am trying to use (All code below is in the default module). I have simplified the code to a single input for the test.
applications/forms/One/Nametest.php
class Application_Form_One_Nametest extends Zend_Form {
public function init() {
$this->setMethod('post');
$name = new Zend_Form_Element_Text('name');
$name->setLabel('Box Name')
->setRequired(true)
->addFilter('StripTags')
->addFilter('StringTrim')
->addValidator('NotEmpty');
$submit = new Zend_Form_Element_Submit('submit');
$submit->setLabel('Submit Message');
$submit->setAttrib('id', 'submitbutton');
$submit->setAttrib('class', 'bluebutton');
$this->addElements(array($name, $submit));
}
}
application/views/scripts/one/formlayout.phtml
<form action="<?= $this->escape($this->form->getAction()) ?>" method="<?= $this->escape($this->form->getMethod()) ?>">
<p>
Please provide us the following information so we can know more about
you.
</p>
<? echo $this->element->name ?>
<? echo $this->element->submit ?>
</form>
application/controllers/IndexController.php
public function formtestAction() {
$form = new Application_Form_One_Nametest();
$form->setDecorators(array(array('ViewScript', array('viewScript' => 'one/formlayout.phtml'))));
$this->view->form = $form;
}
application/views/scripts/index/formtest.phtml
<h1>Formtest</h1>
<?
echo $this->form;
?>
The above code does not throw any errors or render any part of formlayout.phtml including the form tags or text between the p tags.
Can anybody tell me what I might be doing wrong?
I think the problem is your form element's decorator. You should set the decorator to ViewHelper and Error only. It works for me at least.
Here is the code I used and it should work
applications/forms/Form.php
class Application_Form_Form extends Zend_Form {
public function loadDefaultDecorators() {
$this->setDecorators(
array(
array(
'ViewScript',
array(
'viewScript' => 'index/formlayout.phtml',
)
)
)
);
}
public function init() {
$this->setAction('/action');
$this->setMethod('post');
$this->addElement('text', 'name', array(
'decorators' => array('ViewHelper', 'Errors')
));
}
}
application/views/scripts/index/formlayout.phtml
<form action="<?php echo $this->element->getAction(); ?>" method="<?php echo $this->element->getMethod(); ?>">
<div>
<label for="name">Box Name</label>
<?php echo $this->element->name; ?>
</div>
<input type="submit" value="Submit Message" id="submitbutton" class="bluebutton">
</form>
application/views/scripts/index/index.phtml
<!-- application/views/scripts/index/index.phtml -->
<?php echo $this -> form; ?>
application/controllers/IndexController.php
public function indexAction() {
$form = new Application_Form_Form();
$this -> view -> form = $form;
}
Here is a very simple example to get you going adapted from this article.
The form:-
class Application_Form_Test extends Zend_Form
{
public function init()
{
$this->setMethod('POST');
$this->setAction('/');
$text = new Zend_Form_Element_Text('testText');
$submit = new Zend_Form_Element_Submit('submit');
$this->setDecorators(
array(
array('ViewScript', array('viewScript' => '_form_test.phtml'))
)
);
$this->addElements(array($text, $submit));
$this->setElementDecorators(array('ViewHelper'));
}
}
The order in which setDecorators(), addElements() and setElementDecorators() are called is very important here.
The view script _form_test.phtml can be called anything you like, but it needs to be in /views/scripts so that it can be found by the renderer.
/views/scripts/_form_test.phtml would look something like this:-
<form id="contact" action="<?php echo $this->element->getAction(); ?>"
method="<?php echo $this->element->getMethod(); ?>">
<p>
Text<br />
<?php echo $this->element->testText; ?>
</p>
<p>
<?php echo $this->element->submit ?>
</p>
</form>
You instantiate the form, pass it to the view and render it as usual. The output from this example looks like this:-
<form id='contact' action='/' method='post'>
<p>
Text<br />
<input type="text" name="testText" id="testText" value=""></p>
<p>
<input type="submit" name="submit" id="submit" value="submit"></p>
</form>
That should be enough to get you started creating your own forms.
Usually, if you don't see anything on the screen it means that some sort of error happened.
Maybe you have errors turned off or something, maybe not. I'm just trying to give you ideas.
The only things I could spot where the following.
In the below code, you have to still specify the form when trying to print out the elements.
<form>
action="<?php $this->escape($this->element->getAction()) ?>"
method="<?php $this->escape($this->element->getMethod()) ?>" >
<p>
Please provide us the following information so we can know more about
you.
</p>
<?php echo $this->element->getElement( 'name' ); ?>
<?php echo $this->element->getElement( 'submit' ) ?>
</form>
As vascowhite's code shows, once you are inside the viewscript, the variable with the form is called element. The viewscript decorator uses a partial to do the rendering and thus it creates its own scope within the viewscript with different variable names.
So, although in your original view it was called $form, in the viewscript you'll have to call it element.
Also, maybe it was copy/paste haste, but you used <? ?> tags instead of <?= ?> or <?php ?> tags. Maybe that caused some error that is beyond parsing and that's why you got no output.