fix baseline build (old cairo) - 'cairo_rectangle_int_t' does not name a type
[LibreOffice.git] / sax / test / saxdemo.cxx
blob5af47eb763fff40a3441063e6fe317ad4cd9d7ab
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
21 // testcomponent - Loads a service and its testcomponent from dlls performs a test.
22 // Expands the dll-names depending on the actual environment.
23 // Example : testcomponent com.sun.star.io.Pipe stm
25 // Therefore the testcode must exist in teststm and the testservice must be named test.com.sun.star.uno.io.Pipe
28 #include <stdio.h>
29 #include <vector>
30 #include <cstring>
32 #include <com/sun/star/registry/XImplementationRegistration.hpp>
33 #include <com/sun/star/lang/XComponent.hpp>
35 #include <com/sun/star/xml/sax/SAXParseException.hpp>
36 #include <com/sun/star/xml/sax/XParser.hpp>
37 #include <com/sun/star/xml/sax/XExtendedDocumentHandler.hpp>
39 #include <com/sun/star/io/XOutputStream.hpp>
40 #include <com/sun/star/io/XActiveDataSource.hpp>
42 #include <cppuhelper/servicefactory.hxx>
43 #include <cppuhelper/implbase1.hxx>
44 #include <cppuhelper/implbase3.hxx>
46 #include <osl/diagnose.h>
48 using namespace ::std;
49 using namespace ::cppu;
50 using namespace ::com::sun::star::uno;
51 using namespace ::com::sun::star::lang;
52 using namespace ::com::sun::star::registry;
53 using namespace ::com::sun::star::xml::sax;
54 using namespace ::com::sun::star::io;
57 /************
58 * Sequence of bytes -> InputStream
59 ************/
60 class OInputStream : public WeakImplHelper1 < XInputStream >
62 public:
63 OInputStream( const Sequence< sal_Int8 >&seq ) :
64 m_seq( seq ),
65 nPos( 0 )
68 public:
69 virtual sal_Int32 SAL_CALL readBytes( Sequence< sal_Int8 >& aData, sal_Int32 nBytesToRead )
70 throw(NotConnectedException, BufferSizeExceededException, IOException, RuntimeException)
72 nBytesToRead = (nBytesToRead > m_seq.getLength() - nPos ) ?
73 m_seq.getLength() - nPos :
74 nBytesToRead;
75 aData = Sequence< sal_Int8 > ( &(m_seq.getConstArray()[nPos]) , nBytesToRead );
76 nPos += nBytesToRead;
77 return nBytesToRead;
79 virtual sal_Int32 SAL_CALL readSomeBytes(
80 ::com::sun::star::uno::Sequence< sal_Int8 >& aData,
81 sal_Int32 nMaxBytesToRead )
82 throw(NotConnectedException, BufferSizeExceededException, IOException, RuntimeException)
84 return readBytes( aData, nMaxBytesToRead );
86 virtual void SAL_CALL skipBytes( sal_Int32 /* nBytesToSkip */ )
87 throw(NotConnectedException, BufferSizeExceededException, IOException, RuntimeException)
89 // not implemented
91 virtual sal_Int32 SAL_CALL available( )
92 throw(NotConnectedException, IOException, RuntimeException)
94 return m_seq.getLength() - nPos;
96 virtual void SAL_CALL closeInput( )
97 throw(NotConnectedException, IOException, RuntimeException)
99 // not needed
101 Sequence< sal_Int8> m_seq;
102 sal_Int32 nPos;
106 // Helper : create an input stream from a file
108 Reference< XInputStream > createStreamFromFile(
109 const char *pcFile )
111 FILE *f = fopen( pcFile , "rb" );
112 Reference< XInputStream > r;
114 if( f ) {
115 fseek( f , 0 , SEEK_END );
116 int nLength = ftell( f );
117 fseek( f , 0 , SEEK_SET );
119 Sequence<sal_Int8> seqIn(nLength);
120 fread( seqIn.getArray() , nLength , 1 , f );
122 r = Reference< XInputStream > ( new OInputStream( seqIn ) );
123 fclose( f );
125 return r;
129 // The document handler, which is needed for the saxparser
130 // The Documenthandler for reading sax
132 class TestDocumentHandler :
133 public WeakImplHelper3< XExtendedDocumentHandler , XEntityResolver , XErrorHandler >
135 public:
136 TestDocumentHandler( )
140 public: // Error handler
141 virtual void SAL_CALL error(const Any& aSAXParseException) throw (SAXException, RuntimeException)
143 printf( "Error !\n" );
144 throw SAXException(
145 OUString( "error from error handler") ,
146 Reference < XInterface >() ,
147 aSAXParseException );
149 virtual void SAL_CALL fatalError(const Any& /* aSAXParseException */) throw (SAXException, RuntimeException)
151 printf( "Fatal Error !\n" );
153 virtual void SAL_CALL warning(const Any& /* aSAXParseException */) throw (SAXException, RuntimeException)
155 printf( "Warning !\n" );
159 public: // ExtendedDocumentHandler
161 virtual void SAL_CALL startDocument() throw (SAXException, RuntimeException)
163 m_iElementCount = 0;
164 m_iAttributeCount = 0;
165 m_iWhitespaceCount =0;
166 m_iCharCount=0;
167 printf( "document started\n" );
169 virtual void SAL_CALL endDocument() throw (SAXException, RuntimeException)
171 printf( "document finished\n" );
172 printf( "(ElementCount %d),(AttributeCount %d),(WhitespaceCount %d),(CharCount %d)\n",
173 m_iElementCount, m_iAttributeCount, m_iWhitespaceCount , m_iCharCount );
176 virtual void SAL_CALL startElement(const OUString& /* aName */,
177 const Reference< XAttributeList > & xAttribs)
178 throw (SAXException,RuntimeException)
180 m_iElementCount ++;
181 m_iAttributeCount += xAttribs->getLength();
184 virtual void SAL_CALL endElement(const OUString& /* aName */) throw (SAXException,RuntimeException)
186 // ignored
189 virtual void SAL_CALL characters(const OUString& aChars) throw (SAXException,RuntimeException)
191 m_iCharCount += aChars.getLength();
193 virtual void SAL_CALL ignorableWhitespace(const OUString& aWhitespaces) throw (SAXException,RuntimeException)
195 m_iWhitespaceCount += aWhitespaces.getLength();
198 virtual void SAL_CALL processingInstruction(const OUString& /* aTarget */, const OUString& /* aData */) throw (SAXException,RuntimeException)
200 // ignored
203 virtual void SAL_CALL setDocumentLocator(const Reference< XLocator> & /* xLocator */)
204 throw (SAXException,RuntimeException)
206 // ignored
209 virtual InputSource SAL_CALL resolveEntity(
210 const OUString& sPublicId,
211 const OUString& sSystemId)
212 throw (RuntimeException)
214 InputSource source;
215 source.sSystemId = sSystemId;
216 source.sPublicId = sPublicId;
218 source.aInputStream = createStreamFromFile(
219 OUStringToOString( sSystemId, RTL_TEXTENCODING_ASCII_US).getStr() );
221 return source;
224 virtual void SAL_CALL startCDATA() throw (SAXException,RuntimeException)
227 virtual void SAL_CALL endCDATA() throw (SAXException,RuntimeException)
230 virtual void SAL_CALL comment(const OUString& /* sComment */) throw (SAXException,RuntimeException)
233 virtual void SAL_CALL unknown(const OUString& /* sString */) throw (SAXException,RuntimeException)
237 virtual void SAL_CALL allowLineBreak() throw (SAXException, RuntimeException )
242 public:
243 int m_iElementCount;
244 int m_iAttributeCount;
245 int m_iWhitespaceCount;
246 int m_iCharCount;
250 // helper implementation for writing
251 // implements an XAttributeList
253 struct AttributeListImpl_impl;
254 class AttributeListImpl : public WeakImplHelper1< XAttributeList >
256 public:
257 AttributeListImpl();
258 AttributeListImpl( const AttributeListImpl & );
259 ~AttributeListImpl();
261 public:
262 virtual sal_Int16 SAL_CALL getLength() throw (RuntimeException);
263 virtual OUString SAL_CALL getNameByIndex(sal_Int16 i) throw (RuntimeException);
264 virtual OUString SAL_CALL getTypeByIndex(sal_Int16 i) throw (RuntimeException);
265 virtual OUString SAL_CALL getTypeByName(const OUString& aName) throw (RuntimeException);
266 virtual OUString SAL_CALL getValueByIndex(sal_Int16 i) throw (RuntimeException);
267 virtual OUString SAL_CALL getValueByName(const OUString& aName) throw (RuntimeException);
269 public:
270 void addAttribute( const OUString &sName ,
271 const OUString &sType ,
272 const OUString &sValue );
273 void clear();
275 private:
276 struct AttributeListImpl_impl *m_pImpl;
280 struct TagAttribute
282 TagAttribute(){}
283 TagAttribute( const OUString &s_Name,
284 const OUString &s_Type ,
285 const OUString &s_Value )
287 this->sName = s_Name;
288 this->sType = s_Type;
289 this->sValue = s_Value;
292 OUString sName;
293 OUString sType;
294 OUString sValue;
297 struct AttributeListImpl_impl
299 AttributeListImpl_impl()
301 // performance improvement during adding
302 vecAttribute.reserve(20);
304 vector<struct TagAttribute> vecAttribute;
309 sal_Int16 AttributeListImpl::getLength() throw (RuntimeException)
311 return (sal_Int16) m_pImpl->vecAttribute.size();
315 AttributeListImpl::AttributeListImpl( const AttributeListImpl &r )
317 m_pImpl = new AttributeListImpl_impl;
318 *m_pImpl = *(r.m_pImpl);
321 OUString AttributeListImpl::getNameByIndex(sal_Int16 i) throw (RuntimeException)
323 if( i < sal::static_int_cast<sal_Int16>(m_pImpl->vecAttribute.size()) ) {
324 return m_pImpl->vecAttribute[i].sName;
326 return OUString();
330 OUString AttributeListImpl::getTypeByIndex(sal_Int16 i) throw (RuntimeException)
332 if( i < sal::static_int_cast<sal_Int16>(m_pImpl->vecAttribute.size()) ) {
333 return m_pImpl->vecAttribute[i].sType;
335 return OUString();
338 OUString AttributeListImpl::getValueByIndex(sal_Int16 i) throw (RuntimeException)
340 if( i < sal::static_int_cast<sal_Int16>(m_pImpl->vecAttribute.size()) ) {
341 return m_pImpl->vecAttribute[i].sValue;
343 return OUString();
347 OUString AttributeListImpl::getTypeByName( const OUString& sName ) throw (RuntimeException)
349 vector<struct TagAttribute>::iterator ii = m_pImpl->vecAttribute.begin();
351 for( ; ii != m_pImpl->vecAttribute.end() ; ++ii ) {
352 if( (*ii).sName == sName ) {
353 return (*ii).sType;
356 return OUString();
359 OUString AttributeListImpl::getValueByName(const OUString& sName) throw (RuntimeException)
361 vector<struct TagAttribute>::iterator ii = m_pImpl->vecAttribute.begin();
363 for( ; ii != m_pImpl->vecAttribute.end() ; ++ii ) {
364 if( (*ii).sName == sName ) {
365 return (*ii).sValue;
368 return OUString();
373 AttributeListImpl::AttributeListImpl()
375 m_pImpl = new AttributeListImpl_impl;
380 AttributeListImpl::~AttributeListImpl()
382 delete m_pImpl;
386 void AttributeListImpl::addAttribute( const OUString &sName ,
387 const OUString &sType ,
388 const OUString &sValue )
390 m_pImpl->vecAttribute.push_back( TagAttribute( sName , sType , sValue ) );
393 void AttributeListImpl::clear()
395 m_pImpl->vecAttribute.clear();
400 // helper function for writing
401 // ensures that linebreaks are inserted
402 // when writing a long text.
403 // Note: this implementation may be a bit slow,
404 // but it shows, how the SAX-Writer handles the allowLineBreak calls.
406 void writeParagraphHelper(
407 const Reference< XExtendedDocumentHandler > &r ,
408 const OUString & s)
410 int nMax = s.getLength();
411 int nStart = 0;
412 int n = 1;
414 Sequence<sal_uInt16> seq( s.getLength() );
415 memcpy( seq.getArray() , s.getStr() , s.getLength() * sizeof( sal_uInt16 ) );
417 for( n = 1 ; n < nMax ; n++ ){
418 if( 32 == seq.getArray()[n] ) {
419 r->allowLineBreak();
420 r->characters( s.copy( nStart , n - nStart ) );
421 nStart = n;
424 r->allowLineBreak();
425 r->characters( s.copy( nStart , n - nStart ) );
430 // helper implementation for SAX-Writer
431 // writes data to a file
433 class OFileWriter :
434 public WeakImplHelper1< XOutputStream >
436 public:
437 OFileWriter( char *pcFile ) { strncpy( m_pcFile , pcFile, 256 - 1 ); m_f = 0; }
440 public:
441 virtual void SAL_CALL writeBytes(const Sequence< sal_Int8 >& aData)
442 throw (NotConnectedException, BufferSizeExceededException, RuntimeException);
443 virtual void SAL_CALL flush()
444 throw (NotConnectedException, BufferSizeExceededException, RuntimeException);
445 virtual void SAL_CALL closeOutput()
446 throw (NotConnectedException, BufferSizeExceededException, RuntimeException);
447 private:
448 char m_pcFile[256];
449 FILE *m_f;
453 void OFileWriter::writeBytes(const Sequence< sal_Int8 >& aData)
454 throw (NotConnectedException, BufferSizeExceededException, RuntimeException)
456 if( ! m_f ) {
457 m_f = fopen( m_pcFile , "w" );
460 fwrite( aData.getConstArray() , 1 , aData.getLength() , m_f );
464 void OFileWriter::flush()
465 throw (NotConnectedException, BufferSizeExceededException, RuntimeException)
467 fflush( m_f );
470 void OFileWriter::closeOutput()
471 throw (NotConnectedException, BufferSizeExceededException, RuntimeException)
473 fclose( m_f );
474 m_f = 0;
479 // Needed to switch on solaris threads
480 #ifdef SOLARIS
481 extern "C" void ChangeGlobalInit();
482 #endif
483 int main (int argc, char **argv)
486 if( argc < 3) {
487 printf( "usage : saxdemo inputfile outputfile\n" );
488 exit( 0 );
490 #ifdef SOLARIS
491 // switch on threads in solaris
492 ChangeGlobalInit();
493 #endif
495 // create service manager
496 Reference< XMultiServiceFactory > xSMgr = createRegistryServiceFactory(
497 OUString( "applicat.rdb" ) );
499 Reference < XImplementationRegistration > xReg;
502 // Create registration service
503 Reference < XInterface > x = xSMgr->createInstance(
504 OUString("com.sun.star.registry.ImplementationRegistration") );
505 xReg = Reference< XImplementationRegistration > ( x , UNO_QUERY );
507 catch( Exception & ) {
508 printf( "Couldn't create ImplementationRegistration service\n" );
509 exit(1);
512 OString sTestName;
515 // Load dll for the tested component
516 OUString aDllName( "sax.uno" SAL_DLLEXTENSION );
517 xReg->registerImplementation(
518 OUString("com.sun.star.loader.SharedLibrary"),
519 aDllName,
520 Reference< XSimpleRegistry > () );
522 catch( Exception &e ) {
523 printf( "Couldn't reach sax dll\n" );
524 printf( "%s\n" , OUStringToOString( e.Message , RTL_TEXTENCODING_ASCII_US ).getStr() );
526 exit(1);
531 // parser demo
532 // read xml from a file and count elements
534 Reference< XInterface > x = xSMgr->createInstance(
535 OUString("com.sun.star.xml.sax.Parser") );
536 if( x.is() )
538 Reference< XParser > rParser( x , UNO_QUERY );
540 // create and connect the document handler to the parser
541 TestDocumentHandler *pDocHandler = new TestDocumentHandler( );
543 Reference < XDocumentHandler > rDocHandler( (XDocumentHandler *) pDocHandler );
544 Reference< XEntityResolver > rEntityResolver( (XEntityResolver *) pDocHandler );
546 rParser->setDocumentHandler( rDocHandler );
547 rParser->setEntityResolver( rEntityResolver );
549 // create the input stream
550 InputSource source;
551 source.aInputStream = createStreamFromFile( argv[1] );
552 source.sSystemId = OUString::createFromAscii( argv[1] );
556 // start parsing
557 rParser->parseStream( source );
560 catch( Exception & e )
562 OString o1 = OUStringToOString(e.Message, RTL_TEXTENCODING_UTF8 );
563 printf( "Exception during parsing : %s\n" , o1.getStr() );
566 else
568 printf( "couldn't create sax-parser component\n" );
573 // The SAX-Writer demo
575 x= xSMgr->createInstance("com.sun.star.xml.sax.Writer");
576 if( x.is() )
578 printf( "start writing to %s\n" , argv[2] );
580 OFileWriter *pw = new OFileWriter( argv[2] );
581 Reference< XActiveDataSource > source( x , UNO_QUERY );
582 source->setOutputStream( Reference< XOutputStream> ( (XOutputStream*) pw ) );
584 AttributeListImpl *pList = new AttributeListImpl;
585 Reference< XAttributeList > rList( (XAttributeList *) pList );
587 Reference< XExtendedDocumentHandler > r( x , UNO_QUERY );
588 r->startDocument();
590 pList->addAttribute( OUString( "Arg1" ),
591 OUString( "CDATA") ,
592 OUString( "foo\n u") );
593 pList->addAttribute( OUString( "Arg2") ,
594 OUString( "CDATA") ,
595 OUString( "foo2") );
597 r->startElement( OUString( "tag1") , rList );
598 // tells the writer to insert a linefeed
599 r->ignorableWhitespace( OUString() );
601 r->characters( OUString( "huhu") );
602 r->ignorableWhitespace( OUString() );
604 r->startElement( OUString( "hi") , rList );
605 r->ignorableWhitespace( OUString() );
607 // the enpassant must be converted & -> &amp;
608 r->characters( OUString( "&#252;") );
609 r->ignorableWhitespace( OUString() );
611 // '>' must not be converted
612 r->startCDATA();
613 r->characters( OUString( " > foo < ") );
614 r->endCDATA();
615 r->ignorableWhitespace( OUString() );
617 OUString testParagraph = OUString(
618 "This is only a test to check, if the writer inserts line feeds "
619 "if needed or if the writer puts the whole text into one line." );
620 writeParagraphHelper( r , testParagraph );
622 r->ignorableWhitespace( OUString() );
623 r->comment( OUString( "This is a comment !") );
624 r->ignorableWhitespace( OUString() );
626 r->startElement( OUString( "emptytagtest") , rList );
627 r->endElement( OUString( "emptytagtest") );
628 r->ignorableWhitespace( OUString() );
630 r->endElement( OUString( "hi") );
631 r->ignorableWhitespace( OUString() );
633 r->endElement( OUString( "tag1") );
634 r->endDocument();
636 printf( "finished writing\n" );
638 else
640 printf( "couldn't create sax-writer component\n" );
644 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */