1616 */
1717package org .apache .dubbo .registry .zookeeper ;
1818
19+ import com .google .common .collect .Lists ;
20+ import org .apache .curator .CuratorZookeeperClient ;
21+ import org .apache .curator .framework .CuratorFramework ;
22+ import org .apache .curator .framework .CuratorFrameworkFactory ;
23+ import org .apache .curator .framework .WatcherRemoveCuratorFramework ;
24+ import org .apache .curator .framework .api .CreateBuilder ;
25+ import org .apache .curator .framework .api .DeleteBuilder ;
26+ import org .apache .curator .framework .api .ExistsBuilder ;
27+ import org .apache .curator .framework .api .GetChildrenBuilder ;
28+ import org .apache .curator .framework .api .GetDataBuilder ;
29+ import org .apache .curator .framework .api .SetDataBuilder ;
30+ import org .apache .curator .framework .listen .StandardListenerManager ;
31+
1932import org .apache .dubbo .common .URL ;
2033import org .apache .dubbo .common .status .Status ;
2134import org .apache .dubbo .registry .NotifyListener ;
2235import org .apache .dubbo .registry .Registry ;
2336import org .apache .dubbo .registry .status .RegistryStatusChecker ;
37+ import org .apache .dubbo .remoting .zookeeper .curator5 .Curator5ZookeeperClient ;
38+ import org .apache .dubbo .remoting .zookeeper .curator5 .ZookeeperClient ;
39+ import org .apache .dubbo .remoting .zookeeper .curator5 .ZookeeperClientManager ;
2440import org .apache .dubbo .rpc .RpcException ;
2541import org .apache .dubbo .rpc .model .ApplicationModel ;
2642
43+ import java .util .ArrayList ;
2744import java .util .List ;
2845import java .util .Map ;
2946import java .util .Set ;
3047import java .util .concurrent .CountDownLatch ;
3148
49+ import org .apache .zookeeper .KeeperException .NodeExistsException ;
50+ import org .apache .zookeeper .data .Stat ;
3251import org .junit .jupiter .api .Assertions ;
3352import org .junit .jupiter .api .BeforeAll ;
3453import org .junit .jupiter .api .BeforeEach ;
3554import org .junit .jupiter .api .Disabled ;
3655import org .junit .jupiter .api .Test ;
56+ import org .mockito .invocation .InvocationOnMock ;
57+ import org .mockito .stubbing .Answer ;
3758
3859import static org .hamcrest .CoreMatchers .is ;
3960import static org .hamcrest .CoreMatchers .not ;
4061import static org .hamcrest .CoreMatchers .nullValue ;
4162import static org .hamcrest .MatcherAssert .assertThat ;
4263import static org .hamcrest .Matchers .containsString ;
4364import static org .junit .jupiter .api .Assertions .fail ;
65+ import static org .mockito .ArgumentMatchers .any ;
66+ import static org .mockito .ArgumentMatchers .anyBoolean ;
67+ import static org .mockito .ArgumentMatchers .anyInt ;
68+ import static org .mockito .ArgumentMatchers .anyString ;
69+ import static org .mockito .Mockito .doAnswer ;
70+ import static org .mockito .Mockito .doReturn ;
71+ import static org .mockito .Mockito .doThrow ;
4472import static org .mockito .Mockito .mock ;
73+ import static org .mockito .Mockito .mockStatic ;
74+ import static org .mockito .Mockito .spy ;
75+ import static org .mockito .Mockito .when ;
4576
4677class ZookeeperRegistryTest {
4778 private static String zookeeperConnectionAddress1 ;
4879 private ZookeeperRegistry zookeeperRegistry ;
4980 private String service = "org.apache.dubbo.test.injvmServie" ;
50- private URL serviceUrl = URL .valueOf ("zookeeper://zookeeper/" + service + "?notify=false&methods=test1,test2" );
81+ private String url = "zookeeper://zookeeper/" + service + "?notify=false&methods=test1,test2" ;
82+ private URL serviceUrl = URL .valueOf (url );
5183 private URL anyUrl = URL .valueOf ("zookeeper://zookeeper/*" );
5284 private URL registryUrl ;
5385 private ZookeeperRegistryFactory zookeeperRegistryFactory ;
5486 private NotifyListener listener ;
5587
88+ // mock object
89+ private static ZookeeperClientManager mockZookeeperClientManager ;
90+ private static ZookeeperClient mockZookeeperClient ;
91+
92+
5693 @ BeforeAll
5794 public static void beforeAll () {
58- zookeeperConnectionAddress1 = System .getProperty ("zookeeper.connection.address.1" );
95+ zookeeperConnectionAddress1 = "zookeeper://localhost:" + "2181" ;
96+ mockZookeeperClientManager = mock (ZookeeperClientManager .class );
97+ mockZookeeperClient = mock (ZookeeperClient .class );
5998 }
6099
100+
61101 @ BeforeEach
62102 public void setUp () throws Exception {
63103 this .registryUrl = URL .valueOf (zookeeperConnectionAddress1 );
64104 zookeeperRegistryFactory = new ZookeeperRegistryFactory (ApplicationModel .defaultModel ());
105+ zookeeperRegistryFactory .setZookeeperTransporter (mockZookeeperClientManager );
106+ when (mockZookeeperClientManager .connect (registryUrl )).thenReturn (mockZookeeperClient );
65107 this .zookeeperRegistry = (ZookeeperRegistry ) zookeeperRegistryFactory .createRegistry (registryUrl );
66108 }
67109
@@ -105,6 +147,7 @@ void testSubscribe() {
105147 @ Test
106148 void testAvailable () {
107149 zookeeperRegistry .register (serviceUrl );
150+ when (mockZookeeperClient .isConnected ()).thenReturn (true );
108151 assertThat (zookeeperRegistry .isAvailable (), is (true ));
109152
110153 zookeeperRegistry .destroy ();
@@ -113,6 +156,7 @@ void testAvailable() {
113156
114157 @ Test
115158 void testLookup () {
159+ when (mockZookeeperClient .getChildren (any ())).thenReturn (Lists .newArrayList (url ));
116160 List <URL > lookup = zookeeperRegistry .lookup (serviceUrl );
117161 assertThat (lookup .size (), is (1 ));
118162
@@ -134,36 +178,19 @@ void testLookupIllegalUrl() {
134178 @ Test
135179 void testLookupWithException () {
136180 URL errorUrl = URL .valueOf ("multicast://0.0.0.0/" );
181+ when (mockZookeeperClient .getChildren (any ())).thenThrow (new IllegalStateException ());
137182 Assertions .assertThrows (RpcException .class , () -> zookeeperRegistry .lookup (errorUrl ));
138183 }
139184
140- @ Disabled
141- @ Test
142- /*
143- This UT is unstable, consider remove it later.
144- @see https://github.com/apache/dubbo/issues/1787
145- */
146- public void testStatusChecker () {
147- RegistryStatusChecker registryStatusChecker = new RegistryStatusChecker (ApplicationModel .defaultModel ());
148- Status status = registryStatusChecker .check ();
149- assertThat (status .getLevel (), is (Status .Level .UNKNOWN ));
150-
151- Registry registry = zookeeperRegistryFactory .getRegistry (registryUrl );
152- assertThat (registry , not (nullValue ()));
153-
154- status = registryStatusChecker .check ();
155- assertThat (status .getLevel (), is (Status .Level .ERROR ));
156-
157- registry .register (serviceUrl );
158- status = registryStatusChecker .check ();
159- assertThat (status .getLevel (), is (Status .Level .OK ));
160- }
161-
162185 @ Test
163186 void testSubscribeAnyValue () throws InterruptedException {
164187 final CountDownLatch latch = new CountDownLatch (1 );
165188 zookeeperRegistry .register (serviceUrl );
166189 zookeeperRegistry .subscribe (anyUrl , urls -> latch .countDown ());
190+ doAnswer (invocationOnMock -> {
191+ latch .countDown ();
192+ return null ;
193+ }).when (mockZookeeperClient ).create (any (),anyBoolean (),anyBoolean ());
167194 zookeeperRegistry .register (serviceUrl );
168195 latch .await ();
169196 }
@@ -176,6 +203,7 @@ void testDestroy() {
176203
177204 @ Test
178205 void testDoRegisterWithException () {
206+ doThrow (new IllegalStateException ()).when (mockZookeeperClient ).create (any (), anyBoolean (), anyBoolean ());
179207 Assertions .assertThrows (RpcException .class , () -> {
180208 URL errorUrl = URL .valueOf ("multicast://0.0.0.0/" );
181209 zookeeperRegistry .doRegister (errorUrl );
@@ -184,6 +212,7 @@ void testDoRegisterWithException() {
184212
185213 @ Test
186214 void testDoUnregisterWithException () {
215+ doThrow (new IllegalStateException ()).when (mockZookeeperClient ).delete (any ());
187216 Assertions .assertThrows (RpcException .class , () -> {
188217 URL errorUrl = URL .valueOf ("multicast://0.0.0.0/" );
189218 zookeeperRegistry .doUnregister (errorUrl );
0 commit comments