1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240
|
# Set the ExternalProject GIT_TAG to desired_tag, and make sure the
# resulting checked out version is resulting_sha and rebuild.
# This check's the correct behavior of the ExternalProject UPDATE_COMMAND.
# Also verify that a fetch only occurs when fetch_expected is 1.
macro(check_a_tag desired_tag resulting_sha fetch_expected update_strategy)
message( STATUS "Checking ExternalProjectUpdate to tag: ${desired_tag}" )
# Remove the FETCH_HEAD file, so we can check if it gets replaced with a 'git
# fetch'.
set( FETCH_HEAD_file ${ExternalProjectUpdate_BINARY_DIR}/CMakeExternals/Source/TutorialStep1-GIT/.git/FETCH_HEAD )
file( REMOVE ${FETCH_HEAD_file} )
# Give ourselves a marker in the output. It is difficult to tell where we
# are up to without this
message(STATUS "===> check_a_tag ${desired_tag} ${resulting_sha} ${fetch_expected} ${update_strategy}")
# Configure
execute_process(COMMAND ${CMAKE_COMMAND}
-G ${CMAKE_GENERATOR} -T "${CMAKE_GENERATOR_TOOLSET}"
-A "${CMAKE_GENERATOR_PLATFORM}"
-DTEST_GIT_TAG:STRING=${desired_tag}
-DCMAKE_EP_GIT_REMOTE_UPDATE_STRATEGY:STRING=${update_strategy}
${ExternalProjectUpdate_SOURCE_DIR}
WORKING_DIRECTORY ${ExternalProjectUpdate_BINARY_DIR}
RESULT_VARIABLE error_code
)
if(error_code)
message(FATAL_ERROR "Could not configure the project.")
endif()
# Build
execute_process(COMMAND ${CMAKE_COMMAND}
--build ${ExternalProjectUpdate_BINARY_DIR}
RESULT_VARIABLE error_code
)
if(error_code)
message(FATAL_ERROR "Could not build the project.")
endif()
# Check the resulting SHA
execute_process(COMMAND ${GIT_EXECUTABLE}
rev-list --max-count=1 HEAD
WORKING_DIRECTORY ${ExternalProjectUpdate_BINARY_DIR}/CMakeExternals/Source/TutorialStep1-GIT
RESULT_VARIABLE error_code
OUTPUT_VARIABLE tag_sha
OUTPUT_STRIP_TRAILING_WHITESPACE
)
if(error_code)
message(FATAL_ERROR "Could not check the sha.")
endif()
if(NOT (${tag_sha} STREQUAL ${resulting_sha}))
message(FATAL_ERROR "UPDATE_COMMAND produced
${tag_sha}
when
${resulting_sha}
was expected."
)
endif()
if( NOT EXISTS ${FETCH_HEAD_file} AND ${fetch_expected})
message( FATAL_ERROR "Fetch did NOT occur when it was expected.")
endif()
if( EXISTS ${FETCH_HEAD_file} AND NOT ${fetch_expected})
message( FATAL_ERROR "Fetch DID occur when it was not expected.")
endif()
message( STATUS "Checking ExternalProjectUpdate to tag: ${desired_tag} (disconnected)" )
# Remove the FETCH_HEAD file, so we can check if it gets replaced with a 'git
# fetch'.
set( FETCH_HEAD_file ${ExternalProjectUpdate_BINARY_DIR}/CMakeExternals/Source/TutorialStep2-GIT/.git/FETCH_HEAD )
file( REMOVE ${FETCH_HEAD_file} )
# Check initial SHA
execute_process(COMMAND ${GIT_EXECUTABLE}
rev-list --max-count=1 HEAD
WORKING_DIRECTORY ${ExternalProjectUpdate_BINARY_DIR}/CMakeExternals/Source/TutorialStep2-GIT
RESULT_VARIABLE error_code
OUTPUT_VARIABLE initial_sha
OUTPUT_STRIP_TRAILING_WHITESPACE
)
# Configure
execute_process(COMMAND ${CMAKE_COMMAND}
-G ${CMAKE_GENERATOR} -T "${CMAKE_GENERATOR_TOOLSET}"
-A "${CMAKE_GENERATOR_PLATFORM}"
-DTEST_GIT_TAG:STRING=${desired_tag}
${ExternalProjectUpdate_SOURCE_DIR}
WORKING_DIRECTORY ${ExternalProjectUpdate_BINARY_DIR}
RESULT_VARIABLE error_code
)
if(error_code)
message(FATAL_ERROR "Could not configure the project.")
endif()
# Build
execute_process(COMMAND ${CMAKE_COMMAND}
--build ${ExternalProjectUpdate_BINARY_DIR}
RESULT_VARIABLE error_code
)
if(error_code)
message(FATAL_ERROR "Could not build the project.")
endif()
if( EXISTS ${FETCH_HEAD_file} )
message( FATAL_ERROR "Fetch occurred when it was not expected.")
endif()
# Check the resulting SHA
execute_process(COMMAND ${GIT_EXECUTABLE}
rev-list --max-count=1 HEAD
WORKING_DIRECTORY ${ExternalProjectUpdate_BINARY_DIR}/CMakeExternals/Source/TutorialStep2-GIT
RESULT_VARIABLE error_code
OUTPUT_VARIABLE tag_sha
OUTPUT_STRIP_TRAILING_WHITESPACE
)
if(error_code)
message(FATAL_ERROR "Could not check the sha.")
endif()
if(NOT (${tag_sha} STREQUAL ${initial_sha}))
message(FATAL_ERROR "Update occurred when it was not expected.")
endif()
# Update
execute_process(COMMAND ${CMAKE_COMMAND}
--build ${ExternalProjectUpdate_BINARY_DIR}
--target TutorialStep2-GIT-update
RESULT_VARIABLE error_code
)
if(error_code)
message(FATAL_ERROR "Could not build the project.")
endif()
# Check the resulting SHA
execute_process(COMMAND ${GIT_EXECUTABLE}
rev-list --max-count=1 HEAD
WORKING_DIRECTORY ${ExternalProjectUpdate_BINARY_DIR}/CMakeExternals/Source/TutorialStep2-GIT
RESULT_VARIABLE error_code
OUTPUT_VARIABLE tag_sha
OUTPUT_STRIP_TRAILING_WHITESPACE
)
if(error_code)
message(FATAL_ERROR "Could not check the sha.")
endif()
if(NOT (${tag_sha} STREQUAL ${resulting_sha}))
message(FATAL_ERROR "UPDATE_COMMAND produced
${tag_sha}
when
${resulting_sha}
was expected."
)
endif()
if( NOT EXISTS ${FETCH_HEAD_file} AND ${fetch_expected})
message( FATAL_ERROR "Fetch did NOT occur when it was expected.")
endif()
if( EXISTS ${FETCH_HEAD_file} AND NOT ${fetch_expected})
message( FATAL_ERROR "Fetch DID occur when it was not expected.")
endif()
endmacro()
find_package(Git)
set(do_git_tests 0)
if(GIT_EXECUTABLE)
set(do_git_tests 1)
message(STATUS "GIT_VERSION_STRING='${GIT_VERSION_STRING}'")
if("${GIT_VERSION_STRING}" VERSION_LESS 1.6.5)
message(STATUS "No ExternalProject git tests with git client less than version 1.6.5")
set(do_git_tests 0)
endif()
endif()
# When re-running tests locally, this ensures we always start afresh
file(REMOVE_RECURSE ${ExternalProjectUpdate_BINARY_DIR}/CMakeExternals)
if(do_git_tests)
check_a_tag(origin/master b5752a26ae448410926b35c275af3c192a53722e 1 REBASE)
check_a_tag(tag1 d1970730310fe8bc07e73f15dc570071f9f9654a 1 REBASE)
# With the Git UPDATE_COMMAND performance patch, this will not require a
# 'git fetch'
check_a_tag(tag1 d1970730310fe8bc07e73f15dc570071f9f9654a 0 REBASE)
check_a_tag(tag2 5842b503ba4113976d9bb28d57b5aee1ad2736b7 1 REBASE)
check_a_tag(d19707303 d1970730310fe8bc07e73f15dc570071f9f9654a 0 REBASE)
check_a_tag(origin/master b5752a26ae448410926b35c275af3c192a53722e 1 REBASE)
# This is a remote symbolic ref, so it will always trigger a 'git fetch'
check_a_tag(origin/master b5752a26ae448410926b35c275af3c192a53722e 1 REBASE)
foreach(strategy IN ITEMS CHECKOUT REBASE_CHECKOUT)
# Move local master back, then apply a change that will cause a conflict
# during rebase
execute_process(COMMAND ${GIT_EXECUTABLE} checkout master
WORKING_DIRECTORY ${ExternalProjectUpdate_BINARY_DIR}/CMakeExternals/Source/TutorialStep1-GIT
RESULT_VARIABLE error_code
)
if(error_code)
message(FATAL_ERROR "Could not reset local master back to tag1.")
endif()
execute_process(COMMAND ${GIT_EXECUTABLE} reset --hard tag1
WORKING_DIRECTORY ${ExternalProjectUpdate_BINARY_DIR}/CMakeExternals/Source/TutorialStep1-GIT
RESULT_VARIABLE error_code
)
if(error_code)
message(FATAL_ERROR "Could not reset local master back to tag1.")
endif()
set(cmlFile ${ExternalProjectUpdate_BINARY_DIR}/CMakeExternals/Source/TutorialStep1-GIT/CMakeLists.txt)
file(READ ${cmlFile} contents)
string(REPLACE "find TutorialConfig.h" "find TutorialConfig.h (conflict here)"
conflictingContent "${contents}"
)
file(WRITE ${cmlFile} "${conflictingContent}")
execute_process(COMMAND ${GIT_EXECUTABLE} commit -a -m "This should cause a conflict"
WORKING_DIRECTORY ${ExternalProjectUpdate_BINARY_DIR}/CMakeExternals/Source/TutorialStep1-GIT
RESULT_VARIABLE error_code
)
if(error_code)
message(FATAL_ERROR "Could not commit conflicting change.")
endif()
# This should discard our commit but leave behind an annotated tag
check_a_tag(origin/master b5752a26ae448410926b35c275af3c192a53722e 1 ${strategy})
endforeach()
# This file matches a .gitignore rule that the last commit defines. We can't
# directly check that updates don't stash ignored contents because the stash
# and pop are both done within the update step. We don't have an opportunity
# to check things in between, but we can at least check that the update step
# doesn't choke on it.
set(ignoredFile ${ExternalProjectUpdate_BINARY_DIR}/CMakeExternals/Source/TutorialStep1-GIT/ignored_item)
file(TOUCH ${ignoredFile})
check_a_tag(origin/master b5752a26ae448410926b35c275af3c192a53722e 1 REBASE)
if(NOT EXISTS ${ignoredFile})
message(FATAL_ERROR "Ignored file is missing")
endif()
endif()
|