163bba73cSAndrew Rist /**************************************************************
2cdf0e10cSrcweir *
363bba73cSAndrew Rist * Licensed to the Apache Software Foundation (ASF) under one
463bba73cSAndrew Rist * or more contributor license agreements. See the NOTICE file
563bba73cSAndrew Rist * distributed with this work for additional information
663bba73cSAndrew Rist * regarding copyright ownership. The ASF licenses this file
763bba73cSAndrew Rist * to you under the Apache License, Version 2.0 (the
863bba73cSAndrew Rist * "License"); you may not use this file except in compliance
963bba73cSAndrew Rist * with the License. You may obtain a copy of the License at
1063bba73cSAndrew Rist *
1163bba73cSAndrew Rist * http://www.apache.org/licenses/LICENSE-2.0
1263bba73cSAndrew Rist *
1363bba73cSAndrew Rist * Unless required by applicable law or agreed to in writing,
1463bba73cSAndrew Rist * software distributed under the License is distributed on an
1563bba73cSAndrew Rist * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
1663bba73cSAndrew Rist * KIND, either express or implied. See the License for the
1763bba73cSAndrew Rist * specific language governing permissions and limitations
1863bba73cSAndrew Rist * under the License.
1963bba73cSAndrew Rist *
2063bba73cSAndrew Rist *************************************************************/
2163bba73cSAndrew Rist
2263bba73cSAndrew Rist
23cdf0e10cSrcweir
24cdf0e10cSrcweir #include "precompiled_xmloff.hxx"
25cdf0e10cSrcweir
26cdf0e10cSrcweir #include "RDFaImportHelper.hxx"
27cdf0e10cSrcweir
28cdf0e10cSrcweir #include <xmloff/xmlimp.hxx>
29cdf0e10cSrcweir #include <xmloff/nmspmap.hxx>
30cdf0e10cSrcweir
31cdf0e10cSrcweir #include <comphelper/sequenceasvector.hxx>
32cdf0e10cSrcweir
33cdf0e10cSrcweir #include <tools/string.hxx> // for GetAbsoluteReference
34cdf0e10cSrcweir
35cdf0e10cSrcweir #include <com/sun/star/rdf/URI.hpp>
36cdf0e10cSrcweir #include <com/sun/star/rdf/XDocumentMetadataAccess.hpp>
37cdf0e10cSrcweir #include <com/sun/star/rdf/XDocumentRepository.hpp>
38cdf0e10cSrcweir
39cdf0e10cSrcweir #include <rtl/ustring.hxx>
40cdf0e10cSrcweir
41cdf0e10cSrcweir #include <boost/bind.hpp>
42cdf0e10cSrcweir #include <boost/iterator_adaptors.hpp>
43cdf0e10cSrcweir #ifndef BOOST_ITERATOR_ADAPTOR_DWA053000_HPP_ // from iterator_adaptors.hpp
44cdf0e10cSrcweir // N.B.: the check for the header guard _of a specific version of boost_
45cdf0e10cSrcweir // is here so this may work on different versions of boost,
46cdf0e10cSrcweir // which sadly put the goods in different header files
47cdf0e10cSrcweir #include <boost/iterator/transform_iterator.hpp>
48cdf0e10cSrcweir #endif
49cdf0e10cSrcweir
50cdf0e10cSrcweir #include <map>
51cdf0e10cSrcweir #include <iterator>
52cdf0e10cSrcweir #include <functional>
53cdf0e10cSrcweir #include <algorithm>
54cdf0e10cSrcweir
55cdf0e10cSrcweir
56cdf0e10cSrcweir using namespace ::com::sun::star;
57cdf0e10cSrcweir
58cdf0e10cSrcweir namespace xmloff {
59cdf0e10cSrcweir
60cdf0e10cSrcweir /** a bit of context for parsing RDFa attributes */
61cdf0e10cSrcweir class SAL_DLLPRIVATE RDFaReader
62cdf0e10cSrcweir {
63cdf0e10cSrcweir const SvXMLImport & m_rImport;
64cdf0e10cSrcweir
GetImport() const65cdf0e10cSrcweir const SvXMLImport & GetImport() const { return m_rImport; }
66cdf0e10cSrcweir
67cdf0e10cSrcweir //FIXME: this is an ugly hack to workaround buggy SvXMLImport::GetAbsolute
GetAbsoluteReference(::rtl::OUString const & i_rURI) const68cdf0e10cSrcweir ::rtl::OUString GetAbsoluteReference(::rtl::OUString const & i_rURI) const
69cdf0e10cSrcweir {
70cdf0e10cSrcweir if (!i_rURI.getLength() || i_rURI[0] == '#')
71cdf0e10cSrcweir {
72cdf0e10cSrcweir return GetImport().GetBaseURL() + i_rURI;
73cdf0e10cSrcweir }
74cdf0e10cSrcweir else
75cdf0e10cSrcweir {
76cdf0e10cSrcweir return GetImport().GetAbsoluteReference(i_rURI);
77cdf0e10cSrcweir }
78cdf0e10cSrcweir }
79cdf0e10cSrcweir
80cdf0e10cSrcweir public:
RDFaReader(SvXMLImport const & i_rImport)81cdf0e10cSrcweir RDFaReader(SvXMLImport const & i_rImport)
82cdf0e10cSrcweir : m_rImport(i_rImport)
83cdf0e10cSrcweir { }
84cdf0e10cSrcweir
85cdf0e10cSrcweir // returns URI or blank node!
86cdf0e10cSrcweir ::rtl::OUString ReadCURIE(::rtl::OUString const & i_rCURIE) const;
87cdf0e10cSrcweir
88cdf0e10cSrcweir std::vector< ::rtl::OUString >
89cdf0e10cSrcweir ReadCURIEs(::rtl::OUString const & i_rCURIEs) const;
90cdf0e10cSrcweir
91cdf0e10cSrcweir ::rtl::OUString
92cdf0e10cSrcweir ReadURIOrSafeCURIE( ::rtl::OUString const & i_rURIOrSafeCURIE) const;
93cdf0e10cSrcweir };
94cdf0e10cSrcweir
95cdf0e10cSrcweir /** helper to insert RDFa statements into the RDF repository */
96cdf0e10cSrcweir class SAL_DLLPRIVATE RDFaInserter
97cdf0e10cSrcweir {
98cdf0e10cSrcweir const uno::Reference<uno::XComponentContext> m_xContext;
99cdf0e10cSrcweir uno::Reference< rdf::XDocumentRepository > m_xRepository;
100cdf0e10cSrcweir
101cdf0e10cSrcweir typedef ::std::map< ::rtl::OUString, uno::Reference< rdf::XBlankNode > >
102cdf0e10cSrcweir BlankNodeMap_t;
103cdf0e10cSrcweir
104cdf0e10cSrcweir BlankNodeMap_t m_BlankNodeMap;
105cdf0e10cSrcweir
106cdf0e10cSrcweir public:
RDFaInserter(uno::Reference<uno::XComponentContext> const & i_xContext,uno::Reference<rdf::XDocumentRepository> const & i_xRepository)107cdf0e10cSrcweir RDFaInserter(uno::Reference<uno::XComponentContext> const & i_xContext,
108cdf0e10cSrcweir uno::Reference< rdf::XDocumentRepository > const & i_xRepository)
109cdf0e10cSrcweir : m_xContext(i_xContext)
110cdf0e10cSrcweir , m_xRepository(i_xRepository)
111cdf0e10cSrcweir {}
112cdf0e10cSrcweir
113cdf0e10cSrcweir uno::Reference< rdf::XBlankNode >
114cdf0e10cSrcweir LookupBlankNode(::rtl::OUString const & i_rNodeId );
115cdf0e10cSrcweir
116cdf0e10cSrcweir uno::Reference< rdf::XURI >
117cdf0e10cSrcweir MakeURI( ::rtl::OUString const & i_rURI) const;
118cdf0e10cSrcweir
119cdf0e10cSrcweir uno::Reference< rdf::XResource>
120cdf0e10cSrcweir MakeResource( ::rtl::OUString const & i_rResource);
121cdf0e10cSrcweir
122cdf0e10cSrcweir void InsertRDFaEntry(struct RDFaEntry const & i_rEntry);
123cdf0e10cSrcweir };
124cdf0e10cSrcweir
125cdf0e10cSrcweir /** store parsed RDFa attributes */
126cdf0e10cSrcweir struct SAL_DLLPRIVATE ParsedRDFaAttributes
127cdf0e10cSrcweir {
128cdf0e10cSrcweir ::rtl::OUString m_About;
129cdf0e10cSrcweir ::std::vector< ::rtl::OUString > m_Properties;
130cdf0e10cSrcweir ::rtl::OUString m_Content;
131cdf0e10cSrcweir ::rtl::OUString m_Datatype;
132cdf0e10cSrcweir
ParsedRDFaAttributesxmloff::ParsedRDFaAttributes133cdf0e10cSrcweir ParsedRDFaAttributes(
134cdf0e10cSrcweir ::rtl::OUString const & i_rAbout,
135cdf0e10cSrcweir ::std::vector< ::rtl::OUString > const & i_rProperties,
136cdf0e10cSrcweir ::rtl::OUString const & i_rContent,
137cdf0e10cSrcweir ::rtl::OUString const & i_rDatatype)
138cdf0e10cSrcweir : m_About(i_rAbout)
139cdf0e10cSrcweir , m_Properties(i_rProperties)
140cdf0e10cSrcweir , m_Content(i_rContent)
141cdf0e10cSrcweir , m_Datatype(i_rDatatype)
142cdf0e10cSrcweir { }
143cdf0e10cSrcweir };
144cdf0e10cSrcweir
145cdf0e10cSrcweir /** store metadatable object and its RDFa attributes */
146cdf0e10cSrcweir struct SAL_DLLPRIVATE RDFaEntry
147cdf0e10cSrcweir {
148cdf0e10cSrcweir uno::Reference<rdf::XMetadatable> m_xObject;
149cdf0e10cSrcweir ::boost::shared_ptr<ParsedRDFaAttributes> m_pRDFaAttributes;
150cdf0e10cSrcweir
RDFaEntryxmloff::RDFaEntry151cdf0e10cSrcweir RDFaEntry(uno::Reference<rdf::XMetadatable> const & i_xObject,
152cdf0e10cSrcweir ::boost::shared_ptr<ParsedRDFaAttributes> const& i_pRDFaAttributes)
153cdf0e10cSrcweir : m_xObject(i_xObject)
154cdf0e10cSrcweir , m_pRDFaAttributes(i_pRDFaAttributes)
155cdf0e10cSrcweir { }
156cdf0e10cSrcweir };
157cdf0e10cSrcweir
158cdf0e10cSrcweir ////////////////////////////////////////////////////////////////////////////
159cdf0e10cSrcweir
160cdf0e10cSrcweir
isWS(const sal_Unicode i_Char)161cdf0e10cSrcweir static inline bool isWS(const sal_Unicode i_Char)
162cdf0e10cSrcweir {
163cdf0e10cSrcweir return ('\t' == i_Char) || ('\n' == i_Char) || ('\r' == i_Char)
164cdf0e10cSrcweir || (' ' == i_Char);
165cdf0e10cSrcweir }
166cdf0e10cSrcweir
splitAtWS(::rtl::OUString & io_rString)167cdf0e10cSrcweir static ::rtl::OUString splitAtWS(::rtl::OUString & io_rString)
168cdf0e10cSrcweir {
169cdf0e10cSrcweir const sal_Int32 len( io_rString.getLength() );
170cdf0e10cSrcweir sal_Int32 idxstt(0);
171cdf0e10cSrcweir while ((idxstt < len) && ( isWS(io_rString[idxstt])))
172cdf0e10cSrcweir ++idxstt; // skip leading ws
173cdf0e10cSrcweir sal_Int32 idxend(idxstt);
174cdf0e10cSrcweir while ((idxend < len) && (!isWS(io_rString[idxend])))
175cdf0e10cSrcweir ++idxend; // the CURIE
176cdf0e10cSrcweir const ::rtl::OUString ret(io_rString.copy(idxstt, idxend - idxstt));
177cdf0e10cSrcweir io_rString = io_rString.copy(idxend); // rest
178cdf0e10cSrcweir return ret;
179cdf0e10cSrcweir }
180cdf0e10cSrcweir
181cdf0e10cSrcweir ::rtl::OUString
ReadCURIE(::rtl::OUString const & i_rCURIE) const182cdf0e10cSrcweir RDFaReader::ReadCURIE(::rtl::OUString const & i_rCURIE) const
183cdf0e10cSrcweir {
184cdf0e10cSrcweir // the RDFa spec says that a prefix is required (it may be empty: ":foo")
185cdf0e10cSrcweir const sal_Int32 idx( i_rCURIE.indexOf(':') );
186cdf0e10cSrcweir if (idx >= 0)
187cdf0e10cSrcweir {
188cdf0e10cSrcweir ::rtl::OUString Prefix;
189cdf0e10cSrcweir ::rtl::OUString LocalName;
190cdf0e10cSrcweir ::rtl::OUString Namespace;
191cdf0e10cSrcweir sal_uInt16 nKey( GetImport().GetNamespaceMap()._GetKeyByAttrName(
192cdf0e10cSrcweir i_rCURIE, &Prefix, &LocalName, &Namespace) );
193cdf0e10cSrcweir if (Prefix.equalsAscii("_"))
194cdf0e10cSrcweir {
195cdf0e10cSrcweir // eeek, it's a bnode!
196cdf0e10cSrcweir // "_" is not a valid URI scheme => we can identify bnodes
197cdf0e10cSrcweir return i_rCURIE;
198cdf0e10cSrcweir }
199cdf0e10cSrcweir else
200cdf0e10cSrcweir {
201cdf0e10cSrcweir OSL_ENSURE(XML_NAMESPACE_NONE != nKey, "no namespace?");
202cdf0e10cSrcweir if ((XML_NAMESPACE_UNKNOWN != nKey) &&
203cdf0e10cSrcweir (XML_NAMESPACE_XMLNS != nKey))
204cdf0e10cSrcweir {
205cdf0e10cSrcweir // N.B.: empty LocalName is valid!
206cdf0e10cSrcweir const ::rtl::OUString URI(Namespace + LocalName);
207cdf0e10cSrcweir // return GetImport().GetAbsoluteReference(URI);
208cdf0e10cSrcweir return GetAbsoluteReference(URI);
209cdf0e10cSrcweir }
210cdf0e10cSrcweir else
211cdf0e10cSrcweir {
212cdf0e10cSrcweir OSL_TRACE( "ReadCURIE: invalid CURIE: invalid prefix" );
213cdf0e10cSrcweir }
214cdf0e10cSrcweir }
215cdf0e10cSrcweir }
216cdf0e10cSrcweir else
217cdf0e10cSrcweir {
218cdf0e10cSrcweir OSL_TRACE( "ReadCURIE: invalid CURIE: no prefix" );
219cdf0e10cSrcweir }
220*5086b727SPavel Janík
221*5086b727SPavel Janík return ::rtl::OUString();
222cdf0e10cSrcweir }
223cdf0e10cSrcweir
224cdf0e10cSrcweir ::std::vector< ::rtl::OUString >
ReadCURIEs(::rtl::OUString const & i_rCURIEs) const225cdf0e10cSrcweir RDFaReader::ReadCURIEs(::rtl::OUString const & i_rCURIEs) const
226cdf0e10cSrcweir {
227cdf0e10cSrcweir std::vector< ::rtl::OUString > vec;
228cdf0e10cSrcweir ::rtl::OUString CURIEs(i_rCURIEs);
229cdf0e10cSrcweir do {
230cdf0e10cSrcweir ::rtl::OUString curie( splitAtWS(CURIEs) );
231cdf0e10cSrcweir if (curie.getLength())
232cdf0e10cSrcweir {
233cdf0e10cSrcweir const ::rtl::OUString uri(ReadCURIE(curie));
234cdf0e10cSrcweir if (uri.getLength())
235cdf0e10cSrcweir {
236cdf0e10cSrcweir vec.push_back(uri);
237cdf0e10cSrcweir }
238cdf0e10cSrcweir }
239cdf0e10cSrcweir }
240cdf0e10cSrcweir while (CURIEs.getLength());
241cdf0e10cSrcweir if (!vec.size())
242cdf0e10cSrcweir {
243cdf0e10cSrcweir OSL_TRACE( "ReadCURIEs: invalid CURIEs" );
244cdf0e10cSrcweir }
245cdf0e10cSrcweir return vec;
246cdf0e10cSrcweir }
247cdf0e10cSrcweir
248cdf0e10cSrcweir ::rtl::OUString
ReadURIOrSafeCURIE(::rtl::OUString const & i_rURIOrSafeCURIE) const249cdf0e10cSrcweir RDFaReader::ReadURIOrSafeCURIE(::rtl::OUString const & i_rURIOrSafeCURIE) const
250cdf0e10cSrcweir {
251cdf0e10cSrcweir const sal_Int32 len(i_rURIOrSafeCURIE.getLength());
252cdf0e10cSrcweir if (len && (i_rURIOrSafeCURIE[0] == '['))
253cdf0e10cSrcweir {
254cdf0e10cSrcweir if ((len >= 2) && (i_rURIOrSafeCURIE[len - 1] == ']'))
255cdf0e10cSrcweir {
256cdf0e10cSrcweir return ReadCURIE(i_rURIOrSafeCURIE.copy(1, len - 2));
257cdf0e10cSrcweir }
258cdf0e10cSrcweir else
259cdf0e10cSrcweir {
260cdf0e10cSrcweir OSL_TRACE( "ReadURIOrSafeCURIE: invalid SafeCURIE" );
261cdf0e10cSrcweir return ::rtl::OUString();
262cdf0e10cSrcweir }
263cdf0e10cSrcweir }
264cdf0e10cSrcweir else
265cdf0e10cSrcweir {
266cdf0e10cSrcweir if (i_rURIOrSafeCURIE.matchAsciiL("_:", 2)) // blank node
267cdf0e10cSrcweir {
268cdf0e10cSrcweir OSL_TRACE( "ReadURIOrSafeCURIE: invalid URI: scheme is _" );
269cdf0e10cSrcweir return ::rtl::OUString();
270cdf0e10cSrcweir }
271cdf0e10cSrcweir else
272cdf0e10cSrcweir {
273cdf0e10cSrcweir // return GetImport().GetAbsoluteReference(i_rURIOrSafeCURIE);
274cdf0e10cSrcweir return GetAbsoluteReference(i_rURIOrSafeCURIE);
275cdf0e10cSrcweir }
276cdf0e10cSrcweir }
277cdf0e10cSrcweir }
278cdf0e10cSrcweir
279cdf0e10cSrcweir ////////////////////////////////////////////////////////////////////////////
280cdf0e10cSrcweir
281cdf0e10cSrcweir uno::Reference< rdf::XBlankNode >
LookupBlankNode(::rtl::OUString const & i_rNodeId)282cdf0e10cSrcweir RDFaInserter::LookupBlankNode(::rtl::OUString const & i_rNodeId )
283cdf0e10cSrcweir {
284cdf0e10cSrcweir uno::Reference< rdf::XBlankNode > & rEntry( m_BlankNodeMap[ i_rNodeId ] );
285cdf0e10cSrcweir if (!rEntry.is())
286cdf0e10cSrcweir {
287cdf0e10cSrcweir rEntry = m_xRepository->createBlankNode();
288cdf0e10cSrcweir }
289cdf0e10cSrcweir return rEntry;
290cdf0e10cSrcweir }
291cdf0e10cSrcweir
292cdf0e10cSrcweir uno::Reference< rdf::XURI >
MakeURI(::rtl::OUString const & i_rURI) const293cdf0e10cSrcweir RDFaInserter::MakeURI( ::rtl::OUString const & i_rURI) const
294cdf0e10cSrcweir {
295cdf0e10cSrcweir if (i_rURI.matchAsciiL("_:", 2)) // blank node
296cdf0e10cSrcweir {
297cdf0e10cSrcweir OSL_TRACE("MakeURI: cannot create URI for blank node");
298cdf0e10cSrcweir return 0;
299cdf0e10cSrcweir }
300cdf0e10cSrcweir else
301cdf0e10cSrcweir {
302cdf0e10cSrcweir try
303cdf0e10cSrcweir {
304cdf0e10cSrcweir return rdf::URI::create( m_xContext, i_rURI );
305cdf0e10cSrcweir }
306cdf0e10cSrcweir catch (uno::Exception &)
307cdf0e10cSrcweir {
308cdf0e10cSrcweir OSL_ENSURE(false, "MakeURI: cannot create URI");
309cdf0e10cSrcweir return 0;
310cdf0e10cSrcweir }
311cdf0e10cSrcweir }
312cdf0e10cSrcweir }
313cdf0e10cSrcweir
314cdf0e10cSrcweir uno::Reference< rdf::XResource>
MakeResource(::rtl::OUString const & i_rResource)315cdf0e10cSrcweir RDFaInserter::MakeResource( ::rtl::OUString const & i_rResource)
316cdf0e10cSrcweir {
317cdf0e10cSrcweir if (i_rResource.matchAsciiL("_:", 2)) // blank node
318cdf0e10cSrcweir {
319cdf0e10cSrcweir // we cannot use the blank node label as-is: it must be distinct
320cdf0e10cSrcweir // from labels in other graphs, so create fresh ones per XML stream
321cdf0e10cSrcweir // N.B.: content.xml and styles.xml are distinct graphs
322cdf0e10cSrcweir ::rtl::OUString name( i_rResource.copy(2) );
323cdf0e10cSrcweir const uno::Reference< rdf::XBlankNode > xBNode( LookupBlankNode(name) );
324cdf0e10cSrcweir OSL_ENSURE(xBNode.is(), "no blank node?");
325cdf0e10cSrcweir return uno::Reference<rdf::XResource>( xBNode, uno::UNO_QUERY);
326cdf0e10cSrcweir }
327cdf0e10cSrcweir else
328cdf0e10cSrcweir {
329cdf0e10cSrcweir return uno::Reference<rdf::XResource>( MakeURI( i_rResource ),
330cdf0e10cSrcweir uno::UNO_QUERY);
331cdf0e10cSrcweir }
332cdf0e10cSrcweir }
333cdf0e10cSrcweir
334cdf0e10cSrcweir /** i wrote this because c++ implementations cannot agree on which variant
335cdf0e10cSrcweir of boost::bind and std::mem_fun_ref applied to Reference::is compiles */
336cdf0e10cSrcweir class ref_is_null :
337cdf0e10cSrcweir public ::std::unary_function<sal_Bool, const uno::Reference<rdf::XURI> & >
338cdf0e10cSrcweir {
339cdf0e10cSrcweir public:
operator ()(const uno::Reference<rdf::XURI> & i_rRef)340cdf0e10cSrcweir sal_Bool operator() (const uno::Reference<rdf::XURI> & i_rRef)
341cdf0e10cSrcweir {
342cdf0e10cSrcweir return !i_rRef.is();
343cdf0e10cSrcweir }
344cdf0e10cSrcweir };
345cdf0e10cSrcweir
InsertRDFaEntry(struct RDFaEntry const & i_rEntry)346cdf0e10cSrcweir void RDFaInserter::InsertRDFaEntry(
347cdf0e10cSrcweir struct RDFaEntry const & i_rEntry)
348cdf0e10cSrcweir {
349cdf0e10cSrcweir OSL_ENSURE(i_rEntry.m_xObject.is(),
350cdf0e10cSrcweir "InsertRDFaEntry: invalid arg: null object");
351cdf0e10cSrcweir if (!i_rEntry.m_xObject.is()) return;
352cdf0e10cSrcweir
353cdf0e10cSrcweir const uno::Reference< rdf::XResource > xSubject(
354cdf0e10cSrcweir MakeResource( i_rEntry.m_pRDFaAttributes->m_About ) );
355cdf0e10cSrcweir if (!xSubject.is())
356cdf0e10cSrcweir {
357cdf0e10cSrcweir return; // invalid
358cdf0e10cSrcweir }
359cdf0e10cSrcweir
360cdf0e10cSrcweir ::comphelper::SequenceAsVector< uno::Reference< rdf::XURI > > predicates;
361cdf0e10cSrcweir
362cdf0e10cSrcweir predicates.reserve(i_rEntry.m_pRDFaAttributes->m_Properties.size());
363cdf0e10cSrcweir
364cdf0e10cSrcweir ::std::remove_copy_if(
365cdf0e10cSrcweir ::boost::make_transform_iterator(
366cdf0e10cSrcweir i_rEntry.m_pRDFaAttributes->m_Properties.begin(),
367cdf0e10cSrcweir ::boost::bind(&RDFaInserter::MakeURI, this, _1)),
368cdf0e10cSrcweir // argh, this must be the same type :(
369cdf0e10cSrcweir ::boost::make_transform_iterator(
370cdf0e10cSrcweir i_rEntry.m_pRDFaAttributes->m_Properties.end(),
371cdf0e10cSrcweir ::boost::bind(&RDFaInserter::MakeURI, this, _1)),
372cdf0e10cSrcweir ::std::back_inserter(predicates),
373cdf0e10cSrcweir ref_is_null() );
374cdf0e10cSrcweir // compiles only on wntmsci12
375cdf0e10cSrcweir // ::boost::bind( ::std::logical_not<sal_Bool>(), ::boost::bind<sal_Bool>(&uno::Reference<rdf::XURI>::is, _1)));
376cdf0e10cSrcweir // compiles on unxsoli4, wntsci12, but not unxlngi6
377cdf0e10cSrcweir // ::boost::bind( ::std::logical_not<sal_Bool>(), ::boost::bind<sal_Bool, com::sun::star::uno::Reference<rdf::XURI> >(&uno::Reference<rdf::XURI>::is, _1)));
378cdf0e10cSrcweir // compiles on unxsoli4, unxlngi6, but not wntsci12
379cdf0e10cSrcweir // ::std::not1( ::std::mem_fun_ref(&uno::Reference<rdf::XURI>::is)) );
380cdf0e10cSrcweir
381cdf0e10cSrcweir if (!predicates.size())
382cdf0e10cSrcweir {
383cdf0e10cSrcweir return; // invalid
384cdf0e10cSrcweir }
385cdf0e10cSrcweir
386cdf0e10cSrcweir uno::Reference<rdf::XURI> xDatatype;
387cdf0e10cSrcweir if (i_rEntry.m_pRDFaAttributes->m_Datatype.getLength())
388cdf0e10cSrcweir {
389cdf0e10cSrcweir xDatatype = MakeURI( i_rEntry.m_pRDFaAttributes->m_Datatype );
390cdf0e10cSrcweir }
391cdf0e10cSrcweir
392cdf0e10cSrcweir try
393cdf0e10cSrcweir {
394cdf0e10cSrcweir // N.B.: this will call xMeta->ensureMetadataReference, which is why
395cdf0e10cSrcweir // this must be done _after_ importing the whole XML file,
396cdf0e10cSrcweir // to prevent collision between generated ids and ids in the file
397cdf0e10cSrcweir m_xRepository->setStatementRDFa(xSubject, predicates.getAsConstList(),
398cdf0e10cSrcweir i_rEntry.m_xObject,
399cdf0e10cSrcweir i_rEntry.m_pRDFaAttributes->m_Content, xDatatype);
400cdf0e10cSrcweir }
401cdf0e10cSrcweir catch (uno::Exception &)
402cdf0e10cSrcweir {
403cdf0e10cSrcweir OSL_ENSURE(false, "InsertRDFaEntry: setStatementRDFa failed?");
404cdf0e10cSrcweir }
405cdf0e10cSrcweir }
406cdf0e10cSrcweir
407cdf0e10cSrcweir ////////////////////////////////////////////////////////////////////////////
408cdf0e10cSrcweir
RDFaImportHelper(const SvXMLImport & i_rImport)409cdf0e10cSrcweir RDFaImportHelper::RDFaImportHelper(const SvXMLImport & i_rImport)
410cdf0e10cSrcweir : m_rImport(i_rImport)
411cdf0e10cSrcweir {
412cdf0e10cSrcweir }
413cdf0e10cSrcweir
~RDFaImportHelper()414cdf0e10cSrcweir RDFaImportHelper::~RDFaImportHelper()
415cdf0e10cSrcweir {
416cdf0e10cSrcweir }
417cdf0e10cSrcweir
418cdf0e10cSrcweir ::boost::shared_ptr<ParsedRDFaAttributes>
ParseRDFa(::rtl::OUString const & i_rAbout,::rtl::OUString const & i_rProperty,::rtl::OUString const & i_rContent,::rtl::OUString const & i_rDatatype)419cdf0e10cSrcweir RDFaImportHelper::ParseRDFa(
420cdf0e10cSrcweir ::rtl::OUString const & i_rAbout,
421cdf0e10cSrcweir ::rtl::OUString const & i_rProperty,
422cdf0e10cSrcweir ::rtl::OUString const & i_rContent,
423cdf0e10cSrcweir ::rtl::OUString const & i_rDatatype)
424cdf0e10cSrcweir {
425cdf0e10cSrcweir if (!i_rProperty.getLength())
426cdf0e10cSrcweir {
427cdf0e10cSrcweir OSL_TRACE("AddRDFa: invalid input: xhtml:property empty");
428cdf0e10cSrcweir return ::boost::shared_ptr<ParsedRDFaAttributes>();
429cdf0e10cSrcweir }
430cdf0e10cSrcweir // must parse CURIEs here: need namespace declaration context
431cdf0e10cSrcweir RDFaReader reader(GetImport());
432cdf0e10cSrcweir const ::rtl::OUString about( reader.ReadURIOrSafeCURIE(i_rAbout) );
433cdf0e10cSrcweir if (!about.getLength()) {
434cdf0e10cSrcweir return ::boost::shared_ptr<ParsedRDFaAttributes>();
435cdf0e10cSrcweir }
436cdf0e10cSrcweir const ::std::vector< ::rtl::OUString > properties(
437cdf0e10cSrcweir reader.ReadCURIEs(i_rProperty) );
438cdf0e10cSrcweir if (!properties.size()) {
439cdf0e10cSrcweir return ::boost::shared_ptr<ParsedRDFaAttributes>();
440cdf0e10cSrcweir }
441cdf0e10cSrcweir const ::rtl::OUString datatype( i_rDatatype.getLength()
442cdf0e10cSrcweir ? reader.ReadCURIE(i_rDatatype)
443cdf0e10cSrcweir : ::rtl::OUString() );
444cdf0e10cSrcweir return ::boost::shared_ptr<ParsedRDFaAttributes>(
445cdf0e10cSrcweir new ParsedRDFaAttributes(about, properties, i_rContent, datatype));
446cdf0e10cSrcweir }
447cdf0e10cSrcweir
448cdf0e10cSrcweir void
AddRDFa(uno::Reference<rdf::XMetadatable> const & i_xObject,::boost::shared_ptr<ParsedRDFaAttributes> & i_pRDFaAttributes)449cdf0e10cSrcweir RDFaImportHelper::AddRDFa(
450cdf0e10cSrcweir uno::Reference<rdf::XMetadatable> const & i_xObject,
451cdf0e10cSrcweir ::boost::shared_ptr<ParsedRDFaAttributes> & i_pRDFaAttributes)
452cdf0e10cSrcweir {
453cdf0e10cSrcweir if (!i_xObject.is())
454cdf0e10cSrcweir {
455cdf0e10cSrcweir OSL_ENSURE(false, "AddRDFa: invalid arg: null textcontent");
456cdf0e10cSrcweir return;
457cdf0e10cSrcweir }
458cdf0e10cSrcweir if (!i_pRDFaAttributes.get())
459cdf0e10cSrcweir {
460cdf0e10cSrcweir OSL_ENSURE(false, "AddRDFa: invalid arg: null RDFa attributes");
461cdf0e10cSrcweir return;
462cdf0e10cSrcweir }
463cdf0e10cSrcweir m_RDFaEntries.push_back(RDFaEntry(i_xObject, i_pRDFaAttributes));
464cdf0e10cSrcweir }
465cdf0e10cSrcweir
466cdf0e10cSrcweir void
ParseAndAddRDFa(uno::Reference<rdf::XMetadatable> const & i_xObject,::rtl::OUString const & i_rAbout,::rtl::OUString const & i_rProperty,::rtl::OUString const & i_rContent,::rtl::OUString const & i_rDatatype)467cdf0e10cSrcweir RDFaImportHelper::ParseAndAddRDFa(
468cdf0e10cSrcweir uno::Reference<rdf::XMetadatable> const & i_xObject,
469cdf0e10cSrcweir ::rtl::OUString const & i_rAbout,
470cdf0e10cSrcweir ::rtl::OUString const & i_rProperty,
471cdf0e10cSrcweir ::rtl::OUString const & i_rContent,
472cdf0e10cSrcweir ::rtl::OUString const & i_rDatatype)
473cdf0e10cSrcweir {
474cdf0e10cSrcweir ::boost::shared_ptr<ParsedRDFaAttributes> pAttributes(
475cdf0e10cSrcweir ParseRDFa(i_rAbout, i_rProperty, i_rContent, i_rDatatype) );
476cdf0e10cSrcweir if (pAttributes.get())
477cdf0e10cSrcweir {
478cdf0e10cSrcweir AddRDFa(i_xObject, pAttributes);
479cdf0e10cSrcweir }
480cdf0e10cSrcweir }
481cdf0e10cSrcweir
InsertRDFa(uno::Reference<rdf::XRepositorySupplier> const & i_xModel)482cdf0e10cSrcweir void RDFaImportHelper::InsertRDFa(
483cdf0e10cSrcweir uno::Reference< rdf::XRepositorySupplier> const & i_xModel)
484cdf0e10cSrcweir {
485cdf0e10cSrcweir OSL_ENSURE(i_xModel.is(), "InsertRDFa: invalid arg: model null");
486cdf0e10cSrcweir if (!i_xModel.is()) return;
487cdf0e10cSrcweir const uno::Reference< rdf::XDocumentRepository > xRepository(
488cdf0e10cSrcweir i_xModel->getRDFRepository(), uno::UNO_QUERY);
489cdf0e10cSrcweir OSL_ENSURE(xRepository.is(), "InsertRDFa: no DocumentRepository?");
490cdf0e10cSrcweir if (!xRepository.is()) return;
491cdf0e10cSrcweir RDFaInserter inserter(GetImport().GetComponentContext(), xRepository);
492cdf0e10cSrcweir ::std::for_each(m_RDFaEntries.begin(), m_RDFaEntries.end(),
493cdf0e10cSrcweir ::boost::bind(&RDFaInserter::InsertRDFaEntry, &inserter, _1));
494cdf0e10cSrcweir }
495cdf0e10cSrcweir
496cdf0e10cSrcweir } // namespace xmloff
497cdf0e10cSrcweir
498