PeriodicRollingCalendar.cs 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122
  1. using System;
  2. using System.Data;
  3. namespace winsw
  4. {
  5. /**
  6. * This is largely borrowed from the logback Rolling Calendar.
  7. **/
  8. public class PeriodicRollingCalendar
  9. {
  10. private PeriodicityType _periodicityType;
  11. private string _format;
  12. private long _period;
  13. private DateTime _currentRoll;
  14. private DateTime _nextRoll;
  15. public PeriodicRollingCalendar(string format, long period)
  16. {
  17. this._format = format;
  18. this._period = period;
  19. this._currentRoll = DateTime.Now;
  20. }
  21. public void init()
  22. {
  23. this._periodicityType = determinePeriodicityType();
  24. this._nextRoll = nextTriggeringTime(this._currentRoll);
  25. }
  26. public enum PeriodicityType
  27. {
  28. ERRONEOUS, TOP_OF_MILLISECOND, TOP_OF_SECOND, TOP_OF_MINUTE, TOP_OF_HOUR, TOP_OF_DAY
  29. }
  30. private static PeriodicityType[] VALID_ORDERED_LIST = new PeriodicityType[] {
  31. PeriodicityType.TOP_OF_MILLISECOND, PeriodicityType.TOP_OF_SECOND, PeriodicityType.TOP_OF_MINUTE, PeriodicityType.TOP_OF_HOUR, PeriodicityType.TOP_OF_DAY
  32. };
  33. private PeriodicityType determinePeriodicityType()
  34. {
  35. PeriodicRollingCalendar periodicRollingCalendar = new PeriodicRollingCalendar(_format, _period);
  36. DateTime epoch = new DateTime(1970, 1, 1);
  37. foreach (PeriodicityType i in VALID_ORDERED_LIST)
  38. {
  39. string r0 = epoch.ToString(_format);
  40. periodicRollingCalendar.periodicityType = i;
  41. DateTime next = periodicRollingCalendar.nextTriggeringTime(epoch);
  42. string r1 = next.ToString(_format);
  43. if (r0 != null && r1 != null && !r0.Equals(r1))
  44. {
  45. return i;
  46. }
  47. }
  48. return PeriodicityType.ERRONEOUS;
  49. }
  50. private DateTime nextTriggeringTime(DateTime input)
  51. {
  52. DateTime output;
  53. switch (_periodicityType)
  54. {
  55. case PeriodicityType.TOP_OF_MILLISECOND:
  56. output = new DateTime(input.Year, input.Month, input.Day, input.Hour, input.Minute, input.Second, input.Millisecond);
  57. output = output.AddMilliseconds(_period);
  58. return output;
  59. case PeriodicityType.TOP_OF_SECOND:
  60. output = new DateTime(input.Year, input.Month, input.Day, input.Hour, input.Minute, input.Second);
  61. output = output.AddSeconds(_period);
  62. return output;
  63. case PeriodicityType.TOP_OF_MINUTE:
  64. output = new DateTime(input.Year, input.Month, input.Day, input.Hour, input.Minute, 0);
  65. output = output.AddMinutes(_period);
  66. return output;
  67. case PeriodicityType.TOP_OF_HOUR:
  68. output = new DateTime(input.Year, input.Month, input.Day, input.Hour, 0, 0);
  69. output = output.AddHours(_period);
  70. return output;
  71. case PeriodicityType.TOP_OF_DAY:
  72. output = new DateTime(input.Year, input.Month, input.Day);
  73. output = output.AddDays(_period);
  74. return output;
  75. default:
  76. throw new Exception("invalid periodicity type: " + _periodicityType);
  77. }
  78. }
  79. public PeriodicityType periodicityType
  80. {
  81. set
  82. {
  83. this._periodicityType = value;
  84. }
  85. }
  86. public Boolean shouldRoll
  87. {
  88. get
  89. {
  90. DateTime now = DateTime.Now;
  91. if (now > this._nextRoll)
  92. {
  93. this._currentRoll = now;
  94. this._nextRoll = nextTriggeringTime(now);
  95. return true;
  96. }
  97. return false;
  98. }
  99. }
  100. public string format
  101. {
  102. get
  103. {
  104. return this._currentRoll.ToString(this._format);
  105. }
  106. }
  107. }
  108. }