1 /************************************************************** 2 * 3 * Licensed to the Apache Software Foundation (ASF) under one 4 * or more contributor license agreements. See the NOTICE file 5 * distributed with this work for additional information 6 * regarding copyright ownership. The ASF licenses this file 7 * to you under the Apache License, Version 2.0 (the 8 * "License"); you may not use this file except in compliance 9 * with the License. You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, 14 * software distributed under the License is distributed on an 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 * KIND, either express or implied. See the License for the 17 * specific language governing permissions and limitations 18 * under the License. 19 * 20 *************************************************************/ 21 22 // MARKER(update_precomp.py): autogen include statement, do not remove 23 #include "precompiled_ucb.hxx" 24 25 #include "SerfPropFindReqProcImpl.hxx" 26 #include "SerfTypes.hxx" 27 #include "DAVProperties.hxx" 28 29 #include "webdavresponseparser.hxx" 30 #include <comphelper/seqstream.hxx> 31 32 using namespace com::sun::star; 33 34 namespace http_dav_ucp 35 { 36 37 SerfPropFindReqProcImpl::SerfPropFindReqProcImpl( const char* inPath, 38 const DAVRequestHeaders& inRequestHeaders, 39 const Depth inDepth, 40 const std::vector< ::rtl::OUString > & inPropNames, 41 std::vector< DAVResource > & ioResources ) 42 : SerfRequestProcessorImpl( inPath, inRequestHeaders ) 43 , mDepthStr( 0 ) 44 , mpPropNames( &inPropNames ) 45 , mpResources( &ioResources ) 46 , mpResInfo( 0 ) 47 , mbOnlyPropertyNames( false ) 48 , xInputStream( new SerfInputStream() ) 49 { 50 init( inDepth ); 51 } 52 53 SerfPropFindReqProcImpl::SerfPropFindReqProcImpl( const char* inPath, 54 const DAVRequestHeaders& inRequestHeaders, 55 const Depth inDepth, 56 std::vector< DAVResourceInfo > & ioResInfo ) 57 : SerfRequestProcessorImpl( inPath, inRequestHeaders ) 58 , mDepthStr( 0 ) 59 , mpPropNames( 0 ) 60 , mpResources( 0 ) 61 , mpResInfo( &ioResInfo ) 62 , mbOnlyPropertyNames( true ) 63 , xInputStream( new SerfInputStream() ) 64 { 65 init( inDepth ); 66 } 67 68 void SerfPropFindReqProcImpl::init( const Depth inDepth ) 69 { 70 switch ( inDepth ) 71 { 72 case DAVZERO: 73 mDepthStr = "0"; 74 break; 75 case DAVONE: 76 mDepthStr = "1"; 77 break; 78 case DAVINFINITY: 79 mDepthStr = "infinity"; 80 break; 81 } 82 } 83 84 SerfPropFindReqProcImpl::~SerfPropFindReqProcImpl() 85 { 86 } 87 88 #define PROPFIND_HEADER "<?xml version=\"1.0\" encoding=\"utf-8\"?><propfind xmlns=\"DAV:\">" 89 #define PROPFIND_TRAILER "</propfind>" 90 91 serf_bucket_t * SerfPropFindReqProcImpl::createSerfRequestBucket( serf_request_t * inSerfRequest ) 92 { 93 serf_bucket_alloc_t* pSerfBucketAlloc = serf_request_get_alloc( inSerfRequest ); 94 95 // body bucket - certain properties OR all properties OR only property names 96 serf_bucket_t* body_bkt = 0; 97 rtl::OUString aBodyText; 98 { 99 // create and fill body bucket with requested properties 100 const int nPropCount = ( !mbOnlyPropertyNames && mpPropNames ) 101 ? mpPropNames->size() 102 : 0; 103 if ( nPropCount > 0 ) 104 { 105 SerfPropName thePropName; 106 for ( int theIndex = 0; theIndex < nPropCount; theIndex ++ ) 107 { 108 // split fullname into namespace and name! 109 DAVProperties::createSerfPropName( (*mpPropNames)[ theIndex ], 110 thePropName ); 111 112 /* <*propname* xmlns="*propns*" /> */ 113 aBodyText += rtl::OUString::createFromAscii( "<" ); 114 aBodyText += rtl::OUString::createFromAscii( thePropName.name ); 115 aBodyText += rtl::OUString::createFromAscii( " xmlnx=\"" ); 116 aBodyText += rtl::OUString::createFromAscii( thePropName.nspace ); 117 aBodyText += rtl::OUString::createFromAscii( "\"/>" ); 118 } 119 120 aBodyText = rtl::OUString::createFromAscii( "<prop>" ) + 121 aBodyText + 122 rtl::OUString::createFromAscii( "</prop>" ); 123 } 124 else 125 { 126 if ( mbOnlyPropertyNames ) 127 { 128 aBodyText = rtl::OUString::createFromAscii( "<propname/>" ); 129 } 130 else 131 { 132 aBodyText = rtl::OUString::createFromAscii( "<allprop/>" ); 133 } 134 } 135 136 aBodyText = rtl::OUString::createFromAscii( PROPFIND_HEADER ) + 137 aBodyText + 138 rtl::OUString::createFromAscii( PROPFIND_TRAILER ); 139 body_bkt = SERF_BUCKET_SIMPLE_STRING( rtl::OUStringToOString( aBodyText, RTL_TEXTENCODING_UTF8 ), 140 pSerfBucketAlloc ); 141 } 142 143 // create serf request 144 serf_bucket_t *req_bkt = serf_request_bucket_request_create( inSerfRequest, 145 "PROPFIND", 146 getPathStr(), 147 body_bkt, 148 pSerfBucketAlloc ); 149 handleChunkedEncoding(req_bkt, aBodyText.getLength()); 150 151 // set request header fields 152 serf_bucket_t* hdrs_bkt = serf_bucket_request_get_headers( req_bkt ); 153 if (hdrs_bkt != NULL) 154 { 155 // general header fields provided by caller 156 setRequestHeaders( hdrs_bkt ); 157 158 // request specific header fields 159 serf_bucket_headers_set( hdrs_bkt, "Depth", mDepthStr ); 160 if (hdrs_bkt!=NULL && body_bkt != 0 && aBodyText.getLength() > 0 ) 161 { 162 serf_bucket_headers_set( hdrs_bkt, "Content-Type", "application/xml" ); 163 } 164 } 165 else 166 { 167 OSL_ASSERT("Headers Bucket missing"); 168 } 169 170 return req_bkt; 171 } 172 173 void SerfPropFindReqProcImpl::processChunkOfResponseData( const char* data, 174 apr_size_t len ) 175 { 176 if ( xInputStream.is() ) 177 { 178 xInputStream->AddToStream( data, len ); 179 } 180 } 181 182 void SerfPropFindReqProcImpl::handleEndOfResponseData( serf_bucket_t * /*inSerfResponseBucket*/ ) 183 { 184 if ( mbOnlyPropertyNames ) 185 { 186 const std::vector< DAVResourceInfo > rResInfo( parseWebDAVPropNameResponse( xInputStream.get() ) ); 187 *mpResInfo = rResInfo; 188 } 189 else 190 { 191 const std::vector< DAVResource > rResources( parseWebDAVPropFindResponse( xInputStream.get() ) ); 192 *mpResources = rResources; 193 } 194 } 195 196 } // namespace http_dav_ucp 197