View Javadoc
1   /*
2    * MIT License
3    * Copyright (c) 2006-2025 JMockit developers
4    * See LICENSE file for full license text.
5    */
6   package mockit;
7   
8   import static org.junit.jupiter.api.Assertions.assertEquals;
9   import static org.junit.jupiter.api.Assertions.assertFalse;
10  import static org.junit.jupiter.api.Assertions.assertNotNull;
11  import static org.junit.jupiter.api.Assertions.assertNull;
12  import static org.junit.jupiter.api.Assertions.assertSame;
13  import static org.junit.jupiter.api.Assertions.assertTrue;
14  import static org.junit.jupiter.api.Assertions.fail;
15  
16  import java.io.ByteArrayOutputStream;
17  import java.io.File;
18  import java.io.IOException;
19  import java.io.OutputStream;
20  import java.net.HttpURLConnection;
21  import java.net.URL;
22  import java.net.URLConnection;
23  import java.net.URLStreamHandler;
24  import java.nio.file.Path;
25  
26  import mockit.integration.junit5.ExpectedException;
27  import mockit.integration.junit5.JMockitExtension;
28  
29  import org.junit.jupiter.api.Test;
30  import org.junit.jupiter.api.extension.ExtendWith;
31  
32  /**
33   * The Class ClassLoadingAndJREMocksTest.
34   */
35  @ExtendWith(JMockitExtension.class)
36  class ClassLoadingAndJREMocksTest {
37  
38      /**
39       * The Class Foo.
40       */
41      static class Foo {
42      }
43  
44      /**
45       * Fake file.
46       */
47      @Test
48      void fakeFile() {
49          new MockUp<File>() {
50              @Mock
51              void $init(String name) {
52              } // not necessary, except to verify non-occurrence of NPE
53  
54              @Mock
55              boolean exists() {
56                  return true;
57              }
58          };
59  
60          new Foo(); // causes a class load
61          assertTrue(Path.of("filePath").toFile().exists());
62      }
63  
64      /**
65       * Fake file safely using reentrant fake method.
66       */
67      @Test
68      void fakeFileSafelyUsingReentrantFakeMethod() {
69          new MockUp<File>() {
70              @Mock
71              boolean exists(Invocation inv) {
72                  File it = inv.getInvokedInstance();
73                  return "testFile".equals(it.getName()) || inv.<Boolean> proceed();
74              }
75          };
76  
77          checkForTheExistenceOfSeveralFiles();
78      }
79  
80      /**
81       * Check for the existence of several files.
82       */
83      void checkForTheExistenceOfSeveralFiles() {
84          assertFalse(Path.of("someOtherFile").toFile().exists());
85          assertTrue(Path.of("testFile").toFile().exists());
86          assertFalse(Path.of("yet/another/file").toFile().exists());
87          assertTrue(Path.of("testFile").toFile().exists());
88      }
89  
90      /**
91       * Fake file safely using proceed.
92       */
93      @Test
94      void fakeFileSafelyUsingProceed() {
95          new MockUp<File>() {
96              @Mock
97              boolean exists(Invocation inv) {
98                  File it = inv.getInvokedInstance();
99                  return "testFile".equals(it.getName()) || inv.<Boolean> proceed();
100             }
101         };
102 
103         checkForTheExistenceOfSeveralFiles();
104     }
105 
106     /**
107      * Attempt to mock non mockable JRE class.
108      *
109      * @param mock
110      *            the mock
111      */
112     @Test
113     void attemptToMockNonMockableJREClass(@Mocked Integer mock) {
114         assertNull(mock);
115     }
116 
117     /**
118      * Mock URL and URL connection.
119      *
120      * @param mockUrl
121      *            the mock url
122      * @param mockConnection
123      *            the mock connection
124      *
125      * @throws Exception
126      *             the exception
127      */
128     @Test
129     void mockURLAndURLConnection(@Mocked URL mockUrl, @Mocked URLConnection mockConnection) throws Exception {
130         URLConnection conn = mockUrl.openConnection();
131 
132         assertSame(mockConnection, conn);
133     }
134 
135     /**
136      * Mock URL and http URL connection.
137      *
138      * @param mockUrl
139      *            the mock url
140      * @param mockConnection
141      *            the mock connection
142      *
143      * @throws Exception
144      *             the exception
145      */
146     @Test
147     void mockURLAndHttpURLConnection(@Mocked URL mockUrl, @Mocked HttpURLConnection mockConnection) throws Exception {
148         HttpURLConnection conn = (HttpURLConnection) mockUrl.openConnection();
149         assertSame(mockConnection, conn);
150     }
151 
152     /**
153      * Mock URL and http URL connection with dynamic mock.
154      *
155      * @param mockHttpConnection
156      *            the mock http connection
157      *
158      * @throws Exception
159      *             the exception
160      */
161     @Test
162     void mockURLAndHttpURLConnectionWithDynamicMock(@Mocked final HttpURLConnection mockHttpConnection)
163             throws Exception {
164         final URL url = new URL("http://nowhere");
165 
166         new Expectations(url) {
167             {
168                 url.openConnection();
169                 result = mockHttpConnection;
170                 mockHttpConnection.getOutputStream();
171                 result = new ByteArrayOutputStream();
172             }
173         };
174 
175         // Code under test:
176         HttpURLConnection conn = (HttpURLConnection) url.openConnection();
177         conn.setDoOutput(true);
178         conn.setRequestMethod("PUT");
179         OutputStream out = conn.getOutputStream();
180 
181         assertNotNull(out);
182 
183         new Verifications() {
184             {
185                 mockHttpConnection.setDoOutput(true);
186                 mockHttpConnection.setRequestMethod("PUT");
187             }
188         };
189     }
190 
191     /**
192      * Read resource content.
193      *
194      * @return the string
195      *
196      * @throws IOException
197      *             Signals that an I/O exception has occurred.
198      */
199     String readResourceContent() throws IOException {
200         URL url = new URL("http://remoteHost/aResource");
201         URLConnection connection = url.openConnection();
202 
203         connection.setConnectTimeout(1000);
204         connection.connect();
205 
206         return connection.getContent().toString();
207     }
208 
209     /**
210      * Cascading mocked URL with injectable cascaded URL connection.
211      *
212      * @param anyUrl
213      *            the any url
214      * @param cascadedUrlConnection
215      *            the cascaded url connection
216      *
217      * @throws Exception
218      *             the exception
219      */
220     @Test
221     void cascadingMockedURLWithInjectableCascadedURLConnection(@Mocked URL anyUrl,
222             @Injectable final URLConnection cascadedUrlConnection) throws Exception {
223         String testContent = recordURLConnectionToReturnContent(cascadedUrlConnection);
224 
225         String content = readResourceContent();
226 
227         assertEquals(testContent, content);
228     }
229 
230     /**
231      * Record URL connection to return content.
232      *
233      * @param urlConnection
234      *            the url connection
235      *
236      * @return the string
237      *
238      * @throws IOException
239      *             Signals that an I/O exception has occurred.
240      */
241     String recordURLConnectionToReturnContent(final URLConnection urlConnection) throws IOException {
242         final String testContent = "testing";
243         new Expectations() {
244             {
245                 urlConnection.getContent();
246                 result = testContent;
247             }
248         };
249         return testContent;
250     }
251 
252     /**
253      * Fake URL using injectable URL connection.
254      *
255      * @param urlConnection
256      *            the url connection
257      *
258      * @throws Exception
259      *             the exception
260      */
261     @Test
262     void fakeURLUsingInjectableURLConnection(@Injectable final URLConnection urlConnection) throws Exception {
263         final String testContent = recordURLConnectionToReturnContent(urlConnection);
264         new MockUp<URL>() {
265             @Mock
266             void $init(URL context, String spec, URLStreamHandler handler) {
267             }
268 
269             @Mock
270             URLConnection openConnection() {
271                 return urlConnection;
272             }
273         };
274 
275         String content = readResourceContent();
276 
277         assertEquals(testContent, content);
278     }
279 
280     /**
281      * Attempt to mock JRE class that is never mockable.
282      *
283      * @param mockClass
284      *            the mock class
285      */
286     @Test
287     @ExpectedException(IllegalArgumentException.class)
288     public void attemptToMockJREClassThatIsNeverMockable(@Mocked Class<?> mockClass) {
289         fail("Should never get here");
290     }
291 
292 }