Download it now!
Bug 131596 - Allow MailMerge to get document from XInputStream or already opened XComponent
Summary: Allow MailMerge to get document from XInputStream or already opened XComponent
Status: ASSIGNED
Alias: None
Product: LibreOffice
Classification: Unclassified
Component: sdk (show other bugs)
Version:
(earliest affected)
unspecified
Hardware: All All
: medium enhancement
Assignee: Shubham Jain
URL:
Whiteboard:
Keywords: difficultyMedium, easyHack, skillCpp
Depends on:
Blocks: Mail-Merge
  Show dependency treegraph
 
Reported: 2020-03-26 10:26 UTC by Oleg Shchelykalnov
Modified: 2021-01-16 08:26 UTC (History)
6 users (show)

See Also:
Crash report or crash signature:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Oleg Shchelykalnov 2020-03-26 10:26:50 UTC
I'm trying to use MailMerge to generate multiple PDFs from documents stored in database.

I've tried to avoid storing documents back to file system but it looks I cann't wrap BLOBs a way they can be used directly. I disallowed to use XModel loaded XComponentLoader::loadComponentFromURL from XInputStream and there no way to send InputStream argument for LoadFromURL_impl function in unomailmerge.cxx.

Is it possible to expand API to allow use loaded document?
Comment 1 Mike Kaganski 2020-11-30 15:27:11 UTC
Mail merge is implemented using an implementation of XJob interface [1] (SwXMailMerge). Its "execute" method takes a sequence of NamedValues, which is how you pass parameters there.

Extending SwXMailMerge::execute (and SwXMailMerge::setPropertyValue) in sw/source/uibase/uno/unomailmerge.cxx to accept another name-value pair is required for this request. It should basically do a processing of that new pair alternative to what is currently done for UNO_NAME_DOCUMENT_URL.

[1] https://api.libreoffice.org/docs/idl/ref/interfacecom_1_1sun_1_1star_1_1task_1_1XJob.html
Comment 2 Shubham Jain 2021-01-15 18:55:36 UTC
(In reply to Mike Kaganski from comment #1)
> Mail merge is implemented using an implementation of XJob interface [1]
> (SwXMailMerge). Its "execute" method takes a sequence of NamedValues, which
> is how you pass parameters there.
> 
> Extending SwXMailMerge::execute (and SwXMailMerge::setPropertyValue) in
> sw/source/uibase/uno/unomailmerge.cxx to accept another name-value pair is
> required for this request. It should basically do a processing of that new
> pair alternative to what is currently done for UNO_NAME_DOCUMENT_URL.
> 
> [1]
> https://api.libreoffice.org/docs/idl/ref/
> interfacecom_1_1sun_1_1star_1_1task_1_1XJob.html

Hi Mike,
I have changed the definition of SwXMailMerge::execute in unomailmerge.hxx

from :
virtual css::uno::Any SAL_CALL execute( const css::uno::Sequence< css::beans::NamedValue >& Arguments ) override;

to:
virtual css::uno::Any SAL_CALL execute( const css::uno::Sequence< css::beans::NamedValue >& Arguments1, const css::uno::Sequence< css::beans::NamedValue >& Arguments2 ) override;

Now I didn't understand "It should basically do a processing of that new
> pair alternative to what is currently done for UNO_NAME_DOCUMENT_URL"
Do I need to run 1 more loop in unomailmerge.cxx and get UNO_NAME_DOCUMENT_URL of Argument2 as well and how to process them? Can you please guide me a little bit? Thanks!
Comment 3 Mike Kaganski 2021-01-15 19:36:37 UTC
(In reply to Shubham Jain from comment #2)
> I have changed the definition of SwXMailMerge::execute in unomailmerge.hxx
> 
> from :
> virtual css::uno::Any SAL_CALL execute( const css::uno::Sequence<
> css::beans::NamedValue >& Arguments ) override;
> 
> to:
> virtual css::uno::Any SAL_CALL execute( const css::uno::Sequence<
> css::beans::NamedValue >& Arguments1, const css::uno::Sequence<
> css::beans::NamedValue >& Arguments2 ) override;

Why? That is not needed. In addition to trying to change a virtual method (which is a public API), which is impossible, the main thing is that it is not needed. The old "Arguments" is already itself an arbitrary-length sequence of name-value pairs, so all you need to do is to add one more pair into the sequence when you prepare it for calling SwXMailMerge::execute, and then implement the processing of that pair in the function.
Comment 4 Shubham Jain 2021-01-16 08:02:45 UTC
(In reply to Mike Kaganski from comment #3)
 
> ...The old "Arguments" is already itself an arbitrary-length
> sequence of name-value pairs, so all you need to do is to add one more pair
> into the sequence when you prepare it for calling SwXMailMerge::execute, and
> then implement the processing of that pair in the function.

So I need to add the pair in SwXMailMerge::setPropertyValue function before executing it. I think that something needs to be done in the elif block in line #934:

else if (pData == &m_aDocumentURL)
            {
                OUString aText;
                bOK = rValue >>= aText;
                if (!aText.isEmpty()
                    && !LoadFromURL_impl( m_xModel, m_xDocSh, aText, true ))
                    throw RuntimeException("Failed to create document from URL: " + aText, static_cast < cppu::OWeakObject * > ( this ) );
                m_aDocumentURL = aText;
            }
But I can't figure out what to do here. Can you help?