View Javadoc
1   /*
2    * The akquinet maven-latex-plugin project
3    *
4    * Copyright (c) 2011 by akquinet tech@spree GmbH
5    *
6    * Licensed under the Apache License, Version 2.0 (the "License");
7    * you may not use this file except in compliance with the License.
8    * You may obtain a copy of the License at
9    *
10   * http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing, software
13   * distributed under the License is distributed on an "AS IS" BASIS,
14   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15   * See the License for the specific language governing permissions and
16   * limitations under the License.
17   */
18  
19  package eu.simuline.m2latex.core;
20  
21  import eu.simuline.m2latex.mojo.MavenLogWrapper;
22  import eu.simuline.m2latex.mojo.PdfMojo;
23  
24  import java.io.File;
25  import java.io.FileFilter;
26  // import java.io.FileWriter;
27  // import java.io.Writer;
28  import java.io.IOException;
29  import java.util.Optional;
30  import static org.mockito.Mockito.mock;
31  import static org.mockito.Mockito.RETURNS_SMART_NULLS;
32  import static org.mockito.Mockito.when;
33  import static org.mockito.Mockito.doNothing;
34  import static org.mockito.Mockito.doThrow;
35  import static org.mockito.Mockito.doCallRealMethod;
36  import static org.mockito.Mockito.verify;
37  import static org.mockito.Mockito.spy;
38  import static org.mockito.Mockito.verifyNoMoreInteractions;
39  import static org.mockito.Mockito.atLeastOnce;
40  import static org.mockito.Mockito.inOrder;
41  
42  // import static org.mockito.ArgumentMatchers.any;
43  import static org.mockito.ArgumentMatchers.anyString;
44  import static org.mockito.ArgumentMatchers.isNull;
45  import static org.mockito.ArgumentMatchers.eq;
46  import static org.mockito.AdditionalMatchers.aryEq;
47  
48  import org.mockito.InOrder;
49  
50  // import org.mockito.stubbing.Answer;
51  // import org.mockito.invocation.InvocationOnMock;
52  
53  import org.junit.Test;
54  // import org.junit.Ignore;
55  import org.junit.Before;
56  import org.junit.After;
57  // import org.junit.BeforeClass;
58  // import org.junit.AfterClass;
59  
60  import static org.junit.Assert.assertEquals;
61  
62  // FIXME: missing: test of logging
63  // FIXME: mocking and verification in parallel
64  // FIXME: rename: mock-->stub
65  // FIXME: missing: test of warnings and errors
66  public class LatexProcessorTest {
67  
68  	private final static File WORKING_DIR =
69  			new File(System.getProperty("unitTestResourcesDir"));
70  
71  	/**
72  	 * Filter rejecting all files. 
73  	 */
74  	private final static FileFilter FILTER_FALSE = new FileFilter() {
75  		public boolean accept(File pathname) {
76  			return false;
77  		}
78  	};
79  
80  	private final CommandExecutor executor =
81  			mock(CommandExecutor.class, RETURNS_SMART_NULLS);
82  	// pertained because of bugfixes 
83  	//private final InOrder inOrderExec = inOrder(this.executor);
84  
85  	private final TexFileUtils fileUtils =
86  			mock(TexFileUtils.class, RETURNS_SMART_NULLS);
87  
88  	// pertained because of bugfixes 
89  	//private final InOrder inOrderFileUtils = inOrder(this.fileUtils);
90  
91  	private final InOrder inOrder = inOrder(this.executor, this.fileUtils);
92  
93  	private final Settings settings = new Settings();
94  
95  	// mock 
96  	// - ignores debug and info 
97  	// - verifies error and warn
98  	//     private LogWrapper log = mock(MavenLogWrapper.class,
99  	// 				  new Answer<Void>() {
100 	// 	public Void answer(InvocationOnMock invocation) throws Throwable {
101 	// System.out.println("answer..");
102 
103 	// 	    String methodName = invocation.getMethod().getName();
104 	// System.out.println("methodName: "+methodName);
105 	// 	    if (methodName.equals("debug") || methodName.equals("info")) {
106 	// //		invocation.callRealMethod();
107 	// 	    } else {
108 	// 		assert methodName.equals("error") || methodName.equals("warn");
109 	// 		LogWrapper lw = (LogWrapper)invocation.getMock();
110 	// 		if (methodName.equals("error")) {
111 	// 		    verify(lw).error(anyString());
112 	// 		} else {
113 	// 		    verify(lw).warn(anyString());
114 	// 		}
115 	// 		// Object[] args = invocation.getArguments();
116 	// 		// Object mock = invocation.getMock();
117 	// 	    }
118 	// System.out.println("..answer");
119 	// return null;
120 	// 	}
121 	//     });
122 	//private LogWrapper log = mock(MavenLogWrapper.class, RETURNS_SMART_NULLS);
123 	private final LogWrapper log =
124 		spy(new MavenLogWrapper(this.getClass()));
125 
126 	private LatexProcessor processor = new LatexProcessor(this.settings,
127 			this.executor, this.log, this.fileUtils, new PdfMojo());
128 
129 	// FIXME: eliminate all those files 
130 	// present in LatexMainDesc 
131 	// and even the others defining LatexMainDescExt including these also 
132 	private File texFile = new File(WORKING_DIR, "test.tex");// LatexMainDesc 
133 	LatexMainDesc desc = new LatexMainDesc(texFile, null);// TBD: replace null by sth sensible. 
134 
135 	// FIXME: used only once
136 	private File dviPdfFile = new File(WORKING_DIR,
137 			"test." + settings.getPdfViaDvi().getLatexOutputFormat());
138 	private File htmlFile = new File(WORKING_DIR, "test.html");
139 	private File auxFile = new File(WORKING_DIR, "test.aux");
140 	private File logFile = new File(WORKING_DIR, "test.log");// LatexMainDesc 
141 
142 	private File bblFile = new File(WORKING_DIR, "test.bbl");
143 	private File blgFile = new File(WORKING_DIR, "test.blg");
144 
145 	private File idxFile = new File(WORKING_DIR, "test.idx");// LatexMainDesc 
146 	private File indFile = new File(WORKING_DIR, "test.ind");// LatexMainDesc 
147 	private File ilgFile = new File(WORKING_DIR, "test.ilg");// LatexMainDesc 
148 
149 	private File glsFile = new File(WORKING_DIR, "test.gls");// LatexMainDesc 
150 	private File glgFile = new File(WORKING_DIR, "test.glg");// LatexMainDesc 
151 	// this one does never exist. 
152 	private File xxxFile = new File(WORKING_DIR, "test");// LatexMainDesc 
153 
154 	// FIXME: needed for later use: test also if toc/lof/lot are not present 
155 	private File tocFile = new File(WORKING_DIR, "test.toc");
156 	private File lofFile = new File(WORKING_DIR, "test.lof");
157 	private File lotFile = new File(WORKING_DIR, "test.lot");
158 
159 	public LatexProcessorTest() {
160 		//this.settings.setPdfViaDvi(true);
161 
162 		// ensures that neither an error nor a warning occurs 
163 		// FIXME: add tests with errors and warnings. 
164 		doThrow(new AssertionError("Found error. ")).when(this.log)
165 				.error(anyString());
166 		doThrow(new AssertionError("Found warning. ")).when(this.log)
167 				.warn(anyString());
168 		doCallRealMethod().when(this.log).info(anyString());
169 		doNothing().when(this.log).debug(anyString());
170 	}
171 
172 	// FIXME: occurs also in other testclasses: 
173 	// to be unified. 
174 	private static void cleanWorkingDir() {
175 		assert WORKING_DIR.isDirectory() : "Expected directory. ";
176 		File[] files = WORKING_DIR.listFiles();
177 		assert files != null : "Working directory is not readable. ";
178 		for (File file : files) {
179 			if (!file.isHidden()) {
180 				file.delete();
181 			}
182 		}
183 	}
184 
185 	@Before
186 	public void setUp() throws IOException {
187 		cleanWorkingDir();
188 		//this.texFile.createNewFile();
189 		//this.auxFile.createNewFile();
190 		this.logFile.createNewFile();
191 		this.blgFile.createNewFile();
192 		//this.pdfFile.createNewFile();
193 	}
194 
195 	@After
196 	public void tearDown() throws IOException {
197 		cleanWorkingDir();
198 	}
199 
200 	//@Ignore 
201 	// FIXME: does not take pdfViaDvi into account 
202 	@Test
203 	public void testProcessLatexSimple() throws BuildFailureException {
204 
205 		mockProcessLatex2pdf(false, false, false);
206 
207 		this.processor.processLatex2pdf(this.desc);
208 		verifyProcessLatex2pdf(false, false, false);
209 		verifyNoMoreInteractions(this.executor);
210 		verifyNoMoreInteractions(this.fileUtils);
211 		//verifyNoMoreInteractions(this.log);
212 	}
213 
214 	//@Ignore 
215 	@Test
216 	public void testProcessLatexWithBibtex() throws BuildFailureException {
217 
218 		mockProcessLatex2pdf(true, false, false);
219 
220 		this.processor.processLatex2pdf(this.desc);
221 		verifyProcessLatex2pdf(true, false, false);
222 		verifyNoMoreInteractions(this.executor);
223 		verifyNoMoreInteractions(this.fileUtils);
224 		//verifyNoMoreInteractions(this.log);
225 	}
226 
227 	//@Ignore 
228 	@Test
229 	public void testProcessLatex2html() throws BuildFailureException {
230 
231 		mockProcessLatex2html(false, false, false);
232 		this.processor.processLatex2html(this.desc);
233 
234 		verifyProcessLatex2html(false, false, false);
235 		verifyNoMoreInteractions(this.executor);
236 		verifyNoMoreInteractions(this.fileUtils);
237 		//verifyNoMoreInteractions(this.log);
238 	}
239 
240 	private void mockProcessLatex2pdf(boolean needBibtex, boolean needMakeIndex,
241 			boolean needMakeGlossaries) throws BuildFailureException {
242 
243 		mockConstrLatexMainDesc();
244 		assert !this.settings.getPdfViaDvi().isViaDvi();
245 		// FIXME: here should be mockProcessLatex2dev
246 		mockProcessLatex2devCore(needBibtex, needMakeIndex, needMakeGlossaries);
247 
248 		when(this.fileUtils.matchInFile(this.logFile,
249 				LatexProcessor.PATTERN_OUFULL_HVBOX)).thenReturn(Boolean.FALSE);
250 
251 		when(this.fileUtils.matchInFile(this.logFile,
252 				this.settings.getPatternWarnLatex())).thenReturn(Boolean.FALSE);
253 	}
254 
255 	private void verifyProcessLatex2pdf(boolean needBibtex, boolean needMakeIndex,
256 			boolean needMakeGlossary) throws BuildFailureException {
257 
258 		//verifyConstrLatexMainDesc();
259 		assert !this.settings.getPdfViaDvi().isViaDvi();
260 		// FIXME: here should be verifyProcessLatex2dev
261 		verifyProcessLatex2devCore(needBibtex, needMakeIndex, needMakeGlossary);
262 
263 		this.inOrder.verify(this.fileUtils).matchInFile(this.logFile,
264 				LatexProcessor.PATTERN_OUFULL_HVBOX);
265 		this.inOrder.verify(this.fileUtils).matchInFile(this.logFile,
266 				this.settings.getPatternWarnLatex());
267 	}
268 
269 	private void mockProcessLatex2html(boolean needBibtex, boolean needMakeIndex,
270 			boolean needMakeGlossaries) throws BuildFailureException {
271 
272 		mockConstrLatexMainDesc();
273 		mockPreProcessLatex2dev(needBibtex, needMakeIndex, needMakeGlossaries);
274 		mockRunLatex2html();
275 	}
276 
277 	private void verifyProcessLatex2html(boolean needBibtex,
278 			boolean needMakeIndex, boolean needMakeGlossary)
279 			throws BuildFailureException {
280 
281 		//verifyConstrLatexMainDesc();
282 		verifyPreProcessLatex2dev(needBibtex, needMakeIndex, needMakeGlossary);
283 		verifyRunLatex2html();
284 	}
285 
286 	private void mockConstrLatexMainDesc() {
287 		//this.desc = this.processor.getLatexMainDesc(this.texFile);
288 
289 		//File texFile = this.texFile;
290 		//assertEquals(this.xxxFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_VOID));
291 		// assertEquals(this.pdfFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_PDF));
292 		// assertEquals(this.dviFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_DVI));
293 		// assertEquals(this.logFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_LOG));
294 
295 		// assertEquals(this.idxFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_IDX));
296 		// assertEquals(this.indFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_IND));
297 		// assertEquals(this.ilgFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_ILG));
298 
299 		// assertEquals(this.glsFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_GLS));
300 		// assertEquals(this.gloFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_GLO));
301 		// assertEquals(this.glgFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_GLG));
302 	}
303 
304 	//    private void verifyConstrLatexMainDesc() {
305 	//	// FIXME: doubling from mockConstrLatexMainDesc()
306 	//	String[] suffixes = new String[] {
307 	//	    LatexProcessor.SUFFIX_VOID,
308 	//	    LatexProcessor.SUFFIX_PDF,
309 	//	    LatexProcessor.SUFFIX_DVI,
310 	//	    LatexProcessor.SUFFIX_LOG,
311 	//	    LatexProcessor.SUFFIX_IDX,
312 	//	    LatexProcessor.SUFFIX_IND,
313 	//	    LatexProcessor.SUFFIX_ILG,
314 	//	    LatexProcessor.SUFFIX_GLS,
315 	//	    LatexProcessor.SUFFIX_GLO,
316 	//	    LatexProcessor.SUFFIX_GLG
317 	//	};
318 	//	for (int idx = 0; idx < suffixes.length; idx++) {
319 	//	    // FIXME: should work also in order. 
320 	//	    // FIXME: observation: in order works iff no atLeastOnce is required
321 	//	    // On the other hand, I am not sure 
322 	//	    // why I need this in the individual cases. 
323 	//	    //this.inOrder.
324 	//	    //if (idx == 1 ||idx == 2) {continue;}
325 	//	    verify(this.fileUtils, atLeastOnce())
326 	//		.replaceSuffix(this.texFile, suffixes[idx]);
327 	//	}
328 	//    }
329 
330 	// FIXME: pdf never via dvi 
331 	// FIXME: parametrization of needMakeIndex, needMakeGlossaries 
332 	// 
333 	private void mockPreProcessLatex2dev(boolean needBibtex,
334 			boolean needMakeIndex, boolean needMakeGlossaries)
335 			throws BuildFailureException {
336 		assert !needMakeIndex && !needMakeGlossaries;
337 
338 		// run latex 
339 		mockRunLatex();
340 		// FIXME: to indicate whether makeindex must be run: 
341 		// method creates .idx or not: use Mockito.thenAnswer for that
342 
343 		// run bibtex, makeIndex and makeGlossary by need 
344 		//mockRunBibtexByNeed(needBibtex);
345 		mockRunMakeIndexByNeed(needMakeIndex);
346 		mockRunMakeGlossaryByNeed(needMakeGlossaries);
347 
348 		if (needBibtex) {
349 			return;
350 		}
351 		// FIXME: not the truth if makeindex and makeglossaries are included 
352 		// and also not if TOC exists. 
353 
354 		assert !this.tocFile.exists() && !this.lofFile.exists()
355 				&& !this.lotFile.exists();
356 		// determine from presence of toc, lof, lot (and idx and other criteria)
357 		// whether to rerun latex: no 
358 		// File texFile = this.texFile;
359 		// assertEquals(this.tocFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_TOC));
360 		// assertEquals(this.lofFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_LOF));
361 		// assertEquals(this.lotFile, TexFileUtils.replaceSuffix(texFile, LatexProcessor.SUFFIX_LOT));
362 	}
363 
364 	private void verifyPreProcessLatex2dev(boolean needBibtex,
365 			boolean needMakeIndex, boolean needMakeGlossaries)
366 			throws BuildFailureException {
367 		assert !needMakeIndex && !needMakeGlossaries;
368 
369 		// run latex 
370 		verifyRunLatex();
371 
372 		// run bibtex, makeIndex and makeGlossary by need 
373 		//verifyRunBibtexByNeed(needBibtex);
374 		verifyRunMakeIndexByNeed(needMakeIndex);
375 		verifyRunMakeGlossaryByNeed(needMakeGlossaries);
376 
377 		if (needBibtex) {
378 			return;
379 		}
380 		// FIXME: not the truth if makeindex and makeglossaries are included 
381 		// and also not if TOC exists. 
382 
383 		assert !this.tocFile.exists() && !this.lofFile.exists()
384 				&& !this.lotFile.exists();
385 		// determine from presence of toc, lof, lot (and idx and other criteria)
386 		// whether to rerun latex: no 
387 
388 		// TBD: replace tests, maybe also LOL
389 		//	// FIXME: duplicate 
390 		//	String[] suffixes = new String[] {
391 		//	    LatexProcessor.SUFFIX_TOC,
392 		//	    LatexProcessor.SUFFIX_LOF,
393 		//	    LatexProcessor.SUFFIX_LOT
394 		//	};
395 		//	for (int idx = 0; idx < suffixes.length; idx++) {
396 		//	    this.inOrder.verify(this.fileUtils)
397 		//		.replaceSuffix(this.texFile, suffixes[idx]);
398 		//	}
399 	}
400 
401 	// FIXME: currently, neither toc nor lof nor lot exist 
402 	private void mockProcessLatex2devCore(boolean needBibtex,
403 			boolean needMakeIndex, boolean needMakeGlossaries)
404 			throws BuildFailureException {
405 
406 		assert !needMakeIndex && !needMakeGlossaries;
407 		assert !this.tocFile.exists() && !this.lofFile.exists()
408 				&& !this.lotFile.exists();
409 		// FIXME: would be safer to define = -1 
410 		assert this.settings.getMaxNumReRunsLatex() == 5;
411 
412 		mockPreProcessLatex2dev(needBibtex, needMakeIndex, needMakeGlossaries);
413 		// preProcessLatex2dev returns 
414 		// 2 if needBibtex 
415 		// since currently neither makeindex nor makeglossaries are supported 
416 		// and neither toc, lof or lot exist: 
417 		// 0 else 
418 
419 		if (needBibtex) {
420 			// numLatexReRuns == 2 
421 			mockRunLatex();
422 			// numLatexReRuns == 1 
423 			// enter for-loop... 
424 			//mockNeedRun(false, this.settings.getPatternReRunMakeIndex());
425 			mockRunLatex();
426 			mockNeedRun(false, this.settings.getPatternReRunLatex());
427 			// second loop 
428 			//mockNeedRun(false, this.settings.getPatternReRunMakeIndex());
429 			// exit for-loop 
430 		} else {
431 			mockNeedRun(false, this.settings.getPatternReRunLatex());
432 			// enter for-loop... 
433 			//mockNeedRun(false, this.settings.getPatternReRunMakeIndex());
434 			// since both conditions are false 
435 			// exit for-loop 
436 		}
437 	}
438 
439 	// FIXME: currently, neither toc nor lof nor lot exist 
440 	private void verifyProcessLatex2devCore(boolean needBibtex,
441 			boolean needMakeIndex, boolean needMakeGlossary)
442 			throws BuildFailureException {
443 
444 		assert !needMakeIndex && !needMakeGlossary;
445 		assert !this.tocFile.exists() && !this.lofFile.exists()
446 				&& !this.lotFile.exists();
447 		// FIXME: would be safer to define = -1 
448 		assert this.settings.getMaxNumReRunsLatex() == 5;
449 
450 		verifyPreProcessLatex2dev(needBibtex, needMakeIndex, needMakeGlossary);
451 		// preProcessLatex2dev returns 
452 		// 2 if needBibtex 
453 		// since currently neither makeindex nor makeglossaries are supported 
454 		// and neither toc, lof or lot exist: 
455 		// 0 else 
456 
457 		if (needBibtex) {
458 			// numLatexReRuns == 2 
459 			verifyRunLatex();
460 			// numLatexReRuns == 1 
461 			// enter for-loop... 
462 			//verifyNeedRun(this.logFile, this.settings.getPatternReRunMakeIndex());
463 			verifyRunLatex();
464 			verifyNeedRun(this.logFile, this.settings.getPatternReRunLatex());
465 			// second loop 
466 			//verifyNeedRun(this.logFile, this.settings.getPatternReRunMakeIndex());
467 			// exit for-loop 
468 		} else {
469 			verifyNeedRun(this.logFile, this.settings.getPatternReRunLatex());
470 			// enter for-loop... 
471 			//verifyNeedRun(this.logFile, this.settings.getPatternReRunMakeIndex());
472 			// since both conditions are false 
473 			// exit for-loop 
474 		}
475 	}
476 
477 	private void mockNeedRun(Boolean retVal, String pattern)
478         throws BuildFailureException {
479 
480 	when(this.fileUtils.matchInFile(this.logFile, pattern))
481 	    .thenReturn(retVal);
482     }
483 
484 	private void verifyNeedRun(File file, String pattern)
485 			throws BuildFailureException {
486 		// FIXME: should work also in order. 
487 		//this.inOrder.
488 		verify(this.fileUtils, atLeastOnce()).matchInFile(file, pattern);
489 	}
490 
491 // 	private void mockRunBibtexByNeed(Boolean runBibtex) 
492 // 	throws BuildFailureException {
493 	
494 // 	//assertEquals(this.auxFile, TexFileUtils.replaceSuffix(this.texFile, LatexProcessor.SUFFIX_AUX));
495 // 	when(this.fileUtils.matchInFile
496 // 	     (this.auxFile, LatexProcessor.PATTERN_NEED_BIBTEX_RUN))
497 // 	    .thenReturn(runBibtex);
498 
499 // 	// FIXME: really needed?? 
500 // //	Writer writer = new FileWriter(this.auxFile);
501 // 	if (!runBibtex) {
502 // //	    writer.write("% no bibtex run");
503 // //	    writer.flush();
504 // 	    return;
505 // 	}
506 // //	writer.write("\\bibdata % bibtex run"); 
507 // //	writer.flush();
508 
509 // 	//assertEquals(this.bblFile, 
510 // 	//	this.fileUtils.replaceSuffix(this.texFile, LatexProcessor.SUFFIX_BBL));
511 
512 // 	// when(this.executor.execute(texFile.getParentFile(),
513 // 	// 			   this.settings.getTexPath(),
514 // 	// 			   this.settings.getBibtexCommand(),
515 // 	// 			   LatexProcessor.buildArguments
516 // 	// 			   (this.settings.getBibtexOptions(), 
517 // 	// 			    this.auxFile),
518 // 	// 			   this.bblFile))
519 // 	//     .thenReturn("");
520 
521 // 	// log file 
522 // 	//assertEquals(this.blgFile, 
523 // 	//	this.fileUtils.replaceSuffix(this.texFile, LatexProcessor.SUFFIX_BLG));
524 // 	// logging errors and warnings 
525 // 	when(this.fileUtils.matchInFile(this.blgFile, 
526 // 					this.settings.getPatternErrBibtex()))
527 // 	    .thenReturn(Boolean.FALSE);
528 // 	when(this.fileUtils.matchInFile(this.blgFile, 
529 // 					this.settings.getPatternWarnBibtex()))
530 // 	    .thenReturn(Boolean.FALSE);
531 //     }
532 
533 	// private void verifyRunBibtexByNeed(Boolean runBibtex)
534 	// 		throws BuildFailureException {
535 	// 	// TBD: replace this by a proper indication that aux-file was read. 
536 	// 	//	this.inOrder.verify(this.fileUtils)
537 	// 	//	    .replaceSuffix(this.texFile, LatexProcessor.SUFFIX_AUX);
538 	// 	verifyNeedRun(this.auxFile, LatexProcessor.PATTERN_NEED_BIBTEX_RUN);
539 
540 	// 	if (!runBibtex) {
541 	// 		return;
542 	// 	}
543 
544 	// 	// TBD: replace this by a proper indication that bbl-file was read. 
545 	// 	//	this.inOrder.verify(this.fileUtils)
546 	// 	//	    .replaceSuffix(this.texFile, LatexProcessor.SUFFIX_BBL);
547 	// 	this.inOrder.verify(this.executor)
548 	// 			.executeEnvR0(eq(WORKING_DIR), isNull(),
549 	// 					eq(this.settings.getCommand(ConverterCategory.BibTeX)),
550 	// 					aryEq(LatexProcessor.buildArguments(
551 	// 							this.settings.getBibtexOptions(), this.auxFile)),
552 	// 					eq(this.bblFile));
553 
554 	// 	// TBD: replace this by a proper indication that blg-file was written. 
555 	// 	// log file 
556 	// 	//	this.inOrder.verify(this.fileUtils)
557 	// 	//	    .replaceSuffix(this.texFile, LatexProcessor.SUFFIX_BLG);
558 	// 	// logging errors and warnings 
559 	// 	this.inOrder.verify(this.fileUtils).matchInFile(this.blgFile,
560 	// 			this.settings.getPatternErrBibtex());
561 	// 	this.inOrder.verify(this.fileUtils).matchInFile(this.blgFile,
562 	// 			this.settings.getPatternWarnBibtex());
563 	// }
564 
565 	private void mockRunMakeIndexByNeed(boolean runMakeIndex) 
566 	throws BuildFailureException {
567 
568 	when(this.fileUtils.getFileFilterReplace(this.idxFile, "-.+"))
569 	    .thenReturn(FILTER_FALSE);
570 
571 	when(this.fileUtils.listFilesOrWarn(WORKING_DIR, FILTER_FALSE))
572 	    .thenReturn(new File[0]);
573 
574 	assert !runMakeIndex;
575 
576 	if (!runMakeIndex) {
577 	    return;
578 	}
579 	mockRunMakeIndex();
580     }
581 
582 	private void verifyRunMakeIndexByNeed(boolean runMakeIndex)
583 			throws BuildFailureException {
584 
585 		this.inOrder.verify(this.fileUtils).getFileFilterReplace(this.idxFile,
586 				"-.+");
587 		this.inOrder.verify(this.fileUtils).listFilesOrWarn(WORKING_DIR,
588 				FILTER_FALSE);
589 
590 		assert !runMakeIndex;
591 
592 		if (!runMakeIndex) {
593 			return;
594 		}
595 		verifyRunMakeIndex();
596 	}
597 
598 	private void mockRunMakeIndex() throws BuildFailureException {
599 		assert false;
600 
601 		// when(this.executor.execute(this.texFile.getParentFile(),
602 		// 			   this.settings.getTexPath(),
603 		// 			   this.settings.getMakeIndexCommand(),
604 		// 			   LatexProcessor.buildArguments
605 		// 			   (this.settings.getMakeIndexOptions(), 
606 		// 			    this.idxFile),
607 		// 			   this.indFile))
608 		//     .thenReturn("");
609 
610 		// since ilg file does not exist 
611 		when(this.fileUtils.matchInFile(this.ilgFile,
612 				this.settings.getPatternErrMakeIndex())).thenReturn(Boolean.FALSE);
613 	}
614 
615 	private void verifyRunMakeIndex() throws BuildFailureException {
616 		assert false;
617 
618 		this.inOrder.verify(this.executor)
619 				.executeEnvR0(eq(WORKING_DIR), isNull(),
620 						eq(this.settings.getCommand(ConverterCategory.MakeIndex)),
621 						aryEq(LatexProcessor.buildArguments(
622 								this.settings.getMakeIndexOptions(), this.idxFile)),
623 						eq(this.indFile));
624 		this.inOrder.verify(this.fileUtils).matchInFile(this.ilgFile,
625 				this.settings.getPatternErrMakeIndex());
626 	}
627 
628 	private void mockRunMakeGlossaryByNeed(boolean runMakeGlossaries)
629 			throws BuildFailureException {
630 
631 		assert !runMakeGlossaries;
632 		if (!runMakeGlossaries) {
633 			return;
634 		}
635 		assert false;
636 
637 		// when(this.executor.execute(this.texFile.getParentFile(),
638 		// 			   this.settings.getTexPath(),
639 		// 			   this.settings.getMakeGlossariesCommand(),
640 		// 			   LatexProcessor.buildArguments
641 		// 			   (this.settings.getMakeGlossariesOptions(), 
642 		// 			    xxxFile),
643 		// 			   glsFile))
644 		//     .thenReturn("");
645 
646 		// since glg file does not exist 
647 		// when(this.fileUtils.matchInFile(this.glgFile,
648 		// 		this.settings.getPatternErrMakeGlossaries())).thenReturn(Boolean.FALSE);
649 	}
650 
651 	private void verifyRunMakeGlossaryByNeed(boolean runMakeGlossaries)
652 			throws BuildFailureException {
653 
654 		assert !runMakeGlossaries;
655 		if (!runMakeGlossaries) {
656 			return;
657 		}
658 		assert false;
659 
660 		this.inOrder.verify(this.executor).executeEnvR0(eq(WORKING_DIR), isNull(),
661 				eq(this.settings.getCommand(ConverterCategory.MakeGlossaries)),
662 				aryEq(LatexProcessor.buildArguments(
663 						this.settings.getMakeGlossariesOptions(), this.xxxFile)),
664 				eq(this.glsFile));
665 		// this.inOrder.verify(this.fileUtils).matchInFile(this.ilgFile,
666 		// 		this.settings.getPatternErrMakeGlossaries());
667 	}
668 
669 	private void mockRunLatex() throws BuildFailureException {
670 
671 	// when(this.executor.execute(this.texFile.getParentFile(),
672 	// 			   this.settings.getTexPath(),
673 	// 			   this.settings.getLatex2pdfCommand(),
674 	// 			   LatexProcessor
675 	// 			   .buildLatexArguments(this.settings, 
676 	// 						this.settings
677 	// 						.getPdfViaDvi(), 
678 	// 						this.texFile),
679 	// 			   this.dviPdfFile))
680 	//     .thenReturn("");
681 
682 	// Ensure that no failure occurred 
683 	// FIXME: missing: testcases with error 
684 	when(this.fileUtils.matchInFile(this.logFile, 
685 					this.settings.getPatternErrLatex()))
686 	    .thenReturn(Boolean.FALSE);
687     }
688 
689 	private void verifyRunLatex() throws BuildFailureException {
690 
691 		// FIXME: should work also in order. 
692 		//this.inOrder.
693 		verify(this.executor, atLeastOnce()).executeEnvR0(eq(WORKING_DIR), isNull(),
694 				eq(this.settings.getCommand(ConverterCategory.LaTeX)),/// TBD: LatexProcessor.getLatex2pdfCommand()
695 				aryEq(LatexProcessor.buildLatexArguments(this.settings,
696 						this.settings.getPdfViaDvi(), this.texFile, false)),
697 				eq(this.dviPdfFile));
698 
699 		// FIXME: should work also in order. 
700 		//this.inOrder.
701 		verify(this.fileUtils, atLeastOnce()).matchInFile(this.logFile,
702 				this.settings.getPatternErrLatex());
703 	}
704 
705 	private void mockRunLatex2html() throws BuildFailureException {
706 		// html to verify whether execution created the expected html file 
707 		assertEquals(this.htmlFile,
708 				TexFileUtils.replaceSuffix(this.texFile, LatexProcessor.SUFFIX_HTML));
709 
710 		// when(this.executor.execute(this.texFile.getParentFile(),
711 		// 			   this.settings.getTexPath(),
712 		// 			   this.settings.getTex4htCommand(),
713 		// 			   LatexProcessor.buildHtlatexArguments
714 		// 			   (this.settings, this.texFile),
715 		// 			   this.htmlFile))
716 		//     .thenReturn("");
717 
718 
719 		// logging errors, bad boxes and other warnings 
720 		when(this.fileUtils.matchInFile(this.logFile,
721 				this.settings.getPatternErrLatex())).thenReturn(Boolean.FALSE);
722 		when(this.fileUtils.matchInFile(this.logFile,
723 				LatexProcessor.PATTERN_OUFULL_HVBOX)).thenReturn(Boolean.FALSE);
724 		when(this.fileUtils.matchInFile(this.logFile,
725 				this.settings.getPatternWarnLatex())).thenReturn(Boolean.FALSE);
726 	}
727 
728 	private void verifyRunLatex2html() throws BuildFailureException {
729 		// TBD: replace by according test
730 		//	this.inOrder.verify(this.fileUtils)
731 		//	    .replaceSuffix(this.texFile, LatexProcessor.SUFFIX_HTML);
732 		this.inOrder.verify(this.executor).executeEnvR0(eq(WORKING_DIR), isNull(),
733 				eq(this.settings.getTex4htCommand()),
734 				aryEq(
735 						LatexProcessor.buildHtlatexArguments(this.settings, this.texFile)),
736 				eq(this.htmlFile));
737 		String[] patterns = new String[] {this.settings.getPatternErrLatex(),
738 				LatexProcessor.PATTERN_OUFULL_HVBOX,
739 				this.settings.getPatternWarnLatex()};
740 		for (int idx = 0; idx < patterns.length; idx++) {
741 			this.inOrder.verify(this.fileUtils).matchInFile(this.logFile,
742 					patterns[idx]);
743 		}
744 	}
745 }