1

I've created a custom module to show order comments on the invoice which works ok with single invoices. When trying to print invoices via the order grid mass action I get this error:

{"0":"Type Error occurred when creating object: Magento\\Sales\\Controller\\Adminhtml\\Order\\Pdfinvoices\\Interceptor","1":"<pre>#1 Magento\\Framework\\ObjectManager\\Factory\\Compiled->create('Magento\\Sales\\Co...', array()) called at [vendor\/magento\/framework\/ObjectManager\/ObjectManager.php:56]
#2 Magento\\Framework\\ObjectManager\\ObjectManager->create('Magento\\Sales\\Co...') called at [vendor\/magento\/framework\/App\/ActionFactory.php:44]
#3 Magento\\Framework\\App\\ActionFactory->create('Magento\\Sales\\Co...') called at [vendor\/magento\/framework\/App\/Router\/Base.php:304]
#4 Magento\\Framework\\App\\Router\\Base->matchAction(&Magento\\Framework\\App\\Request\\Http#000000004aa3a963000000000d13c128#, array('areaFrontName' => 'adminarea', 'moduleFrontName' => 'sales', 'actionPath' => 'order', 'actionName' => 'pdfinvoices', 'variables' => array('key' => 'a16160358ca3a448...'))) called at [vendor\/magento\/framework\/App\/Router\/Base.php:165]
#5 Magento\\Framework\\App\\Router\\Base->match(&Magento\\Framework\\App\\Request\\Http#000000004aa3a963000000000d13c128#) called at [vendor\/magento\/framework\/App\/FrontController.php:95]
#6 Magento\\Framework\\App\\FrontController->dispatch(&Magento\\Framework\\App\\Request\\Http#000000004aa3a963000000000d13c128#) called at [vendor\/magento\/framework\/Interception\/Interceptor.php:58]
#7 Magento\\Framework\\App\\FrontController\\Interceptor->___callParent('dispatch', array(&Magento\\Framework\\App\\Request\\Http#000000004aa3a963000000000d13c128#)) called at [vendor\/magento\/framework\/Interception\/Interceptor.php:138]
#8 Magento\\Framework\\App\\FrontController\\Interceptor->Magento\\Framework\\Interception\\{closure}(&Magento\\Framework\\App\\Request\\Http#000000004aa3a963000000000d13c128#) called at [vendor\/magento\/framework\/Interception\/Interceptor.php:153]
#9 Magento\\Framework\\App\\FrontController\\Interceptor->___callPlugins('dispatch', array(&Magento\\Framework\\App\\Request\\Http#000000004aa3a963000000000d13c128#), array(array('default_store_se...', 'page_cache_from_...', 'storeCookieValid...', 'install', 'configHash'))) called at [generated\/code\/Magento\/Framework\/App\/FrontController\/Interceptor.php:26]
#10 Magento\\Framework\\App\\FrontController\\Interceptor->dispatch(&Magento\\Framework\\App\\Request\\Http#000000004aa3a963000000000d13c128#) called at [vendor\/magento\/framework\/App\/Http.php:136]
#11 Magento\\Framework\\App\\Http->launch() called at [vendor\/magento\/framework\/App\/Bootstrap.php:258]
#12 Magento\\Framework\\App\\Bootstrap->run(&Magento\\Framework\\App\\Http\\Interceptor#000000004aa3a99c000000000d13c128#) called at [index.php:39]
<\/pre>","url":"\/adminarea\/sales\/order\/pdfinvoices\/key\/a16160358ca3a44836acecccac1531300de1f39f164af578cad46aa2f98aa8d6\/","script_name":"\/index.php"}

Here's my module code: app\code\Denial\InvoiceComments\registration.php

use \Magento\Framework\Component\ComponentRegistrar;
ComponentRegistrar::register(ComponentRegistrar::MODULE, 'Denial_InvoiceComments', __DIR__);

app\code\Denial\InvoiceComments\etc\di.xml

<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
<preference for="Magento\Sales\Model\Order\Pdf\Invoice" type="Denial\InvoiceComments\Model\Rewrite\Order\Pdf\Invoice" />
</config>

app\code\Denial\InvoiceComments\etc\module.xml

<?xml version="1.0"?>

<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:Module/etc/module.xsd">
<module name="Denial_InvoiceComments" setup_version="0.0.1">
    <sequence>
    <module name="Magento_Sales" />
   </sequence>
</module>
</config>

app\code\Denial\InvoiceComments\Model\Rewrite\Order\Pdf\Invoice.php

<?php
/**
 * Copyright © Magento, Inc. All rights reserved.
 * See COPYING.txt for license details.
 */
namespace Denial\InvoiceComments\Model\Rewrite\Order\Pdf;

use Magento\Sales\Model\ResourceModel\Order\Invoice\Collection;
use Magento\Sales\Model\Order\Pdf\AbstractPdf;
use Magento\Sales\Model\Order\Pdf\Config;


class Invoice extends AbstractPdf
{
/**
 * @var \Magento\Store\Model\StoreManagerInterface
 */
protected $_storeManager;

/**
 * @var \Magento\Framework\Locale\ResolverInterface
 */
protected $_localeResolver;

/**
 * @param \Magento\Payment\Helper\Data $paymentData
 * @param \Magento\Framework\Stdlib\StringUtils $string
 * @param \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig
 * @param \Magento\Framework\Filesystem $filesystem
 * @param Config $pdfConfig
 * @param \Magento\Sales\Model\Order\Pdf\Total\Factory $pdfTotalFactory
 * @param \Magento\Sales\Model\Order\Pdf\ItemsFactory $pdfItemsFactory
 * @param \Magento\Framework\Stdlib\DateTime\TimezoneInterface $localeDate
 * @param \Magento\Framework\Translate\Inline\StateInterface $inlineTranslation
 * @param \Magento\Sales\Model\Order\Address\Renderer $addressRenderer
 * @param \Magento\Store\Model\StoreManagerInterface $storeManager
 * @param \Magento\Framework\Locale\ResolverInterface $localeResolver
 * @param array $data
 *
 * @SuppressWarnings(PHPMD.ExcessiveParameterList)
 */
public function __construct(
    \Magento\Payment\Helper\Data $paymentData,
    \Magento\Framework\Stdlib\StringUtils $string,
    \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig,
    \Magento\Framework\Filesystem $filesystem,
    Config $pdfConfig,
    \Magento\Sales\Model\Order\Pdf\Total\Factory $pdfTotalFactory,
    \Magento\Sales\Model\Order\Pdf\ItemsFactory $pdfItemsFactory,
    \Magento\Framework\Stdlib\DateTime\TimezoneInterface $localeDate,
    \Magento\Framework\Translate\Inline\StateInterface $inlineTranslation,
    \Magento\Sales\Model\Order\Address\Renderer $addressRenderer,
    \Magento\Store\Model\StoreManagerInterface $storeManager,
    \Magento\Framework\Locale\ResolverInterface $localeResolver,
    array $data = []
) {
    $this->_storeManager = $storeManager;
    $this->_localeResolver = $localeResolver;
    parent::__construct(
        $paymentData,
        $string,
        $scopeConfig,
        $filesystem,
        $pdfConfig,
        $pdfTotalFactory,
        $pdfItemsFactory,
        $localeDate,
        $inlineTranslation,
        $addressRenderer,
        $data
    );
}


/**
 * Draw header for item table
 *
 * @param \Zend_Pdf_Page $page
 * @return void
 */
protected function _drawHeader(\Zend_Pdf_Page $page)
{
    /* Add table head */
    $this->_setFontRegular($page, 10);
    $page->setFillColor(new \Zend_Pdf_Color_Rgb(0.93, 0.92, 0.92));
    $page->setLineColor(new \Zend_Pdf_Color_GrayScale(0.5));
    $page->setLineWidth(0.5);
    $page->drawRectangle(25, $this->y, 570, $this->y - 15);
    $this->y -= 10;
    $page->setFillColor(new \Zend_Pdf_Color_Rgb(0, 0, 0));

    //columns headers
    $lines[0][] = ['text' => __('Products'), 'feed' => 35];

    $lines[0][] = ['text' => __('SKU'), 'feed' => 290, 'align' => 'right'];

    $lines[0][] = ['text' => __('Qty'), 'feed' => 435, 'align' => 'right'];

    $lines[0][] = ['text' => __('Price'), 'feed' => 375, 'align' => 'right'];

    $lines[0][] = ['text' => __('Tax'), 'feed' => 495, 'align' => 'right'];

    $lines[0][] = ['text' => __('Subtotal'), 'feed' => 565, 'align' => 'right'];

    $lineBlock = ['lines' => $lines, 'height' => 5];

    $this->drawLineBlocks($page, [$lineBlock], ['table_header' => true]);
    $page->setFillColor(new \Zend_Pdf_Color_GrayScale(0));
    $this->y -= 20;
}

/**
 * Return PDF document
 *
 * @param array|Collection $invoices
 * @return \Zend_Pdf
 */
public function getPdf($invoices = [])
{
   $this->_beforeGetPdf();
    $this->_initRenderer('invoice');

    $pdf = new \Zend_Pdf();
    $this->_setPdf($pdf);
    $style = new \Zend_Pdf_Style();
    $this->_setFontBold($style, 10);

    foreach ($invoices as $invoice) {
        if ($invoice->getStoreId()) {
            $this->_localeResolver->emulate($invoice->getStoreId());
            $this->_storeManager->setCurrentStore($invoice->getStoreId());
        }

        $page = $this->newPage();
        $order = $invoice->getOrder();
        /* Add image */
        $this->insertLogo($page, $invoice->getStore());
        /* Add address */
        $this->insertAddress($page, $invoice->getStore());
        /* Add head */
        $this->insertOrder(
            $page,
            $order,
            $this->_scopeConfig->isSetFlag(
                self::XML_PATH_SALES_PDF_INVOICE_PUT_ORDER_ID,
                \Magento\Store\Model\ScopeInterface::SCOPE_STORE,
                $order->getStoreId()
            )
        );
        /* Add document text and number */
        $this->insertDocumentNumber($page, __('Invoice # ') . $invoice->getIncrementId());
        /* Add table */
        $this->_drawHeader($page);
        /* Add body */
        foreach ($invoice->getAllItems() as $item) {
            if ($item->getOrderItem()->getParentItem()) {
                continue;
            }
            /* Draw item */
            $this->_drawItem($item, $page, $order);
            $page = end($pdf->pages);
        }
        /* Add totals */
        $this->insertTotals($page, $invoice);
        if ($invoice->getStoreId()) {
            $this->_localeResolver->revert();
        }

    foreach ($invoice->getOrder()->getStatusHistoryCollection() as $status){
    $textChunk = wordwrap(strip_tags($status->getComment()), 120, "\n");
    foreach(explode("\n", $textChunk) as $textLine){
            if ($textLine!=='') {
                    $page->drawText(strip_tags(ltrim($textLine)), 35, $this->y, 'UTF-8');
                    $this->y -= 15;
            }
    }
    }
    }
    $this->_afterGetPdf();
    return $pdf;
}


/**
 * Create new page and assign to PDF object
 *
 * @param  array $settings
 * @return \Zend_Pdf_Page
 */
public function newPage(array $settings = [])
{
    /* Add new table head */
    $page = $this->_getPdf()->newPage(\Zend_Pdf_Page::SIZE_A4);
    $this->_getPdf()->pages[] = $page;
    $this->y = 800;
    if (!empty($settings['table_header'])) {
        $this->_drawHeader($page);
    }
    return $page;
}

}

app\code\Denial\InvoiceComments\view\adminhtml\layout\sales_order_invoice_view.xml

<?xml version="1.0"?>
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
<body>
    <referenceBlock name="order_comments">
    <action method="setTemplate">
        <argument name="template" xsi:type="string">Denial_InvoiceComments::order/comments/view.phtml</argument>
    </action>
</referenceBlock>
</body>
</page>

app\code\Denial\InvoiceComments\view\adminhtml\templates\order\comments\view.phtml

<?php
/**
 * Copyright © Magento, Inc. All rights reserved.
 * See COPYING.txt for license details.
 */

// @codingStandardsIgnoreFile

?>
<?php if ($_entity = $block->getEntity()): ?>
<div id="comments_block" class="edit-order-comments">
    <div class="order-history-block">
        <div class="admin__field field-row">
            <label class="admin__field-label"
                for="history_comment"><?= /* @escapeNotVerified */ __('Comment Text') ?></label>
            <div class="admin__field-control">
                <textarea name="comment[comment]"
                        class="admin__control-textarea"
                        rows="3"
                        cols="5"
                        id="history_comment"></textarea>
            </div>
        </div>
        <div class="admin__field">
            <div class="order-history-comments-options">
                <?php if ($block->canSendCommentEmail()): ?>
                    <div class="admin__field admin__field-option">
                        <input name="comment[is_customer_notified]"
                            type="checkbox"
                            class="admin__control-checkbox"
                            id="history_notify"
                            value="1" />
                        <label class="admin__field-label"
                            for="history_notify"><?= /* @escapeNotVerified */ __('Notify Customer by Email') ?></label>
                    </div>
                <?php endif; ?>
                <div class="admin__field admin__field-option">
                    <input name="comment[is_visible_on_front]"
                        type="checkbox"
                        id="history_visible"
                        class="admin__control-checkbox"
                        value="1" />
                    <label class="admin__field-label"
                        for="history_visible"> <?= /* @escapeNotVerified */ __('Visible on Storefront') ?></label>
                </div>
            </div>
            <div class="order-history-comments-actions">
                <?= $block->getChildHtml('submit_button') ?>
            </div>
        </div>
    </div>

<h3> Order Comments </h3>
<ul class="note-list">
<?php foreach ($_entity->getOrder()->getStatusHistoryCollection() as $status): ?>
    <?php  if ($status->getComment()): ?>
    <span class="note-list-date"><?= /* @noEscape */ $block->formatDate($status->getCreatedAt(), \IntlDateFormatter::MEDIUM) ?></span>
            <span class="note-list-time"><?= /* @noEscape */ $block->formatTime($status->getCreatedAt(), \IntlDateFormatter::MEDIUM) ?></span>
            <span class="note-list-customer">
                <?= /* @escapeNotVerified */ __('Customer') ?>
                <?php if ($status->getIsCustomerNotified()): ?>
                    <span class="note-list-customer-notified"><?= /* @escapeNotVerified */ __('Notified') ?></span>
                <?php else: ?>
                    <span class="note-list-customer-not-notified"><?= /* @escapeNotVerified */ __('Not Notified') ?></span>
                <?php endif; ?>
            </span>
    <div class="note-list-comment"><?= $block->escapeHtml($status->getComment(), ['b', 'br', 'strong', 'i', 'u', 'a']) ?></div>
    <?php endif; ?>
<?php endforeach; ?>
</ul>
<h3> Invoice Comments </h3>    
<ul class="note-list">
        <?php foreach ($_entity->getCommentsCollection(true) as $_comment): ?>
            <li>
                <span class="note-list-date"><?= /* @noEscape */ $block->formatDate($_comment->getCreatedAt(), \IntlDateFormatter::MEDIUM) ?></span>
                <span class="note-list-time"><?= /* @noEscape */ $block->formatTime($_comment->getCreatedAt(), \IntlDateFormatter::MEDIUM) ?></span>
                <span class="note-list-customer">
                    <?= /* @escapeNotVerified */ __('Customer') ?>
                    <?php if ($_comment->getIsCustomerNotified()): ?>
                        <span class="note-list-customer-notified"><?= /* @escapeNotVerified */ __('Notified') ?></span>
                    <?php else: ?>
                        <span class="note-list-customer-not-notified"><?= /* @escapeNotVerified */ __('Not Notified') ?></span>
                    <?php endif; ?>
                </span>
                <div class="note-list-comment"><?= $block->escapeHtml($_comment->getComment(), ['b', 'br', 'strong', 'i', 'u', 'a']) ?></div>
            </li>
        <?php endforeach; ?>
    </ul>
</div>
<script>
require(['prototype'], function(){

submitComment = function() {
    submitAndReloadArea($('comments_block').parentNode, '<?= /* @escapeNotVerified */ $block->getSubmitUrl() ?>')
}

if ($('submit_comment_button')) {
    $('submit_comment_button').observe('click', submitComment);
}

});
</script>
<?php endif; ?>

What have I missed?

More info from the logs:

[2019-12-05 09:58:31] main.CRITICAL: Type Error occurred when creating object: Magento\Sales\Controller\Adminhtml\Order\Pdfinvoices\Interceptor, Argument 6 passed to Magento\Sales\Controller\Adminhtml\Order\Pdfinvoices\Interceptor::__construct() must be an instance of Magento\Sales\Model\Order\Pdf\Invoice, instance of Denial\InvoiceComments\Model\Rewrite\Order\Pdf\Invoice given, called in /home/sitename/public_html/vendor/magento/framework/ObjectManager/Factory/AbstractFactory.php on line 116 [] []
[2019-12-05 09:58:31] main.ERROR: Type Error occurred when creating object: Magento\Sales\Controller\Adminhtml\Order\Pdfinvoices\Interceptor [] []

How do I change the required instance name?

1
+50

Please replace following code in

Denial\InvoiceComments\Model\Rewrite\Order\Pdf\Invoice.php file

 <?php
    /**
     * Copyright © Magento, Inc. All rights reserved.
     * See COPYING.txt for license details.
     */
    namespace Denial\InvoiceComments\Model\Rewrite\Order\Pdf;

    use Magento\Sales\Model\ResourceModel\Order\Invoice\Collection;
    use Magento\Sales\Model\Order\Pdf\AbstractPdf;
    use Magento\Sales\Model\Order\Pdf\Config;
    use Magento\Sales\Model\Order\Pdf\Invoice as MagentoInvoice;

    class Invoice extends MagentoInvoice
    {

        /**
         * Draw header for item table
         *
         * @param \Zend_Pdf_Page $page
         * @return void
         */
        protected function _drawHeader(\Zend_Pdf_Page $page)
        {
            /* Add table head */
            $this->_setFontRegular($page, 10);
            $page->setFillColor(new \Zend_Pdf_Color_Rgb(0.93, 0.92, 0.92));
            $page->setLineColor(new \Zend_Pdf_Color_GrayScale(0.5));
            $page->setLineWidth(0.5);
            $page->drawRectangle(25, $this->y, 570, $this->y - 15);
            $this->y -= 10;
            $page->setFillColor(new \Zend_Pdf_Color_Rgb(0, 0, 0));

            //columns headers
            $lines[0][] = ['text' => __('Products'), 'feed' => 35];

            $lines[0][] = ['text' => __('SKU'), 'feed' => 290, 'align' => 'right'];

            $lines[0][] = ['text' => __('Qty'), 'feed' => 435, 'align' => 'right'];

            $lines[0][] = ['text' => __('Price'), 'feed' => 375, 'align' => 'right'];

            $lines[0][] = ['text' => __('Tax'), 'feed' => 495, 'align' => 'right'];

            $lines[0][] = ['text' => __('Subtotal'), 'feed' => 565, 'align' => 'right'];

            $lineBlock = ['lines' => $lines, 'height' => 5];

            $this->drawLineBlocks($page, [$lineBlock], ['table_header' => true]);
            $page->setFillColor(new \Zend_Pdf_Color_GrayScale(0));
            $this->y -= 20;
        }

        /**
         * Return PDF document
         *
         * @param array|Collection $invoices
         * @return \Zend_Pdf
         */
        public function getPdf($invoices = [])
        {
            $this->_beforeGetPdf();
            $this->_initRenderer('invoice');

            $pdf = new \Zend_Pdf();
            $this->_setPdf($pdf);
            $style = new \Zend_Pdf_Style();
            $this->_setFontBold($style, 10);

            foreach ($invoices as $invoice) {
                if ($invoice->getStoreId()) {
                    $this->_localeResolver->emulate($invoice->getStoreId());
                    $this->_storeManager->setCurrentStore($invoice->getStoreId());
                }

                $page = $this->newPage();
                $order = $invoice->getOrder();
                /* Add image */
                $this->insertLogo($page, $invoice->getStore());
                /* Add address */
                $this->insertAddress($page, $invoice->getStore());
                /* Add head */
                $this->insertOrder(
                    $page,
                    $order,
                    $this->_scopeConfig->isSetFlag(
                        self::XML_PATH_SALES_PDF_INVOICE_PUT_ORDER_ID,
                        \Magento\Store\Model\ScopeInterface::SCOPE_STORE,
                        $order->getStoreId()
                    )
                );
                /* Add document text and number */
                $this->insertDocumentNumber($page, __('Invoice # ') . $invoice->getIncrementId());
                /* Add table */
                $this->_drawHeader($page);
                /* Add body */
                foreach ($invoice->getAllItems() as $item) {
                    if ($item->getOrderItem()->getParentItem()) {
                        continue;
                    }
                    /* Draw item */
                    $this->_drawItem($item, $page, $order);
                    $page = end($pdf->pages);
                }
                /* Add totals */
                $this->insertTotals($page, $invoice);
                if ($invoice->getStoreId()) {
                    $this->_localeResolver->revert();
                }

                foreach ($invoice->getOrder()->getStatusHistoryCollection() as $status){
                    $textChunk = wordwrap(strip_tags($status->getComment()), 120, "\n");
                    foreach(explode("\n", $textChunk) as $textLine){
                        if ($textLine!=='') {
                            $page->drawText(strip_tags(ltrim($textLine)), 35, $this->y, 'UTF-8');
                            $this->y -= 15;
                        }
                    }
                }
            }
            $this->_afterGetPdf();
            return $pdf;
        }


        /**
         * Create new page and assign to PDF object
         *
         * @param  array $settings
         * @return \Zend_Pdf_Page
         */
        public function newPage(array $settings = [])
        {
            /* Add new table head */
            $page = $this->_getPdf()->newPage(\Zend_Pdf_Page::SIZE_A4);
            $this->_getPdf()->pages[] = $page;
            $this->y = 800;
            if (!empty($settings['table_header'])) {
                $this->_drawHeader($page);
            }
            return $page;
        }
}
0

Here is the problem,
As per log sixth argument of Magento\Sales\Controller\Adminhtml\Order\Pdfinvoices must be type of Magento\Sales\Model\Order\Pdf\Invoice. You have defined preference for Magento\Sales\Model\Order\Pdf\Invoice. So, magetno will use Denial\InvoiceComments\Model\Rewrite\Order\Pdf\Invoice instead of Magento\Sales\Model\Order\Pdf\Invoice.

And here is the solution,
Extend Denial\InvoiceComments\Model\Rewrite\Order\Pdf\Invoice to Magento\Sales\Model\Order\Pdf\Invoice and override necessary code.

class Invoice extends \Magento\Sales\Model\Order\Pdf\Invoice
{
    \\ Your code here
}

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.