Beispiel #1
0
 /// <summary>
 /// Remove the specified download.
 /// </summary>
 private void RemoveDownload(KfsFileDownload f)
 {
     InodeTree.Remove(f.Version.Inode);
     OrderTree.Remove(f.OrderID);
     if (DoneTree.ContainsKey(f.OrderID)) DoneTree.Remove(f.OrderID);
     Share.UnregisterFileTransfer(f);
 }
Beispiel #2
0
 /// <summary>
 /// Add the file download to the list of errors, unless 'reason' is null.
 /// </summary>
 public void ReportError(String reason, KfsFileDownload f)
 {
     if (reason != null)
     {
         f.Error = new KfsTransferError(TransferErrorType.Download, f, reason);
         Share.OnTransferError(f.Error);
     }
 }
Beispiel #3
0
        /// <summary>
        /// Move a file in the share.
        /// </summary>
        public void MoveDownloadedFile(KfsFileDownload f)
        {
            try
            {
                // Get the corresponding server file.
                KfsServerFile s = Share.ServerView.GetObjectByInode(f.Version.Inode) as KfsServerFile;

                // The file has been deleted on the server.
                if (s == null) throw new Exception("cannot open file, it has been deleted on the server");

                // Update the local status and check whether the move is safe.
                s.UpdateLocalStatus();

                if (s.CurrentLocalStatus == LocalStatus.Error)
                    throw new Exception("cannot open file: " + s.LocalError);

                if (s.CurrentLocalStatus == LocalStatus.Modified)
                    throw new Exception("cannot update file: local copy has been modified");

                // Create the missing parent directories, if possible.
                Share.AddMissingLocalDirectories(s.Parent.RelativePath);

                // Move the file at its proper location.
                if (File.Exists(s.FullPath))
                    File.SetAttributes(s.FullPath, FileAttributes.Normal);

                if (new FileInfo(f.CachePath).Length < 10 * 1024 * 1024)
                    File.Copy(f.CachePath, s.FullPath, true);
                else if (!Misc.CopyFile(f.CachePath, s.FullPath, false, true, false, true, true))
                    throw new Exception("Unable to copy " + s.Name);

                // Update the downloaded version.
                s.UpdateDownloadVersion(f.Version, true);

                // Update the local status of the downloaded file.
                s.UpdateLocalStatus();

                // Open the file for the user.
                if (f.OpenWhenDownloadedFlag)
                    Misc.OpenFileInWorkerThread(s.FullPath);
            }

            catch (Exception ex)
            {
                ReportError(ex.Message, f);
            }

            finally
            {
                RemoveDownload(f);
            }
        }
Beispiel #4
0
        /// <summary>
        /// Queue the download of the specified file version. The method checks
        /// if the file is already being downloaded. If the file has already been
        /// downloaded, the file is added to the DoneTree immediately.
        /// </summary>
        public void QueueDownload(KfsServerFileVersion version, bool openFlag)
        {
            // The download is already queued.
            if (InodeTree.ContainsKey(version.Inode))
            {
                if (openFlag) InodeTree[version.Inode].OpenWhenDownloadedFlag = true;
                return;
            }

            // Queue the file download.
            UInt64 orderID = Share.TransferOrderID++;
            String relPath = Share.ServerView.GetObjectByInode(version.Inode).RelativePath;
            KfsFileDownload f = new KfsFileDownload(Share, orderID, relPath, version, openFlag);
            InodeTree[f.Version.Inode] = f;
            OrderTree[f.OrderID] = f;
            Share.RegisterFileTransfer(f);

            // The file is already in the cache.
            if (HasFullVersion(version))
            {
                f.Status = FileTransferStatus.Batched;
                OnFileDownloadCompleted(f.OrderID);
            }

            // The file is empty. Create it immediately.
            else if (version.Size == 0)
            {
                Directory.CreateDirectory(Share.CacheDirPath);

                File.Create(VersionCachePath(version)).Close();
                f.Status = FileTransferStatus.Batched;
                OnFileDownloadCompleted(f.OrderID);
            }
        }
Beispiel #5
0
        /// <summary>
        /// Move a file in the share.
        /// </summary>
        public void MoveDownloadedFile(KfsFileDownload f)
        {
            try
            {
                // Get the corresponding server file.
                KfsServerFile s = Share.ServerView.GetObjectByInode(f.Version.Inode) as KfsServerFile;

                // The file has been deleted on the server.
                if (s == null) throw new Exception("cannot open file, it has been deleted on the server");

                // Update the local status and check whether the move is safe.
                s.UpdateLocalStatus();

                if (s.CurrentLocalStatus == LocalStatus.Error)
                    throw new Exception("cannot open file: " + s.LocalError);

                if (s.CurrentLocalStatus == LocalStatus.Modified)
                    throw new Exception("cannot update file: local copy has been modified");

                // Create the missing parent directories, if possible.
                Share.AddMissingLocalDirectories(s.Parent.RelativePath);

                // Get the file information.
                UInt64 observedID, observedSize;
                DateTime observedDate;
                FileStream stream = null;

                try
                {
                    stream = new FileStream(f.CachePath, FileMode.Open, FileAccess.Read);
                    KfsPath.GetLowLevelFileInfo(stream, out observedID, out observedSize, out observedDate);
                }

                finally
                {
                    if (stream != null) stream.Close();
                }

                // Move the file at its proper location.
                File.Delete(s.FullPath);
                File.Move(f.CachePath, s.FullPath);

                // Update the downloaded version and the persistent status.
                s.UpdateDownloadVersion(f.Version, true);
                s.UpdatePersistentStatus(LocalStatus.Unmodified, observedDate, observedID, observedSize, f.Version.Hash);

                // Open the file for the user.
                if (f.OpenWhenDownloadedFlag)
                    Misc.OpenFileInWorkerThread(s.FullPath);
            }

            catch (Exception ex)
            {
                ReportError(ex.Message, f);
            }

            finally
            {
                RemoveDownload(f);
            }
        }