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 
23 
24 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_ftp.hxx"
26 
27 /**************************************************************************
28 								TODO
29  **************************************************************************
30 
31  *************************************************************************/
32 
33 #include <ucbhelper/contentbroker.hxx>
34 #include <osl/socket.hxx>
35 #include "ftpcontentprovider.hxx"
36 #include "ftpcontent.hxx"
37 #include "ftploaderthread.hxx"
38 
39 
40 using namespace ftp;
41 using namespace com::sun::star::lang;
42 using namespace com::sun::star::container;
43 using namespace com::sun::star::uno;
44 using namespace com::sun::star::ucb;
45 using namespace com::sun::star::beans;
46 
47 
48 
49 //=========================================================================
50 //=========================================================================
51 //
52 // ContentProvider Implementation.
53 //
54 //=========================================================================
55 //=========================================================================
56 
FTPContentProvider(const Reference<XMultiServiceFactory> & rSMgr)57 FTPContentProvider::FTPContentProvider(
58     const Reference< XMultiServiceFactory >& rSMgr)
59 : ::ucbhelper::ContentProviderImplHelper(rSMgr),
60   m_ftpLoaderThread(0),
61   m_pProxyDecider(0)
62 {
63 }
64 
65 //=========================================================================
66 // virtual
~FTPContentProvider()67 FTPContentProvider::~FTPContentProvider()
68 {
69 	delete m_ftpLoaderThread;
70 	delete m_pProxyDecider;
71 }
72 
73 //=========================================================================
74 //
75 // XInterface methods.
76 //
77 //=========================================================================
78 
79 XINTERFACE_IMPL_3(FTPContentProvider,
80 				  XTypeProvider,
81 				  XServiceInfo,
82 				  XContentProvider)
83 
84 //=========================================================================
85 //
86 // XTypeProvider methods.
87 //
88 //=========================================================================
89 
90 XTYPEPROVIDER_IMPL_3(FTPContentProvider,
91 					 XTypeProvider,
92 					 XServiceInfo,
93 					 XContentProvider)
94 
95 //=========================================================================
96 //
97 // XServiceInfo methods.
98 //
99 //=========================================================================
100 
101 XSERVICEINFO_IMPL_1(
102     FTPContentProvider,
103     rtl::OUString::createFromAscii("com.sun.star.comp.FTPContentProvider"),
104     rtl::OUString::createFromAscii(FTP_CONTENT_PROVIDER_SERVICE_NAME));
105 
106 //=========================================================================
107 //
108 // Service factory implementation.
109 //
110 //=========================================================================
111 
112 ONE_INSTANCE_SERVICE_FACTORY_IMPL(FTPContentProvider);
113 
114 
115 //=========================================================================
116 //
117 // XContentProvider methods.
118 //
119 //=========================================================================
120 
121 // virtual
122 Reference<XContent> SAL_CALL
queryContent(const Reference<XContentIdentifier> & xCanonicId)123 FTPContentProvider::queryContent(
124 	const Reference< XContentIdentifier >& xCanonicId
125 )
126     throw(
127 		IllegalIdentifierException,
128 		RuntimeException
129 	)
130 {
131     // Check, if a content with given id already exists...
132     Reference<XContent> xContent = queryExistingContent(xCanonicId).get();
133     if(xContent.is())
134         return xContent;
135 
136 	// A new content has to be returned:
137 	{
138 		// Initialize
139 		osl::MutexGuard aGuard( m_aMutex );
140         if(!m_ftpLoaderThread || !m_pProxyDecider)
141 		{
142 			try {
143 				init();
144 			} catch( ... ) {
145 				throw RuntimeException();
146 			}
147 
148 			if(!m_ftpLoaderThread || !m_pProxyDecider)
149 				throw RuntimeException();
150 		}
151     }
152 
153 	try {
154 		FTPURL aURL(xCanonicId->getContentIdentifier(),
155 					this);
156 
157 		if(!m_pProxyDecider->shouldUseProxy(
158 			rtl::OUString::createFromAscii("ftp"),
159 			aURL.host(),
160 			aURL.port().toInt32()))
161         {
162 			xContent = new FTPContent(m_xSMgr,this,xCanonicId,aURL);
163             registerNewContent(xContent);
164         }
165 		else {
166 			Reference<XContentProvider>
167 				xProvider(getHttpProvider());
168 			if(xProvider.is())
169 				return xProvider->queryContent(xCanonicId);
170 			else
171 				throw RuntimeException();
172 		}
173 	} catch(const malformed_exception&) {
174 		throw IllegalIdentifierException();
175 	}
176 
177 	// may throw IllegalIdentifierException
178     return xContent;
179 }
180 
181 
182 
183 
init()184 void FTPContentProvider::init() {
185 	m_ftpLoaderThread = new FTPLoaderThread();
186 	m_pProxyDecider = new ucbhelper::InternetProxyDecider(m_xSMgr);
187 }
188 
189 
190 
handle()191 CURL* FTPContentProvider::handle() {
192 	// Cannot be zero if called from here;
193 	return m_ftpLoaderThread->handle();
194 }
195 
196 
forHost(const rtl::OUString & host,const rtl::OUString & port,const rtl::OUString & username,rtl::OUString & password,rtl::OUString & account)197 bool FTPContentProvider::forHost(
198     const rtl::OUString& host,
199     const rtl::OUString& port,
200     const rtl::OUString& username,
201     rtl::OUString& password,
202     rtl::OUString& account)
203 {
204     osl::MutexGuard aGuard(m_aMutex);
205     for(unsigned int i = 0; i < m_ServerInfo.size(); ++i)
206         if(host == m_ServerInfo[i].host &&
207            port == m_ServerInfo[i].port &&
208 		   username == m_ServerInfo[i].username )
209 		{
210             password = m_ServerInfo[i].password;
211             account = m_ServerInfo[i].account;
212             return true;
213         }
214 
215     return false;
216 }
217 
218 
setHost(const rtl::OUString & host,const rtl::OUString & port,const rtl::OUString & username,const rtl::OUString & password,const rtl::OUString & account)219 bool  FTPContentProvider::setHost(
220     const rtl::OUString& host,
221     const rtl::OUString& port,
222     const rtl::OUString& username,
223     const rtl::OUString& password,
224     const rtl::OUString& account)
225 {
226     ServerInfo inf;
227     inf.host = host;
228     inf.port = port;
229     inf.username = username;
230     inf.password = password;
231     inf.account = account;
232 
233     bool present(false);
234     osl::MutexGuard aGuard(m_aMutex);
235     for(unsigned int i = 0; i < m_ServerInfo.size(); ++i)
236         if(host == m_ServerInfo[i].host &&
237            port == m_ServerInfo[i].port &&
238 		   username == m_ServerInfo[i].username)
239 		{
240 			present = true;
241 			m_ServerInfo[i].password = password;
242 			m_ServerInfo[i].account = account;
243 		}
244 
245     if(!present)
246         m_ServerInfo.push_back(inf);
247 
248     return !present;
249 }
250 
251 
252 
253 Reference<XContentProvider>
getHttpProvider()254 FTPContentProvider::getHttpProvider()
255     throw(RuntimeException)
256 {
257 	// used for access to ftp-proxy
258 	ucbhelper::ContentBroker *pBroker = ucbhelper::ContentBroker::get();
259 
260 	if(pBroker) {
261 		Reference<XContentProviderManager > xManager(
262 			pBroker->getContentProviderManagerInterface());
263 
264 		if(xManager.is())
265 			return
266 				xManager->queryContentProvider(
267 					rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("http:")));
268 		else
269 			throw RuntimeException(
270 				rtl::OUString(RTL_CONSTASCII_USTRINGPARAM(
271 					"bad ucbhelper::ContentBroker")),
272 				*this);
273 	} else
274 		return 0;
275 
276 }
277