Statistics
| Branch: | Revision:

root / trunk / Pithos.Core / Agents / FileInfoExtensions.cs @ cfed7823

History | View | Annotate | Download (4 kB)

1
using System;
2
using System.Collections.Generic;
3
using System.Diagnostics.Contracts;
4
using System.Linq;
5
using System.Text;
6
using System.IO;
7
using System.Text.RegularExpressions;
8
using System.Threading.Tasks;
9
using Pithos.Network;
10

    
11
namespace Pithos.Core.Agents
12
{
13
    static class FileInfoExtensions
14
    {
15
        public static  string AsRelativeTo(this FileInfo fileInfo,string path )
16
        {
17
            if (String.IsNullOrWhiteSpace(path))
18
                throw new ArgumentNullException("path");            
19
            Contract.EndContractBlock();
20
            
21

    
22
            if (!path.EndsWith("\\"))
23
                path=path.ToLower() + "\\";
24
            int pathLength = path.Length;            
25
            
26
            var filePath = fileInfo.FullName;
27

    
28
            if (!filePath.StartsWith(path,StringComparison.InvariantCultureIgnoreCase))
29
                throw new ArgumentException(String.Format("The path {0} doesn't contain the file {1}",path,filePath));
30
            
31
            var relativePath = filePath.Substring(pathLength, filePath.Length - pathLength);
32

    
33
            return relativePath;
34
        }
35

    
36
        public static string AsRelativeUrlTo(this FileInfo fileInfo,string path )
37
        {
38
            if (String.IsNullOrWhiteSpace(path))
39
                throw new ArgumentNullException("path");
40
            Contract.EndContractBlock();
41

    
42
            var relativePath = fileInfo.AsRelativeTo(path);
43
            var replacedSlashes = relativePath.Replace("\\","/");
44
            var escaped = Uri.EscapeUriString(replacedSlashes);
45
            return escaped;
46
        }
47

    
48
        public static string RelativeUriToFilePath(this Uri uri)
49
        {
50
            var unescaped = Uri.UnescapeDataString(uri.ToString());
51
            var path = unescaped.Replace("/", "\\");
52
            return path;
53
        }
54

    
55

    
56
        public static int Read(this FileInfo fileInfo,byte[] buffer,int offset,int count)
57
        {            
58
            //Open the stream only long enough to read a block
59
            using (var stream = fileInfo.OpenRead())
60
            {
61
                stream.Seek(offset, SeekOrigin.Begin);
62
                return  stream.Read(buffer, 0, count);                
63
            }
64
        }
65

    
66
        public static Task<int> ReadAsync(this FileInfo fileInfo, byte[] buffer, int offset, int count)
67
        {
68
            //The using statement is not used because we will work asyncronously
69
            var stream = FileAsync.OpenRead(fileInfo.FullName);
70
            try
71
            {
72
                stream.Seek(offset, SeekOrigin.Begin);
73
                var read = stream.ReadAsync(buffer, offset, count);
74
                return read.ContinueWith(t =>
75
                {
76
                    //Make sure the stream closes
77
                    stream.Close();
78
                    stream = null;
79
                    
80
                    t.PropagateExceptions();
81

    
82
                    return t.Result;
83
                });
84
            }
85
            catch (Exception)
86
            {
87
                //In case of error make sure we close the stream                
88
                //The stream may have been 
89
                if (stream!=null)
90
                    stream.Close();
91
                throw;
92
            }
93

    
94
        }
95

    
96
        public static string CalculateHash(this FileInfo info,int blockSize,string algorithm)
97
        {
98
            if (info==null)
99
                throw new ArgumentNullException("info");
100
            if (String.IsNullOrWhiteSpace(info.FullName))
101
                throw new ArgumentException("info");
102
            if (blockSize<=0)
103
                throw new ArgumentOutOfRangeException("blockSize",blockSize,"blockSize must be greater than 0");
104
            if (String.IsNullOrWhiteSpace(algorithm))
105
                throw new ArgumentNullException("algorithm");
106
            Contract.EndContractBlock();
107

    
108
            if (info.Length <= blockSize)
109
                return Signature.CalculateMD5(info.FullName);
110
            else
111
                return Signature.CalculateTreeHash(info.FullName, blockSize, algorithm).TopHash.ToHashString();
112

    
113
        }
114

    
115
    }
116
}