Skip to content

Missing Excel Templates in Inventory Journals

I have now solved this at multiple customers, so I think it’s time to write a post about it.

Have you ever wondered why custom Excel templates does not show on inventory journals?

The reason is most likely that your template are using an entity that is based on journal lines (InventJournalTrans), and not journal header (InventJournalTable). The way D365 figures out what templates to show, is to look at the forms primary data source. In these cases, the primary data source is InventJournalTable.

You could rewrite your template to use an entity that matches the forms primary data source. But there is an alternative!

Did you know that the “Open in office” menu is 100% configurable? It is! Microsoft has pretty good documentation about how to interface with it: https://docs.microsoft.com/en-us/dynamics365/fin-ops-core/dev-itpro/office-integration/customize-open-office-menu

The way I fixed this in the counting form was to extend customizeMenuOptions, to include the needed entities.

    public void customizeMenuOptions(OfficeMenuOptions _menuOptions)
    {
        next customizeMenuOptions(_menuOptions);
                
        OfficeMenuDataEntityOptions entityOptions  = OfficeMenuDataEntityOptions::construct(tableStr(InventInventoryCountingJournalLineEntity));
        entityOptions.dataSourceIdInternal(InventJournalTrans_ds.id());
        _menuOptions.dataEntityOptions().addEnd(entityOptions);
    }

The downside to this approach is that the filters D365 sets by default, is way to restrictive. In this case, it sets LineNum as a filter.

Since the form InventJournalCount does not implement the OfficeITemplateCustomExporter interface, I had to set the filters using a event handler. Place it where it suites best following you development best practice (You do follow a best practice, right?)

    [SubscribesTo(classStr(OfficeTemplateExportMenuItem), delegateStr(OfficeTemplateExportMenuItem, getInitialTemplateFilters))]
    public static void OfficeTemplateExportMenuItem_getInitialTemplateFilters(OfficeTemplateExportMenuItem _menuItem, FormRun _formRun, Map _initialFilters)
    {
        if  (_formRun.name() == formStr(InventJournalCount) && _menuItem.dataEntityName() ==  tableStr(InventInventoryCountingJournalLineEntity))
        {
            // Add an initial filter.
            ExportToExcelFilterTreeBuilder bldr = new ExportToExcelFilterTreeBuilder(_menuItem.dataEntityName());
            FormDataSource formDs = _formRun.dataSource(formDataSourceStr(InventJournalCount, InventJournalTable));
            InventJournalTable InventJournalTable = formDs.cursor();
            
            var filter = bldr.and(
                    bldr.areEqual(fieldStr(InventInventoryCountingJournalLineEntity, DataAreaId), curExt()),
                    bldr.areEqual(fieldStr(InventInventoryCountingJournalLineEntity, JournalNumber), InventJournalTable.JournalId));

            _initialFilters.insert(_menuItem.dataEntityName(), filter);
            _menuItem.applyRecordFilter(false);
        }
    }

Leave a Reply

Your email address will not be published. Required fields are marked *