Skip to content

Instantly share code, notes, and snippets.

@Potherca
Last active February 7, 2020 07:11
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Potherca/6d615b893c2f93ce391e4c7a5c6fade9 to your computer and use it in GitHub Desktop.
Save Potherca/6d615b893c2f93ce391e4c7a5c6fade9 to your computer and use it in GitHub Desktop.
Automated reproduction of all scenarios related to Dealerdirect/phpcodesniffer-composer-installer issues #105

Introduction

This gist contains a BASH script that runs through all scenarios related to Dealerdirect/phpcodesniffer-composer-installer issues #105.

For v0.6.0 of phpcodesniffer-composer-installer, all scenario(s) fail.

These are the scenario reported in the issue and the scenario with 'composer run-script'

Screenshot of test results

Usage example

The test scenarios can be run like this:

bash ./reproduce_issue_105.sh /tmp

The test scenarios can also be run with a development version of the phpcodesniffer-composer-installer plugin. In order to do so, pass the path to plugin as the second parameter:

bash ./reproduce_issue_105.sh /tmp ./phpcodesniffer-composer-installer

Factors

The following factors are involved in the scenarios:

  • Running a composer command (A)
  • Running composer run-script (B)

Variations

The Commands and Run Scripts are present in the scenarios in the following variations:

  1. install command (1)
  2. update command (2)
  3. post-install-cmd script (3)
  4. post-update-cmd script (4)
  5. install-codestandards script (5)

Flow

The scenarios all go through the same flow.

Scenarios

The above factors, in their variations, give us the following 5 possible scenarios:

  1. (A)
    1. (1)
    2. (2)
  2. (B)
    1. (3)
    2. (4)
    3. (5)

Example output

For v0.6.0 of phpcodesniffer-composer-installer, running the scenarios gives the following output:

❌ 01. Running scenario for command 'install'
❌ 02. Running scenario for command 'update'
❌ 03. Running scenario for script 'post-install-cmd'
❌ 04. Running scenario for script 'post-update-cmd'
❌ 05. Running scenario for script 'install-codestandards'
       [ END ]
 ❌ Failure
{
"name": "potherca/phpcodesniffer-composer-installer-issue-105",
"description": "Full reproduction scenario for 'dealerdirect/phpcodesniffer-composer-installer' issue 105",
"type": "project",
"license": "GPL-3.0-or-later",
"authors": [{
"name": "Ben Peachey",
"email": "potherca@gmail.com"
}],
"require": {},
"config": {
"sort-packages": true
},
"scripts": {
"post-install-cmd": [
"echo ' =====> post-install-cmd'"
],
"post-update-cmd": [
"echo ' =====> post-update-cmd'"
],
"install-codestandards": [
"Dealerdirect\\Composer\\Plugin\\Installers\\PHPCodeSniffer\\Plugin::run",
"echo ' =====> install-codestandards'"
]
}
}
#!/usr/bin/env bash
set -o errexit -o errtrace -o nounset -o pipefail
reproduce_issue_105() {
local sIssueNumber sScript sScriptPath
local bDebug
local -i iExitCode=0
readonly sIssueNumber=105
readonly bDebug=false
readonly sScriptPath="$(realpath "$(dirname "$(readlink -f "$0")")")"
usage() {
readonly sScript="$(basename "$0")"
cat << EOF
Usage: ${sScript} <directory> [plugin-path]
Runs all test scenarios related to issues #${sIssueNumber} on <directory>
Example:
bash ${sScript} /tmp
The test scenarios can also be run with a development version of the
phpcodesniffer-composer-installer plugin.
In order to do so, pass the [plugin-path] as the second parameter:
bash ${sScript} /tmp ./phpcodesniffer-composer-installer
For issue details see https://github.com/Dealerdirect/phpcodesniffer-composer-installer/issues/${sIssueNumber}
EOF
}
composer_init() {
cp "${sScriptPath}/composer.json" "${sDirectory}/composer.json"
}
message(){
printf '%-80s\n' "$(echo -e "${@}")"
}
message_replace(){
if [[ "${bDebug}" = true ]];then
echo -e "${@}"
else
echo -en "${*}\r"
fi
}
run() {
local -i iCounter
local sDirectory sDirectoryParameter sOutput sPluginPath sPluginPathParameter sScenario sResult
readonly sDirectoryParameter="${1?One parameter required: <directory> [plugin-path]}"
readonly sDirectory="$(realpath "${sDirectoryParameter}")"
if [[ "${2:-}" != '' ]];then
readonly sPluginPathParameter="${2}"
readonly sPluginPath="$(realpath "${sPluginPathParameter}")"
else
readonly sPluginPath=''
fi
local -a -r aScenarios=(
'install:command'
'update:command'
'post-install-cmd:script'
'post-update-cmd:script'
'install-codestandards:script'
)
cleanup() {
if [[ -n ${sDirectory:-} ]];then
rm -rdf "${sDirectory}/vendor/" "${sDirectory}/composer.json" "${sDirectory}/composer.lock"
fi
}
if [[ -d "${sDirectory}" ]];then
trap cleanup EXIT INT TERM
iCounter=0
pushd "${sDirectory}" > /dev/null
for sScenario in "${aScenarios[@]}"; do
iCounter=$((iCounter+1))
sCounterText="$(printf "%02d" "${iCounter}")"
local IFS=:
read -r sCommand sType <<< "${sScenario}"
sScenarioText="Running scenario for ${sType} '${sCommand}'"
echo " ${sCounterText}. [START] ${sScenarioText}"
composer_init "$(basename "${sDirectory}")" "${sIssueNumber}"
message_replace " [. ] Install plugin v0.5.0"
composer require --quiet --ignore-platform-reqs 'dealerdirect/phpcodesniffer-composer-installer:0.5.0'
message_replace " [.. ] Update plugin to v0.6.1"
composer require --quiet --ignore-platform-reqs --no-update 'dealerdirect/phpcodesniffer-composer-installer'
message_replace " [... ] Install updated plugin"
sOutput="$(composer update --ignore-platform-reqs 2>&1)"
{
echo "${sOutput}" | grep --quiet " =====> post-update-cmd"
} || echo '!!! NOT FOUND !!!'
if [[ "${sPluginPath}" != '' ]];then
message_replace " [...* ] Use plugin from ${sPluginPath}"
rm -rdf "${sDirectory}/vendor/dealerdirect/phpcodesniffer-composer-installer"
mkdir -p "${sDirectory}/vendor/dealerdirect"
cp -r "${sPluginPath}" "${sDirectory}/vendor/dealerdirect/phpcodesniffer-composer-installer"
fi
sResult='✔️'
message_replace " [.... ] Running ${sType} ${sCommand}"
if [[ "${sType}" = 'script' ]];then
sOutput="$(composer run-script "${sCommand}" 2>&1)"
{
echo "${sOutput}" | grep --quiet " =====> ${sCommand}"
} || {
if [[ "${bDebug}" = true ]];then
echo "Could not find ' =====> ${sCommand}' in the ouptut: "
echo "${sOutput}"
fi
sResult='❌'
iExitCode=1
}
else
sOutput="$(composer "${sCommand}" --ignore-platform-reqs 2>&1)"
{
echo "${sOutput}" | grep --quiet " =====> post-${sCommand}-cmd"
} || {
if [[ "${bDebug}" = true ]];then
echo "Could not find ' =====> post-${sCommand}-cmd' in the ouptut: "
echo "${sOutput}"
fi
sResult='❌'
iExitCode=1
}
fi
message_replace " [.....] Remove folders/files"
cleanup
message_replace " [ END ]"
message "\e[1A\r${sResult} ${sCounterText}. ${sScenarioText}"
done
if [[ "${iExitCode}" = 0 ]];then
echo -e "\n ✔ Success"
else
echo -e "\n ❌ Failure"
fi
popd > /dev/null
else
echo "Given directory '${sDirectoryParameter}' does not exist"
iExitCode=65
fi
}
if [[ "${*}" = '' ]] || [[ "${1}" = '-h' ]] || [[ "${1}" = '--help' ]];then
usage
else
run "${@}"
fi
exit "${iExitCode}"
}
if [[ "${BASH_SOURCE[0]}" != "$0" ]]; then
export -f reproduce_issue_105
else
reproduce_issue_105 "${@}"
exit $?
fi
@BrianHenryIE
Copy link

Wow. I’ve still to take it all in. Good work.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment