Prechádzať zdrojové kódy

ctest: allow test output to override the 'details' field

Parse test output for <CTestDetails>...</CTestDetails>.
If found, use this value to override the default 'Details' string reported
to CDash.
Zack Galbreath 4 rokov pred
rodič
commit
02f1271bdf

+ 11 - 0
Help/command/ctest_test.rst

@@ -259,3 +259,14 @@ The following example demonstrates how to upload non-image files to CDash.
 If the name of the file to upload is known at configure time, you can use the
 :prop_test:`ATTACHED_FILES` or :prop_test:`ATTACHED_FILES_ON_FAIL` test
 properties instead.
+
+Custom Details
+""""""""""""""
+
+The following example demonstrates how to specify a custom value for the
+``Test Details`` field displayed on CDash.
+
+.. code-block:: c++
+
+   std::cout <<
+     "<CTestDetails>My Custom Details Value</CTestDetails>" << std::endl;

+ 16 - 0
Source/CTest/cmCTestRunTest.cxx

@@ -40,6 +40,22 @@ void cmCTestRunTest::CheckOutput(std::string const& line)
 {
   cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
              this->GetIndex() << ": " << line << std::endl);
+
+  // Check for special CTest XML tags in this line of output.
+  // If any are found, this line is excluded from ProcessOutput.
+  if (!line.empty() && line.find("<CTest") != std::string::npos) {
+    if (this->TestHandler->CustomCompletionStatusRegex.find(line)) {
+      this->TestResult.CustomCompletionStatus =
+        this->TestHandler->CustomCompletionStatusRegex.match(1);
+      cmCTestLog(this->CTest, HANDLER_VERBOSE_OUTPUT,
+                 this->GetIndex() << ": "
+                                  << "Test Details changed to '"
+                                  << this->TestResult.CustomCompletionStatus
+                                  << "'" << std::endl);
+      return;
+    }
+  }
+
   this->ProcessOutput += line;
   this->ProcessOutput += "\n";
 

+ 9 - 1
Source/CTest/cmCTestTestHandler.cxx

@@ -308,6 +308,10 @@ cmCTestTestHandler::cmCTestTestHandler()
   // regex to detect each individual <DartMeasurement>...</DartMeasurement>
   this->DartStuff1.compile(
     "(<DartMeasurement[^<]*</DartMeasurement[a-zA-Z]*>)");
+
+  // regex to detect <CTestDetails>...</CTestDetails>
+  this->CustomCompletionStatusRegex.compile(
+    "<CTestDetails>(.*)</CTestDetails>");
 }
 
 void cmCTestTestHandler::Initialize()
@@ -1460,7 +1464,11 @@ void cmCTestTestHandler::GenerateDartOutput(cmXMLWriter& xml)
     xml.StartElement("NamedMeasurement");
     xml.Attribute("type", "text/string");
     xml.Attribute("name", "Completion Status");
-    xml.Element("Value", result.CompletionStatus);
+    if (result.CustomCompletionStatus.empty()) {
+      xml.Element("Value", result.CompletionStatus);
+    } else {
+      xml.Element("Value", result.CustomCompletionStatus);
+    }
     xml.EndElement(); // NamedMeasurement
 
     xml.StartElement("NamedMeasurement");

+ 2 - 0
Source/CTest/cmCTestTestHandler.h

@@ -175,6 +175,7 @@ public:
     std::string ExceptionStatus;
     bool CompressOutput;
     std::string CompletionStatus;
+    std::string CustomCompletionStatus;
     std::string Output;
     std::string DartString;
     int TestCount;
@@ -358,6 +359,7 @@ private:
   ListOfTests TestList;
   size_t TotalNumberOfTests;
   cmsys::RegularExpression DartStuff;
+  cmsys::RegularExpression CustomCompletionStatusRegex;
 
   std::ostream* LogFile;
 

+ 12 - 0
Tests/RunCMake/ctest_test/RunCMakeTest.cmake

@@ -169,3 +169,15 @@ add_test(
   run_ctest(TestMeasurements)
 endfunction()
 run_measurements()
+
+# Verify that test output can override the Completion Status.
+function(run_completion_status)
+  set(CASE_CMAKELISTS_SUFFIX_CODE [[
+add_test(
+  NAME custom_details
+  COMMAND ${CMAKE_COMMAND} -E
+  echo test output\n<CTestDetails>CustomDetails</CTestDetails>\nmore output)
+  ]])
+  run_ctest(TestCompletionStatus)
+endfunction()
+run_completion_status()

+ 16 - 0
Tests/RunCMake/ctest_test/TestCompletionStatus-check.cmake

@@ -0,0 +1,16 @@
+file(READ "${RunCMake_TEST_BINARY_DIR}/Testing/TAG" _tag)
+string(REGEX REPLACE "^([^\n]*)\n.*$" "\\1" _date "${_tag}")
+file(READ "${RunCMake_TEST_BINARY_DIR}/Testing/${_date}/Test.xml" _test_contents)
+
+# Check custom completion status.
+if(NOT _test_contents MATCHES [[<Value>CustomDetails</Value>]])
+  string(APPEND RunCMake_TEST_FAILED
+    "Could not find expected <Value>CustomDetails</Value> in Test.xml")
+endif()
+# Check test output.
+if(NOT _test_contents MATCHES "test output")
+  string(APPEND RunCMake_TEST_FAILED "Could not find expected string 'test output' in Test.xml")
+endif()
+if(NOT _test_contents MATCHES "more output")
+  string(APPEND RunCMake_TEST_FAILED "Could not find expected string 'more output' in Test.xml")
+endif()