質問: new StreamWriter(fsw)) { sw.WriteLine(string.Join(",", snInfo)); } } catch { //エラー通知 } } ``` ファイル書き換えのメソッドです。 まず、書き換える前の状態を知るために一度書き換えるファイルを読み込み、配列に入れます。 そして引数をもとに、配列の中身を変更し、書き換えを行っています。 usingでストリームを閉じているはずなのですが、読込み時にエラーが発生する場合があります。 しかし、エラーが発生しない場合もあります。 問題2 ファイルの書き換えを複数のPCから同時に行う ↓ 別のプロセスが使用中とエラーが発生する。 こちらは先ほどの書き込みメソッドのCatch部分に”他の端末から操作している可能性があります。”とメッセージを表示しているのですが、できれば他の端末の処理が終わるまで自動で待ち、ファイルのアクセスが可能になった時点で操作を反映させたいと思っています。(ユーザーからそうして欲しいと依頼があったため) **自分でやってみた解決策** 問題1に対して。。。 おそらく、FileSystemWatcherが反応した時点で書き込みのストリームが閉じられていないので、イベントが発生した時点でスレッドを50ミリ秒止めています。 こうすることでエラーは発生しなくなりました。 しかし、本当に書き込みのストリームが閉じられていないのが原因か分からない状況です。 問題2に対して。。。 書込みメソッドのcatchの部分でもう一度書き込みメソッドを呼び出し、成功するまで永久ループをさせています。 しかし、これではかなり危険だと思っていて何か他の方法がないかと探しています。 ここでデータベースを用いることで排他制御ができるのではないかと思い、修正前の質問に至ります。 データベース排他制御を使うことで問題2が解決できるのではないかと考えていますが、ファイルの情報量がかなり少ないですし、採用するほどのものなのかがわかりません。 また、データベースにしてしまうと、ファイル監視ができなくなるのではないかと思い悩んでいます。 この2つの問題を解決するにはどのような作りをすると良いと思いますか? 皆様のご意見を参考にいろいろ試したいと思っています。よろしくお願いします。
回答: 問題1についてですが、そもそも、以下のコードのcsvファイル書込時のFileStreamコンストラクタの第4引数は正しいのでしょうか? ``` //変更した値をcsvファイルに書込 using (FileStream fsw = new FileStream(filePath, FileMode.Create, FileAccess.Write, FileShare.Write)) ``` FileShare.Writeだと、このファイルへの他からの書き込みは許可するが、読取は許可しないことになりますので、FileShare.Readにして読取を許可した方が良いのではないでしょうか? これであれば、FileSystemWatcherのイベントが発生した時点では、読取は許可されているので、例外の発生なく、読取モードで変更後の内容を得られるかも知れません。 また、問題2については、私ならタイマーを使用してリトライさせます。 例外発生したら、タイマーをセットして、タイマーTickでリトライ。 安全のため、何回かリトライしてもダメだったらメッセージを出して中断する、という感じです。 タイマーのインターバルが1秒くらいがいいのか、0.5秒くらいがいいのか、は実用的な程度にすればよいと思います。