1 /************************************************************************* 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 28 // MARKER(update_precomp.py): autogen include statement, do not remove 29 #include "precompiled_framework.hxx" 30 31 //_________________________________________________________________________________________________________________ 32 // my own includes 33 //_________________________________________________________________________________________________________________ 34 #include <dispatch/systemexec.hxx> 35 #include <threadhelp/readguard.hxx> 36 #include <general.h> 37 #include <services.h> 38 39 //_________________________________________________________________________________________________________________ 40 // interface includes 41 //_________________________________________________________________________________________________________________ 42 #include <com/sun/star/system/XSystemShellExecute.hpp> 43 #include <com/sun/star/util/XStringSubstitution.hpp> 44 #include <com/sun/star/system/SystemShellExecuteFlags.hpp> 45 #include <com/sun/star/frame/DispatchResultState.hpp> 46 47 //_________________________________________________________________________________________________________________ 48 // includes of other projects 49 //_________________________________________________________________________________________________________________ 50 51 #include <vcl/svapp.hxx> 52 53 //_________________________________________________________________________________________________________________ 54 // namespace 55 //_________________________________________________________________________________________________________________ 56 57 namespace framework{ 58 59 //_________________________________________________________________________________________________________________ 60 // non exported const 61 //_________________________________________________________________________________________________________________ 62 63 #define PROTOCOL_VALUE "systemexecute:" 64 #define PROTOCOL_LENGTH 14 65 66 //_________________________________________________________________________________________________________________ 67 // non exported definitions 68 //_________________________________________________________________________________________________________________ 69 70 //_________________________________________________________________________________________________________________ 71 // declarations 72 //_________________________________________________________________________________________________________________ 73 74 //_________________________________________________________________________________________________________________ 75 // XInterface, XTypeProvider, XServiceInfo 76 77 DEFINE_XINTERFACE_5(SystemExec , 78 OWeakObject , 79 DIRECT_INTERFACE(css::lang::XTypeProvider ), 80 DIRECT_INTERFACE(css::lang::XServiceInfo ), 81 DIRECT_INTERFACE(css::frame::XDispatchProvider ), 82 DIRECT_INTERFACE(css::frame::XNotifyingDispatch), 83 DIRECT_INTERFACE(css::frame::XDispatch )) 84 85 DEFINE_XTYPEPROVIDER_5(SystemExec , 86 css::lang::XTypeProvider , 87 css::lang::XServiceInfo , 88 css::frame::XDispatchProvider , 89 css::frame::XNotifyingDispatch, 90 css::frame::XDispatch ) 91 92 DEFINE_XSERVICEINFO_MULTISERVICE(SystemExec , 93 ::cppu::OWeakObject , 94 SERVICENAME_PROTOCOLHANDLER , 95 IMPLEMENTATIONNAME_SYSTEMEXEC) 96 97 DEFINE_INIT_SERVICE(SystemExec, 98 { 99 /*Attention 100 I think we don't need any mutex or lock here ... because we are called by our own static method impl_createInstance() 101 to create a new instance of this class by our own supported service factory. 102 see macro DEFINE_XSERVICEINFO_MULTISERVICE and "impl_initService()" for further informations! 103 */ 104 } 105 ) 106 107 //_________________________________________________________________________________________________________________ 108 109 SystemExec::SystemExec( const css::uno::Reference< css::lang::XMultiServiceFactory >& xFactory ) 110 // Init baseclasses first 111 : ThreadHelpBase( &Application::GetSolarMutex() ) 112 , OWeakObject ( ) 113 // Init member 114 , m_xFactory ( xFactory ) 115 { 116 } 117 118 //_________________________________________________________________________________________________________________ 119 120 SystemExec::~SystemExec() 121 { 122 m_xFactory = NULL; 123 } 124 125 //_________________________________________________________________________________________________________________ 126 127 css::uno::Reference< css::frame::XDispatch > SAL_CALL SystemExec::queryDispatch( const css::util::URL& aURL , 128 const ::rtl::OUString&, 129 sal_Int32 ) throw( css::uno::RuntimeException ) 130 { 131 css::uno::Reference< css::frame::XDispatch > xDispatcher; 132 if (aURL.Complete.compareToAscii(PROTOCOL_VALUE,PROTOCOL_LENGTH)==0) 133 xDispatcher = this; 134 return xDispatcher; 135 } 136 137 //_________________________________________________________________________________________________________________ 138 139 css::uno::Sequence< css::uno::Reference< css::frame::XDispatch > > SAL_CALL SystemExec::queryDispatches( const css::uno::Sequence< css::frame::DispatchDescriptor >& lDescriptor ) throw( css::uno::RuntimeException ) 140 { 141 sal_Int32 nCount = lDescriptor.getLength(); 142 css::uno::Sequence< css::uno::Reference< css::frame::XDispatch > > lDispatcher( nCount ); 143 for( sal_Int32 i=0; i<nCount; ++i ) 144 { 145 lDispatcher[i] = this->queryDispatch( 146 lDescriptor[i].FeatureURL, 147 lDescriptor[i].FrameName, 148 lDescriptor[i].SearchFlags); 149 } 150 return lDispatcher; 151 } 152 153 //_________________________________________________________________________________________________________________ 154 155 void SAL_CALL SystemExec::dispatch( const css::util::URL& aURL , 156 const css::uno::Sequence< css::beans::PropertyValue >& lArguments ) throw( css::uno::RuntimeException ) 157 { 158 dispatchWithNotification(aURL, lArguments, css::uno::Reference< css::frame::XDispatchResultListener >()); 159 } 160 161 //_________________________________________________________________________________________________________________ 162 163 void SAL_CALL SystemExec::dispatchWithNotification( const css::util::URL& aURL , 164 const css::uno::Sequence< css::beans::PropertyValue >&, 165 const css::uno::Reference< css::frame::XDispatchResultListener >& xListener ) throw( css::uno::RuntimeException ) 166 { 167 // convert "systemexec:file:///c:/temp/test.html" => "file:///c:/temp/test.html" 168 sal_Int32 c = aURL.Complete.getLength()-PROTOCOL_LENGTH; 169 if (c<1) // we dont check for valid URLs here! The system will show an error message ... 170 { 171 impl_notifyResultListener(xListener, css::frame::DispatchResultState::FAILURE); 172 return; 173 } 174 ::rtl::OUString sSystemURLWithVariables = aURL.Complete.copy(PROTOCOL_LENGTH, c); 175 176 // SAFE -> 177 ReadGuard aReadLock(m_aLock); 178 css::uno::Reference< css::lang::XMultiServiceFactory > xFactory = m_xFactory; 179 aReadLock.unlock(); 180 // <- SAFE 181 182 // TODO check security settings ... 183 184 try 185 { 186 css::uno::Reference< css::util::XStringSubstitution > xPathSubst( 187 xFactory->createInstance(SERVICENAME_SUBSTITUTEPATHVARIABLES), 188 css::uno::UNO_QUERY_THROW); 189 190 ::rtl::OUString sSystemURL = xPathSubst->substituteVariables(sSystemURLWithVariables, sal_True); // sal_True force an exception if unknown variables exists ! 191 192 css::uno::Reference< css::system::XSystemShellExecute > xShell( 193 xFactory->createInstance(SERVICENAME_SYSTEMSHELLEXECUTE), 194 css::uno::UNO_QUERY_THROW); 195 196 xShell->execute(sSystemURL, ::rtl::OUString(), css::system::SystemShellExecuteFlags::DEFAULTS); 197 impl_notifyResultListener(xListener, css::frame::DispatchResultState::SUCCESS); 198 } 199 catch(const css::uno::Exception&) 200 { 201 impl_notifyResultListener(xListener, css::frame::DispatchResultState::FAILURE); 202 } 203 } 204 205 //_________________________________________________________________________________________________________________ 206 207 void SAL_CALL SystemExec::addStatusListener( const css::uno::Reference< css::frame::XStatusListener >&, 208 const css::util::URL& ) throw( css::uno::RuntimeException ) 209 { 210 // not suported yet 211 } 212 213 //_________________________________________________________________________________________________________________ 214 215 void SAL_CALL SystemExec::removeStatusListener( const css::uno::Reference< css::frame::XStatusListener >&, 216 const css::util::URL& ) throw( css::uno::RuntimeException ) 217 { 218 // not suported yet 219 } 220 221 //_________________________________________________________________________________________________________________ 222 223 void SystemExec::impl_notifyResultListener(const css::uno::Reference< css::frame::XDispatchResultListener >& xListener, 224 const sal_Int16 nState ) 225 { 226 if (xListener.is()) 227 { 228 css::frame::DispatchResultEvent aEvent; 229 aEvent.State = nState; 230 xListener->dispatchFinished(aEvent); 231 } 232 } 233 234 } // namespace framework 235