2008-09-07 Atsushi Enomoto <atsushi@ximian.com>
authorAtsushi Eno <atsushieno@gmail.com>
Mon, 7 Sep 2009 08:58:58 +0000 (08:58 -0000)
committerAtsushi Eno <atsushieno@gmail.com>
Mon, 7 Sep 2009 08:58:58 +0000 (08:58 -0000)
* UriTemplate.cs, UriTemplateMatch.cs : add support for wildcard.

* UriTemplateTest.cs : add test for wildcard.

svn path=/trunk/mcs/; revision=141410

mcs/class/System.ServiceModel.Web/System/ChangeLog
mcs/class/System.ServiceModel.Web/System/UriTemplate.cs
mcs/class/System.ServiceModel.Web/System/UriTemplateMatch.cs
mcs/class/System.ServiceModel.Web/Test/System/ChangeLog
mcs/class/System.ServiceModel.Web/Test/System/UriTemplateTest.cs

index 6cbea6dc9c4bf61d90ed0b3b5c1efbd1784ed24c..df31d8b9d8d1d9d816027958c8c23070db024886 100644 (file)
@@ -1,3 +1,7 @@
+2008-09-07  Atsushi Enomoto  <atsushi@ximian.com>
+
+       * UriTemplate.cs, UriTemplateMatch.cs : add support for wildcard.
+
 2008-09-07  Atsushi Enomoto  <atsushi@ximian.com>
 
        * UriTemplate.cs : implement IsEquivalentTo().
index 38daeb2de5fabbcecb929a2465d90e2612d11fd4..3e61eb21f5aecbb55b7a89cb6ee0e2da4462d412 100644 (file)
@@ -190,6 +190,8 @@ namespace System
 
                // Match
 
+               static readonly char [] slashSep = {'/'};
+
                public UriTemplateMatch Match (Uri baseAddress, Uri candidate)
                {
                        CheckBaseAddress (baseAddress);
@@ -215,7 +217,7 @@ namespace System
                        m.RequestUri = candidate;
                        var vc = m.BoundVariables;
 
-                       string cp = baseAddress.MakeRelativeUri(candidate).ToString();
+                       string cp = baseAddress.MakeRelativeUri(candidate).ToString ();
                        if (IgnoreTrailingSlash && cp [cp.Length - 1] == '/')
                                cp = cp.Substring (0, cp.Length - 1);
 
@@ -247,11 +249,17 @@ namespace System
                        int tEnd = template.IndexOf ('?');
                        if (tEnd < 0)
                                tEnd = template.Length;
-
-                       if ((cp.Length - c) != (tEnd - i) ||
+                       bool wild = (template [tEnd - 1] == '*');
+                       if (wild)
+                               tEnd--;
+                       if (!wild && (cp.Length - c) != (tEnd - i) ||
                            String.CompareOrdinal (cp, c, template, i, tEnd - i) != 0)
                                return null; // suffix doesn't match
-                       
+                       if (wild) {
+                               c += tEnd - i;
+                               foreach (var pe in cp.Substring (c).Split (slashSep, StringSplitOptions.RemoveEmptyEntries))
+                                       m.WildcardPathSegments.Add (pe);
+                       }
                        if (candidate.Query.Length == 0)
                                return m;
 
@@ -290,6 +298,9 @@ namespace System
 
                ReadOnlyCollection<string> ParsePathTemplate (string template, int index, int end)
                {
+                       int widx = template.IndexOf ('*', index, end);
+                       if (widx >= 0 && widx != end - 1)
+                               throw new FormatException (String.Format ("Wildcard in UriTemplate is valid only if it is placed at the last part of the path: '{0}'", template));
                        List<string> list = null;
                        int prevEnd = -2;
                        for (int i = index; i <= end; ) {
index 099a94d970067bd387b1f1d473bca0a2b72826ca..b437f43d5d2b7e5c22a5c5ff20c3b152562bfa5e 100644 (file)
@@ -41,7 +41,7 @@ namespace System
                NameValueCollection nvc, query_params;
                object data;
                UriTemplate template;
-               Collection<string> path_segments;
+               Collection<string> path_segments, wildcard;
 
                public Uri BaseUri {
                        get { return base_uri; }
@@ -87,9 +87,12 @@ namespace System
                        set { template = value; }
                }
 
-               [MonoTODO]
                public Collection<string> WildcardPathSegments {
-                       get { throw new NotImplementedException (); }
+                       get {
+                               if (wildcard == null)
+                                       wildcard = new Collection<string> ();
+                               return wildcard;
+                       }
                }
        }
 }
index 5608e3a51515f4bd4d2850edb5d0c58851c01970..28a71c6a86b959802ed3d523bed2527fa3c88ff3 100644 (file)
@@ -1,3 +1,7 @@
+2009-09-07  Atsushi Enomoto  <atsushi@ximian.com>
+
+       * UriTemplateTest.cs : add test for wildcard.
+
 2009-09-07  Atsushi Enomoto  <atsushi@ximian.com>
 
        * UriTemplateEquivalenceComparerTest.cs : new test.
index 94adfbb6c7350a90a581688f9b0ee3b05e5e2ed7..ba10ecb70e72dee20dc862bd605d69ffb03e9852 100644 (file)
@@ -77,6 +77,13 @@ namespace MonoTests.System
                        new UriTemplate ("http://localhost:8080/{foo}/{");
                }
 
+               [Test]
+               [ExpectedException (typeof (FormatException))]
+               public void ConstructorBrokenTemplate3 ()
+               {
+                       new UriTemplate ("http://localhost:8080/{foo}/*/baz");
+               }
+
                [Test]
                public void ToString ()
                {
@@ -345,6 +352,20 @@ namespace MonoTests.System
                        Assert.AreEqual ("vv", m.QueryParameters ["p1"], "#5");
                }
 
+               [Test]
+               public void MatchWildcard ()
+               {
+                       var t = new UriTemplate ("/hoge/*?p1={foo}");
+                       var m = t.Match (new Uri ("http://localhost"), new Uri ("http://localhost/hoge/ppp/qqq?p1=v1"));
+                       Assert.IsNotNull (m, "#0");
+                       Assert.IsNotNull (m.QueryParameters, "#1.0");
+                       Assert.AreEqual ("v1", m.QueryParameters ["p1"], "#1");
+                       Assert.IsNotNull (m.WildcardPathSegments, "#2.0");
+                       Assert.AreEqual (2, m.WildcardPathSegments.Count, "#2");
+                       Assert.AreEqual ("ppp", m.WildcardPathSegments [0], "#3");
+                       Assert.AreEqual ("qqq", m.WildcardPathSegments [1], "#4");
+               }
+
                [Test]
                public void IgnoreTrailingSlash ()
                {