瀏覽代碼

Merge pull request #175 from oleg-nenashev/TimeSpan_settings_parsing

Fix #159 - Time span settings parsing
Oleg Nenashev 8 年之前
父節點
當前提交
71dfc0b291

+ 6 - 14
src/Core/WinSWCore/ServiceDescriptor.cs

@@ -126,16 +126,8 @@ namespace winsw
 
         private TimeSpan SingleTimeSpanElement(XmlNode parent, string tagName, TimeSpan defaultValue)
         {
-            var e = parent.SelectSingleNode(tagName);
-
-            if (e == null)
-            {
-                return defaultValue;
-            }
-            else
-            {
-                return ParseTimeSpan(e.InnerText);
-            }
+            var value = SingleElement(tagName, true);
+            return (value != null) ? ParseTimeSpan(value) : defaultValue;
         }
 
         private TimeSpan ParseTimeSpan(string v)
@@ -505,7 +497,7 @@ namespace winsw
         {
             get
             {
-                return SingleTimeSpanElement(dom.FirstChild, "waithint", Defaults.WaitHint);
+                return SingleTimeSpanElement(dom, "waithint", Defaults.WaitHint);
             }
         }
 
@@ -519,7 +511,7 @@ namespace winsw
         {
             get
             {
-                return SingleTimeSpanElement(dom.FirstChild, "sleeptime", Defaults.SleepTime);
+                return SingleTimeSpanElement(dom, "sleeptime", Defaults.SleepTime);
             }
         }
 
@@ -615,7 +607,7 @@ namespace winsw
         {
             get
             {
-                return SingleTimeSpanElement(dom.FirstChild, "resetfailure", Defaults.ResetFailureAfter);
+                return SingleTimeSpanElement(dom, "resetfailure", Defaults.ResetFailureAfter);
             }
         }
 
@@ -703,7 +695,7 @@ namespace winsw
         {
             get
             {
-                return SingleTimeSpanElement(dom.FirstChild, "stoptimeout", Defaults.StopTimeout);
+                return SingleTimeSpanElement(dom, "stoptimeout", Defaults.StopTimeout);
             }
         }
 

+ 61 - 0
src/Test/winswTests/ServiceDescriptorTests.cs

@@ -7,6 +7,7 @@ namespace winswTests
 {
     using System;
     using WMI;
+    using winswTests.Util;
 
     [TestFixture]
     public class ServiceDescriptorTests
@@ -250,5 +251,65 @@ namespace winswTests
             var serviceDescriptor = ServiceDescriptor.FromXML(seedXml);
             Assert.That(serviceDescriptor.AllowServiceAcountLogonRight, Is.EqualTo(false));
         }
+
+        [Test]
+        public void VerifyWaitHint_FullXML()
+        {
+            var sd = ConfigXmlBuilder.create()
+                .WithTag("waithint", "20 min")
+                .ToServiceDescriptor(true);
+            Assert.That(sd.WaitHint, Is.EqualTo(TimeSpan.FromMinutes(20)));
+        }
+
+        /// <summary>
+        /// Test for https://github.com/kohsuke/winsw/issues/159
+        /// </summary>
+        [Test]
+        public void VerifyWaitHint_XMLWithoutVersion()
+        {
+            var sd = ConfigXmlBuilder.create(printXMLVersion: false)
+                .WithTag("waithint", "21 min")
+                .ToServiceDescriptor(true);
+            Assert.That(sd.WaitHint, Is.EqualTo(TimeSpan.FromMinutes(21)));
+        }
+
+        [Test]
+        public void VerifyWaitHint_XMLWithoutComment()
+        {
+            var sd = ConfigXmlBuilder.create(xmlComment: null)
+                .WithTag("waithint", "22 min")
+                .ToServiceDescriptor(true);
+            Assert.That(sd.WaitHint, Is.EqualTo(TimeSpan.FromMinutes(22)));
+        }
+        
+        [Test]
+        public void VerifyWaitHint_XMLWithoutVersionAndComment()
+        {
+            var sd = ConfigXmlBuilder.create(xmlComment: null, printXMLVersion: false)
+                .WithTag("waithint", "23 min")
+                .ToServiceDescriptor(true);
+            Assert.That(sd.WaitHint, Is.EqualTo(TimeSpan.FromMinutes(23)));
+        }
+
+        [Test]
+        public void VerifySleepTime()
+        {
+            var sd = ConfigXmlBuilder.create().WithTag("sleeptime", "3 hrs").ToServiceDescriptor(true);
+            Assert.That(sd.SleepTime, Is.EqualTo(TimeSpan.FromHours(3)));
+        }
+
+        [Test]
+        public void VerifyResetFailureAfter()
+        {
+            var sd = ConfigXmlBuilder.create().WithTag("resetfailure", "75 sec").ToServiceDescriptor(true);
+            Assert.That(sd.ResetFailureAfter, Is.EqualTo(TimeSpan.FromSeconds(75)));
+        }
+
+        [Test]
+        public void VerifyStopTimeout()
+        {
+            var sd = ConfigXmlBuilder.create().WithTag("stoptimeout", "35 secs").ToServiceDescriptor(true);
+            Assert.That(sd.StopTimeout, Is.EqualTo(TimeSpan.FromSeconds(35)));
+        }
     }
 }

+ 92 - 0
src/Test/winswTests/Util/ConfigXmlBuilder.cs

@@ -0,0 +1,92 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+using winsw;
+
+namespace winswTests.Util
+{
+    /// <summary>
+    /// Configuration XML builder, which simplifies testing of WinSW Configuration file.
+    /// </summary>
+    class ConfigXmlBuilder
+    {
+        public string Name { get; set; }
+        public string Id { get; set; }
+        public string Description { get; set; }
+        public string Executable { get; set; }
+        public bool PrintXMLVersion { get; set; }
+        public string XMLComment  { get; set; }
+
+        private List<String> configEntries;
+
+        // TODO: Switch to the initializer?
+        private ConfigXmlBuilder()
+        {
+            configEntries = new List<string>();
+        }
+
+        public static ConfigXmlBuilder create(string id = null, string name = null, 
+            string description = null, string executable = null, bool printXMLVersion = true, 
+            string xmlComment =  "")
+        {
+            var config = new ConfigXmlBuilder();
+            config.Id = id ?? "myapp";
+            config.Name = name ?? "MyApp Service";
+            config.Description = description ?? "MyApp Service (powered by WinSW)";
+            config.Executable = executable ?? "%BASE%\\myExecutable.exe";
+            config.PrintXMLVersion = printXMLVersion;
+            config.XMLComment = (xmlComment != null && xmlComment.Length == 0) 
+                ? "Just a sample configuration file generated by the test suite" 
+                : xmlComment;
+            return config;
+        }
+
+        public string ToXMLString(bool dumpConfig = false)
+        {
+            StringBuilder str = new StringBuilder();
+            if (PrintXMLVersion)
+            {
+                // TODO: The encoding is generally wrong
+                str.Append("<?xml version=\"1.0\" encoding=\"utf-8\"?>\n");
+            }
+            if (XMLComment != null)
+            {
+                str.AppendFormat("<!--{0}-->\n", XMLComment);
+            }
+            str.Append("<service>\n");
+            str.AppendFormat("  <id>{0}</id>\n", Id);
+            str.AppendFormat("  <name>{0}</name>\n", Name);
+            str.AppendFormat("  <description>{0}</description>\n", Description);
+            str.AppendFormat("  <executable>{0}</executable>\n", Executable);
+            foreach (String entry in configEntries)
+            {
+                // We do not care much about pretty formatting here
+                str.AppendFormat("  {0}\n", entry);
+            }
+            str.Append("</service>\n");
+            string res = str.ToString();
+            if (dumpConfig)
+            {
+                Console.Out.WriteLine("Produced config:");
+                Console.Out.WriteLine(res);
+            }
+            return res;
+        }
+
+        public ServiceDescriptor ToServiceDescriptor(bool dumpConfig = false)
+        {
+            return ServiceDescriptor.FromXML(ToXMLString(dumpConfig));
+        } 
+
+        public ConfigXmlBuilder WithRawEntry(string entry)
+        {
+            configEntries.Add(entry);
+            return this;
+        }
+
+        public ConfigXmlBuilder WithTag(string tagName, string value)
+        { 
+            return WithRawEntry(String.Format("<{0}>{1}</{0}>", tagName, value));
+        }
+    }
+}

+ 1 - 0
src/Test/winswTests/winswTests.csproj

@@ -63,6 +63,7 @@
     <Compile Include="Properties\AssemblyInfo.cs" />
     <Compile Include="ServiceDescriptorTests.cs" />
     <Compile Include="Util\CLITestHelper.cs" />
+    <Compile Include="Util\ConfigXmlBuilder.cs" />
     <Compile Include="Util\ServiceDescriptorAssert.cs" />
   </ItemGroup>
   <ItemGroup>