A fork of Eusth's IPA
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

129 lines
3.8KB

  1. using System;
  2. using System.Collections.Generic;
  3. using System.Collections.Specialized;
  4. using System.IO;
  5. using System.Linq;
  6. using System.Text;
  7. namespace IPA.Patcher
  8. {
  9. /// <summary>
  10. /// A unit for backup. WIP.
  11. /// </summary>
  12. public class BackupUnit
  13. {
  14. public string Name { get; private set; }
  15. private DirectoryInfo _BackupPath;
  16. private PatchContext _Context;
  17. private List<string> _Files = new List<string>();
  18. public BackupUnit(PatchContext context) : this(context, DateTime.Now.ToString("yyyy-MM-dd_h-mm-ss"))
  19. {
  20. }
  21. private BackupUnit(PatchContext context, string name)
  22. {
  23. Name = name;
  24. _Context = context;
  25. _BackupPath = new DirectoryInfo(Path.Combine(_Context.BackupPath, Name));
  26. }
  27. public static BackupUnit FromDirectory(DirectoryInfo directory, PatchContext context)
  28. {
  29. var unit = new BackupUnit(context, directory.Name);
  30. // Parse directory
  31. foreach(var file in directory.GetFiles("*", SearchOption.AllDirectories)) {
  32. var relativePath = file.FullName.Substring(directory.FullName.Length + 1);
  33. unit._Files.Add(relativePath);
  34. }
  35. return unit;
  36. }
  37. public void Add(string file)
  38. {
  39. Add(new FileInfo(file));
  40. }
  41. internal void Delete()
  42. {
  43. _BackupPath.Delete(true);
  44. }
  45. /// <summary>
  46. /// Adds a file to the list of changed files and backups it.
  47. /// </summary>
  48. /// <param name="path"></param>
  49. public void Add(FileInfo file)
  50. {
  51. if(!file.FullName.StartsWith(_Context.ProjectRoot))
  52. {
  53. Console.Error.WriteLine("Invalid file path for backup! {0}", file);
  54. return;
  55. }
  56. var relativePath = file.FullName.Substring(_Context.ProjectRoot.Length + 1);
  57. var backupPath = new FileInfo(Path.Combine(_BackupPath.FullName, relativePath));
  58. if(_Files.Contains(relativePath))
  59. {
  60. Console.WriteLine("Skipping backup of {0}", relativePath);
  61. return;
  62. }
  63. // Copy over
  64. backupPath.Directory.Create();
  65. if (file.Exists)
  66. {
  67. file.CopyTo(backupPath.FullName);
  68. } else
  69. {
  70. // Make empty file
  71. backupPath.Create().Close();
  72. }
  73. // Add to list
  74. _Files.Add(relativePath);
  75. }
  76. /// <summary>
  77. /// Reverts the changes made in this unit.
  78. /// </summary>
  79. public void Restore()
  80. {
  81. foreach(var relativePath in _Files)
  82. {
  83. Console.WriteLine("Restoring {0}", relativePath);
  84. // Original version
  85. var backupFile = new FileInfo(Path.Combine(_BackupPath.FullName, relativePath));
  86. var target = new FileInfo(Path.Combine(_Context.ProjectRoot, relativePath));
  87. if (backupFile.Exists)
  88. {
  89. if (backupFile.Length > 0)
  90. {
  91. Console.WriteLine(" {0} => {1}", backupFile.FullName, target.FullName);
  92. target.Directory.Create();
  93. backupFile.CopyTo(target.FullName, true);
  94. } else
  95. {
  96. Console.WriteLine(" x {0}", target.FullName);
  97. if(target.Exists)
  98. {
  99. target.Delete();
  100. }
  101. }
  102. } else {
  103. Console.Error.WriteLine("Backup not found!");
  104. }
  105. }
  106. }
  107. }
  108. }