display form data in another view in Zend - zend-framework

I am new in Zend, my problem can be simple for you. I want to make a controller that displays form input data in another view. data are an email text and a text file uploaded. I created the index view and result view.
but i get nothing. when I replace the value of $email with text it works!! I can't find what is going wrong.
The controller also should display a sorted file by firstname
Id,Firstname,Lastname
5,John,Doe
6,Adam,Ant
7,Victor,Hugo
8,Britannie,Spears
this is my controller :
public function indexAction()
{
// initialzing of the customized form
$form = new Application_Form_Upload();
$rq = $this->getRequest();
$isForm = true; // the form has to be shown only if true
if ($rq->isPost()) {
if ($form->isValid($rq->getPost())) {
// show the uploaded data instead of the form
$isForm = false;
$this->view->data = new Application_Model_DataViewer();
$this->view->data->parseFromForm($form);
$result = new Zend_View();
$this->view->result= $result;
$this->render('result');
}
}
if ($isForm) {
$this->view->form = $form;}
}
this is my model :
class Application_Model_DataViewer
{
/**
* #var string Entered e-mail address
*/
private $email;
/**
* #var array Array of extracted data from uploaded file
*/
private $data;
public function __construct(){
$this->email=null;
$this->data=array();
}
/**
* Extracts the data from the form-object and saves it internally
* #param $form Application_Form_Upload
*/
public function parseFromForm($form){
if(!isset($form))return;
if(!isset($form->file)||!$form->file instanceof Zend_Form_Element_File){
throw new Zend_Exception('The field File is empty or has wrong type');
}
// for validation of the IDs
$ival = new Zend_Validate_Int();
// reading the CSV-file (values should be separated by comma, if not - should be extended)
if(($fp = #fopen($form->file->getFileName(), 'r')) !== false){
while(($data = fgetcsv($fp, 500, ',')) !== false){
if(
!is_array($data)
||!$ival->isValid($data[0])
||count($data)<3
)continue;
$this->data[$data[1]] = $data;
}
}else{return;}
#fclose($fp);
ksort($this->data);
$this->email = $form->getValue('email');
}
/**
* #return null|string
*/
public function getEmail(){
return $this->email;
}
/**
* #return array
*/
public function getData(){
return $this->data;
}
}
and here is my index and result views
<?php
// the form should only be rendered if form must be shown
if(isset($this->form)){
$this->form->setAction($this->url());
echo $this->form;
}
?>
result view:
<?php
// if the required data is submitted, it will be checked and displayed
if(isset($this->data)){
?>
<p>Thank you <strong><?php echo $this->escape($this->data->getEmail()); ?></strong>.</p>
<p>The result of the sorting is:
<?php
foreach($this->data->getData() as $row){
echo '<div>', $this->escape($row[0]), ',',
$this->escape($row[1]), ',',
$this->escape($row[2]), '</div>';
}
?></p><?php
}
?>

Use the partial helper in the view.
See: http://framework.zend.com/manual/2.2/en/modules/zend.view.helpers.partial.html
eg. your index.phtml
if ($this->data) {
echo $this->partial("result.phtml", array("data" => $this->data->getData()));
}
you can access the variable in result.phtml by $this->data

Related

ContentEntityForm buildForm method parent out of memory

I have the following issue with my form class that extends the ContentEntityForm class.
When calling the parent buildForm which is needed my system runs out of memory.
/**
* {#inheritdoc}
*/
public function buildForm(array $form, FormStateInterface $form_state) {
$form = parent::buildForm($form, $form_state);
// Here is already runs of memory. $form is never initiated.
/* #var $entity \Drupal\sg_configuration_rule\Entity\ConfigurationRule */
$entity = $this->entity;
$form_state->set('old_cron_value', $entity->get('cron_settings')->first()->value);
$type = FALSE;
if (!$entity->isNew()) {
$type = $entity->getPluginInstance()->getPluginId();
}
if ($entity->isNew()) {
$type = \Drupal::request()->query->get('type');
if (!$type) {
return new RedirectResponse(Url::fromRoute('configuration_rule.add_form_step1')->toString());
}
}
if ($type) {
try {
/** #var \Drupal\sg_base_api\Plugin\BaseApiPluginInterface $enabled_api */
$enabled_api = $this->baseApiPluginManager->createInstance($type);
}
catch (PluginException $exception) {
LoggerService::error($exception->getMessage());
return new RedirectResponse(Url::fromRoute('configuration_rule.add_form_step1')->toString());
}
$enabled_api->configRuleForm($form, $entity);
$form['plugin_type']['widget'][0]['value']['#value'] = $type;
$form['plugin_type']['widget'][0]['value']['#access'] = FALSE;
$form['plugin_type']['widget'][0]['value']['#disabled'] = TRUE;
$form['server_node']['widget']['#options'] = $this->getServerNodesByType($enabled_api->entityType());
}
$form['user_id']['#access'] = FALSE;
return $form;
}
When i check the parent function i noticed that the line:
$form = $this->form($form, $form_state); is causing this in the class EntityForm(Core method).
/**
* {#inheritdoc}
*/
public function buildForm(array $form, FormStateInterface $form_state) {
// During the initial form build, add this form object to the form state and
// allow for initial preparation before form building and processing.
if (!$form_state->has('entity_form_initialized')) {
$this->init($form_state);
}
// Ensure that edit forms have the correct cacheability metadata so they can
// be cached.
if (!$this->entity->isNew()) {
\Drupal::service('renderer')->addCacheableDependency($form, $this->entity);
}
// Retrieve the form array using the possibly updated entity in form state.
// This is causing my memory timeout.
$form = $this->form($form, $form_state);
// Retrieve and add the form actions array.
$actions = $this->actionsElement($form, $form_state);
if (!empty($actions)) {
$form['actions'] = $actions;
}
return $form;
}
If i comment that line out it is working fine but this is needed to save my values in config. Also this is core and should work.
Anyone else have this problem and knows the solutions to this?
Thanks.
This is solved, the error was that too much results where loaded in a select field.

Zend Framework query db and getParam

At the moment I have a page where I have retrieved information on a club by the id of that club. I now have a comments box where I want to retrieve the comments about that club, in the comments table I have the club_id and the parameter "club_id" is passed into this page. At the moment I am retrieving all of the comments from the table but I want just the comments for that club. A point in the right direction would be great!
Controller:
class ClubDescriptionController extends Zend_Controller_Action
{
public $auth = null;
public function init()
{
$this->auth=Zend_Auth::getInstance();
}
http://pastebin.com/m66Sg26x
protected function authoriseUser()
{
if (!$this->auth->hasIdentity()) {
$route = array('controller'=>'auth', 'action'=>'index');
$this->_helper->redirector->gotoRoute($route);
}
}
}
Model:
class Application_Model_DbTable_Comments extends Zend_Db_Table_Abstract
{
protected $_name = 'comments';
public function getComment($id) {
$id = (int) $id;
$row = $this->fetchRow('id = ' . $id);
if (!$row) {
throw new Exception("Count not find row $id");
}
return $row->toArray();
}
public function addComment($comment, $club_id) {
$data = array(
'comment' => $comment,
'club_id' => $club_id,
'comment_date' => new Zend_Db_Expr('NOW()'),
);
$this->insert($data);
}
public function deleteComment($id) {
$this->delete('id =' . (int) $id);
}
}
The view:
<div id="view-comments">
<?php foreach($this->comments as $comments) : ?>
<p id="individual-comment">
<?php echo $this->escape($comments->comment);?> -
<i><?php echo $this->escape($comments->comment_date);?></i>
</p>
<?php endforeach; ?>
</div>
I realise I am going to have to use the getComment(); function in my model and query it by the id but I'm getting confused on exactly how...
Thanks
It's been a while since I used Db_Table but I think you want to create a select object, which allows you to build a query that will select comments with the correct club_id:
$comments = new Application_Model_DbTable_Comments();
$select = $comments->select();
$select->where('club_id = ?', $id);
$this->view->comments = $comments->fetchAll($select);
you may want to order the comments by date, if so, you can do this by adding an order clause to the select:
$select->order('comment_date ASC');
take a look at the docs for Zend_Db_Table_Select, which has quite a few examples: http://framework.zend.com/manual/en/zend.db.table.html#zend.db.table.fetch-all
In your controller you are calling
$this->view->comments = $comments->fetchAll();
it should be
$this->view->comments = $comments->getComment($this->_request->getParam('club_id'));
where id variable will be fetched from url.
Here is the working controller:
public function indexAction() {
//authorisation
$this->authoriseUser();
//to get the paramter club_id to query for specific club information
$id = (int) $this->_request->getParam('club_id', 0);
//submit a comment
$form = new Application_Form_Comment();
$form->submit->setLabel('Comment');
$this->view->form = $form;
if ($this->getRequest()->isPost()) {
$formData = $this->getRequest()->getPost();
if ($form->isValid($formData)) {
$comment = new Application_Model_DbTable_Comments();
$comment->addComment($formData['comment'], $id);
} else {
$form->populate($formData);
}
}
//initialise table
$clubs = new Application_Model_DbTable_Clubs();
$clubs = $clubs->getClub($id);
$this->view->clubs = $clubs;
//to get the comments for the club
$comments = new Application_Model_DbTable_Comments();
$select = $comments->select();
$select->where('club_id = ?', $id);
$select->order('comment_date ASC');
$this->view->comments = $comments->fetchAll($select);
}

Zend_Form action and method

Zend_Form action and method shows by default <form action="" method="post">
... My wish is not like that... Just be written <form> .. Is that possible ??
How can I do ???
well you can simply do the following but there really is no reason to to this!
why would you want en empty form tag?
add this to your config to let the framework "know" your new helper
resources.view.helperPath.My_View_Helper = "My/View/Helper"
then in the file library/My/View/Helper.php create the class
class My_View_Helper_Form extends Zend_View_Helper_Form
{
/**
* Render HTML form without any attributes on the form-tag
*
* #param string $name Form name
* #param null|array $attribs HTML form attributes
* #param false|string $content Form content
* #return string
*/
public function form($name, $attribs = null, $content = false)
{
$info = $this->_getInfo($name, $content, $attribs);
extract($info);
if (!empty($id)) {
$id = ' id="' . $this->view->escape($id) . '"';
} else {
$id = '';
}
if (array_key_exists('id', $attribs) && empty($attribs['id'])) {
unset($attribs['id']);
}
$xhtml = '<form>';
if (false !== $content) {
$xhtml .= $content
. '</form>';
}
return $xhtml;
}
}
it will automatically be used when you have configured your view resource properly

Zend Framework: What shld i use to automatically render out messages if any from FlashMessenger

i wonder if many of my pages may use a FlashMessenger, whats the best way to automatically render out all messages say at the top of the page (like those here in SO, telling the user they got a badge etc)
I have this view helper:
<?php
class Zf_View_Helper_FlashMessenger extends Zend_View_Helper_Abstract
{
/**
* #var Zend_Controller_Action_Helper_FlashMessenger
*/
private $_flashMessenger = null;
/**
* Display Flash Messages.
*
* #param  string $key Message level for string messages
* #param  string $template Format string for message output
* #return string Flash messages formatted for output
*/
public function flashMessenger($key = 'success',
$template='<div id="flash-message" style="display:none"><p class="%s">%s</p></div>')
{
$flashMessenger = $this->_getFlashMessenger();
//get messages from previous requests
$messages = $flashMessenger->getMessages();
//add any messages from this request
if ($flashMessenger->hasCurrentMessages()) {
$messages = array_merge(
$messages,
$flashMessenger->getCurrentMessages()
);
//we don't need to display them twice.
$flashMessenger->clearCurrentMessages();
}
//initialise return string
$output ='';
//process messages
foreach ($messages as $message)
{
if (is_array($message)) {
list($key,$message) = each($message);
}
$output .= sprintf($template,$key,$message);
}
return $output;
}
/**
* Lazily fetches FlashMessenger Instance.
*
* #return Zend_Controller_Action_Helper_FlashMessenger
*/
public function _getFlashMessenger()
{
if (null === $this->_flashMessenger) {
$this->_flashMessenger =
Zend_Controller_Action_HelperBroker::getStaticHelper(
'FlashMessenger');
}
return $this->_flashMessenger;
}
}
In my controller I have this:
if($form->isValid($formData))
{
$Model = $this->getModel();
$id = $Model->add($formData);
$this->_helper->flashMessenger('The category has been inserted.');
$this->_helper->redirector('list');
}
So, in my view I just echo the helper:
<?php echo $this->flashMessenger(); ?>
You could use a preDispatch-Plugin to inject the content of the FlashMessenger into your view and output it in your layout template.

Attach an array with $this->form

I have an array in a log.phtml, ie:
<?php
//application/logmessage/log.phtml//
require_once 'Zend/Log.php';
require_once 'Zend/Log/Writer/Stream.php';
class Logger {
/**
* Array variable store full file back trace information.
*
* #access protected
*/
protected $backTrace = array();
/**
* Array variable store full message information.
*
* #access protected
*/
protected $messageInfo = array();
/**
* Constructor: loads the debug and error logs.
*
*/
public function __construct( $type, $msg ) {
$mock = new Zend_Log_Writer_Mock;
$logger = new Zend_Log( $mock );
$logger->$type( $msg );
// Get full message information.
array_push( $this->messageInfo, $mock->events[0] );
// Get full information of file, from where the message come.
array_push( $this->backTrace, debug_backtrace() );
// Set all required informationn in their respective variables.
$messageText = $this->messageInfo[0]["message"];
$priority = $this->messageInfo[0]["priorityName"];
$backTraceFile = $this->backTrace[0][0]["file"];
$backTraceLine = $this->backTrace[0][0]["line"];
$logArray = array( "Message" => $messageText, "Priority" => $priority,
"Line" => $backTraceLine, "File" => $backTraceFile );
}
}
?>
Now i want to display the $logArray array along with form, my form file is like:
<?php
//application/views/scripts/miscellaneous/index.phtml//
//require_once('../application/logmessage/log.phtml');
echo $this->form;
?>
How could i display Log array with form ....?
How could i return $logArray() from " application/logmessage/log.phtml " to
" application/views/scripts/miscellaneous/index.phtml "
add this code in your Logger:
public $logArray;
also change last line with
$this->logArray = array( "Message" => $messageText, "Priority" => $priority,
"Line" => $backTraceLine, "File" => $backTraceFile );
}
now you can access to $logArray from view, controller, form, etc. for example we call Logger in controller and send it to view
/** Controller **/
$logger = new Logger($msg, $type);
$this->view->logArray = $loagger->logArray;
/** View **/
print_r($this->logArray);
dont forget to replace print_r with your custom helper to create a beautiful user interface
echo $this->myCustomHelper($this->logArray);
I visit http://framework.zend.com/manual/en/zend.registry.html and the only thing that I added is:
<?php
//application/logmessage/log.phtml//
require_once 'Zend/Log.php';
require_once 'Zend/Log/Writer/Stream.php';
class Logger {
/**
* Array variable store full file back trace information.
*
* #access protected
*/
protected $backTrace = array();
/**
* Array variable store full message information.
*
* #access protected
*/
protected $messageInfo = array();
/**
* Constructor: loads the debug and error logs.
*
*/
public function __construct( $type, $msg ) {
$mock = new Zend_Log_Writer_Mock;
$logger = new Zend_Log( $mock );
$logger->$type( $msg );
//var_dump($mock->events[0]);
// Get full message information.
array_push( $this->messageInfo, $mock->events[0] );
// Get full information of file, from where the message come.
array_push( $this->backTrace, debug_backtrace() );
// Set all required informationn in their respective variables.
$messageText = $this->messageInfo[0]["message"];
$priority = $this->messageInfo[0]["priorityName"];
$backTracePath = $this->backTrace[0][0]["file"];
$backTraceLine = $this->backTrace[0][0]["line"];
$logArray = array( "Message" => $messageText, "Priority" => $priority,
"Line" => $backTraceLine, "Path" => $backTracePath );
// Pass the array for display.
Zend_Registry::set('logArray', $logArray);
}
}
?>
and a little code in
<?php
//application/views/scripts/miscellaneous/index.phtml//
echo $this->form;
$logArray = Zend_Registry::get('logArray');
print_r($logArray);
?>
It works excellently.