videocollection/mpxmyvideoscollection/src/vcxmyvideosasyncfileoperations.cpp
branchRCL_3
changeset 10 112a725ff2c2
parent 9 5294c000a26d
child 15 8f0df5c82986
--- a/videocollection/mpxmyvideoscollection/src/vcxmyvideosasyncfileoperations.cpp	Mon Mar 15 12:40:47 2010 +0200
+++ b/videocollection/mpxmyvideoscollection/src/vcxmyvideosasyncfileoperations.cpp	Wed Mar 31 21:34:36 2010 +0300
@@ -39,6 +39,7 @@
 #include "vcxmyvideoscategories.h"
 #include "vcxmyvideosmessagelist.h"
 #include "vcxmyvideosasyncfileoperations.h"
+#include "vcxmyvideosasyncfilecopy.h"
 
 // ============================ MEMBER FUNCTIONS ==============================
 
@@ -49,8 +50,6 @@
 CVcxMyVideosAsyncFileOperations* CVcxMyVideosAsyncFileOperations::NewL(
     CVcxMyVideosCollectionPlugin& aCollection )
     {
-    MPX_FUNC("CVcxMyVideosAsyncFileOperations::NewL");
-
     CVcxMyVideosAsyncFileOperations* self = new (ELeave) CVcxMyVideosAsyncFileOperations(
             aCollection );
     CleanupStack::PushL(self);
@@ -64,11 +63,12 @@
 // ----------------------------------------------------------------------------
 //
 CVcxMyVideosAsyncFileOperations::~CVcxMyVideosAsyncFileOperations()
-    {
-    MPX_FUNC("CVcxMyVideosAsyncFileOperations::~CVcxMyVideosAsyncFileOperations");
-        
+    {        
     iOperationIdArray.Close();
     iOperationResult.Close();
+    delete iFileCopier;
+    delete iMediaForMoveOp;
+    delete iMediaForCopyOp;
     }
 
 // ----------------------------------------------------------------------------
@@ -78,7 +78,6 @@
 CVcxMyVideosAsyncFileOperations::CVcxMyVideosAsyncFileOperations( CVcxMyVideosCollectionPlugin& aCollection )
 : iCollection( aCollection )
     {
-    MPX_FUNC("CVcxMyVideosAsyncFileOperations::CVcxMyVideosAsyncFileOperations");
     }
 
 // ----------------------------------------------------------------------------
@@ -87,7 +86,7 @@
 //
 void CVcxMyVideosAsyncFileOperations::ConstructL ()
     {
-    MPX_FUNC("CVcxMyVideosAsyncFileOperations::ConstructL");
+    iFileCopier = CVcxMyVideosAsyncFileCopy::NewL( iCollection.iFs );
     }
     
 // ----------------------------------------------------------------------------
@@ -230,57 +229,21 @@
     CMPXMedia& cmd = iCollection.iActiveTask->GetCommand();
     
     TBool done;
-    
-    TBool isMoveOperation = EFalse;    
-    TUint32 cmdId = cmd.ValueTObjectL<TUint32>( KVcxMediaMyVideosCommandId );    
-    if ( cmdId == KVcxCommandMyVideosMove )
-        {
-        MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: move operation");
-        isMoveOperation = ETrue;
-        }
-        
-    // Start operations
-    if ( iCurrentOperationIndex == 0 )
+            
+    if ( iCurrentOperationIndex == 0 && !iFileCopier->CopyIsOngoing() )
         {
-        if ( !cmd.IsSupported( KMPXMediaArrayContents ) )
-            {
-            MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: error, no array defined");
-            User::Leave( KErrArgument );
-            }
-    
-        CMPXMediaArray* idMediaArray = cmd.Value<CMPXMediaArray>(
-                KMPXMediaArrayContents );
-
-        if ( idMediaArray->Count() == 0 )
-            {
-            MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: error, no items in array ");
-            User::Leave( KErrArgument );
-            }
-        
-        iTargetDrive = cmd.ValueTObjectL<TInt32>( KVcxMediaMyVideosInt32Value );
-        
-        TMPXItemId mpxId;    
-        iOperationIdArray.Reset();
-        TInt count = idMediaArray->Count();
-        for ( TInt i = 0; i < count; i++ )
-            {
-            mpxId = idMediaArray->AtL( i )->
-                            ValueTObjectL<TMPXItemId>( KMPXMediaGeneralId );
-            MPX_DEBUG3("CVcxMyVideosAsyncFileOperations:: MPX ID: (%d, %d) will be moved ",
-                    mpxId.iId1,
-                    mpxId.iId2);
-            iOperationIdArray.AppendL( idMediaArray->AtL( i )->
-                    ValueTObjectL<TMPXItemId>(KMPXMediaGeneralId ).iId1 );
-            }
-        
-        iCollection.SendMyVideosMessageL( KVcxMessageMyVideosMoveOrCopyStarted, &cmd );
-
-        iOperationResult.Reset();
+        InitMoveOrCopyOperationsL( cmd );        
         }
 
     TRAPD( err, MoveOrCopyVideoL( iOperationIdArray[iCurrentOperationIndex],
-            iTargetDrive, isMoveOperation ));
+            iTargetDrive ));
 
+    if ( iFileCopier->CopyIsOngoing() && err == KErrNone )
+        {
+        // copy didnt finish yet, lets do some more steps before jumping to next file
+        return EFalse;
+        }
+        
     iOperationResult.AppendL( err );
     
     iCurrentOperationIndex++;
@@ -290,7 +253,7 @@
         {
         iCurrentOperationIndex = 0;
         done                   = ETrue;
-        if ( isMoveOperation )
+        if ( iIsMoveOperation )
             {
             SendOperationRespL( KVcxMessageMyVideosMoveResp );
             }
@@ -308,12 +271,65 @@
     }
 
 // ----------------------------------------------------------------------------
+// CVcxMyVideosAsyncFileOperations::InitMoveOrCopyOperationsL
+// ----------------------------------------------------------------------------
+//
+void CVcxMyVideosAsyncFileOperations::InitMoveOrCopyOperationsL( CMPXMedia& aCmd )
+    {
+    if ( !aCmd.IsSupported( KMPXMediaArrayContents ) )
+        {
+        MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: error, no array defined");
+        User::Leave( KErrArgument );
+        }
+
+    CMPXMediaArray* idMediaArray = aCmd.Value<CMPXMediaArray>(
+            KMPXMediaArrayContents );
+
+    if ( idMediaArray->Count() == 0 )
+        {
+        MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: error, no items in array ");
+        User::Leave( KErrArgument );
+        }
+    
+    TUint32 cmdId = aCmd.ValueTObjectL<TUint32>( KVcxMediaMyVideosCommandId );    
+    if ( cmdId == KVcxCommandMyVideosMove )
+        {
+        MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: move operation");
+        iIsMoveOperation = ETrue;
+        }
+    else
+        {
+        iIsMoveOperation = EFalse;
+        }
+
+    iTargetDrive = aCmd.ValueTObjectL<TInt32>( KVcxMediaMyVideosInt32Value );
+    
+    TMPXItemId mpxId;    
+    iOperationIdArray.Reset();
+    TInt count = idMediaArray->Count();
+    for ( TInt i = 0; i < count; i++ )
+        {
+        mpxId = idMediaArray->AtL( i )->
+                        ValueTObjectL<TMPXItemId>( KMPXMediaGeneralId );
+        MPX_DEBUG3("CVcxMyVideosAsyncFileOperations:: MPX ID: (%d, %d) will be moved ",
+                mpxId.iId1,
+                mpxId.iId2);
+        iOperationIdArray.AppendL( idMediaArray->AtL( i )->
+                ValueTObjectL<TMPXItemId>(KMPXMediaGeneralId ).iId1 );
+        }
+    
+    iCollection.SendMyVideosMessageL( KVcxMessageMyVideosMoveOrCopyStarted, &aCmd );
+
+    iOperationResult.Reset();
+    }
+    
+// ----------------------------------------------------------------------------
 // CVcxMyVideosAsyncFileOperations::CancelOperationL
 // Called when leave or cancel occurs for the operation, generates resp msg.
 // ----------------------------------------------------------------------------
 //
 void CVcxMyVideosAsyncFileOperations::CancelOperationL( TInt aErr )
-    {
+    {    
     if ( iCollection.iActiveTask->IsActive() )
         {
         TInt mvCmdId = -1;
@@ -332,11 +348,22 @@
             case KVcxCommandMyVideosMove:
                 MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: generating KVcxMessageMyVideosMoveResp");
                 messageId = KVcxMessageMyVideosMoveResp;
+                if ( iFileCopier->CopyIsOngoing() )
+                    {
+                    //these have to be in this order, otherwise wrong item gets removed from mds
+                    TRAP_IGNORE( HandleFileCopyCompletedL( aErr ) ); // rolls mds back
+                    iFileCopier->Cancel(); // removes generated file and resets variables
+                    }
                 break;
                 
             case KVcxCommandMyVideosCopy:
                 MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: generating KVcxMessageMyVideosCopyResp");
                 messageId = KVcxMessageMyVideosCopyResp;
+                if ( iFileCopier->CopyIsOngoing() )
+                    {
+                    TRAP_IGNORE( HandleFileCopyCompletedL( aErr ) ); // rolls mds back
+                    iFileCopier->Cancel(); // removes generated file and resets variables
+                    }
                 break;
                 
             case KVcxCommandMyVideosDelete:
@@ -413,13 +440,39 @@
 // CVcxMyVideosAsyncFileOperations::MoveOrCopyVideoL
 // ----------------------------------------------------------------------------
 //
-void CVcxMyVideosAsyncFileOperations::MoveOrCopyVideoL( TUint32 aMdsId, TInt aTargetDrive,
-        TBool aMove )
+void CVcxMyVideosAsyncFileOperations::MoveOrCopyVideoL( TUint32 aMdsId, TInt aTargetDrive )
     {
-    MPX_FUNC("CVcxMyVideosAsyncFileOperations::MoveOrCopyVideoL");
+    if ( iFileCopier->CopyIsOngoing() )
+        {
+        TInt err = iFileCopier->DoNextBlockCopy();
+        if ( err != KErrNone || !iFileCopier->CopyIsOngoing() )
+            {
+            HandleFileCopyCompletedL( err );
+            }
+        return;
+        }
+        
+    //New file copy starts -> do sanity checks and mds and collection preparations
+    InitSingleMoveOrCopyL( aMdsId, aTargetDrive );
+            
+    MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: copying: %S", &iSourcePath);
+    MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: to     : %S", &iTargetPath);
+    
+    TBool completed = ETrue; // set to avoid warning
+    TRAPD( err, completed = iFileCopier->CopyL( iSourcePath, iTargetPath ) );
+    
+    if ( completed || err )
+        {
+        HandleFileCopyCompletedL( err );
+        }
+    }    
 
-    MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: mds id = %d", aMdsId);
-    
+// ----------------------------------------------------------------------------
+// CVcxMyVideosAsyncFileOperations::InitSingleMoveOrCopyL
+// ----------------------------------------------------------------------------
+//
+void CVcxMyVideosAsyncFileOperations::InitSingleMoveOrCopyL( TUint32 aMdsId, TInt aTargetDrive )
+    {
     //get media from cache or mds
     TInt pos;
     CMPXMedia* videoInCache = iCollection.iCache->FindVideoByMdsIdL( aMdsId, pos );
@@ -450,130 +503,124 @@
         User::Leave( KErrInUse );
         }
 
-    const TInt KMaxPathLength = 255;    
-    TBuf<KMaxPathLength> sourcePath( video->ValueText( KMPXMediaGeneralUri ) );
+    iSourcePath = video->ValueText( KMPXMediaGeneralUri );
             
-    MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: source path = %S", &sourcePath);
-
-    if ( !DriveHasEnoughFreeSpaceL( sourcePath, aTargetDrive ) )
+    if ( !DriveHasEnoughFreeSpaceL( iSourcePath, aTargetDrive ) )
         {
         MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: target drive full -> skipping");
         User::Leave( KErrDiskFull );
         }
 
+    TUint att = 0;
+    iCollection.iFs.Att( iSourcePath, att);    
+    if ( iIsMoveOperation && (att & KEntryAttReadOnly) )
+        {
+        MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: move operation and source file is read only -> skipping");
+        User::Leave( KErrAccessDenied );
+        }
+
     TInt sourceDrive;
-    User::LeaveIfError( iCollection.iFs.CharToDrive( sourcePath[0], sourceDrive ) );
+    User::LeaveIfError( iCollection.iFs.CharToDrive( iSourcePath[0], sourceDrive ) );
 
     if ( sourceDrive == aTargetDrive )
         {
-        MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: source and target drives are the same, doing nothing.");
+        MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: source and target drives are the same, leaving with KErrAlreadyExists.");
         CleanupStack::PopAndDestroy( video ); // <-1
-        return;
+        User::Leave( KErrAlreadyExists );
         }
+    
+    GenerateTargetPathForMoveOrCopyL( iSourcePath, iTargetPath, aTargetDrive );
 
-    TBuf<KMaxPathLength> targetPath;
-    
-    GenerateTargetPathForMoveOrCopyL( sourcePath, targetPath, aTargetDrive );
-
-    MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: target path = %S", &targetPath );
+    MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: target path = %S", &iTargetPath );
     
     // update mds and cache
-    CMPXMedia* mediaForMoveOp = NULL;
-    CMPXMedia* mediaForCopyOp = NULL;
-    if ( aMove )
+    delete iMediaForMoveOp;
+    iMediaForMoveOp = NULL;
+    delete iMediaForCopyOp;
+    iMediaForCopyOp = NULL;
+
+    if ( iIsMoveOperation )
         {
         // Update existing media.
         // Create new media object with only KMPXMediaGeneralId, and KMPXMediaGeneralUri
         // attributes set, that way update is lighter operation.
-        mediaForMoveOp = CMPXMedia::NewL();
-        CleanupStack::PushL( mediaForMoveOp ); // 2->
-        mediaForMoveOp->SetTObjectValueL<TMPXItemId>( KMPXMediaGeneralId,
+        iMediaForMoveOp = CMPXMedia::NewL();
+        iMediaForMoveOp->SetTObjectValueL<TMPXItemId>( KMPXMediaGeneralId,
                video->ValueTObjectL<TMPXItemId>( KMPXMediaGeneralId ) );
-        mediaForMoveOp->SetTextValueL( KMPXMediaGeneralUri, targetPath );
+        iMediaForMoveOp->SetTextValueL( KMPXMediaGeneralUri, iTargetPath );
         
-        iCollection.SetVideoL( *mediaForMoveOp );
+        iCollection.SetVideoL( *iMediaForMoveOp );
         }
     else
         {
         // Create new media.
-        mediaForCopyOp = CMPXMedia::CopyL( *video );
-        CleanupStack::PushL( mediaForCopyOp ); // 2->
-        mediaForCopyOp->SetTextValueL( KMPXMediaGeneralUri, targetPath );
-        iCollection.AddVideoToMdsAndCacheL( *mediaForCopyOp );
+        iMediaForCopyOp = CMPXMedia::CopyL( *video );
+        iMediaForCopyOp->SetTextValueL( KMPXMediaGeneralUri, iTargetPath );
+        iCollection.AddVideoToMdsAndCacheL( *iMediaForCopyOp );
         }
-        
-    //copy file, delete original if move case
-    TRAPD( err, BaflUtils::EnsurePathExistsL( iCollection.iFs, targetPath ) );
-    
-    TUint att = 0;
-    iCollection.iFs.Att( sourcePath, att);    
-    if ( aMove && (att & KEntryAttReadOnly) )
-        {
-        MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: move operation and source file is read only -> skipping");
-        err = KErrAccessDenied;
-        }
-         
-    if ( err == KErrNone )
+ 
+     CleanupStack::PopAndDestroy( video ); // <-1           
+    }
+
+
+// ----------------------------------------------------------------------------
+// CVcxMyVideosAsyncFileOperations::HandleFileCopyCompletedL
+// ----------------------------------------------------------------------------
+//
+void CVcxMyVideosAsyncFileOperations::HandleFileCopyCompletedL( TInt aErr )
+    {
+    if ( aErr == KErrNone )
         {
-        MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: copying: %S", &sourcePath);
-        MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: to     : %S", &targetPath);
-        err = BaflUtils::CopyFile( iCollection.iFs, sourcePath, targetPath );
-        if ( err == KErrNone )
+        MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: Copy succeeded");
+        if ( iIsMoveOperation )
             {
-            MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: Copy succeeded");
-            if ( aMove )
+            MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: move case");
+            aErr = BaflUtils::DeleteFile( iCollection.iFs, iSourcePath );
+            if ( aErr != KErrNone )
                 {
-                MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: move case");
-                err = BaflUtils::DeleteFile( iCollection.iFs, sourcePath );
-                if ( err != KErrNone )
+                MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: delete for source file failed: %d", aErr );
+                MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: deleting target file");
+                TInt delErr = BaflUtils::DeleteFile( iCollection.iFs, iTargetPath );
+                if ( delErr != KErrNone )
                     {
-                    MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: delete for source file failed: %d", err );
-                    MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: deleting target file");
-                    TInt delErr = BaflUtils::DeleteFile( iCollection.iFs, targetPath );
-                    if ( delErr != KErrNone )
-                        {
-                        MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: delete for target file failed: %d", delErr );
-                        }
+                    MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: delete for target file failed: %d", delErr );
                     }
                 }
             }
-        else
-            {
-            MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: CopyFile failed: %d", err);
-            }
+        }
+    else
+        {
+        MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: CopyFile failed: %d", aErr);
         }
     
     // roll mds and cache back if file operations failed
-    if ( err != KErrNone )
+    if ( aErr != KErrNone )
         {
-        if ( aMove )
+        if ( iIsMoveOperation )
             {
-            MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: move failed %d", err );
+            MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: move failed %d", aErr );
             MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: setting media path back and leaving." );
-            mediaForMoveOp->SetTextValueL( KMPXMediaGeneralUri, sourcePath );
-            iCollection.SetVideoL( *mediaForMoveOp );
+            iMediaForMoveOp->SetTextValueL( KMPXMediaGeneralUri, iSourcePath );
+            iCollection.SetVideoL( *iMediaForMoveOp );
             }
         else
             {
-            MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: copy failed %d", err );
+            MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: copy failed %d", aErr );
             MPX_DEBUG1("CVcxMyVideosAsyncFileOperations:: deleting the added media object and leaving");
-            iCollection.iMyVideosMdsDb->RemoveVideo( mediaForCopyOp->ValueTObjectL<TMPXItemId>(
+            iCollection.iMyVideosMdsDb->RemoveVideo( iMediaForCopyOp->ValueTObjectL<TMPXItemId>(
                     KMPXMediaGeneralId ).iId1 );
             }
-        User::Leave( err );
         }
     
-    if ( aMove )
-        {
-        CleanupStack::PopAndDestroy( mediaForMoveOp ); // <-2
-        }
-    else
-        {
-        CleanupStack::PopAndDestroy( mediaForCopyOp ); // <-2
-        }
-    CleanupStack::PopAndDestroy( video ); // <-1
-    }    
+    delete iMediaForMoveOp;
+    iMediaForMoveOp = NULL;    
+    delete iMediaForCopyOp;
+    iMediaForCopyOp = NULL;
 
+    User::LeaveIfError( aErr );
+    
+    }
+    
 // ----------------------------------------------------------------------------
 // CVcxMyVideosAsyncFileOperations::DriveHasEnoughFreeSpaceL
 // ----------------------------------------------------------------------------
@@ -614,6 +661,8 @@
     {
     MPX_DEBUG2("CVcxMyVideosAsyncFileOperations:: source path = %S", &aSourcePath );
     
+    aTargetPath.Zero();
+    
     TChar targetDriveChar;
     User::LeaveIfError( iCollection.iFs.DriveToChar( aTargetDrive, targetDriveChar ) );    
     aTargetPath.Append( targetDriveChar );