Guest User

Untitled

a guest
Oct 8th, 2018
143
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 12.65 KB | None | 0 0
  1. using System;
  2. using System.Net;
  3. using System.IO;
  4. using System.Diagnostics;
  5.  
  6. namespace TinyWebDav
  7. {
  8. /// <summary>
  9. /// 簡易WebDAVクライアントクラス
  10. /// </summary>
  11. public class WebDavClient
  12. {
  13. #region "プライベートフィールド"
  14. private string userName;
  15. private string userPassword;
  16. private string baseUrl;
  17. #endregion
  18.  
  19.  
  20. #region"コンストラクタ"
  21. /// <summary>
  22. /// コンストラクタ
  23. /// </summary>
  24. /// <param name="userName">ユーザ名</param>
  25. /// <param name="userPassword">パスワード</param>
  26. /// <param name="baseUrl">ベースURL</param>
  27. public WebDavClient(string userName, string userPassword, string baseUrl)
  28. {
  29. if (string.IsNullOrEmpty(userName))
  30. {
  31. throw new AggregateException("ユーザ名が空です");
  32. }
  33. if (string.IsNullOrEmpty(baseUrl))
  34. {
  35. throw new AggregateException("ベースが空です");
  36. }
  37. this.userName = userName;
  38. this.userPassword = userPassword;
  39. this.baseUrl = baseUrl;
  40. }
  41. #endregion
  42.  
  43.  
  44. #region"ファイルアップロード"
  45. /// <summary>
  46. /// ファイルアップロード
  47. /// </summary>
  48. /// <param name="folderName">アップロード対象フォルダ</param>
  49. /// <param name="localPath">アップロード対象ファイルのローカルパス(フルパス)</param>
  50. /// <returns>HTTPレスポンスコード</returns>
  51. /// <remarks>アップロード後のファイル名はローカルにあるものと同じになる。同一ファイル名は上書きされる。</remarks>
  52. public HttpStatusCode UploadFile(string folderName, string localPath)
  53. {
  54. return UploadFile(folderName, localPath, Path.GetFileName(localPath));
  55. }
  56.  
  57. /// <summary>
  58. /// ファイルアップロード
  59. /// </summary>
  60. /// <param name="folderName">アップロード先のフォルダ名(ルートに置く場合は空で)</param>
  61. /// <param name="localPath">アップロード対象ファイルのローカルパス(フルパス)</param>
  62. /// <param name="uploadedFileName">アップロード後のファイル名</param>
  63. /// <returns>HTTPレスポンスコード</returns>
  64. /// <remarks>同一ファイル名は上書きされる。</remarks>
  65. public HttpStatusCode UploadFile(string folderName, string localPath, string uploadedFileName)
  66. {
  67. #region"引数チェック"
  68. if (!File.Exists(localPath))
  69. throw new FileNotFoundException(string.Format("指定されたファイル<{0}>が存在しません", localPath));
  70.  
  71. if (string.IsNullOrEmpty(uploadedFileName))
  72. throw new ArgumentException("アップロード後ファイル名が未指定です");
  73.  
  74. if (uploadedFileName.IndexOfAny(Path.GetInvalidFileNameChars()) > 0)
  75. throw new ArgumentException(string.Format("指定されたファイル名<{0}>に使用不可能な文字が含まれています", uploadedFileName));
  76. #endregion
  77.  
  78. try
  79. {
  80. // HttpWebRequestを初期化
  81. var req = httpWebRequestFactory(makeUrl(folderName, uploadedFileName));
  82. req.Method = WebRequestMethods.File.UploadFile;
  83.  
  84. // アップロードするファイルをオープン
  85. using (FileStream inSt = new FileStream(localPath, FileMode.Open))
  86. {
  87. //HttpWebRequestにサイズを設定
  88. req.ContentLength = inSt.Length;
  89.  
  90. // ファイルをバッファに読み込み・サーバーへ書き込み
  91. using (Stream outSt = req.GetRequestStream())
  92. {
  93. int bufSize = 1024*1024;
  94. byte[] buffer = new byte[bufSize];
  95. int bytesReaded = 0;
  96. while ((bytesReaded = inSt.Read(buffer, 0, bufSize)) > 0)
  97. {
  98. outSt.Write(buffer, 0, bytesReaded);
  99. }
  100. outSt.Flush();
  101. }
  102. }
  103.  
  104. // 結果取得
  105. using (HttpWebResponse res = (HttpWebResponse)req.GetResponse())
  106. {
  107. return res.StatusCode;
  108. }
  109. }
  110. catch (WebException we)
  111. {
  112. var errResponse = (HttpWebResponse)we.Response;
  113. Debug.WriteLine(errResponse.Headers.ToString());
  114. Debug.WriteLine("Status Code: {0}", errResponse.StatusCode);
  115. throw;
  116. }
  117. }
  118. #endregion
  119.  
  120. #region"フォルダ作成"
  121. /// <summary>
  122. /// フォルダ作成
  123. /// </summary>
  124. /// <param name="path">作成したいパス(ルート以下を全て記述)</param>
  125. /// <returns>
  126. /// </returns>
  127. /// <remarks>
  128. /// 上位のパスが存在しない場合、例外(409)が発生する。
  129. /// </remarks>
  130. public HttpStatusCode CreateFolder(string path)
  131. {
  132. #region"引数チェック"
  133. if (string.IsNullOrEmpty(path))
  134. throw new ArgumentException("引数pathはNullにはできません");
  135. #endregion
  136.  
  137. try
  138. {
  139. var req = httpWebRequestFactory(makeUrl(path));
  140. req.Method = WebRequestMethods.Http.MkCol;
  141. using (HttpWebResponse res = (HttpWebResponse)req.GetResponse())
  142. {
  143. return res.StatusCode;
  144. }
  145. }
  146. catch (WebException we)
  147. {
  148. var errResponse = (HttpWebResponse)we.Response;
  149. Debug.WriteLine(errResponse.Headers.ToString());
  150. Debug.WriteLine("Status Code: {0}", errResponse.StatusCode);
  151. throw;
  152. }
  153.  
  154. }
  155. #endregion
  156.  
  157. #region "存在チェック"
  158. /// <summary>
  159. /// パスが存在するかチェック
  160. /// </summary>
  161. /// <param name="folerName"></param>
  162. /// <param name="fileName"></param>
  163. /// <returns></returns>
  164. public bool Exists(string folerName, string fileName)
  165. {
  166. var req = httpWebRequestFactory(makeUrl(folerName,fileName));
  167. req.Method = WebRequestMethods.Http.Head;
  168.  
  169. HttpWebResponse res;
  170. try
  171. {
  172. using (res = (HttpWebResponse)req.GetResponse())
  173. {
  174. switch (res.StatusCode)
  175. {
  176. case HttpStatusCode.OK:
  177. // このあたりは多分OK。
  178. return true;
  179. default:
  180. Debug.WriteLine(res.Headers.ToString());
  181. Debug.WriteLine("Status Code: {0}", res.StatusCode);
  182. return false;
  183. }
  184. }
  185. }
  186. catch (WebException we)
  187. {
  188. var errResponse = (HttpWebResponse)we.Response;
  189. switch (errResponse.StatusCode)
  190. {
  191. case HttpStatusCode.Forbidden:
  192. // 403だけど帰ってきてるので、存在はしている(と思われる)
  193. return true;
  194. case HttpStatusCode.NotFound:
  195. // 404なので、これは無い。
  196. return false;
  197. default:
  198. // 他はとりあえずthrowする。
  199. Debug.WriteLine(errResponse.Headers.ToString());
  200. Debug.WriteLine("Status Code: {0}", errResponse.StatusCode);
  201. throw;
  202. }
  203. }
  204. }
  205.  
  206. /// <summary>
  207. /// パス(ルート以下)が存在するかチェック
  208. /// </summary>
  209. /// <param name="path">ルート以下のパス</param>
  210. /// <returns></returns>
  211. public bool Exists(string path)
  212. {
  213. var req = httpWebRequestFactory(makeUrl(path));
  214. req.Method = WebRequestMethods.Http.Head;
  215.  
  216. HttpWebResponse res;
  217. try
  218. {
  219. using (res = (HttpWebResponse)req.GetResponse())
  220. {
  221. switch (res.StatusCode)
  222. {
  223. case HttpStatusCode.OK:
  224. // このあたりは多分OK。
  225. return true;
  226. default:
  227. Debug.WriteLine(res.Headers.ToString());
  228. Debug.WriteLine("Status Code: {0}", res.StatusCode);
  229. return false;
  230. }
  231. }
  232. }
  233. catch (WebException we)
  234. {
  235. var errResponse = (HttpWebResponse)we.Response;
  236. switch (errResponse.StatusCode)
  237. {
  238. case HttpStatusCode.Forbidden:
  239. // 403だけど帰ってきてるので、存在はしている(と思われる)
  240. return true;
  241. case HttpStatusCode.NotFound:
  242. // 404なので、これは無い。
  243. return false;
  244. default:
  245. // 他はとりあえずthrowする。
  246. Debug.WriteLine(errResponse.Headers.ToString());
  247. Debug.WriteLine("Status Code: {0}", errResponse.StatusCode);
  248. throw;
  249. }
  250. }
  251. }
  252. #endregion
  253.  
  254.  
  255. #region"ヘルパ"
  256. /// <summary>
  257. /// HttpWebRequestファクトリー
  258. /// </summary>
  259. /// <param name="url"></param>
  260. /// <returns></returns>
  261. private HttpWebRequest httpWebRequestFactory(string url)
  262. {
  263. HttpWebRequest req = (HttpWebRequest)HttpWebRequest.Create(url);
  264. req.Credentials = new NetworkCredential(userName, userPassword);
  265. return req;
  266. }
  267.  
  268.  
  269. /// <summary>
  270. /// リクエスト用のURL作成
  271. /// </summary>
  272. /// <param name="folderName"></param>
  273. /// <param name="fileName"></param>
  274. /// <returns></returns>
  275. private string makeUrl(string folderName , string fileName)
  276. {
  277. return this.baseUrl.TrimEnd("/".ToCharArray()) + "/" + folderNameNormalizer(folderName) + fileNameNormalizer(fileName);
  278. }
  279.  
  280. /// <summary>
  281. /// リクエスト用のURL作成
  282. /// </summary>
  283. /// <param name="folderName"></param>
  284. /// <returns></returns>
  285. private string makeUrl(string path)
  286. {
  287. return this.baseUrl.TrimEnd("/".ToCharArray()) + "/" + pathNormalizer(path);
  288. }
  289.  
  290.  
  291. /// <summary>
  292. /// フォルダ名URL正規化
  293. /// </summary>
  294. /// <param name="folderName"></param>
  295. /// <returns>
  296. /// 正規化された、URL用のフォルダ名(先頭のスラッシュ無し、末尾にスラッシュあり)
  297. /// ただし、空文字列の場合はスラッシュ無。
  298. /// </returns>
  299. private string folderNameNormalizer(string folderName)
  300. {
  301. if (string.IsNullOrEmpty(folderName))
  302. {
  303. return "";
  304. }
  305. else
  306. {
  307. return folderName.TrimEnd("/".ToCharArray()).TrimStart("/".ToCharArray()) + "/";
  308. }
  309. }
  310.  
  311. /// <summary>
  312. /// ファイル名URL正規化
  313. /// </summary>
  314. /// <param name="fileName"></param>
  315. /// <returns>
  316. /// 正規化された、URL用のファイル名(先頭のスラッシュ無し)
  317. /// </returns>
  318. private string fileNameNormalizer(string fileName)
  319. {
  320. return fileName.TrimStart("/".ToCharArray());
  321. }
  322.  
  323. /// <summary>
  324. /// パス(ルート以下)の正規化
  325. /// </summary>
  326. /// <param name="path">パス(ルート以下)</param>
  327. /// <returns>
  328. /// 正規化された、URL用のパス名(先頭のスラッシュ無し)
  329. /// 末尾にもスラッシュは付与しない(ファイル名のケースを考慮)
  330. /// </returns>
  331. private string pathNormalizer(string path)
  332. {
  333. return path.TrimStart("/".ToCharArray());
  334. }
  335. #endregion
  336. }
  337. }
Add Comment
Please, Sign In to add comment