View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *      http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.apache.juneau.commons.io;
18  
19  import static org.junit.jupiter.api.Assertions.*;
20  
21  import java.io.*;
22  
23  import org.apache.juneau.*;
24  import org.junit.jupiter.api.*;
25  
26  /**
27   * Tests for {@link Console}.
28   */
29  class Console_Test extends TestBase {
30  
31  	private PrintStream originalOut;
32  	private PrintStream originalErr;
33  	private ByteArrayOutputStream outCapture;
34  	private ByteArrayOutputStream errCapture;
35  
36  	@BeforeEach
37  	void setUp() {
38  		originalOut = System.out;
39  		originalErr = System.err;
40  		outCapture = new ByteArrayOutputStream();
41  		errCapture = new ByteArrayOutputStream();
42  		System.setOut(new PrintStream(outCapture));
43  		System.setErr(new PrintStream(errCapture));
44  	}
45  
46  	@AfterEach
47  	void tearDown() {
48  		System.setOut(originalOut);
49  		System.setErr(originalErr);
50  	}
51  
52  	//====================================================================================================
53  	// Constructor (line 29)
54  	//====================================================================================================
55  	@Test
56  	void a00_constructor() {
57  		// Test line 29: class instantiation
58  		// Console has an implicit public no-arg constructor
59  		var instance = new Console();
60  		assertNotNull(instance);
61  	}
62  
63  	//====================================================================================================
64  	// out(String, Object...) tests
65  	//====================================================================================================
66  
67  	@Test
68  	void a01_out_basic() {
69  		Console.out("test");
70  		var output = outCapture.toString();
71  		assertTrue(output.contains("test"), output);
72  		assertTrue(output.endsWith(System.lineSeparator()), output);
73  	}
74  
75  	@Test
76  	void a02_out_withSingleArgument() {
77  		Console.out("test{0}", 123);
78  		var output = outCapture.toString();
79  		assertTrue(output.contains("test123"), output);
80  	}
81  
82  	@Test
83  	void a03_out_withMultipleArguments() {
84  		Console.out("test{0} {1} {2}", "a", "b", "c");
85  		var output = outCapture.toString();
86  		assertTrue(output.contains("testa b c"), output);
87  	}
88  
89  	@Test
90  	void a04_out_withNullArgument() {
91  		Console.out("test{0}", (Object)null);
92  		var output = outCapture.toString();
93  		assertTrue(output.contains("testnull"), output);
94  	}
95  
96  	@Test
97  	void a05_out_withEmptyMessage() {
98  		Console.out("");
99  		var output = outCapture.toString();
100 		assertTrue(output.endsWith(System.lineSeparator()), output);
101 	}
102 
103 	@Test
104 	void a06_out_withNoArguments() {
105 		Console.out("test");
106 		var output = outCapture.toString();
107 		assertTrue(output.contains("test"), output);
108 	}
109 
110 	@Test
111 	void a07_out_withMessageFormatPattern() {
112 		Console.out("Value: {0,number}", 12345);
113 		var output = outCapture.toString();
114 		assertTrue(output.contains("Value:"), output);
115 		// MessageFormat may add locale-specific formatting (e.g., commas), so check for digits
116 		assertTrue(output.matches("(?s).*Value:.*[0-9].*"), 
117 			"Output should contain 'Value:' and at least one digit. Actual: " + output);
118 	}
119 
120 	@Test
121 	void a08_out_withSpecialCharacters() {
122 		Console.out("test{0}", "a\nb\tc");
123 		var output = outCapture.toString();
124 		assertTrue(output.contains("testa"), output);
125 	}
126 
127 	@Test
128 	void a09_out_withNumberFormatting() {
129 		Console.out("Number: {0,number,integer}", 1234);
130 		var output = outCapture.toString();
131 		assertTrue(output.contains("Number:"), output);
132 		// MessageFormat may add locale-specific formatting (e.g., commas), so check for digits
133 		assertTrue(output.matches("(?s).*Number:.*[0-9].*"), 
134 			"Output should contain 'Number:' and at least one digit. Actual: " + output);
135 	}
136 
137 	@Test
138 	void a10_out_withDateFormatting() {
139 		Console.out("Date: {0,date}", new java.util.Date(0));
140 		var output = outCapture.toString();
141 		assertTrue(output.contains("Date:"), output);
142 	}
143 
144 	@Test
145 	void a11_out_doesNotWriteToErr() {
146 		Console.out("test");
147 		var errOutput = errCapture.toString();
148 		assertTrue(errOutput.isEmpty(), "err should be empty but was: " + errOutput);
149 	}
150 
151 	//====================================================================================================
152 	// err(String, Object...) tests
153 	//====================================================================================================
154 
155 	@Test
156 	void b01_err_basic() {
157 		Console.err("test");
158 		var output = errCapture.toString();
159 		assertTrue(output.contains("test"), output);
160 		assertTrue(output.endsWith(System.lineSeparator()), output);
161 	}
162 
163 	@Test
164 	void b02_err_withSingleArgument() {
165 		Console.err("test{0}", 123);
166 		var output = errCapture.toString();
167 		assertTrue(output.contains("test123"), output);
168 	}
169 
170 	@Test
171 	void b03_err_withMultipleArguments() {
172 		Console.err("test{0} {1} {2}", "a", "b", "c");
173 		var output = errCapture.toString();
174 		assertTrue(output.contains("testa b c"), output);
175 	}
176 
177 	@Test
178 	void b04_err_withNullArgument() {
179 		Console.err("test{0}", (Object)null);
180 		var output = errCapture.toString();
181 		assertTrue(output.contains("testnull"), output);
182 	}
183 
184 	@Test
185 	void b05_err_withEmptyMessage() {
186 		Console.err("");
187 		var output = errCapture.toString();
188 		assertTrue(output.endsWith(System.lineSeparator()), output);
189 	}
190 
191 	@Test
192 	void b06_err_withNoArguments() {
193 		Console.err("test");
194 		var output = errCapture.toString();
195 		assertTrue(output.contains("test"), output);
196 	}
197 
198 	@Test
199 	void b07_err_withMessageFormatPattern() {
200 		Console.err("Error: {0,number}", 12345);
201 		var output = errCapture.toString();
202 		assertTrue(output.contains("Error:"), output);
203 		// MessageFormat may add locale-specific formatting (e.g., commas), so check for digits
204 		assertTrue(output.matches("(?s).*Error:.*[0-9].*"), 
205 			"Output should contain 'Error:' and at least one digit. Actual: " + output);
206 	}
207 
208 	@Test
209 	void b08_err_withSpecialCharacters() {
210 		Console.err("test{0}", "a\nb\tc");
211 		var output = errCapture.toString();
212 		assertTrue(output.contains("testa"), output);
213 	}
214 
215 	@Test
216 	void b09_err_withNumberFormatting() {
217 		Console.err("Number: {0,number,integer}", 1234);
218 		var output = errCapture.toString();
219 		assertTrue(output.contains("Number:"), output);
220 		// MessageFormat may add locale-specific formatting (e.g., commas), so check for digits
221 		assertTrue(output.matches("(?s).*Number:.*[0-9].*"), 
222 			"Output should contain 'Number:' and at least one digit. Actual: " + output);
223 	}
224 
225 	@Test
226 	void b10_err_withDateFormatting() {
227 		Console.err("Date: {0,date}", new java.util.Date(0));
228 		var output = errCapture.toString();
229 		assertTrue(output.contains("Date:"), output);
230 	}
231 
232 	@Test
233 	void b11_err_doesNotWriteToOut() {
234 		Console.err("test");
235 		var outOutput = outCapture.toString();
236 		assertTrue(outOutput.isEmpty(), "out should be empty but was: " + outOutput);
237 	}
238 
239 	//====================================================================================================
240 	// Integration tests
241 	//====================================================================================================
242 
243 	@Test
244 	void c01_bothOutAndErr() {
245 		Console.out("out message");
246 		Console.err("err message");
247 		var outOutput = outCapture.toString();
248 		var errOutput = errCapture.toString();
249 		assertTrue(outOutput.contains("out message"), outOutput);
250 		assertTrue(errOutput.contains("err message"), errOutput);
251 		assertFalse(outOutput.contains("err message"), outOutput);
252 		assertFalse(errOutput.contains("out message"), errOutput);
253 	}
254 
255 	@Test
256 	void c02_multipleCalls() {
257 		Console.out("message1");
258 		Console.out("message2");
259 		Console.err("error1");
260 		Console.err("error2");
261 		var outOutput = outCapture.toString();
262 		var errOutput = errCapture.toString();
263 		assertTrue(outOutput.contains("message1"), outOutput);
264 		assertTrue(outOutput.contains("message2"), outOutput);
265 		assertTrue(errOutput.contains("error1"), errOutput);
266 		assertTrue(errOutput.contains("error2"), errOutput);
267 	}
268 
269 	@Test
270 	void c03_complexFormatting() {
271 		Console.out("User {0} has {1} items worth {2,number,currency}", "John", 5, 99.99);
272 		var output = outCapture.toString();
273 		assertTrue(output.contains("User"), output);
274 		assertTrue(output.contains("John"), output);
275 		assertTrue(output.contains("5"), output);
276 	}
277 }
278