Kaydet (Commit) 6ab2cabe authored tarafından Giuseppe Castagno's avatar Giuseppe Castagno

tdf#101094 (8) OPTIONS: Add options check in Content::resourceTypeForLocks

Change-Id: Ia1bcc1be9e61626da2d60ea679d4b6e7e114ac9f
Reviewed-on: https://gerrit.libreoffice.org/27661Tested-by: 's avatarJenkins <ci@libreoffice.org>
Reviewed-by: 's avatarGiuseppe Castagno <giuseppe.castagno@acca-esse.eu>
üst 73cd9c48
...@@ -2782,7 +2782,8 @@ void Content::destroy( bool bDeletePhysical ) ...@@ -2782,7 +2782,8 @@ void Content::destroy( bool bDeletePhysical )
// returns the resource type, to be checked for locks // returns the resource type, to be checked for locks
Content::ResourceType Content::resourceTypeForLocks( Content::ResourceType Content::resourceTypeForLocks(
const uno::Reference< ucb::XCommandEnvironment >& Environment ) const uno::Reference< ucb::XCommandEnvironment >& Environment,
const std::unique_ptr< DAVResourceAccess > & rResAccess)
{ {
ResourceType eResourceTypeForLocks = UNKNOWN; ResourceType eResourceTypeForLocks = UNKNOWN;
{ {
...@@ -2814,12 +2815,6 @@ Content::ResourceType Content::resourceTypeForLocks( ...@@ -2814,12 +2815,6 @@ Content::ResourceType Content::resourceTypeForLocks(
if ( eResourceTypeForLocks == UNKNOWN ) if ( eResourceTypeForLocks == UNKNOWN )
{ {
// resource type for lock/unlock operations still unknown, need to ask the server // resource type for lock/unlock operations still unknown, need to ask the server
std::unique_ptr< DAVResourceAccess > xResAccess;
xResAccess.reset( new DAVResourceAccess(
m_xContext,
m_rSessionFactory,
rURL ) );
const OUString aScheme( const OUString aScheme(
rURL.copy( 0, rURL.indexOf( ':' ) ).toAsciiLowerCase() ); rURL.copy( 0, rURL.indexOf( ':' ) ).toAsciiLowerCase() );
...@@ -2830,6 +2825,20 @@ Content::ResourceType Content::resourceTypeForLocks( ...@@ -2830,6 +2825,20 @@ Content::ResourceType Content::resourceTypeForLocks(
} }
else else
{ {
DAVOptions aDAVOptions;
getResourceOptions( Environment, aDAVOptions, rResAccess );
if( aDAVOptions.isClass1() ||
aDAVOptions.isClass2() ||
aDAVOptions.isClass3() )
{
// this is at least a DAV, lock to be confirmed
// class 2 is needed for full lock support
// see
// <https://tools.ietf.org/html/rfc4918#section-18.2>
eResourceTypeForLocks = DAV_NOLOCK;
if( aDAVOptions.isClass2() )
{
// ok, possible lock, check for it
try try
{ {
// we need only DAV:supportedlock // we need only DAV:supportedlock
...@@ -2839,7 +2848,9 @@ Content::ResourceType Content::resourceTypeForLocks( ...@@ -2839,7 +2848,9 @@ Content::ResourceType Content::resourceTypeForLocks(
aProperties[ 0 ].Name = DAVProperties::SUPPORTEDLOCK; aProperties[ 0 ].Name = DAVProperties::SUPPORTEDLOCK;
ContentProperties::UCBNamesToDAVNames( aProperties, aPropNames ); ContentProperties::UCBNamesToDAVNames( aProperties, aPropNames );
xResAccess->PROPFIND( DAVZERO, aPropNames, resources, Environment ); rResAccess->PROPFIND( DAVZERO, aPropNames, resources, Environment );
bool wasSupportedlockFound = false;
// only one resource should be returned // only one resource should be returned
if ( resources.size() == 1 ) if ( resources.size() == 1 )
...@@ -2857,13 +2868,15 @@ Content::ResourceType Content::resourceTypeForLocks( ...@@ -2857,13 +2868,15 @@ Content::ResourceType Content::resourceTypeForLocks(
{ {
if ( (*it).Name == DAVProperties::SUPPORTEDLOCK ) if ( (*it).Name == DAVProperties::SUPPORTEDLOCK )
{ {
wasSupportedlockFound = true;
uno::Sequence< ucb::LockEntry > aSupportedLocks; uno::Sequence< ucb::LockEntry > aSupportedLocks;
if ( (*it).Value >>= aSupportedLocks ) if ( (*it).Value >>= aSupportedLocks )
{ {
// this is at least a DAV, no lock confirmed yet
eResourceTypeForLocks = DAV_NOLOCK;
for ( sal_Int32 n = 0; n < aSupportedLocks.getLength(); ++n ) for ( sal_Int32 n = 0; n < aSupportedLocks.getLength(); ++n )
{ {
// TODO: if the lock type is changed from 'exclusive write' to 'shared write'
// e.g. to implement 'Calc shared file feature', the ucb::LockScope_EXCLUSIVE
// value should be checked as well, adaptation the code may be needed
if ( aSupportedLocks[ n ].Scope == ucb::LockScope_EXCLUSIVE && if ( aSupportedLocks[ n ].Scope == ucb::LockScope_EXCLUSIVE &&
aSupportedLocks[ n ].Type == ucb::LockType_WRITE ) aSupportedLocks[ n ].Type == ucb::LockType_WRITE )
{ {
...@@ -2879,10 +2892,23 @@ Content::ResourceType Content::resourceTypeForLocks( ...@@ -2879,10 +2892,23 @@ Content::ResourceType Content::resourceTypeForLocks(
} }
} }
} }
// check if this is still only a DAV_NOLOCK
// a fallback for resources that do not have DAVProperties::SUPPORTEDLOCK property
// we check for the returned OPTION if LOCK is allowed on the resource
if ( !wasSupportedlockFound && eResourceTypeForLocks == DAV_NOLOCK )
{
SAL_INFO( "ucb.ucp.webdav", "This WebDAV server has no supportedlock property, check for allowed LOCK method in OPTIONS" );
// ATTENTION: if the lock type is changed from 'exclusive write' to 'shared write'
// e.g. to implement 'Calc shared file feature' on WebDAV directly, and we arrive to this fallback
// and the LOCK is allowed, we should assume that only exclusive write lock is available
// this is just a reminder...
if ( aDAVOptions.isLockAllowed() )
eResourceTypeForLocks = DAV;
}
} }
catch ( DAVException const & e ) catch ( DAVException const & e )
{ {
xResAccess->resetUri(); rResAccess->resetUri();
//grab the error code //grab the error code
switch( e.getStatus() ) switch( e.getStatus() )
{ {
...@@ -2915,6 +2941,11 @@ Content::ResourceType Content::resourceTypeForLocks( ...@@ -2915,6 +2941,11 @@ Content::ResourceType Content::resourceTypeForLocks(
} }
} }
} }
else
eResourceTypeForLocks = NON_DAV;
}
}
osl::MutexGuard g(m_aMutex); osl::MutexGuard g(m_aMutex);
if (m_eResourceTypeForLocks == UNKNOWN) if (m_eResourceTypeForLocks == UNKNOWN)
{ {
...@@ -2932,6 +2963,21 @@ Content::ResourceType Content::resourceTypeForLocks( ...@@ -2932,6 +2963,21 @@ Content::ResourceType Content::resourceTypeForLocks(
return m_eResourceTypeForLocks; return m_eResourceTypeForLocks;
} }
Content::ResourceType Content::resourceTypeForLocks(
const uno::Reference< ucb::XCommandEnvironment >& Environment )
{
std::unique_ptr< DAVResourceAccess > xResAccess;
{
osl::MutexGuard aGuard( m_aMutex );
xResAccess.reset( new DAVResourceAccess( *m_xResAccess.get() ) );
}
Content::ResourceType ret = resourceTypeForLocks( Environment, xResAccess );
{
osl::Guard< osl::Mutex > aGuard( m_aMutex );
m_xResAccess.reset( new DAVResourceAccess( *xResAccess.get() ) );
}
return ret;
}
void Content::lock( void Content::lock(
const uno::Reference< ucb::XCommandEnvironment >& Environment ) const uno::Reference< ucb::XCommandEnvironment >& Environment )
...@@ -2986,7 +3032,7 @@ void Content::lock( ...@@ -2986,7 +3032,7 @@ void Content::lock(
// this exception is mapped directly to the ucb correct one, without // this exception is mapped directly to the ucb correct one, without
// going into the cancelCommandExecution() user interaction // going into the cancelCommandExecution() user interaction
// this exception should be managed by the issuer of 'lock' command // this exception should be managed by the issuer of 'lock' command
switch(e.getError()) switch( e.getError() )
{ {
case DAVException::DAV_LOCKED: case DAVException::DAV_LOCKED:
{ {
......
...@@ -184,7 +184,11 @@ private: ...@@ -184,7 +184,11 @@ private:
static bool shouldAccessNetworkAfterException( const DAVException & e ); static bool shouldAccessNetworkAfterException( const DAVException & e );
ResourceType resourceTypeForLocks( ResourceType resourceTypeForLocks(
const css::uno::Reference< css::ucb::XCommandEnvironment >& Environment ); const css::uno::Reference< css::ucb::XCommandEnvironment >& rEnvironment,
const std::unique_ptr< DAVResourceAccess > & rResAccess );
ResourceType resourceTypeForLocks(
const css::uno::Reference< css::ucb::XCommandEnvironment >& rEnvironment );
void addProperty( const css::ucb::PropertyCommandArgument &aCmdArg, void addProperty( const css::ucb::PropertyCommandArgument &aCmdArg,
const css::uno::Reference< css::ucb::XCommandEnvironment >& Environment ) const css::uno::Reference< css::ucb::XCommandEnvironment >& Environment )
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment