OSDN Git Service

RelatedPostsTabModelの読み込み中にタブを閉じるとKeyNotFoundExceptionが発生する不具合を修正
authorKimura Youichi <kim.upsilon@bucyou.net>
Wed, 13 Nov 2019 14:01:42 +0000 (23:01 +0900)
committerKimura Youichi <kim.upsilon@bucyou.net>
Wed, 13 Nov 2019 19:32:25 +0000 (04:32 +0900)
TweenMain.OpenRelatedTab 内の2回目の TabCollection.IndexOf でエラーになる

OpenTween.Tests/ExtensionsTest.cs
OpenTween.Tests/Models/TabCollectionTest.cs [new file with mode: 0644]
OpenTween/Extensions.cs
OpenTween/Models/TabCollection.cs
OpenTween/Resources/ChangeLog.txt

index 7ee7cc0..f117b73 100644 (file)
@@ -60,6 +60,32 @@ namespace OpenTween
         }
 
         [Theory]
+        [InlineData("aaa", new string[0], -1)]
+        [InlineData("aaa", new[] { "aaa" }, 0)]
+        [InlineData("bbb", new[] { "aaa" }, -1)]
+        [InlineData("bbb", new[] { "aaa", "bbb" }, 1)]
+        public void FindIndex_Test(string item, string[] array, int expected)
+        {
+            // このテストでは items が List<T> または T[] のインスタンスと認識されないようにする
+            var items = new LinkedList<string>(array).AsEnumerable();
+            Assert.Equal(expected, items.FindIndex(x => x == item));
+        }
+
+        [Fact]
+        public void FindIndex_ListTest()
+        {
+            var items = new List<string> { "aaa", "bbb" }.AsEnumerable();
+            Assert.Equal(1, items.FindIndex(x => x == "bbb"));
+        }
+
+        [Fact]
+        public void FindIndex_ArrayTest()
+        {
+            var items = new[] { "aaa", "bbb" }.AsEnumerable();
+            Assert.Equal(1, items.FindIndex(x => x == "bbb"));
+        }
+
+        [Theory]
         [InlineData("abc", new int[] { 'a', 'b', 'c' })]
         [InlineData("🍣", new int[] { 0x1f363 })] // サロゲートペア
         public void ToCodepoints_Test(string s, int[] expected)
diff --git a/OpenTween.Tests/Models/TabCollectionTest.cs b/OpenTween.Tests/Models/TabCollectionTest.cs
new file mode 100644 (file)
index 0000000..40d9491
--- /dev/null
@@ -0,0 +1,87 @@
+// OpenTween - Client of Twitter
+// Copyright (c) 2019 kim_upsilon (@kim_upsilon) <https://upsilo.net/~upsilon/>
+// All rights reserved.
+//
+// This file is part of OpenTween.
+//
+// This program is free software; you can redistribute it and/or modify it
+// under the terms of the GNU General Public License as published by the Free
+// Software Foundation; either version 3 of the License, or (at your option)
+// any later version.
+//
+// This program is distributed in the hope that it will be useful, but
+// WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
+// for more details.
+//
+// You should have received a copy of the GNU General Public License along
+// with this program. If not, see <http://www.gnu.org/licenses/>, or write to
+// the Free Software Foundation, Inc., 51 Franklin Street - Fifth Floor,
+// Boston, MA 02110-1301, USA.
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+using Xunit;
+
+namespace OpenTween.Models
+{
+    public class TabCollectionTest
+    {
+        [Fact]
+        public void Getter_Test()
+        {
+            var tabs = new TabCollection();
+            var tab = new PublicSearchTabModel("hoge");
+            tabs.Add(tab);
+
+            Assert.Equal(tab, tabs["hoge"]);
+        }
+
+        [Fact]
+        public void IndexOf_TabName_Test()
+        {
+            var tabs = new TabCollection();
+            var tab1 = new PublicSearchTabModel("aaaaa");
+            var tab2 = new PublicSearchTabModel("bbbbb");
+
+            tabs.Add(tab1);
+            tabs.Add(tab2);
+
+            Assert.Equal(1, tabs.IndexOf("bbbbb"));
+        }
+
+        [Fact]
+        public void IndexOf_TabName_NotExistsTest()
+        {
+            var tabs = new TabCollection();
+
+            Assert.Equal(-1, tabs.IndexOf("hoge"));
+        }
+
+        [Fact]
+        public void TryGetValue_TabName_Test()
+        {
+            var tabs = new TabCollection();
+            var tab1 = new PublicSearchTabModel("aaaaa");
+            var tab2 = new PublicSearchTabModel("bbbbb");
+
+            tabs.Add(tab1);
+            tabs.Add(tab2);
+
+            Assert.True(tabs.TryGetValue("bbbbb", out var actualTab));
+            Assert.Equal(tab2, actualTab);
+        }
+
+        [Fact]
+        public void TryGetValue_TabName_NotExistsTest()
+        {
+            var tabs = new TabCollection();
+
+            Assert.False(tabs.TryGetValue("hoge", out var actualTab));
+            Assert.Null(actualTab);
+        }
+    }
+}
index a31adbb..069a9e3 100644 (file)
@@ -70,6 +70,27 @@ namespace OpenTween
             return false;
         }
 
+        public static int FindIndex<T>(this IEnumerable<T> enumerable, Predicate<T> finder)
+        {
+            if (enumerable is List<T> list)
+                return list.FindIndex(finder);
+
+            if (enumerable is T[] array)
+                return Array.FindIndex(array, finder);
+
+            var index = 0;
+
+            foreach (var item in enumerable)
+            {
+                if (finder(item))
+                    return index;
+
+                index++;
+            }
+
+            return -1;
+        }
+
         public static IEnumerable<(T Value, int Index)> WithIndex<T>(this IEnumerable<T> enumerable)
         {
             var i = 0;
index 45922f8..086ead0 100644 (file)
 
 using System.Collections.ObjectModel;
 using System.Diagnostics.CodeAnalysis;
+using System.Linq;
 
 namespace OpenTween.Models
 {
     public class TabCollection : KeyedCollection<string, TabModel>, IReadOnlyTabCollection
     {
         public int IndexOf(string tabName)
-            => this.IndexOf(this[tabName]);
+            => this.Items.FindIndex(x => x.TabName == tabName);
 
         public bool TryGetValue(string tabName, [NotNullWhen(true)] out TabModel? tab)
-            => this.Dictionary.TryGetValue(tabName, out tab);
+        {
+            if (this.Dictionary is { } dict)
+                return dict.TryGetValue(tabName, out tab);
+
+            tab = this.Items.FirstOrDefault(x => x.TabName == tabName);
+
+            return tab != null;
+        }
 
         protected override string GetKeyForItem(TabModel tab)
             => tab.TabName;
index 1f43987..c49069c 100644 (file)
@@ -1,6 +1,7 @@
 更新履歴
 
 ==== Ver 2.4.3-dev(2019/xx/xx)
+ * FIX: 関連発言表示のタブを読み込み中に閉じるとエラーが発生する不具合を修正
 
 ==== Ver 2.4.2(2019/10/23)
  * FIX: タブ更新時にエラーが発生するとプロセスが異常終了する場合がある不具合を修正