c# service renaming files! - c#

I have a windows service , that takes files with metadata(FIDEF) and corresponding video file and , translates the XML(FIDEF) using XSLT .
I get the file directory listing for FIDEF's and if a video file of the same name exists it translates it. That works ok , but it is on a timer to search every minute. I am trying to handle situations where the same file name enters the input directory but is already in the output directory. I just have it changing the output name to (copy) thus if another file enters i should get (copy)(copy).mov but the service won't start with filenames of the same directory already in the output , it works once and then does not seem to pick up any new files.
Any Help would be great as I have tried a few things with no good results. I believe its the renaming methods, but I've put most of the code up in case its a clean up issue or something else.
(forgive some of the names just trying different things).
private void getFileList()
{
//Get FILE LIST FROM Directory
try
{
// Process Each String/File In Directory
string result;
//string filename;
filepaths = null;
filepaths = Directory.GetFiles(path, Filetype);
foreach (string s in filepaths)
{
for (int i = 0; i < filepaths.Length; i++)
{
//Result Returns Video Name
result = Path.GetFileNameWithoutExtension(filepaths[i]);
FileInfo f = new FileInfo(filepaths[i]);
PreformTranslation(f, outputPath + result , result);
}
}
}
catch (Exception e)
{
EventLog.WriteEntry("Error " + e);
}
}
private void MoveVideoFiles(String Input, String Output)
{
File.Move(Input, Output);
}
private string GetUniqueName(string name)
{
//Original Filename
String ValidName = name;
//remove FIDEF from filename
String Justname1 = Path.GetFileNameWithoutExtension(name);
//get .mov extension
String Extension2 = Path.GetExtension(Justname1);
//get filename with NO extensions
String Justname = Path.GetFileNameWithoutExtension(Justname1);
//get .Fidef
String Extension = Path.GetExtension(name);
int cnt = 0;
//string[] FileName = Justname.Split('(');
//string Name = FileName[0];
while (File.Exists(ValidName)==true)
{
ValidName = outputPath + Justname + "(Copy)" + Extension2 + Extension;
cnt++;
}
return ValidName;
}
private string getMovFile(string name)
{
String ValidName = name;
String Ext = Path.GetExtension(name);
String JustName = Path.GetFileNameWithoutExtension(name);
while(File.Exists(ValidName))
{
ValidName = outputPath + JustName + "(Copy)" + Ext;
}
return ValidName;
}
//Preforms the translation requires XSL & FIDEF name.
private void PreformTranslation(FileInfo FileName, String OutputFileName , String result)
{
string FidefName = OutputFileName + ".FIDEF";
String CopyName;
String copyVidName = outputPath + result;
XslCompiledTransform myXslTransform;
myXslTransform = new XslCompiledTransform();
try
{
myXslTransform.Load(XSLname);
}
catch
{
EventLog.WriteEntry("Error in loading XSL");
}
try
{ //only process FIDEF's with corresponding Video file
if (AllFidef == "no")
{
//Check if video exists if yes,
if (File.Exists(path + result))
{
//Check for FIDEF File Already Existing in the Output Directory.
if (File.Exists(FidefName))
{
//Get unique name
CopyName = GetUniqueName(FidefName);
copyVidName= getMovFile(copyVidName);
//Translate and create new FIDEF.
//double checking the file is here
if (File.Exists(outputPath + result))
{
myXslTransform.Transform(FileName.ToString(), CopyName);
File.Delete(FileName.ToString());
MoveVideoFiles(path + result, copyVidName);
}
////Move Video file with Corresponding Name.
}
else
{ //If no duplicate file exsists in Directory just move.
myXslTransform.Transform(FileName.ToString(), OutputFileName + ".FIDEF");
MoveVideoFiles(path + result, outputPath + result);
}
}
}
else
{
//Must have FIDEF extension
//Processes All FIDEFS and moves any video files if found.
myXslTransform.Transform(FileName.ToString(), OutputFileName + ".FIDEF");
if (File.Exists(path + result))
{
MoveVideoFiles(path + result, outputPath + result);
}
}
}
catch (Exception e)
{
EventLog.WriteEntry("Error Transforming " + "FILENAME = " + FileName.ToString()
+ " OUTPUT_FILENAME = " + OutputFileName + "\r\n" +"\r\n"+ e);
}
}

There is a lot wrong with your code. getFileList has the unneeded inner for loop for starters. Get rid of it. Your foreach loop has s, which can replace filepaths[i] from your for loop. Also, don't do outputPath + result to make file paths. Use Path.Combine(outputPath, result) instead, since Path.Combine handles directory characters for you. Also, you need to come up with a better name for getFileList, since that is not what the method does at all. Do not make your method names liars.
I would simply get rid of MoveVideoFiles. The compiler just might too.
GetUniqueName only works if your file name is of the form name.mov.fidef, which I'm assuming it is. You really need better variable names though, otherwise it will be a maintenance nightware later on. I would get rid of the == true in the while loop condition, but that is optional. The assignment inside the while is why your files get overwritten. You always generate the same name (something(Copy).mov.fidef), and as far as I can see, if the file exists, I think you blow the stack looping forever. You need to fix that loop to generate a new name (and don't forget Path.Combine). Maybe something like this (note this is untested):
int copyCount = 0;
while (File.Exists(ValidName))
{
const string CopyName = "(Copy)";
string copyString = copyCount == 0 ? CopyName : (CopyName + "(" + copyCount + ")");
string tempName = Justname + copyString + Extension2 + Extension;
ValidName = Path.Combine(outputPath, tempName);
copyCount++;
}
This generates something(Copy).mov.fidef for the first copy, something(Copy)(2).mov.fidef for the second, and so on. Maybe not what you want, but you can make adjustments.
At this point you have a lot to do. getMovFile looks as though it could use work in the same manner as GetUniqueName. You'll figure it out. Good luck.

Related

Moving files using SSIS and Script Component

I need to write a code in script component in SSIS that will move files to corresponding folders. Files that I'm getting are usually named, for example "Dem323_04265.45.23.4", "Dem65_459.452.56", "Ec2345_456.156.7894" and I need to move them to a corresponding folders. The name of my folders are "Oklahoma City (323)", "New York(65)".. I need to move those files to matching folders, so for example "Dem323_04265.45.23.4" would go to folder "Oklahoma City (323)". I need to modify my code so the number that is located between first two or three letter and underline matches number located in parenthesis. I've been working on this for several days already and I'm new with ssis and c#, so any help would be appreciated. This is the code I have so far:
public void Main()
{
string filename;
// string datepart;
bool FolderExistFlg;
filename = Dts.Variables["User::FileName"].Value.ToString();
// datepart = (filename.Substring(filename.Length - 12)).Substring(0, 8);
var folderNumber = Regex.Match(
filename,
//Dts.Variables["OutputMainFolder"].Value.ToString(),
#"\(([^)]*)\)").Groups[1].Value;
FolderExistFlg = Directory.Exists(Dts.Variables["OutputMainFolder"].Value.ToString() + "\\" + folderNumber);
if (!FolderExistFlg)
{
Directory.CreateDirectory(Dts.Variables["OutputMainFolder"].Value.ToString() + "\\" + folderNumber);
}
File.Move(Dts.Variables["SourceFolder"].Value.ToString() + "\\" + filename + "\\" + folderNumber,
Dts.Variables["OutputMainFolder"].Value.ToString() + "\\" + filename);
Dts.TaskResult = (int)ScriptResults.Success;
}
#region ScriptResults declaration
enum ScriptResults
{
Success = Microsoft.SqlServer.Dts.Runtime.DTSExecResult.Success,
Failure = Microsoft.SqlServer.Dts.Runtime.DTSExecResult.Failure
};
#endregion
}
}
Here you go, the below snippet would move the files as per the match criteria. You need to take care of the source input as per your configuration.
string filePath = #"C:\Packages\StackOverflow";
//string fileName = string.Empty;
//get list of files
string[] filePaths = Directory.GetFiles(filePath);
//get list of folders
string[] dirPaths = Directory.GetDirectories(filePath);
//loop through the files and move them
foreach(string fileNames in filePaths)
{
string[] pathArr = fileNames.Split('\\');
string fileName = pathArr.Last().ToString();
int index = fileName.IndexOf('_');
string fileNamePart = fileName.Substring(0, index);
//get the first numeric part of the filename to perform the match
var fileNameNumPart = Regex.Replace(fileNamePart, "[^0-9]", "");
//find related directory
var dirMatch = dirPaths.FirstOrDefault(stringToCheck => stringToCheck.Contains(fileNameNumPart.ToString()));
if (dirMatch != null)
{
// move would fail if file already exists in destination
if (!File.Exists(dirMatch + '\\' + fileName))
{
File.Move(fileNames, dirMatch + '\\' + fileName);
}
}
}

FileUpload if exist concat (counter) to the name [duplicate]

This question already has answers here:
FileUpload - if file name exist concat a number between parentheses at the end of name
(3 answers)
Closed 5 years ago.
I have a fileupload control, What I want to achieve is to concat a nuber to it, in order it to be unique.
All the posts that I found are talking about adding a GUID or DateTime
What i want to achieve is if the file exist in folder then the file name will be filename + (counter)
Example:
The folder contain a file name- file.png
1) When I upload the same file name again, the existing one wont get delete and the new one will be called file(1).png.
2) When I upload the same file name again, (file.png)
now the new file will be called file(2)
I have this code which handle the 1'st case but not the second:
public static string GetUniqueName(string fileName)
{
string dir = Globals.Directories.GetCustomCategoryThumbnailDir();
string fileExtension = Path.GetExtension(fileName);
string fileNameWE = Path.GetFileNameWithoutExtension(fileName);
string[] files = Directory.GetFiles(dir, "*" + fileExtension)
.Select(Path.GetFileName)
.ToArray();
string uniqueName = fileNameWE;
int nextNum = 0;
bool fileExist = false;
string pattern = #"(.*)\(([\d]+)\)";
foreach (var file in files)
{
var tempFileName = Path.GetFileNameWithoutExtension(file);
var match = Regex.Match(tempFileName, pattern);
if (tempFileName.Equals(fileNameWE))
{
// file exist in folder
fileExist = true;
}
if (tempFileName.StartsWith(fileNameWE) && match.Success)
{
// there is a file name that start with "fileToUpload" name, we want to to take the number
nextNum = Convert.ToInt32(match.Groups[2].Value);
nextNum++;
}
}
if (nextNum == 0 && !fileExist)
{
// filename dont exist
return fileNameWE + fileExtension;
}
if (nextNum == 0 && fileExist)
{
// the file name exist without (1)
fileNameWE = $"{fileNameWE}(1)";
return fileNameWE + fileExtension;
}
else
{
var haveParentessis = Regex.Match(fileNameWE, pattern);
if (haveParentessis.Success)
{
// we need to reset the nextNum
nextNum = 1;
}
// return the new unique name with suffix
fileNameWE = string.Format("{0}({1})", fileNameWE, nextNum);
return fileNameWE + fileExtension;
}
}
How can I achieve that?
Yeah, that's cause your while loop as pointed below is local to the function and thus the counter variable which is also a local variable won't be maintained it's current value. So in essence every request you get a new page instance and thus your counter will get re-initialized to 0
while (File.Exists(Path.Combine(dir, fileNameWE + fileExtension)))
{
fileNameWE = fileNameWE + "(" + counter.ToString() + ")";
counter++;
}
To get this done, you should store the counter variable in Session and retrieve it back. Don't forget it's an web application and thus the state won't be maintained unless you do it explicitly
if (File.Exists(Path.Combine(dir, fileNameWE + fileExtension)))
{
counter = (Session["counter"] != null) ? ((int)Session["counter"])++ : default(int);
fileNameWE = fileNameWE + "(" + counter.ToString() + ")";
Session["counter"] = counter;
}
I got this to work by using regular expressions, below. No persistent counter is required. I think the concat problem is because there's nothing done to deal with the existing (1) suffix. I coded this potential solution and hope it helps! NB: only lightly tested in debugger, and I am a novice
{
string fileName = #"C:\Uploads\Testfile.bin";
string fileExtension = Path.GetExtension(fileName);
string fileNameWE = Path.GetFileNameWithoutExtension(fileName);
string pattern = #"(.*)\(([\d]+)\)$";
var match = Regex.Match(fileNameWE, pattern);
if (match.Success)
{
int nextNum = Convert.ToInt32(match.Groups[2].Value);
nextNum++;
fileNameWE = $"{match.Groups[1].Value}({nextNum})";
}
else
{
fileNameWE = $"{fileNameWE}(1)";
}
}

Versioning file name and saving it to different location

After the else block Path.Combine method combines every part and gives the file name when Console.WriteLine(result); is used. But it doesn't actually create the file with that name.
I want to get the EmployeeDetails.txt file, make a version of it (i.e. renaming the filename) and saves it to C:\Hitory folder.
How to achieve that?
Using File.Move throws FileNotFoundexception
void ModRec()
{
string filename = #"C:\Current\EmployeeDetails.txt";
string current = #"C:\Current\";
string history = #"C:\History\";
FileInfo fileinfo = new FileInfo(filename);
if (fileinfo.Exists)
{
if (!Directory.Exists(history))
{
Directory.CreateDirectory(history);
}
}
else
{
Console.WriteLine("\t\t\tFile doesn't exist!");
Console.ReadLine();
Menu1();
}
var extension = Path.GetExtension(filename);
var fileNamePart = Path.GetFileNameWithoutExtension(filename);
var path = Path.GetDirectoryName(filename);
var version = 0;
string result;
do
{
version++;
result = Path.Combine(path, fileNamePart + "_" + version + extension);
}
while (File.Exists(result));
//File.Move(current, history);
}
Your loop at the end needs to change slightly, because
result = Path.Combine(path, fileNamePart + "_" + version + extension);
is looking in the directory where the file already is, rather than in the history directory where you want it to be, so you'll be scanning for duplicates in the wrong location. The Path.Combine therefore needs to reference the value of history:
result = Path.Combine(history, fileNamePart + "_" + version + extension);
Secondly, you cannot use Move to move a file to a directory in the same way that you can from the command line, you need to specify the two parameters as filenames, so
File.Move(current, history);
becomes
File.Move(filename, result);
The resulting code at the end of your method should therefore look like this:
do
{
version++;
result = Path.Combine(history, fileNamePart + "_" + version + extension);
}
while (File.Exists(result));
File.Move(filename, result);
Incidentally, where you test whether the file already exists, you simply call Menu1 and then carry on. Can you guarantee that that will ensure that the next thing that the user does will create a valid file? I'm guessing that it most likely cannot guarantee that, so you should exit your method at that point, or perhaps put the remainder of the body inside the fileinfo.Exists block.
That leaves the desirability of invoking a menu from inside this method, but that's a design question outside of the scope of what you've asked here.
Try this instead:
void ModRec()
{
string filename = #"C:\Current\EmployeeDetails.txt";
string current = #"C:\Current\";
string history = #"C:\History\";
FileInfo fileinfo = new FileInfo(filename);
if (fileinfo.Exists)
{
if (!Directory.Exists(history))
{
Directory.CreateDirectory(history);
}
}
else
{
Console.WriteLine("\t\t\tFile doesn't exist!");
Console.ReadLine();
Menu1();
}
var extension = Path.GetExtension(filename);
var fileNamePart = Path.GetFileNameWithoutExtension(filename);
var path = Path.GetDirectoryName(filename);
var version = 0;
string result;
do
{
version++;
result = Path.Combine(history, fileNamePart + "_" + version + extension);
}
while (File.Exists(result));
File.Move(filename, result);
}
Path.Combine() does not touch filesystem at all. No files/folders would be ever crated.
Try File.Move(filename, history);. That is, instead of current, which is a directory, move the file (assuming filename is a full path).

File.Move() rename not working

My app takes "unclean" file names and "cleans" them up. "Unclean" file names contain characters like #, #, ~, +, %, etc. The "cleaning" process replaces those chars with "". However, I found that if there are two files in the same folder that, after a cleaning, will have the same name, my app does not rename either file. (I.e. ##test.txt and ~test.txt will both be named test.txt after the cleaning).
Therefore, I put in a loop that basically checks to see if the file name my app is trying to rename already exists in the folder. However, I tried running this and it would not rename all the files. Am I doing something wrong?
Here's my code:
public void FileCleanup(List<string> paths)
{
string regPattern = (#"[~#&!%+{}]+");
string replacement = "";
Regex regExPattern = new Regex(regPattern);
List<string> existingNames = new List<string>();
StreamWriter errors = new StreamWriter(#"C:\Documents and Settings\joe.schmoe\Desktop\SharePointTesting\Errors.txt");
StreamWriter resultsofRename = new StreamWriter(#"C:\Documents and Settings\joe.schmoe\Desktop\SharePointTesting\Results of File Rename.txt");
var filesCount = new Dictionary<string, int>();
string replaceSpecialCharsWith = "_";
foreach (string files2 in paths)
try
{
string filenameOnly = Path.GetFileName(files2);
string pathOnly = Path.GetDirectoryName(files2);
string sanitizedFileName = regExPattern.Replace(filenameOnly, replacement);
string sanitized = Path.Combine(pathOnly, sanitizedFileName);
if (!System.IO.File.Exists(sanitized))
{
System.IO.File.Move(files2, sanitized);
resultsofRename.Write("Path: " + pathOnly + " / " + "Old File Name: " + filenameOnly + "New File Name: " + sanitized + "\r\n" + "\r\n");
}
else
{
existingNames.Add(sanitized);
foreach (string names in existingNames)
{
string sanitizedPath = regExPattern.Replace(names, replaceSpecialCharsWith);
if (filesCount.ContainsKey(sanitizedPath))
{
filesCount[names]++;
}
else
{
filesCount.Add(sanitizedPath, 1);
}
string newFileName = String.Format("{0},{1}, {2}", Path.GetFileNameWithoutExtension(sanitizedPath),
filesCount[sanitizedPath] != 0
? filesCount[sanitizedPath].ToString()
: "",
Path.GetExtension(sanitizedPath));
string newFilePath = Path.Combine(Path.GetDirectoryName(sanitizedPath), newFileName);
System.IO.File.Move(names, newFileName);
}
}
}
catch (Exception e)
{
//write to streamwriter
}
}
}
Anybody have ANY idea why my code won't rename duplicate files uniquely?
You do foreach (string names in existingNames), but existingNames is empty.
You have your if (System.IO.File.Exists(sanitized)) backwards: it makes up a new name if the file doesn't exist, instead of when it exists.
You make a string newFileName, but still use sanitizedPath instead of newFileName to do the renaming.
The second parameter to filesCount.Add(sanitizedPath, 0) should be 1 or 2. After all, you have then encountered your second file with the same name.
If filesCount[sanitizedPath] equals 0, you don't change the filename at all, so you overwrite the existing file.
In addition to the problem pointed out by Sjoerd, it appears that you are checking to see if the file exists and if it does exist you move it. Your if statement should be
if (!System.IO.File.Exists(sanitized))
{
...
}
else
{
foreach (string names in existingNames)
{
...
}
}
}
Update:
I agree that you should split the code up into smaller methods. It will help you identify which pieces are working and which aren't. That being said, I would get rid of the existingNames list. It is not needed because you have the filesCount Dictionary. Your else clause would then look something like this:
if (filesCount.ContainsKey(sanitized))
{
filesCount[sanitized]++;
}
else
{
filesCount.Add(sanitized, 1);
}
string newFileName = String.Format("{0}{1}.{2}",
Path.GetFileNameWithoutExtension(sanitized),
filesCount[sanitized].ToString(),
Path.GetExtension(sanitized));
string newFilePath = Path.Combine(Path.GetDirectoryName(sanitized), newFileName);
System.IO.File.Move(files2, newFileName);
Please note that I changed your String.Format method call. You had some commas and spaces in there that looked incorrect for building a path, although I could be missing something in your implementation. Also, in the Move I changed the first argument from "names" to "files2".
A good way to make the code less messy would be to split it to methods as logical blocks.
FindUniqueName(string filePath, string fileName);
The method would prefix the fileName with a character, until the fileName is unique withing the filePath.
MoveFile(string filePath, string from, string to);
The method would use the FindUniqueName method if the file already exists.
It would be way easier to test the cleanup that way.
Also you should check if a file actually requires renaming:
if (String.Compare(sanitizedFileName, filenameOnly, true) != 0)
MoveFile(pathOnly, fileNameOnly, sanitizedFileName);
private string FindUniqueName(string fileDirectory, string from, string to)
{
string fileName = to;
// There most likely won't be that many files with the same name to reach max filename length.
while (File.Exists(Path.Combine(fileDirectory, fileName)))
{
fileName = "_" + fileName;
}
return fileName;
}
private void MoveFile(string fileDirectory, string from, string to)
{
to = FindUniqueName(fileDirectory, from, to);
File.Move(Path.Combine(fileDirectory, from), Path.Combine(fileDirectory, to));
}

Problem with Existing File Name & Creating a Unique File Name

I have this code:
public void FileCleanup(List<string> paths)
{
string regPattern = (#"[~#&!%+{}]+");
string replacement = "";
string replacement_unique = "_";
Regex regExPattern = new Regex(regPattern);
List<string> existingNames = new List<string>();
StreamWriter errors = new StreamWriter(#"C:\Documents and Settings\jane.doe\Desktop\SharePointTesting\Errors.txt");
StreamWriter resultsofRename = new StreamWriter(#"C:\Documents and Settings\jane.doe\Desktop\SharePointTesting\Results of File Rename.txt");
foreach (string files2 in paths)
try
{
string filenameOnly = Path.GetFileName(files2);
string pathOnly = Path.GetDirectoryName(files2);
string sanitizedFileName = regExPattern.Replace(filenameOnly, replacement);
string sanitized = Path.Combine(pathOnly, sanitizedFileName);
if (!System.IO.File.Exists(sanitized))
{
existingNames.Add(sanitized);
try
{
foreach (string names in existingNames)
{
string filename = Path.GetFileName(names);
string filepath = Path.GetDirectoryName(names);
string cleanName = regExPattern.Replace(filename, replacement_unique);
string scrubbed = Path.Combine(filepath, cleanName);
System.IO.File.Move(names, scrubbed);
//resultsofRename.Write("Path: " + pathOnly + " / " + "Old File Name: " + filenameOnly + "New File Name: " + sanitized + "\r\n" + "\r\n");
resultsofRename = File.AppendText("Path: " + filepath + " / " + "Old File Name: " + filename + "New File Name: " + scrubbed + "\r\n" + "\r\n");
}
}
catch (Exception e)
{
errors.Write(e);
}
}
else
{
System.IO.File.Move(files2, sanitized);
resultsofRename.Write("Path: " + pathOnly + " / " + "Old File Name: " + filenameOnly + "New File Name: " + sanitized + "\r\n" + "\r\n");
}
}
catch (Exception e)
{
//write to streamwriter
}
}
}
}
What i'm trying to do here is rename "dirty" filenames by removing invalid chars (defined in the Regex), replace them with "". However, i noticed if i have duplicate file names, the app does not rename them. I.e. if i have ##test.txt and ~~test.txt in the same folder, they'd be renamed to test.txt. So, i created another foreach loop that instead replaces the invalid char with a "_" versus a blank space.
Problem is, whenever i try to run this, nothing ends up happening! None of the files are renamed!
Can someone tell me if my code is incorrect and how to fix it?
ALSO-- does anybody know how i could replace the invalid char in the 2nd foreach loop with a different char everytime? That way if there are multiple instances of i.e. %Test.txt, ~Test.txt and #test.txt (all to be renamed to test.txt), they can somehow be uniquely named with a different char?
However, would you know how to replace the invalid char with a different unique character every time so that each filename remains unique?
This is one way:
char[] uniques = ",'%".ToCharArray(); // whatever chars you want
foreach (string file in files)
{
foreach (char c in uniques)
{
string replaced = regexPattern.Replace(file, c.ToString());
if (File.Exists(replaced)) continue;
// create file
}
}
You may of course want to refactor this into its own method. Take note also that the maximum number of files only differing by unique character is limited to the number of characters in your uniques array, so if you have a lot of files with the same name only differing by the special characters you listed, it might be wise to use a different method, such as appending a digit to the end of the file name.
how would i append a digit to the end of the file name (with a different # everytime?)
A slightly modified version of Josh's suggestion would work that keeps track of the modified file names mapped to the number of times the same file name has been generated after the replacement:
var filesCount = new Dictionary<string, int>();
string replaceSpecialCharsWith = "_"; // or "", whatever
foreach (string file in files)
{
string sanitizedPath = regexPattern.Replace(file, replaceSpecialCharsWith);
if (filesCount.ContainsKey(sanitizedPath))
{
filesCount[file]++;
}
else
{
filesCount.Add(sanitizedPath, 0);
}
string newFileName = String.Format("{0}{1}{2}",
Path.GetFileNameWithoutExtension(sanitizedPath),
filesCount[sanitizedPath] != 0
? filesCount[sanitizedPath].ToString()
: "",
Path.GetExtension(sanitizedPath));
string newFilePath = Path.Combine(Path.GetDirectoryName(sanitizedPath),
newFileName);
// create file...
}
just a suggestion
after removing/replacing the special characters append timestamp to the file name. timestamps are unique so appending them to filenames will give you a unique filename.
How about maintaining a dictionary of all renamed files, checking each file against it, and if already existing add a number to the end of it?
In response to the answer #Josh Smeaton's gave here's some sample code using a dictionary to keep track of the file names :-
class Program
{
private static readonly Dictionary<string,int> _fileNames = new Dictionary<string, int>();
static void Main(string[] args)
{
var fileName = GetUniqueFileName("filename.txt");
Console.WriteLine(fileName);
fileName = GetUniqueFileName("someotherfilename.txt");
Console.WriteLine(fileName);
fileName = GetUniqueFileName("filename.txt");
Console.WriteLine(fileName);
fileName = GetUniqueFileName("adifferentfilename.txt");
Console.WriteLine(fileName);
fileName = GetUniqueFileName("filename.txt");
Console.WriteLine(fileName);
fileName = GetUniqueFileName("adifferentfilename.txt");
Console.WriteLine(fileName);
Console.ReadLine();
}
private static string GetUniqueFileName(string fileName)
{
// If not already in the dictionary add it otherwise increment the counter
if (!_fileNames.ContainsKey(fileName))
_fileNames.Add(fileName, 0);
else
_fileNames[fileName] += 1;
// Now return the new name using the counter if required (0 means it's just been added)
return _fileNames[fileName].ToString().Replace("0", string.Empty) + fileName;
}
}

Categories