GroupFileContainer.cs
7.68 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
using HslCommunication.Core;
using HslCommunication.LogNet;
using System;
using System.Collections.Generic;
using System.IO;
using System.Text;
namespace HslCommunication.Enthernet
{
/// <summary>
/// 文件集容器,绑定一个文件夹的文件信息组
/// </summary>
public class GroupFileContainer
{
#region Constructor
/// <summary>
/// 实例化一个新的数据管理容器
/// </summary>
/// <param name="logNet">日志记录对象,可以为空</param>
/// <param name="path">文件的路径</param>
public GroupFileContainer(ILogNet logNet, string path)
{
LogNet = logNet;
GroupFileContainerLoadByPath(path);
}
#endregion
#region Public Members
/// <summary>
/// 包含所有文件列表信息的json文本缓存
/// </summary>
public string JsonArrayContent
{
get { return m_JsonArrayContent; }
}
/// <summary>
/// 获取文件的数量
/// </summary>
public int FileCount
{
get { return m_filesCount; }
}
#endregion
#region Event Handle
private void OnFileCountChanged()
{
FileCountChanged?.Invoke(m_filesCount);
}
/// <summary>
/// 当文件数量发生变化的时候触发的事件
/// </summary>
public event Action<int> FileCountChanged;
#endregion
#region Upload Download Delete
/// <summary>
/// 下载文件时调用
/// </summary>
/// <param name="fileName">文件的实际名称</param>
/// <returns>文件名映射过去的实际的文件名字</returns>
public string GetCurrentFileMappingName(string fileName)
{
string source = Guid.NewGuid().ToString("N");
hybirdLock.Enter();
for (int i = 0; i < m_files.Count; i++)
{
if (m_files[i].FileName == fileName)
{
source = m_files[i].MappingName;
m_files[i].DownloadTimes++;
}
}
hybirdLock.Leave();
// 更新缓存
coordinatorCacheJsonArray.StartOperaterInfomation();
return source;
}
/// <summary>
/// 上传文件时掉用
/// </summary>
/// <param name="fileName">文件名,带后缀,不带任何的路径</param>
/// <param name="fileSize">文件的大小</param>
/// <param name="mappingName">文件映射名称</param>
/// <param name="owner">文件的拥有者</param>
/// <param name="description">文件的额外描述</param>
/// <returns>映射的文件名称</returns>
public string UpdateFileMappingName(string fileName, long fileSize, string mappingName, string owner, string description)
{
string source = string.Empty;
hybirdLock.Enter();
for (int i = 0; i < m_files.Count; i++)
{
if (m_files[i].FileName == fileName)
{
source = m_files[i].MappingName;
m_files[i].MappingName = mappingName;
m_files[i].Description = description;
m_files[i].FileSize = fileSize;
m_files[i].Owner = owner;
m_files[i].UploadTime = DateTime.Now;
break;
}
}
if (string.IsNullOrEmpty(source))
{
// 文件不存在
m_files.Add(new GroupFileItem()
{
FileName = fileName,
FileSize = fileSize,
DownloadTimes = 0,
Description = description,
Owner = owner,
MappingName = mappingName,
UploadTime = DateTime.Now
});
}
hybirdLock.Leave();
// 更新缓存
coordinatorCacheJsonArray.StartOperaterInfomation();
return source;
}
/// <summary>
/// 删除一个文件信息
/// </summary>
/// <param name="fileName">实际的文件名称</param>
/// <returns>映射之后的文件名</returns>
public string DeleteFile(string fileName)
{
string source = string.Empty;
hybirdLock.Enter();
for (int i = 0; i < m_files.Count; i++)
{
if (m_files[i].FileName == fileName)
{
source = m_files[i].MappingName;
m_files.RemoveAt(i);
break;
}
}
hybirdLock.Leave();
// 更新缓存
coordinatorCacheJsonArray.StartOperaterInfomation();
return source;
}
#endregion
#region Private Method
/// <summary>
/// 缓存JSON文本的方法,该机制使用乐观并发模型完成
/// </summary>
private void CacheJsonArrayContent()
{
hybirdLock.Enter();
m_filesCount = m_files.Count;
m_JsonArrayContent = Newtonsoft.Json.Linq.JArray.FromObject(m_files).ToString();
// 保存文件
using (StreamWriter sw = new StreamWriter(m_filePath + FileListResources, false, Encoding.UTF8))
{
sw.Write(m_JsonArrayContent);
}
hybirdLock.Leave();
// 通知更新
OnFileCountChanged();
}
/// <summary>
/// 从目录进行加载数据,必须实例化的时候加载,加载失败会导致系统异常,旧的文件丢失
/// </summary>
/// <param name="path"></param>
private void GroupFileContainerLoadByPath(string path)
{
m_filePath = path;
if (!Directory.Exists(m_filePath))
{
Directory.CreateDirectory(m_filePath);
}
if (File.Exists(m_filePath + FileListResources))
{
try
{
using (StreamReader sr = new StreamReader(m_filePath + FileListResources, Encoding.UTF8))
{
m_files = Newtonsoft.Json.Linq.JArray.Parse(sr.ReadToEnd()).ToObject<List<GroupFileItem>>();
}
}
catch (Exception ex)
{
LogNet?.WriteException("GroupFileContainer", "Load files txt failed,", ex);
}
}
if (m_files == null)
{
m_files = new List<GroupFileItem>();
}
coordinatorCacheJsonArray = new HslAsyncCoordinator(CacheJsonArrayContent);
CacheJsonArrayContent();
}
#endregion
#region Private Members
private const string FileListResources = "\\list.txt"; // 文件名
private ILogNet LogNet; // 日志对象
private string m_JsonArrayContent = "[]"; // 缓存数据
private int m_filesCount = 0; // 文件数量
private SimpleHybirdLock hybirdLock = new SimpleHybirdLock(); // 简单混合锁
private HslAsyncCoordinator coordinatorCacheJsonArray; // 乐观并发模型
private List<GroupFileItem> m_files; // 文件队列
private string m_filePath; // 文件路径
#endregion
}
}