Parse those nasty VSS history files. Put them in a format more suitable for Gource.
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.IO;
namespace ConsoleApplication2
{
class Program
{
static void Main(string[] args)
{
try
{
//List<HistoryItem> items = new List<HistoryItem>();
using (StreamReader sr = new StreamReader("C:\\Users\\Torrance\\Desktop\\vss.txt"))
{
// first line of the file is the project name
string projectName = sr.ReadLine();
// create an object that we will reuse to combine data
HistoryItem current = new HistoryItem(projectName);
string line = string.Empty;
while ((line = sr.ReadLine()) != null)
{
// just skip over blank lines
if (string.IsNullOrEmpty(line)) { continue; }
// if the line has a single space at the start, the line is a continuation of
// the previous record, append to the current working item
if (line.Substring(0, 1) == " ")
{
current.Append(line);
continue;
}
// we are at the next item, add what we were working on and start the next
if (!current.IsEmpty)
{
// write new output
string s = current.ToString();
if (!string.IsNullOrEmpty(s))
{
File.AppendAllText(@"C:\Users\Torrance\Desktop\vss.out", s + Environment.NewLine);
}
Console.WriteLine(s);
current.Reset();
}
current.Init(line);
}
}
}
catch (Exception e)
{
Console.WriteLine(e.Message);
}
}
public class HistoryItem
{
public string project;
public string user;
public string time;
public string item;
public string parent;
public HistoryItem(string project)
{
this.project = project;
}
public bool IsEmpty
{
get
{
if (string.IsNullOrEmpty(this.item)) { return true; } else { return false; }
}
}
public void Reset()
{
this.item = string.Empty;
this.user = string.Empty;
this.time = string.Empty;
this.parent = string.Empty;
}
public void Init(string line)
{
this.item = line.Substring(0, 21).Trim();
this.user = line.Substring(21, 11).Trim();
this.time = line.Substring(32, 19).Trim();
this.parent = line.Substring(51, 38).Trim();
}
public void Append(string line)
{
this.item += line.Substring(0, 21).Trim();
this.user += line.Substring(21, 11).Trim();
this.time += line.Substring(32, 19).Trim();
this.parent += line.Substring(51, 38).Trim();
}
public override string ToString()
{
// get the user
string username = this.user;
#region parse out the date
string dt = this.time;
string d = dt.Substring(0, 8).Trim();
//string t = dt.Substring(10, 6).Trim();
string[] a = d.Split('/');
string month = a[0];
string day = a[1];
string year = a[2];
if (month.Length == 1) { month = "0" + month; }
if (day.Length == 1) { day = "0" + day; }
if ((year == "99") || (year == "98") || (year == "97"))
{
year = "19" + year;
}
else
{
year = "20" + year;
}
string datetime = year + "/" + month + "/" + day + " 00:00:00.000";
#endregion
#region name the item
string f = this.item;
string label = this.parent;
string historyType = "M";
string filename = string.Empty;
if (label.StartsWith("Checked in") ||
label.StartsWith("Renamed") ||
label.StartsWith("Recovered") ||
label.StartsWith("Moved") ||
label.StartsWith("Branched") ||
label.StartsWith("Rollback")
)
{
label = this.project;
historyType = "M";
filename = label + "/" + f;
}
else if (label.StartsWith("Added"))
{
label = this.project;
historyType = "A";
filename = label + "/" + f;
}
else if (label.StartsWith("Deleted") || label.StartsWith("Destroyed"))
{
label = this.project;
historyType = "D";
filename = label + "/" + f;
}
else if (label.StartsWith("Shared"))
{
label = label.Substring(7);
historyType = "S";
filename = label;
return string.Empty;
//
// looks like this
//$/Aims66/AimsClient68/AdmTicketerPrivateComments.frx
// doesnt match up with the path of all the other types of entries
}
else if (label.StartsWith("Purged") || label.StartsWith("Pinned") || label.StartsWith("Unpinned"))
{
return string.Empty;
}
else
{
return string.Empty;
}
#endregion
string s = datetime + "\t" + username + "\t" + historyType + "\t" + filename;
return s;
}
}
}
}
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.IO;
namespace ConsoleApplication2
{
class Program
{
static void Main(string[] args)
{
try
{
//List<HistoryItem> items = new List<HistoryItem>();
using (StreamReader sr = new StreamReader("C:\\Users\\Torrance\\Desktop\\vss.txt"))
{
// first line of the file is the project name
string projectName = sr.ReadLine();
// create an object that we will reuse to combine data
HistoryItem current = new HistoryItem(projectName);
string line = string.Empty;
while ((line = sr.ReadLine()) != null)
{
// just skip over blank lines
if (string.IsNullOrEmpty(line)) { continue; }
// if the line has a single space at the start, the line is a continuation of
// the previous record, append to the current working item
if (line.Substring(0, 1) == " ")
{
current.Append(line);
continue;
}
// we are at the next item, add what we were working on and start the next
if (!current.IsEmpty)
{
// write new output
string s = current.ToString();
if (!string.IsNullOrEmpty(s))
{
File.AppendAllText(@"C:\Users\Torrance\Desktop\vss.out", s + Environment.NewLine);
}
Console.WriteLine(s);
current.Reset();
}
current.Init(line);
}
}
}
catch (Exception e)
{
Console.WriteLine(e.Message);
}
}
public class HistoryItem
{
public string project;
public string user;
public string time;
public string item;
public string parent;
public HistoryItem(string project)
{
this.project = project;
}
public bool IsEmpty
{
get
{
if (string.IsNullOrEmpty(this.item)) { return true; } else { return false; }
}
}
public void Reset()
{
this.item = string.Empty;
this.user = string.Empty;
this.time = string.Empty;
this.parent = string.Empty;
}
public void Init(string line)
{
this.item = line.Substring(0, 21).Trim();
this.user = line.Substring(21, 11).Trim();
this.time = line.Substring(32, 19).Trim();
this.parent = line.Substring(51, 38).Trim();
}
public void Append(string line)
{
this.item += line.Substring(0, 21).Trim();
this.user += line.Substring(21, 11).Trim();
this.time += line.Substring(32, 19).Trim();
this.parent += line.Substring(51, 38).Trim();
}
public override string ToString()
{
// get the user
string username = this.user;
#region parse out the date
string dt = this.time;
string d = dt.Substring(0, 8).Trim();
//string t = dt.Substring(10, 6).Trim();
string[] a = d.Split('/');
string month = a[0];
string day = a[1];
string year = a[2];
if (month.Length == 1) { month = "0" + month; }
if (day.Length == 1) { day = "0" + day; }
if ((year == "99") || (year == "98") || (year == "97"))
{
year = "19" + year;
}
else
{
year = "20" + year;
}
string datetime = year + "/" + month + "/" + day + " 00:00:00.000";
#endregion
#region name the item
string f = this.item;
string label = this.parent;
string historyType = "M";
string filename = string.Empty;
if (label.StartsWith("Checked in") ||
label.StartsWith("Renamed") ||
label.StartsWith("Recovered") ||
label.StartsWith("Moved") ||
label.StartsWith("Branched") ||
label.StartsWith("Rollback")
)
{
label = this.project;
historyType = "M";
filename = label + "/" + f;
}
else if (label.StartsWith("Added"))
{
label = this.project;
historyType = "A";
filename = label + "/" + f;
}
else if (label.StartsWith("Deleted") || label.StartsWith("Destroyed"))
{
label = this.project;
historyType = "D";
filename = label + "/" + f;
}
else if (label.StartsWith("Shared"))
{
label = label.Substring(7);
historyType = "S";
filename = label;
return string.Empty;
//
// looks like this
//$/Aims66/AimsClient68/AdmTicketerPrivateComments.frx
// doesnt match up with the path of all the other types of entries
}
else if (label.StartsWith("Purged") || label.StartsWith("Pinned") || label.StartsWith("Unpinned"))
{
return string.Empty;
}
else
{
return string.Empty;
}
#endregion
string s = datetime + "\t" + username + "\t" + historyType + "\t" + filename;
return s;
}
}
}
}