Merge branch 'development' into phpstan-strict

This commit is contained in:
Clemens Schwaighofer
2025-05-15 21:42:47 +09:00
3651 changed files with 40990 additions and 456855 deletions

9
.gitignore vendored
View File

@@ -0,0 +1,9 @@
.libs
node_modules/
composer.lock
vendor/
tools/
www/composer.lock
www/vendor
**/.env
**/.target

View File

@@ -27,6 +27,7 @@ use Phan\Config;
return [ return [
// "target_php_version" => "8.2", // "target_php_version" => "8.2",
"minimum_target_php_version" => "8.2",
// turn color on (-C) // turn color on (-C)
"color_issue_messages_if_supported" => true, "color_issue_messages_if_supported" => true,
// If true, missing properties will be created when // If true, missing properties will be created when
@@ -95,8 +96,6 @@ return [
"exclude_analysis_directory_list" => [ "exclude_analysis_directory_list" => [
'www/vendor', 'www/vendor',
'www/tests', 'www/tests',
'www/lib/Smarty',
'www/lib/smarty-4.3.0',
'www/templates_c', 'www/templates_c',
'www/log', 'www/log',
'www/tmp', 'www/tmp',
@@ -117,10 +116,6 @@ return [
// ignore the old qq tests // ignore the old qq tests
'www/admin/qq_file_upload_front.php', 'www/admin/qq_file_upload_front.php',
'www/admin/qq_file_upload_ajax.php', 'www/admin/qq_file_upload_ajax.php',
// symlink ignore
'www/lib/smarty-4.3.0/libs/Smarty.class.php',
// legacy edit base (until removal)
'www/includes/edit_base.LEGACY.php'
], ],
// what not to show as problem // what not to show as problem
@@ -133,7 +128,12 @@ return [
'PhanWriteOnlyPublicProperty', 'PhanWriteOnlyPublicProperty',
'PhanUnreferencedConstant', 'PhanUnreferencedConstant',
'PhanWriteOnlyPublicProperty', 'PhanWriteOnlyPublicProperty',
'PhanReadOnlyPublicProperty' 'PhanReadOnlyPublicProperty',
// start ignore annotations
'PhanUnextractableAnnotationElementName',
'PhanUnextractableAnnotationSuffix',
// enum problems in comments
'PhanCommentObjectInClassConstantType'
], ],
// Override to hardcode existence and types of (non-builtin) globals in the global scope. // Override to hardcode existence and types of (non-builtin) globals in the global scope.

12
.phive/phars.xml Normal file
View File

@@ -0,0 +1,12 @@
<?xml version="1.0" encoding="UTF-8"?>
<phive xmlns="https://phar.io/phive">
<phar name="phpunit" version="^10.3.5" installed="10.3.5" location="./tools/phpunit" copy="false"/>
<phar name="phpcbf" version="^3.7.2" installed="3.10.3" location="./tools/phpcbf" copy="false"/>
<phar name="phpcs" version="^3.10.3" installed="3.10.3" location="./tools/phpcs" copy="false"/>
<phar name="phpstan" version="^2.0" installed="2.0.4" location="./tools/phpstan" copy="false"/>
<phar name="phan" version="^5.4.3" installed="5.4.3" location="./tools/phan" copy="false"/>
<phar name="psalm" version="^5.15.0" installed="5.24.0" location="./tools/psalm" copy="false"/>
<phar name="phpdox" version="^0.12.0" installed="0.12.0" location="./tools/phpdox" copy="false"/>
<phar name="phpdocumentor" version="^3.4.2" installed="3.4.3" location="./tools/phpDocumentor" copy="false"/>
<phar name="php-cs-fixer" version="^3.34.1" installed="3.57.2" location="./tools/php-cs-fixer" copy="false"/>
</phive>

2
.shellcheckrc Normal file
View File

@@ -0,0 +1,2 @@
shell=bash
external-sources=true

View File

@@ -1,19 +1,20 @@
#!/usr/bin/env bash #!/usr/bin/env bash
BASE_FOLDER=$(dirname $(readlink -f $0))"/"; BASE_FOLDER=$(dirname "$(readlink -f "$0")")"/";
# Assume script is in 4dev/bin # Assume script is in 4dev/bin
base_folder="${BASE_FOLDER}../../www/"; base_folder="${BASE_FOLDER}../../www/";
# locale gettext po to mo translator master # locale gettext po to mo translator master
for file in $(ls -1 ${base_folder}../4dev/locale/*.po); do for file in "${base_folder}"../4dev/locale/*.po; do
file=$(basename $file .po); [[ -e "$file" ]] || break
file=$(basename "$file" .po);
locale=$(echo "${file}" | cut -d "-" -f 1); locale=$(echo "${file}" | cut -d "-" -f 1);
domain=$(echo "${file}" | cut -d "-" -f 2); domain=$(echo "${file}" | cut -d "-" -f 2);
echo "- Translate language file '${file}' for locale '${locale}' and domain '${domain}':"; echo "- Translate language file '${file}' for locale '${locale}' and domain '${domain}':";
if [ ! -d "${base_folder}/includes/locale/${locale}/LC_MESSAGES/" ]; then if [ ! -d "${base_folder}/includes/locale/${locale}/LC_MESSAGES/" ]; then
mkdir -p "${base_folder}/includes/locale/${locale}/LC_MESSAGES/"; mkdir -p "${base_folder}/includes/locale/${locale}/LC_MESSAGES/";
fi; fi;
msgfmt -o ${base_folder}/includes/locale/${locale}/LC_MESSAGES/${domain}.mo ${base_folder}../4dev/locale/${locale}-${domain}.po; msgfmt -o "${base_folder}/includes/locale/${locale}/LC_MESSAGES/${domain}.mo" "${base_folder}../4dev/locale/${locale}-${domain}.po";
done; done;
# __END__ # __END__

View File

@@ -2,16 +2,18 @@
# read source mo files and writes target js files in object form # read source mo files and writes target js files in object form
# check for ARG 1 is "mv" # check for ARG 1 is "no-move"
# then move the files directly and don't do manual check (don't create temp files) # then do not move the files directly for manual check
FILE_MOVE=0; FILE_MOVE=1;
if [ "${1}" = "mv" ]; then if [ "${1}" = "no-move" ]; then
echo "+++ CREATE TEMPORARY FILES +++";
FILE_MOVE=0;
else
echo "*** Direct write ***"; echo "*** Direct write ***";
FILE_MOVE=1;
fi; fi;
target=''; target='';
BASE_FOLDER=$(dirname $(readlink -f $0))"/"; BASE_FOLDER=$(dirname "$(readlink -f "$0")")"/";
# Assume script is in 4dev/bin # Assume script is in 4dev/bin
base_folder="${BASE_FOLDER}../../www/"; base_folder="${BASE_FOLDER}../../www/";
po_folder='../4dev/locale/' po_folder='../4dev/locale/'
@@ -26,9 +28,9 @@ if [ "${target}" == '' ]; then
echo "*** Non smarty ***"; echo "*** Non smarty ***";
TEXTDOMAINDIR=${base_folder}${mo_folder}. TEXTDOMAINDIR=${base_folder}${mo_folder}.
# default is admin # default is admin
TEXTDOMAIN=admin; TEXTDOMAIN="admin";
fi; fi;
js_folder="layout/${TEXTDOMAIN}/javascript/"; js_folder="${TEXTDOMAIN}/layout/javascript/";
error=0; error=0;
# this checks if the TEXTDOMAIN target actually exists # this checks if the TEXTDOMAIN target actually exists
@@ -44,15 +46,16 @@ if [ ${error} -eq 1 ]; then
fi; fi;
# locale gettext po to mo translator master # locale gettext po to mo translator master
for file in $(ls -1 ${base_folder}../4dev/locale/*.po); do for file in "${base_folder}"../4dev/locale/*.po; do
file=$(basename $file .po); [[ -e "$file" ]] || break
echo "Translate language ${file}"; file=$(basename "$file" .po);
locale=$(echo "${file}" | cut -d "-" -f 1); locale=$(echo "${file}" | cut -d "-" -f 1);
domain=$(echo "${file}" | cut -d "-" -f 2); domain=$(echo "${file}" | cut -d "-" -f 2);
echo "- Translate language file '${file}' for locale '${locale}' and domain '${domain}':";
if [ ! -d "${base_folder}/includes/locale/${locale}/LC_MESSAGES/" ]; then if [ ! -d "${base_folder}/includes/locale/${locale}/LC_MESSAGES/" ]; then
mkdir -p "${base_folder}/includes/locale/${locale}/LC_MESSAGES/"; mkdir -p "${base_folder}/includes/locale/${locale}/LC_MESSAGES/";
fi; fi;
msgfmt -o ${base_folder}/includes/locale/${locale}/LC_MESSAGES/${domain}.mo ${base_folder}${po_folder}${locale}-${domain}.po; msgfmt -o "${base_folder}/includes/locale/${locale}/LC_MESSAGES/${domain}.mo" "${base_folder}${po_folder}${locale}-${domain}.po";
done; done;
rx_msgid_empty="^msgid \"\""; rx_msgid_empty="^msgid \"\"";
@@ -62,7 +65,7 @@ rx_msgstr="^msgstr \""
# quick copy string at the end # quick copy string at the end
quick_copy=''; quick_copy='';
for language in ${language_list[*]}; do for language in "${language_list[@]}"; do
# I don't know which one must be set, but I think at least LANGUAGE # I don't know which one must be set, but I think at least LANGUAGE
case ${language} in case ${language} in
ja) ja)
@@ -79,7 +82,8 @@ for language in ${language_list[*]}; do
esac; esac;
# write only one for language and then symlink files # write only one for language and then symlink files
template_file=$(echo ${template_file_stump} | sed -e "s/##SUFFIX##//" | sed -e "s/##LANGUAGE##/${LANG}/"); template_file=$(echo ${template_file_stump} | sed -e "s/##SUFFIX##//" | sed -e "s/##LANGUAGE##/${LANG}/");
original_file=$(echo ${template_file} | sed -e 's/\.TMP//g'); # original_file=$(echo ${template_file} | sed -e 's/\.TMP//g');
original_file=${template_file//.TMP/};
if [ "${FILE_MOVE}" -eq 0 ]; then if [ "${FILE_MOVE}" -eq 0 ]; then
file=${target_folder}${template_file}; file=${target_folder}${template_file};
else else
@@ -88,16 +92,18 @@ for language in ${language_list[*]}; do
echo "===> Write translation file ${file}"; echo "===> Write translation file ${file}";
echo ". = normal, : = escape, x = skip"; echo ". = normal, : = escape, x = skip";
# init line [aka don't touch this file] # init line [aka don't touch this file]
echo "// AUTO FILL, changes will be overwritten" > $file; echo "// AUTO FILL, changes will be overwritten" > "$file";
echo "// source: ${suffix}, language: ${language}" >> $file; {
echo "// Translation strings in the format" >> $file; echo "// source: ${suffix}, language: ${language}";
echo "// \"Original\":\"Translated\""$'\n' >> $file; echo "// Translation strings in the format";
echo "var i18n = {" >> $file; echo "// \"Original\":\"Translated\""$'\n'
echo "var i18n = {"
} >> "$file"
# translations stuff # translations stuff
# read the po file # read the po file
pos=0; # do we add a , for the next line pos=0; # do we add a , for the next line
cat "${base_folder}${po_folder}${language}-${TEXTDOMAIN}.po" | cat "${base_folder}${po_folder}${language}-${TEXTDOMAIN}.po" |
while read str; do while read -r str; do
# echo "S: ${str}"; # echo "S: ${str}";
# skip empty # skip empty
if [[ "${str}" =~ ${rx_msgid_empty} ]]; then if [[ "${str}" =~ ${rx_msgid_empty} ]]; then
@@ -112,12 +118,13 @@ for language in ${language_list[*]}; do
str_source=$(echo "${str}" | sed -e "s/^msgid \"//" | sed -e "s/\"$//"); str_source=$(echo "${str}" | sed -e "s/^msgid \"//" | sed -e "s/\"$//");
# close right side, if not last add , # close right side, if not last add ,
if [ "${pos}" -eq 1 ]; then if [ "${pos}" -eq 1 ]; then
echo -n "," >> $file; echo -n "," >> "$file";
fi; fi;
# all " inside string need to be escaped # all " inside string need to be escaped
str_source=$(echo "${str_source}" | sed -e 's/"/\\"/g'); # str_source=$(echo "${str_source}" | sed -e 's/"/\\"/g');
str_source=${str_source//\"/\\\"}
# fix with proper layout # fix with proper layout
echo -n "\"$str_source\":\"$(TEXTDOMAINDIR=${TEXTDOMAINDIR} LANGUAGE=${language} LANG=${LANG} gettext ${TEXTDOMAIN} "${str_source}")\"" >> $file; echo -n "\"$str_source\":\"$(TEXTDOMAINDIR=${TEXTDOMAINDIR} LANGUAGE=${language} LANG=${LANG} gettext "${TEXTDOMAIN}" "${str_source}")\"" >> "$file";
pos=1; pos=1;
elif [[ "${str}" =~ ${rx_msgstr} ]]; then elif [[ "${str}" =~ ${rx_msgstr} ]]; then
# open right side (ignore) # open right side (ignore)
@@ -128,8 +135,8 @@ for language in ${language_list[*]}; do
fi; fi;
done; done;
echo "" >> $file; echo "" >> "$file";
echo "};" >> $file; echo "};" >> "$file";
echo " [DONE]"; echo " [DONE]";
# on no move # on no move
@@ -140,19 +147,19 @@ for language in ${language_list[*]}; do
fi; fi;
# symlink to master file # symlink to master file
for suffix in ${source_list[*]}; do for suffix in "${source_list[@]}"; do
# symlink with full lang name # symlink with full lang name
symlink_file[0]=$(echo ${template_file_stump} | sed -e "s/##SUFFIX##/${suffix}_/" | sed -e "s/##LANGUAGE##/${LANG}/" | sed -e 's/\.TMP//g'); symlink_file[0]=$(echo ${template_file_stump} | sed -e "s/##SUFFIX##/${suffix}_/" | sed -e "s/##LANGUAGE##/${LANG}/" | sed -e 's/\.TMP//g');
# create second one with lang (no country) + encoding # create second one with lang (no country) + encoding
symlink_file[1]=$(echo ${template_file_stump} | sed -e "s/##SUFFIX##/${suffix}_/" | sed -e "s/##LANGUAGE##/${LANGUAGE}\.${ENCODING}/" | sed -e 's/\.TMP//g'); symlink_file[1]=$(echo ${template_file_stump} | sed -e "s/##SUFFIX##/${suffix}_/" | sed -e "s/##LANGUAGE##/${LANGUAGE}\.${ENCODING}/" | sed -e 's/\.TMP//g');
for template_file in ${symlink_file[@]}; do for template_file in "${symlink_file[@]}"; do
# if this is not symlink, create them # if this is not symlink, create them
if [ ! -h "${template_file}" ]; then if [ ! -h "${template_file}" ]; then
echo "Create symlink: ${template_file}"; echo "Create symlink: ${template_file}";
# symlik to original # symlik to original
cd "${target_folder}"; cd "${target_folder}" || exit;
ln -sf "${original_file}" "${template_file}"; ln -sf "${original_file}" "${template_file}";
cd - >/dev/null; cd - >/dev/null || exit;
fi; fi;
done; done;
done; done;

View File

@@ -1,3 +1,5 @@
base="/storage/var/www/html/developers/clemens/core_data/php_libraries/trunk/"; base="/storage/var/www/html/developers/clemens/core_data/php_libraries/trunk/";
# must be run in ${base}www/ # must be run in ${base}
phan --progress-bar -C --analyze-twice cd $base || exit;
${base}tools/phan --progress-bar -C --analyze-twice;
cd ~ || exit;

View File

@@ -1,3 +1,5 @@
base="/storage/var/www/html/developers/clemens/core_data/php_libraries/trunk/"; base="/storage/var/www/html/developers/clemens/core_data/php_libraries/trunk/";
# must be run in ${base}www/ # must be run in ${base}
phpstan cd $base || exit;
${base}tools/phpstan;
cd ~ || exit;

View File

@@ -1,46 +1,96 @@
#!/bin/env bash #!/bin/env bash
base="/storage/var/www/html/developers/clemens/core_data/php_libraries/trunk/"; function error() {
if [ -t 1 ]; then echo "[MAK] ERROR: $*" >&2; fi; exit 0;
}
usage() {
cat <<EOF
Usage: $(basename "${BASH_SOURCE[0]}") [-h] [-t] [-v] [-p VERSION]
Runs all the PHP unit tests.
If -p is not set, the default intalled PHP is used.
Available options:
-h, --help Print this help and exit
-t, --testdox Enable testdox output for phpunit
-v, --verbose Enable verbose output for PHPunit
-p, --php VERSION Chose PHP version in the form of "N.N", if not found will exit
EOF
exit
}
# set base variables
BASE_PATH="/storage/var/www/html/developers/clemens/core_data/php_libraries/trunk/";
PHPUNIT_CONFIG="${BASE_PATH}phpunit.xml";
PHP_BIN_PATH=$(which php);
if [ -z "${PHP_BIN_PATH}" ]; then
echo "Cannot find php binary";
exit;
fi;
DEFAULT_PHP_VERSION=$(${PHP_BIN_PATH} -r "echo PHP_MAJOR_VERSION.'.'.PHP_MINOR_VERSION;");
if [ -z "${DEFAULT_PHP_VERSION}" ]; then
echo "Cannot set default PHP version";
exit;
fi;
# -c phpunit.xml # -c phpunit.xml
# --testdox # --testdox
# call with "t" to give verbose testdox output # call with "-tt" to give verbose testdox output
# SUPPORTED: https://www.php.net/supported-versions.php # SUPPORTED: https://www.php.net/supported-versions.php
# call with php version number to force a certain php version # call with -p <php version number> to force a certain php version
opt_testdox=""; opt_testdox="";
if [ "${1}" = "t" ] || [ "${2}" = "t" ]; then opt_verbose="";
opt_testdox="--testdox"; php_version="";
fi; no_php_version=0;
php_bin=""; while [ -n "${1-}" ]; do
if [ ! -z "${1}" ]; then
case "${1}" in case "${1}" in
# "7.3") php_bin="/usr/bin/php7.3 "; ;; -t | --testdox)
"7.4") php_bin="/usr/bin/php7.4 "; ;; opt_testdox="--testdox";
"8.0") php_bin="/usr/bin/php8.0 "; ;; ;;
"8.1") php_bin="/usr/bin/php8.1 "; ;; -v | --verbose)
"8.2") php_bin="/usr/bin/php8.2 "; ;; opt_verbose="--verbose";
*) echo "Not support PHP: ${1}"; exit; ;; ;;
esac; -p | --php)
fi; php_version="${2-}";
if [ ! -z "${2}" ] && [ -z "${php_bin}" ]; then shift
case "${2}" in ;;
# "7.3") php_bin="/usr/bin/php7.3 "; ;; -h | --help)
"7.4") php_bin="/usr/bin/php7.4 "; ;; usage
"8.0") php_bin="/usr/bin/php8.0 "; ;; ;;
"8.1") php_bin="/usr/bin/php8.1 "; ;; # invalid option
"8.2") php_bin="/usr/bin/php8.2 "; ;; -?*)
*) echo "Not support PHP: ${1}"; exit; ;; error "[!] Unknown option: '$1'."
esac; ;;
fi; esac
shift;
done;
phpunit_call="${php_bin}${base}www/vendor/bin/phpunit ${opt_testdox} -c ${base}phpunit.xml ${base}4dev/tests/"; if [ -z "${php_version}" ]; then
php_version="${DEFAULT_PHP_VERSION}";
no_php_version=1;
fi;
php_bin="${PHP_BIN_PATH}${php_version}";
echo "Use PHP Version: ${php_version}";
if [ ! -f "${php_bin}" ]; then
echo "Set php ${php_bin} does not exist";
exit;
fi;
php_bin="${php_bin} ";
# Note 4dev/tests/bootstrap.php has to be set as bootstrap file in phpunit.xml
phpunit_call="${php_bin}${BASE_PATH}vendor/bin/phpunit ${opt_testdox} ${opt_verbose} -c ${PHPUNIT_CONFIG} ${BASE_PATH}4dev/tests/";
${phpunit_call}; ${phpunit_call};
if [ ! -z "${php_bin}" ]; then echo -e "\nPHPUnit Config: ${PHPUNIT_CONFIG}";
echo "CALLED WITH PHP: ${php_bin}"$(${php_bin} --version); if [ "${no_php_version}" -eq 0 ]; then
echo "CALLED WITH PHP: ${php_bin}$(${php_bin} --version)";
else else
echo "Default PHP used: "$(php --version); echo "Default PHP used: $(php --version)";
fi; fi;
# __END__ # __END__

View File

@@ -0,0 +1,22 @@
#!/bin/env bash
# syncs
# 4dev/tests/
# www/lib/CoreLibs/
#
# to the composer corelibs all repo
GO="${1}";
DRY_RUN="";
if [ "${GO}" != "go" ]; then
DRY_RUN="-n ";
fi;
BASE="/storage/var/www/html/developers/clemens/core_data/";
SOURCE="${BASE}php_libraries/master/"
TARGET="${BASE}composer-packages/CoreLibs-Composer-All/"
rsync ${DRY_RUN}-Plzvrupt --stats --delete ${SOURCE}4dev/tests/ ${TARGET}test/phpunit/
rsync ${DRY_RUN}-Plzvrupt --stats --delete ${SOURCE}www/lib/CoreLibs/ ${TARGET}src/
# __END__

View File

@@ -5,9 +5,9 @@ RETURNS TRIGGER AS
$$ $$
BEGIN BEGIN
IF TG_OP = 'INSERT' THEN IF TG_OP = 'INSERT' THEN
NEW.date_created := 'now'; NEW.date_created := clock_timestamp();
ELSIF TG_OP = 'UPDATE' THEN ELSIF TG_OP = 'UPDATE' THEN
NEW.date_updated := 'now'; NEW.date_updated := clock_timestamp();
END IF; END IF;
RETURN NEW; RETURN NEW;
END; END;

View File

@@ -7,10 +7,11 @@ DECLARE
random_length INT = 25; -- that should be long enough random_length INT = 25; -- that should be long enough
BEGIN BEGIN
IF TG_OP = 'INSERT' THEN IF TG_OP = 'INSERT' THEN
NEW.date_created := 'now'; NEW.date_created := clock_timestamp();
NEW.cuid := random_string(random_length); NEW.cuid := random_string(random_length);
NEW.cuuid := gen_random_uuid();
ELSIF TG_OP = 'UPDATE' THEN ELSIF TG_OP = 'UPDATE' THEN
NEW.date_updated := 'now'; NEW.date_updated := clock_timestamp();
END IF; END IF;
RETURN NEW; RETURN NEW;
END; END;

View File

@@ -8,12 +8,12 @@ DECLARE
random_length INT = 32; -- long for massive data random_length INT = 32; -- long for massive data
BEGIN BEGIN
IF TG_OP = 'INSERT' THEN IF TG_OP = 'INSERT' THEN
NEW.date_created := 'now'; NEW.date_created := clock_timestamp();
IF NEW.uid IS NULL THEN IF NEW.uid IS NULL THEN
NEW.uid := random_string(random_length); NEW.uid := random_string(random_length);
END IF; END IF;
ELSIF TG_OP = 'UPDATE' THEN ELSIF TG_OP = 'UPDATE' THEN
NEW.date_updated := 'now'; NEW.date_updated := clock_timestamp();
END IF; END IF;
RETURN NEW; RETURN NEW;
END; END;

View File

@@ -1,19 +0,0 @@
-- adds the created or updated date tags
-- OLD, DEPRECATED, use set_generic.sql
-- CREATE OR REPLACE FUNCTION set_generic()
-- RETURNS TRIGGER AS
-- $$
-- BEGIN
-- IF TG_OP = 'INSERT' THEN
-- NEW.date_created := clock_timestamp();
-- NEW.user_created := current_user;
-- ELSIF TG_OP = 'UPDATE' THEN
-- NEW.date_updated := clock_timestamp();
-- NEW.user_updated := current_user;
-- END IF;
-- RETURN NEW;
-- END;
-- $$
-- LANGUAGE 'plpgsql';

View File

@@ -0,0 +1,110 @@
-- Upgrade serial to identity type
--
-- Original: https://www.enterprisedb.com/blog/postgresql-10-identity-columns-explained#section-6
--
-- @param reclass tbl The table where the column is located, prefix with 'schema.' if different schema
-- @param name col The column to be changed
-- @param varchar identity_type [default=a] Allowed a, d, assigned, default
-- @param varchar col_type [default=''] Allowed smallint, int, bigint, int2, int4, int8
-- @returns varchar status tring
-- @raises EXCEPTON on column not found, no linked sequence, more than one linked sequence found, invalid col type
--
CREATE OR REPLACE FUNCTION upgrade_serial_to_identity(
tbl regclass,
col name,
identity_type varchar = 'a',
col_type varchar = ''
)
RETURNS varchar
LANGUAGE plpgsql
AS $$
DECLARE
colnum SMALLINT;
seqid OID;
count INT;
col_type_oid INT;
col_type_len INT;
current_col_atttypid OID;
current_col_attlen INT;
status_string VARCHAR;
BEGIN
-- switch between always (default) or default identiy type
IF identity_type NOT IN ('a', 'd', 'assigned', 'default') THEN
identity_type := 'a';
ELSE
IF identity_type = 'default' THEN
identity_type := 'd';
ELSIF identity_type = 'assigned' THEN
identity_type := 'a';
END IF;
END IF;
-- find column number, attribute oid and attribute len
SELECT attnum, atttypid, attlen
INTO colnum, current_col_atttypid, current_col_attlen
FROM pg_attribute
WHERE attrelid = tbl AND attname = col;
IF NOT FOUND THEN
RAISE EXCEPTION 'column does not exist';
END IF;
-- find sequence
SELECT INTO seqid objid
FROM pg_depend
WHERE (refclassid, refobjid, refobjsubid) = ('pg_class'::regclass, tbl, colnum)
AND classid = 'pg_class'::regclass AND objsubid = 0
AND deptype = 'a';
GET DIAGNOSTICS count = ROW_COUNT;
IF count < 1 THEN
RAISE EXCEPTION 'no linked sequence found';
ELSIF count > 1 THEN
RAISE EXCEPTION 'more than one linked sequence found';
END IF;
IF col_type <> '' AND col_type NOT IN ('smallint', 'int', 'bigint', 'int2', 'int4', 'int8') THEN
RAISE EXCEPTION 'Invalid col type: %', col_type;
END IF;
-- drop the default
EXECUTE 'ALTER TABLE ' || tbl || ' ALTER COLUMN ' || quote_ident(col) || ' DROP DEFAULT';
-- change the dependency between column and sequence to internal
UPDATE pg_depend
SET deptype = 'i'
WHERE (classid, objid, objsubid) = ('pg_class'::regclass, seqid, 0)
AND deptype = 'a';
-- mark the column as identity column
UPDATE pg_attribute
-- set to 'd' for default
SET attidentity = identity_type
WHERE attrelid = tbl
AND attname = col;
status_string := 'Updated to identity for table "' || tbl || '" and columen "' || col || '" with type "' || identity_type || '"';
-- set type if requested and not empty
IF col_type <> '' THEN
-- rewrite smallint, int, bigint
IF col_type = 'smallint' THEN
col_type := 'int2';
ELSIF col_type = 'int' THEN
col_type := 'int4';
ELSIF col_type = 'bigint' THEN
col_type := 'int8';
END IF;
-- get the length and oid for selected
SELECT oid, typlen INTO col_type_oid, col_type_len FROM pg_type WHERE typname = col_type;
-- set only if diff or hight
IF current_col_atttypid <> col_type_oid AND col_type_len > current_col_attlen THEN
status_string := status_string || '. Change col type: ' || col_type;
-- update type
UPDATE pg_attribute
SET
atttypid = col_type_oid, attlen = col_type_len
WHERE attrelid = tbl
AND attname = col;
END IF;
END IF;
RETURN status_string;
END;
$$;

View File

@@ -7,7 +7,7 @@
-- DROP TABLE edit_access; -- DROP TABLE edit_access;
CREATE TABLE edit_access ( CREATE TABLE edit_access (
edit_access_id SERIAL PRIMARY KEY, edit_access_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
enabled SMALLINT NOT NULL DEFAULT 0, enabled SMALLINT NOT NULL DEFAULT 0,
protected SMALLINT DEFAULT 0, protected SMALLINT DEFAULT 0,
deleted SMALLINT DEFAULT 0, deleted SMALLINT DEFAULT 0,

View File

@@ -7,7 +7,7 @@
-- DROP TABLE edit_access_data; -- DROP TABLE edit_access_data;
CREATE TABLE edit_access_data ( CREATE TABLE edit_access_data (
edit_access_data_id SERIAL PRIMARY KEY, edit_access_data_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
edit_access_id INT NOT NULL, edit_access_id INT NOT NULL,
FOREIGN KEY (edit_access_id) REFERENCES edit_access (edit_access_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE, FOREIGN KEY (edit_access_id) REFERENCES edit_access (edit_access_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE,
enabled SMALLINT NOT NULL DEFAULT 0, enabled SMALLINT NOT NULL DEFAULT 0,

View File

@@ -8,7 +8,7 @@
-- DROP TABLE edit_access_right; -- DROP TABLE edit_access_right;
CREATE TABLE edit_access_right ( CREATE TABLE edit_access_right (
edit_access_right_id SERIAL PRIMARY KEY, edit_access_right_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
name VARCHAR, name VARCHAR,
level SMALLINT, level SMALLINT,
type VARCHAR, type VARCHAR,

View File

@@ -7,7 +7,7 @@
-- DROP TABLE edit_access_user; -- DROP TABLE edit_access_user;
CREATE TABLE edit_access_user ( CREATE TABLE edit_access_user (
edit_access_user_id SERIAL PRIMARY KEY, edit_access_user_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
edit_access_id INT NOT NULL, edit_access_id INT NOT NULL,
FOREIGN KEY (edit_access_id) REFERENCES edit_access (edit_access_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE, FOREIGN KEY (edit_access_id) REFERENCES edit_access (edit_access_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE,
edit_user_id INT NOT NULL, edit_user_id INT NOT NULL,

View File

@@ -8,6 +8,7 @@
-- DROP TABLE edit_generic; -- DROP TABLE edit_generic;
CREATE TABLE edit_generic ( CREATE TABLE edit_generic (
cuid VARCHAR, cuid VARCHAR,
cuuid UUID DEFAULT gen_random_uuid(),
date_created TIMESTAMP WITHOUT TIME ZONE DEFAULT clock_timestamp(), date_created TIMESTAMP WITHOUT TIME ZONE DEFAULT clock_timestamp(),
date_updated TIMESTAMP WITHOUT TIME ZONE date_updated TIMESTAMP WITHOUT TIME ZONE
); );

View File

@@ -7,7 +7,7 @@
-- DROP TABLE edit_group; -- DROP TABLE edit_group;
CREATE TABLE edit_group ( CREATE TABLE edit_group (
edit_group_id SERIAL PRIMARY KEY, edit_group_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
edit_scheme_id INT, edit_scheme_id INT,
FOREIGN KEY (edit_scheme_id) REFERENCES edit_scheme (edit_scheme_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE, FOREIGN KEY (edit_scheme_id) REFERENCES edit_scheme (edit_scheme_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE,
edit_access_right_id INT NOT NULL, edit_access_right_id INT NOT NULL,

View File

@@ -8,7 +8,7 @@
-- DROP TABLE edit_language; -- DROP TABLE edit_language;
CREATE TABLE edit_language ( CREATE TABLE edit_language (
edit_language_id SERIAL PRIMARY KEY, edit_language_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
enabled SMALLINT NOT NULL DEFAULT 0, enabled SMALLINT NOT NULL DEFAULT 0,
lang_default SMALLINT NOT NULL DEFAULT 0, lang_default SMALLINT NOT NULL DEFAULT 0,
long_name VARCHAR, long_name VARCHAR,

View File

@@ -7,35 +7,54 @@
-- DROP TABLE edit_log; -- DROP TABLE edit_log;
CREATE TABLE edit_log ( CREATE TABLE edit_log (
edit_log_id SERIAL PRIMARY KEY, edit_log_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
euid INT, -- this is a foreign key, but I don't nedd to reference to it euid INT, -- this is a foreign key, but I don't nedd to reference to it
FOREIGN KEY (euid) REFERENCES edit_user (edit_user_id) MATCH FULL ON UPDATE CASCADE ON DELETE SET NULL, FOREIGN KEY (euid) REFERENCES edit_user (edit_user_id) MATCH FULL ON UPDATE CASCADE ON DELETE SET NULL,
username VARCHAR, eucuid VARCHAR,
password VARCHAR, eucuuid UUID, -- this is the one we want to use, full UUIDv4 from the edit user table
-- date_created equal, but can be overridden
event_date TIMESTAMP WITHOUT TIME ZONE DEFAULT CURRENT_TIMESTAMP, event_date TIMESTAMP WITHOUT TIME ZONE DEFAULT CURRENT_TIMESTAMP,
ip VARCHAR, -- session ID if set
session_id VARCHAR,
-- username
username VARCHAR,
-- DEPRECATED [password]
password VARCHAR,
ip_address JSONB, -- REMOTE_IP and all other IPs (X_FORWARD, etc) as JSON block
-- DEPRECATED [ip]
ip VARCHAR, -- just the REMOTE_IP, full set see ip_address
-- string blocks, general
error TEXT, error TEXT,
event TEXT, event TEXT,
-- bytea or string type storage of any data
data_binary BYTEA, data_binary BYTEA,
data TEXT, data TEXT,
-- set page name only
page VARCHAR, page VARCHAR,
action VARCHAR, -- various info data sets
action_id VARCHAR,
action_yes VARCHAR,
action_flag VARCHAR,
action_menu VARCHAR,
action_loaded VARCHAR,
action_value VARCHAR,
action_type VARCHAR,
action_error VARCHAR,
user_agent VARCHAR, user_agent VARCHAR,
referer VARCHAR, referer VARCHAR,
script_name VARCHAR, script_name VARCHAR,
query_string VARCHAR, query_string VARCHAR,
request_scheme VARCHAR, -- http or https
server_name VARCHAR, server_name VARCHAR,
http_host VARCHAR, http_host VARCHAR,
http_accept VARCHAR, http_data JSONB,
http_accept_charset VARCHAR, -- DEPRECATED [http*]
http_accept_encoding VARCHAR, http_accept VARCHAR, -- in http_data
session_id VARCHAR http_accept_charset VARCHAR, -- in http_data
http_accept_encoding VARCHAR, -- in http_data
-- any action var, -> same set in action_data as JSON
action_data JSONB,
-- DEPRECATED [action*]
action VARCHAR, -- in action_data
action_id VARCHAR, -- in action_data
action_sub_id VARCHAR, -- in action_data
action_yes VARCHAR, -- in action_data
action_flag VARCHAR, -- in action_data
action_menu VARCHAR, -- in action_data
action_loaded VARCHAR, -- in action_data
action_value VARCHAR, -- in action_data
action_type VARCHAR, -- in action_data
action_error VARCHAR -- in action_data
) INHERITS (edit_generic) WITHOUT OIDS; ) INHERITS (edit_generic) WITHOUT OIDS;

View File

@@ -7,10 +7,8 @@
-- DROP TABLE edit_menu_group; -- DROP TABLE edit_menu_group;
CREATE TABLE edit_menu_group ( CREATE TABLE edit_menu_group (
edit_menu_group_id SERIAL PRIMARY KEY, edit_menu_group_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
name VARCHAR, name VARCHAR,
flag VARCHAR, flag VARCHAR,
order_number INT NOT NULL order_number INT NOT NULL
) INHERITS (edit_generic) WITHOUT OIDS; ) INHERITS (edit_generic) WITHOUT OIDS;

View File

@@ -7,7 +7,7 @@
-- DROP TABLE edit_page; -- DROP TABLE edit_page;
CREATE TABLE edit_page ( CREATE TABLE edit_page (
edit_page_id SERIAL PRIMARY KEY, edit_page_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
content_alias_edit_page_id INT, -- alias for page content, if the page content is defined on a different page, ege for ajax backend pages content_alias_edit_page_id INT, -- alias for page content, if the page content is defined on a different page, ege for ajax backend pages
FOREIGN KEY (content_alias_edit_page_id) REFERENCES edit_page (edit_page_id) MATCH FULL ON DELETE RESTRICT ON UPDATE CASCADE, FOREIGN KEY (content_alias_edit_page_id) REFERENCES edit_page (edit_page_id) MATCH FULL ON DELETE RESTRICT ON UPDATE CASCADE,
filename VARCHAR, filename VARCHAR,

View File

@@ -7,7 +7,7 @@
-- DROP TABLE edit_page_access; -- DROP TABLE edit_page_access;
CREATE TABLE edit_page_access ( CREATE TABLE edit_page_access (
edit_page_access_id SERIAL PRIMARY KEY, edit_page_access_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
edit_group_id INT NOT NULL, edit_group_id INT NOT NULL,
FOREIGN KEY (edit_group_id) REFERENCES edit_group (edit_group_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE, FOREIGN KEY (edit_group_id) REFERENCES edit_group (edit_group_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE,
edit_page_id INT NOT NULL, edit_page_id INT NOT NULL,
@@ -16,5 +16,3 @@ CREATE TABLE edit_page_access (
FOREIGN KEY (edit_access_right_id) REFERENCES edit_access_right (edit_access_right_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE, FOREIGN KEY (edit_access_right_id) REFERENCES edit_access_right (edit_access_right_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE,
enabled SMALLINT NOT NULL DEFAULT 0 enabled SMALLINT NOT NULL DEFAULT 0
) INHERITS (edit_generic) WITHOUT OIDS; ) INHERITS (edit_generic) WITHOUT OIDS;

View File

@@ -8,7 +8,7 @@
-- DROP TABLE edit_page_content; -- DROP TABLE edit_page_content;
CREATE TABLE edit_page_content ( CREATE TABLE edit_page_content (
edit_page_content_id SERIAL PRIMARY KEY, edit_page_content_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
edit_page_id INT NOT NULL, edit_page_id INT NOT NULL,
FOREIGN KEY (edit_page_id) REFERENCES edit_page (edit_page_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE, FOREIGN KEY (edit_page_id) REFERENCES edit_page (edit_page_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE,
edit_access_right_id INT NOT NULL, edit_access_right_id INT NOT NULL,

View File

@@ -7,7 +7,7 @@
-- DROP TABLE edit_query_string; -- DROP TABLE edit_query_string;
CREATE TABLE edit_query_string ( CREATE TABLE edit_query_string (
edit_query_string_id SERIAL PRIMARY KEY, edit_query_string_id SERIAINT GENERATED ALWAYS AS IDENTITYL PRIMARY KEY,
edit_page_id INT NOT NULL, edit_page_id INT NOT NULL,
FOREIGN KEY (edit_page_id) REFERENCES edit_page (edit_page_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE, FOREIGN KEY (edit_page_id) REFERENCES edit_page (edit_page_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE,
enabled SMALLINT NOT NULL DEFAULT 0, enabled SMALLINT NOT NULL DEFAULT 0,

View File

@@ -7,7 +7,7 @@
-- DROP TABLE edit_scheme; -- DROP TABLE edit_scheme;
CREATE TABLE edit_scheme ( CREATE TABLE edit_scheme (
edit_scheme_id SERIAL PRIMARY KEY, edit_scheme_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
enabled SMALLINT NOT NULL DEFAULT 0, enabled SMALLINT NOT NULL DEFAULT 0,
name VARCHAR, name VARCHAR,
header_color VARCHAR, header_color VARCHAR,

View File

@@ -7,7 +7,7 @@
-- DROP TABLE edit_user; -- DROP TABLE edit_user;
CREATE TABLE edit_user ( CREATE TABLE edit_user (
edit_user_id SERIAL PRIMARY KEY, edit_user_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
connect_edit_user_id INT, -- possible reference to other user connect_edit_user_id INT, -- possible reference to other user
FOREIGN KEY (connect_edit_user_id) REFERENCES edit_user (edit_user_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE, FOREIGN KEY (connect_edit_user_id) REFERENCES edit_user (edit_user_id) MATCH FULL ON DELETE CASCADE ON UPDATE CASCADE,
edit_language_id INT NOT NULL, edit_language_id INT NOT NULL,
@@ -35,11 +35,10 @@ CREATE TABLE edit_user (
strict SMALLINT DEFAULT 0, strict SMALLINT DEFAULT 0,
locked SMALLINT DEFAULT 0, locked SMALLINT DEFAULT 0,
protected SMALLINT NOT NULL DEFAULT 0, protected SMALLINT NOT NULL DEFAULT 0,
-- legacy, debug flags
debug SMALLINT NOT NULL DEFAULT 0,
db_debug SMALLINT NOT NULL DEFAULT 0,
-- is admin user -- is admin user
admin SMALLINT NOT NULL DEFAULT 0, admin SMALLINT NOT NULL DEFAULT 0,
-- force lgout counter
force_logout INT DEFAULT 0,
-- last login log -- last login log
last_login TIMESTAMP WITHOUT TIME ZONE, last_login TIMESTAMP WITHOUT TIME ZONE,
-- login error -- login error
@@ -76,9 +75,8 @@ COMMENT ON COLUMN edit_user.deleted IS 'Login is deleted (master switch), overri
COMMENT ON COLUMN edit_user.strict IS 'If too many failed logins user will be locked, default off'; COMMENT ON COLUMN edit_user.strict IS 'If too many failed logins user will be locked, default off';
COMMENT ON COLUMN edit_user.locked IS 'Locked from too many wrong password logins'; COMMENT ON COLUMN edit_user.locked IS 'Locked from too many wrong password logins';
COMMENT ON COLUMN edit_user.protected IS 'User can only be chnaged by admin user'; COMMENT ON COLUMN edit_user.protected IS 'User can only be chnaged by admin user';
COMMENT ON COLUMN edit_user.debug IS 'Turn debug flag on (legacy)';
COMMENT ON COLUMN edit_user.db_debug IS 'Turn DB debug flag on (legacy)';
COMMENT ON COLUMN edit_user.admin IS 'If set, this user is SUPER admin'; COMMENT ON COLUMN edit_user.admin IS 'If set, this user is SUPER admin';
COMMENT ON COLUMN edit_user.force_logout IS 'Counter for forced log out, if this one is higher than the session set one the session gets terminated';
COMMENT ON COLUMN edit_user.last_login IS 'Last succesfull login tiemstamp'; COMMENT ON COLUMN edit_user.last_login IS 'Last succesfull login tiemstamp';
COMMENT ON COLUMN edit_user.login_error_count IS 'Number of failed logins, reset on successful login'; COMMENT ON COLUMN edit_user.login_error_count IS 'Number of failed logins, reset on successful login';
COMMENT ON COLUMN edit_user.login_error_date_last IS 'Last login error date'; COMMENT ON COLUMN edit_user.login_error_date_last IS 'Last login error date';

View File

@@ -7,7 +7,7 @@
-- DROP TABLE edit_visible_group; -- DROP TABLE edit_visible_group;
CREATE TABLE edit_visible_group ( CREATE TABLE edit_visible_group (
edit_visible_group_id SERIAL PRIMARY KEY, edit_visible_group_id INT GENERATED ALWAYS AS IDENTITY PRIMARY KEY,
name VARCHAR, name VARCHAR,
flag VARCHAR flag VARCHAR
) INHERITS (edit_generic) WITHOUT OIDS; ) INHERITS (edit_generic) WITHOUT OIDS;

View File

@@ -0,0 +1,31 @@
# DB Query Params ? and : to $
dbReturn*
dbExec
keep
->query
->params
for reference
## : named params
in order for each named found replace with order number:
```txt
:name, :foo, :bar, :name =>
$1, $2, $3, $1
```
```php
$query = str_replace(
[':name', ':foo', ':bar'],
['$1', '$2', '$3'],
$query
);
```
## ? Params
Foreach ? set $1 to $n and store that in new params array
in QUERY for each ? replace with matching $n

View File

@@ -1,4 +1,4 @@
#!/bin/bash #!/usr/bin/env bash
# create path # create path
path=$(pwd)"/"$0; path=$(pwd)"/"$0;
@@ -10,6 +10,11 @@ TARGET_HOST_WEB="<user>@<host>";
TMP_DIR=$LOCAL_BASE_DIR"/4dev/tmp/"; TMP_DIR=$LOCAL_BASE_DIR"/4dev/tmp/";
tmpf_web=$TMP_DIR"sync.exclude.tmp"; tmpf_web=$TMP_DIR"sync.exclude.tmp";
if [ ! -d "$LOCAL_BASE_DIR" ]; then
echo "Folder: $LOCAL_BASE_DIR not found";
exit;
fi;
# if vendor be sure group folder is +x # if vendor be sure group folder is +x
chmod -R ug+rX ${LOCAL_DIR}/vender/ chmod -R ug+rX ${LOCAL_DIR}/vender/

View File

@@ -0,0 +1,40 @@
<?php
declare(strict_types=1);
namespace tests;
use PHPUnit\Framework\TestCase;
/**
* Test base setup
* @testdox AAASetupData\AAASetupDataTest just setup BASE
*/
final class CoreLibsAAASetupDataTest extends TestCase
{
/**
* Covers nothing
*
* @testdox Just setup BASE
*
* @return void
*/
public function testSetupData(): void
{
if (!defined('BASE')) {
define(
'BASE',
str_replace('/configs', '', __DIR__)
. DIRECTORY_SEPARATOR
);
}
$this->assertEquals(
str_replace('/configs', '', __DIR__)
. DIRECTORY_SEPARATOR,
BASE,
'BASE Path set check'
);
}
}
// __END__

View File

@@ -0,0 +1 @@
../Language/includes/

1
4dev/tests/AAASetupData/log Symbolic link
View File

@@ -0,0 +1 @@
../Debug/log/

View File

@@ -0,0 +1,65 @@
<?php // phpcs:ignore PSR1.Files.SideEffects
/**
* AUTHOR: Clemens Schwaighofer
* CREATED: Ymd
* DESCRIPTION:
* DescriptionHere
*/
declare(strict_types=1);
/**
* build return json
*
* @param array<string,mixed> $http_headers
* @param ?string $body
* @return string
*/
function buildContent(array $http_headers, ?string $body): string
{
if (is_string($body) && !empty($body)) {
$_body = json_decode($body, true);
if (!is_array($_body)) {
$body = [$body];
} else {
$body = $_body;
}
} elseif (is_string($body)) {
$body = [];
}
return json_encode([
'HEADERS' => $http_headers,
"REQUEST_TYPE" => $_SERVER['REQUEST_METHOD'],
"PARAMS" => $_GET,
"BODY" => $body,
]);
}
$http_headers = array_filter($_SERVER, function ($value, $key) {
if (str_starts_with($key, 'HTTP_')) {
return true;
}
}, ARRAY_FILTER_USE_BOTH);
header("Content-Type: application/json; charset=UTF-8");
// if the header has Authorization and RunAuthTest then exit with 401
if (!empty($http_headers['HTTP_AUTHORIZATION']) && !empty($http_headers['HTTP_RUNAUTHTEST'])) {
header("HTTP/1.1 401 Unauthorized");
print buildContent($http_headers, '{"code": 401, "content": {"Error": "Not Authorized"}}');
exit(1);
}
// if server request type is get set file_get to null -> no body
if ($_SERVER['REQUEST_METHOD'] == "GET") {
$file_get = null;
} elseif (($file_get = file_get_contents('php://input')) === false) {
header("HTTP/1.1 404 Not Found");
print buildContent($http_headers, '{"code": 404, "content": {"Error": "file_get_contents failed"}}');
exit(1);
}
print buildContent($http_headers, $file_get);
// __END__

View File

@@ -7,6 +7,16 @@ namespace tests;
use PHPUnit\Framework\TestCase; use PHPUnit\Framework\TestCase;
use PHPUnit\Framework\MockObject\MockObject; use PHPUnit\Framework\MockObject\MockObject;
/*
Not yet covered tests:
- loginGetLocale
- loginGetHeaderColor
- loginGetPages
- loginGetPageLookupList
- loginPageAccessAllowed
- loginGetEuid
*/
/** /**
* Test class for ACL\Login * Test class for ACL\Login
* @coversDefaultClass \CoreLibs\ACL\Login * @coversDefaultClass \CoreLibs\ACL\Login
@@ -14,8 +24,12 @@ use PHPUnit\Framework\MockObject\MockObject;
*/ */
final class CoreLibsACLLoginTest extends TestCase final class CoreLibsACLLoginTest extends TestCase
{ {
private static $db; private static \CoreLibs\DB\IO $db;
private static $log; private static \CoreLibs\Logging\Logging $log;
private static string $edit_access_cuid;
private static string $edit_user_cuid;
private static string $edit_user_cuuid;
/** /**
* start DB conneciton, setup DB, etc * start DB conneciton, setup DB, etc
@@ -60,13 +74,10 @@ final class CoreLibsACLLoginTest extends TestCase
// logger is always needed // logger is always needed
// define basic connection set valid and one invalid // define basic connection set valid and one invalid
self::$log = new \CoreLibs\Debug\Logging([ self::$log = new \CoreLibs\Logging\Logging([
// 'log_folder' => __DIR__ . DIRECTORY_SEPARATOR . 'log', // 'log_folder' => __DIR__ . DIRECTORY_SEPARATOR . 'log',
'log_folder' => DIRECTORY_SEPARATOR . 'tmp', 'log_folder' => DIRECTORY_SEPARATOR . 'tmp',
'file_id' => 'CoreLibs-ACL-Login-Test', 'log_file_id' => 'CoreLibs-ACL-Login-Test',
'debug_all' => true,
'echo_all' => false,
'print_all' => true,
]); ]);
// test database we need to connect do, if not possible this test is skipped // test database we need to connect do, if not possible this test is skipped
self::$db = new \CoreLibs\DB\IO( self::$db = new \CoreLibs\DB\IO(
@@ -103,25 +114,48 @@ final class CoreLibsACLLoginTest extends TestCase
self::$db->dbSetMaxQueryCall(-1); self::$db->dbSetMaxQueryCall(-1);
// insert additional content for testing (locked user, etc) // insert additional content for testing (locked user, etc)
$queries = [ $queries = [
"INSERT INTO edit_access_data " <<<SQL
. "(edit_access_id, name, value, enabled) VALUES " INSERT INTO edit_access_data (
. "((SELECT edit_access_id FROM edit_access WHERE uid = 'AdminAccess'), " edit_access_id, name, value, enabled
. "'test', 'value', 1)" ) VALUES (
(SELECT edit_access_id FROM edit_access WHERE uid = 'AdminAccess'),
'test', 'value', 1
)
SQL
]; ];
foreach ($queries as $query) { foreach ($queries as $query) {
self::$db->dbExec($query); self::$db->dbExec($query);
} }
// read edit access cuid, edit user cuid and edit user cuuid
$row = self::$db->dbReturnRowParams(
"SELECT cuid FROM edit_access WHERE uid = $1",
["AdminAccess"]
);
self::$edit_access_cuid = $row['cuid'] ?? '';
if (empty(self::$edit_access_cuid)) {
self::markTestIncomplete(
'Cannot read edit access cuid for "AdminAccess".'
);
}
$row = self::$db->dbReturnRowParams(
"SELECT cuid, cuuid FROM edit_user WHERE username = $1",
["admin"]
);
self::$edit_user_cuid = $row['cuid'] ?? '';
self::$edit_user_cuuid = $row['cuuid'] ?? '';
if (empty(self::$edit_user_cuid) || empty(self::$edit_user_cuuid)) {
self::markTestIncomplete(
'Cannot read edit user cuid or cuuid for "admin".'
);
}
// define mandatory constant // define mandatory constant
// must set // must set
// TARGET // TARGET
define('TARGET', 'test'); define('TARGET', 'test');
// LOGIN DB SCHEMA // LOGIN DB SCHEMA
// define('LOGIN_DB_SCHEMA', '');
// SHOULD SET // SHOULD SET
// PASSWORD_MIN_LENGTH (d9)
// PASSWORD_MAX_LENGTH (d255)
// DEFAULT_ACL_LEVEL (d80) // DEFAULT_ACL_LEVEL (d80)
// OPT: // OPT:
@@ -164,8 +198,10 @@ final class CoreLibsACLLoginTest extends TestCase
// change_password, pw_username, pw_old_password, pw_new_password, // change_password, pw_username, pw_old_password, pw_new_password,
// pw_new_password_confirm // pw_new_password_confirm
// 3[session]: override session set // 3[session]: override session set
// 4[error] : expected error code, 0 for all ok, 3000 for login page view // 4[error] : expected error code, 0 for all ok, 100 for login page view
// note that 1000 (no db), 2000 (no session) must be tested too // note that 1000 (no db), 2000 (no session), 3000 (options set error)
// must be tested too
// <1000 info, >=1000 critical error
// 5[return] : expected return array, eg login_error code, // 5[return] : expected return array, eg login_error code,
// or other info data to match // or other info data to match
$tests = [ $tests = [
@@ -177,7 +213,7 @@ final class CoreLibsACLLoginTest extends TestCase
[], [],
[], [],
[], [],
3000, 100,
[ [
'login_error' => 0, 'login_error' => 0,
'error_string' => 'Success: <b>No error</b>', 'error_string' => 'Success: <b>No error</b>',
@@ -195,7 +231,7 @@ final class CoreLibsACLLoginTest extends TestCase
[], [],
[], [],
[], [],
3000, 100,
[ [
'login_error' => 0, 'login_error' => 0,
'error_string' => 'Success: <b>No error</b>', 'error_string' => 'Success: <b>No error</b>',
@@ -218,7 +254,7 @@ final class CoreLibsACLLoginTest extends TestCase
[], [],
[], [],
[], [],
3000, 100,
[ [
'login_error' => 0, 'login_error' => 0,
'error_string' => 'Success: <b>No error</b>', 'error_string' => 'Success: <b>No error</b>',
@@ -230,22 +266,25 @@ final class CoreLibsACLLoginTest extends TestCase
'ajax_post_action' => 'login', 'ajax_post_action' => 'login',
], ],
], ],
'load, session euid set only, php error' => [ 'load, session eucuuid set only, php error' => [
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
], ],
[], [],
[], [],
[ [
'EUID' => 1, 'LOGIN_EUID' => 1,
'LOGIN_EUCUID' => 'abc',
'LOGIN_EUCUUID' => '1233456-1234-1234-1234-123456789012',
], ],
2, 2,
[], [],
], ],
'load, session euid set, all set' => [ 'load, session eucuuid set, all set' => [
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'edit_access_uid' => 'AdminAccess', 'edit_access_uid' => 'AdminAccess',
'edit_access_data' => 'test', 'edit_access_data' => 'test',
'base_access' => 'list', 'base_access' => 'list',
@@ -254,18 +293,23 @@ final class CoreLibsACLLoginTest extends TestCase
[], [],
[], [],
[ [
'EUID' => 1, 'LOGIN_EUID' => 1,
'USER_NAME' => '', 'LOGIN_EUCUID' => 'abc',
'GROUP_NAME' => '', 'LOGIN_EUCUUID' => 'SET_EUCUUID_IN_TEST',
'ADMIN' => 1, 'LOGIN_USER_NAME' => '',
'GROUP_ACL_LEVEL' => -1, 'LOGIN_GROUP_NAME' => '',
'PAGES_ACL_LEVEL' => [], 'LOGIN_ADMIN' => 1,
'USER_ACL_LEVEL' => -1, 'LOGIN_GROUP_ACL_LEVEL' => -1,
'UNIT_UID' => [ 'LOGIN_PAGES_ACL_LEVEL' => [],
'AdminAccess' => 1, 'LOGIN_USER_ACL_LEVEL' => -1,
'LOGIN_USER_ADDITIONAL_ACL' => [],
'LOGIN_GROUP_ADDITIONAL_ACL' => [],
'LOGIN_UNIT_UID' => [
'AdminAccess' => '123456789012',
], ],
'UNIT' => [ 'LOGIN_UNIT' => [
1 => [ '123456789012' => [
'id' => 1,
'acl_level' => 80, 'acl_level' => 80,
'name' => 'Admin Access', 'name' => 'Admin Access',
'uid' => 'AdminAccess', 'uid' => 'AdminAccess',
@@ -274,10 +318,11 @@ final class CoreLibsACLLoginTest extends TestCase
'data' => [ 'data' => [
'test' => 'value', 'test' => 'value',
], ],
'additional_acl' => []
], ],
], ],
// 'UNIT_DEFAULT' => '', // 'LOGIN_UNIT_DEFAULT' => '',
// 'DEFAULT_ACL_LIST' => [], // 'LOGIN_DEFAULT_ACL_LIST' => [],
], ],
0, 0,
[ [
@@ -285,6 +330,7 @@ final class CoreLibsACLLoginTest extends TestCase
'admin_flag' => true, 'admin_flag' => true,
'check_access' => true, 'check_access' => true,
'check_access_id' => 1, 'check_access_id' => 1,
'check_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'check_access_data' => 'value', 'check_access_data' => 'value',
'base_access' => true, 'base_access' => true,
'page_access' => true, 'page_access' => true,
@@ -302,7 +348,7 @@ final class CoreLibsACLLoginTest extends TestCase
'login_password' => '', 'login_password' => '',
], ],
[], [],
3000, 100,
[ [
'login_error' => 102, 'login_error' => 102,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -323,7 +369,7 @@ final class CoreLibsACLLoginTest extends TestCase
'login_password' => 'abc', 'login_password' => 'abc',
], ],
[], [],
3000, 100,
[ [
'login_error' => 102, 'login_error' => 102,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -344,7 +390,7 @@ final class CoreLibsACLLoginTest extends TestCase
'login_password' => '', 'login_password' => '',
], ],
[], [],
3000, 100,
[ [
'login_error' => 102, 'login_error' => 102,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -365,7 +411,7 @@ final class CoreLibsACLLoginTest extends TestCase
'login_password' => 'abc', 'login_password' => 'abc',
], ],
[], [],
3000, 100,
[ [
'login_error' => 1010, 'login_error' => 1010,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -389,7 +435,7 @@ final class CoreLibsACLLoginTest extends TestCase
'login_password' => 'abc', 'login_password' => 'abc',
], ],
[], [],
3000, 100,
[ [
// default password is plain text // default password is plain text
'login_error' => 1012, 'login_error' => 1012,
@@ -404,6 +450,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'base_access' => 'list', 'base_access' => 'list',
'page_access' => 'list', 'page_access' => 'list',
'test_deleted' => true 'test_deleted' => true
@@ -415,7 +462,7 @@ final class CoreLibsACLLoginTest extends TestCase
'login_password' => 'admin', 'login_password' => 'admin',
], ],
[], [],
3000, 100,
[ [
'login_error' => 106, 'login_error' => 106,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -429,6 +476,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'base_access' => 'list', 'base_access' => 'list',
'page_access' => 'list', 'page_access' => 'list',
'test_enabled' => true 'test_enabled' => true
@@ -440,7 +488,7 @@ final class CoreLibsACLLoginTest extends TestCase
'login_password' => 'admin', 'login_password' => 'admin',
], ],
[], [],
3000, 100,
[ [
'login_error' => 104, 'login_error' => 104,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -454,6 +502,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'base_access' => 'list', 'base_access' => 'list',
'page_access' => 'list', 'page_access' => 'list',
'test_locked' => true 'test_locked' => true
@@ -465,7 +514,7 @@ final class CoreLibsACLLoginTest extends TestCase
'login_password' => 'admin', 'login_password' => 'admin',
], ],
[], [],
3000, 100,
[ [
'login_error' => 105, 'login_error' => 105,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -479,6 +528,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'base_access' => 'list', 'base_access' => 'list',
'page_access' => 'list', 'page_access' => 'list',
'test_get_locked' => true, 'test_get_locked' => true,
@@ -503,6 +553,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'base_access' => 'list', 'base_access' => 'list',
'page_access' => 'list', 'page_access' => 'list',
'test_locked_period_until' => 'on' 'test_locked_period_until' => 'on'
@@ -514,7 +565,7 @@ final class CoreLibsACLLoginTest extends TestCase
'login_password' => 'admin', 'login_password' => 'admin',
], ],
[], [],
3000, 100,
[ [
'login_error' => 107, 'login_error' => 107,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -528,6 +579,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'edit_access_uid' => 'AdminAccess', 'edit_access_uid' => 'AdminAccess',
'edit_access_data' => 'test', 'edit_access_data' => 'test',
'base_access' => 'list', 'base_access' => 'list',
@@ -547,6 +599,7 @@ final class CoreLibsACLLoginTest extends TestCase
'admin_flag' => true, 'admin_flag' => true,
'check_access' => true, 'check_access' => true,
'check_access_id' => 1, 'check_access_id' => 1,
'check_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'check_access_data' => 'value', 'check_access_data' => 'value',
'base_access' => true, 'base_access' => true,
'page_access' => true, 'page_access' => true,
@@ -557,6 +610,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'base_access' => 'list', 'base_access' => 'list',
'page_access' => 'list', 'page_access' => 'list',
'test_locked_period_after' => 'on' 'test_locked_period_after' => 'on'
@@ -568,7 +622,7 @@ final class CoreLibsACLLoginTest extends TestCase
'login_password' => 'admin', 'login_password' => 'admin',
], ],
[], [],
3000, 100,
[ [
'login_error' => 107, 'login_error' => 107,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -582,6 +636,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'base_access' => 'list', 'base_access' => 'list',
'page_access' => 'list', 'page_access' => 'list',
'test_locked_period_until' => 'on', 'test_locked_period_until' => 'on',
@@ -594,7 +649,7 @@ final class CoreLibsACLLoginTest extends TestCase
'login_password' => 'admin', 'login_password' => 'admin',
], ],
[], [],
3000, 100,
[ [
'login_error' => 107, 'login_error' => 107,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -608,6 +663,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'base_access' => 'list', 'base_access' => 'list',
'page_access' => 'list', 'page_access' => 'list',
'test_login_user_id_locked' => true 'test_login_user_id_locked' => true
@@ -619,7 +675,7 @@ final class CoreLibsACLLoginTest extends TestCase
'login_password' => 'admin', 'login_password' => 'admin',
], ],
[], [],
3000, 100,
[ [
'login_error' => 108, 'login_error' => 108,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -633,6 +689,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'edit_access_uid' => 'AdminAccess', 'edit_access_uid' => 'AdminAccess',
'edit_access_data' => 'test', 'edit_access_data' => 'test',
'base_access' => 'list', 'base_access' => 'list',
@@ -651,6 +708,7 @@ final class CoreLibsACLLoginTest extends TestCase
'admin_flag' => true, 'admin_flag' => true,
'check_access' => true, 'check_access' => true,
'check_access_id' => 1, 'check_access_id' => 1,
'check_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'check_access_data' => 'value', 'check_access_data' => 'value',
'base_access' => true, 'base_access' => true,
'page_access' => true, 'page_access' => true,
@@ -661,6 +719,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'edit_access_uid' => 'AdminAccess', 'edit_access_uid' => 'AdminAccess',
'edit_access_data' => 'test', 'edit_access_data' => 'test',
'base_access' => 'list', 'base_access' => 'list',
@@ -680,6 +739,7 @@ final class CoreLibsACLLoginTest extends TestCase
'admin_flag' => true, 'admin_flag' => true,
'check_access' => true, 'check_access' => true,
'check_access_id' => 1, 'check_access_id' => 1,
'check_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'check_access_data' => 'value', 'check_access_data' => 'value',
'base_access' => true, 'base_access' => true,
'page_access' => true, 'page_access' => true,
@@ -690,6 +750,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'edit_access_uid' => 'AdminAccess', 'edit_access_uid' => 'AdminAccess',
'edit_access_data' => 'test', 'edit_access_data' => 'test',
'base_access' => 'list', 'base_access' => 'list',
@@ -709,6 +770,7 @@ final class CoreLibsACLLoginTest extends TestCase
'admin_flag' => true, 'admin_flag' => true,
'check_access' => true, 'check_access' => true,
'check_access_id' => 1, 'check_access_id' => 1,
'check_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'check_access_data' => 'value', 'check_access_data' => 'value',
'base_access' => true, 'base_access' => true,
'page_access' => true, 'page_access' => true,
@@ -719,6 +781,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'edit_access_uid' => 'AdminAccess', 'edit_access_uid' => 'AdminAccess',
'edit_access_data' => 'test', 'edit_access_data' => 'test',
'base_access' => 'list', 'base_access' => 'list',
@@ -738,6 +801,7 @@ final class CoreLibsACLLoginTest extends TestCase
'admin_flag' => true, 'admin_flag' => true,
'check_access' => true, 'check_access' => true,
'check_access_id' => 1, 'check_access_id' => 1,
'check_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'check_access_data' => 'value', 'check_access_data' => 'value',
'base_access' => true, 'base_access' => true,
'page_access' => true, 'page_access' => true,
@@ -755,7 +819,7 @@ final class CoreLibsACLLoginTest extends TestCase
], ],
[], [],
[], [],
3000, 100,
[ [
'login_error' => 1010, 'login_error' => 1010,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -769,6 +833,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'edit_access_uid' => 'AdminAccess', 'edit_access_uid' => 'AdminAccess',
'edit_access_data' => 'test', 'edit_access_data' => 'test',
'base_access' => 'list', 'base_access' => 'list',
@@ -792,6 +857,7 @@ final class CoreLibsACLLoginTest extends TestCase
'admin_flag' => true, 'admin_flag' => true,
'check_access' => true, 'check_access' => true,
'check_access_id' => 1, 'check_access_id' => 1,
'check_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'check_access_data' => 'value', 'check_access_data' => 'value',
'base_access' => true, 'base_access' => true,
'page_access' => true, 'page_access' => true,
@@ -802,6 +868,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'edit_access_uid' => 'AdminAccess', 'edit_access_uid' => 'AdminAccess',
'edit_access_data' => 'test', 'edit_access_data' => 'test',
'base_access' => 'list', 'base_access' => 'list',
@@ -825,6 +892,7 @@ final class CoreLibsACLLoginTest extends TestCase
'admin_flag' => true, 'admin_flag' => true,
'check_access' => true, 'check_access' => true,
'check_access_id' => 1, 'check_access_id' => 1,
'check_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'check_access_data' => 'value', 'check_access_data' => 'value',
'base_access' => true, 'base_access' => true,
'page_access' => true, 'page_access' => true,
@@ -835,6 +903,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'base_access' => 'list', 'base_access' => 'list',
'page_access' => 'list', 'page_access' => 'list',
'test_login_user_id_revalidate_after' => 'on', 'test_login_user_id_revalidate_after' => 'on',
@@ -847,7 +916,7 @@ final class CoreLibsACLLoginTest extends TestCase
], ],
[], [],
[], [],
3000, 100,
[ [
'login_error' => 1101, 'login_error' => 1101,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -861,6 +930,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'edit_access_uid' => 'AdminAccess', 'edit_access_uid' => 'AdminAccess',
'edit_access_data' => 'test', 'edit_access_data' => 'test',
'base_access' => 'list', 'base_access' => 'list',
@@ -881,6 +951,7 @@ final class CoreLibsACLLoginTest extends TestCase
'admin_flag' => true, 'admin_flag' => true,
'check_access' => true, 'check_access' => true,
'check_access_id' => 1, 'check_access_id' => 1,
'check_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'check_access_data' => 'value', 'check_access_data' => 'value',
'base_access' => true, 'base_access' => true,
'page_access' => true, 'page_access' => true,
@@ -891,6 +962,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'base_access' => 'list', 'base_access' => 'list',
'page_access' => 'list', 'page_access' => 'list',
'test_login_user_id_valid_from' => 'on', 'test_login_user_id_valid_from' => 'on',
@@ -903,7 +975,7 @@ final class CoreLibsACLLoginTest extends TestCase
], ],
[], [],
[], [],
3000, 100,
[ [
'login_error' => 1102, 'login_error' => 1102,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -917,6 +989,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'edit_access_uid' => 'AdminAccess', 'edit_access_uid' => 'AdminAccess',
'edit_access_data' => 'test', 'edit_access_data' => 'test',
'base_access' => 'list', 'base_access' => 'list',
@@ -937,6 +1010,7 @@ final class CoreLibsACLLoginTest extends TestCase
'admin_flag' => true, 'admin_flag' => true,
'check_access' => true, 'check_access' => true,
'check_access_id' => 1, 'check_access_id' => 1,
'check_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'check_access_data' => 'value', 'check_access_data' => 'value',
'base_access' => true, 'base_access' => true,
'page_access' => true, 'page_access' => true,
@@ -947,6 +1021,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'base_access' => 'list', 'base_access' => 'list',
'page_access' => 'list', 'page_access' => 'list',
'test_login_user_id_valid_until' => 'on', 'test_login_user_id_valid_until' => 'on',
@@ -959,7 +1034,7 @@ final class CoreLibsACLLoginTest extends TestCase
], ],
[], [],
[], [],
3000, 100,
[ [
'login_error' => 1102, 'login_error' => 1102,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -973,6 +1048,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'base_access' => 'list', 'base_access' => 'list',
'page_access' => 'list', 'page_access' => 'list',
'test_login_user_id_valid_from' => 'on', 'test_login_user_id_valid_from' => 'on',
@@ -986,7 +1062,7 @@ final class CoreLibsACLLoginTest extends TestCase
], ],
[], [],
[], [],
3000, 100,
[ [
'login_error' => 1102, 'login_error' => 1102,
'error_string' => '<span style="color: red;">Fatal Error:</span> ' 'error_string' => '<span style="color: red;">Fatal Error:</span> '
@@ -1000,6 +1076,7 @@ final class CoreLibsACLLoginTest extends TestCase
[ [
'page_name' => 'edit_users.php', 'page_name' => 'edit_users.php',
'edit_access_id' => 1, 'edit_access_id' => 1,
'edit_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'edit_access_uid' => 'AdminAccess', 'edit_access_uid' => 'AdminAccess',
'edit_access_data' => 'test', 'edit_access_data' => 'test',
'base_access' => 'list', 'base_access' => 'list',
@@ -1030,6 +1107,7 @@ final class CoreLibsACLLoginTest extends TestCase
'admin_flag' => true, 'admin_flag' => true,
'check_access' => true, 'check_access' => true,
'check_access_id' => 1, 'check_access_id' => 1,
'check_access_cuid' => 'SET_EDIT_ACCESS_CUID_IN_TEST',
'check_access_data' => 'value', 'check_access_data' => 'value',
'base_access' => true, 'base_access' => true,
'page_access' => true, 'page_access' => true,
@@ -1077,9 +1155,9 @@ final class CoreLibsACLLoginTest extends TestCase
/** @var \CoreLibs\Create\Session&MockObject */ /** @var \CoreLibs\Create\Session&MockObject */
$session_mock = $this->createPartialMock( $session_mock = $this->createPartialMock(
\CoreLibs\Create\Session::class, \CoreLibs\Create\Session::class,
['startSession', 'checkActiveSession', 'sessionDestroy'] ['getSessionId', 'checkActiveSession', 'sessionDestroy']
); );
$session_mock->method('startSession')->willReturn('ACLLOGINTEST12'); $session_mock->method('getSessionId')->willReturn('ACLLOGINTEST12');
$session_mock->method('checkActiveSession')->willReturn(true); $session_mock->method('checkActiveSession')->willReturn(true);
$session_mock->method('sessionDestroy')->will( $session_mock->method('sessionDestroy')->will(
$this->returnCallback(function () { $this->returnCallback(function () {
@@ -1099,20 +1177,39 @@ final class CoreLibsACLLoginTest extends TestCase
$_POST[$post_var] = $post_value; $_POST[$post_var] = $post_value;
} }
// set ingoing session cuuid if requested
if (isset($session['LOGIN_EUCUUID']) && $session['LOGIN_EUCUUID'] == 'SET_EUCUUID_IN_TEST') {
$session['LOGIN_EUCUUID'] = self::$edit_user_cuuid;
}
// set _SESSION data // set _SESSION data
foreach ($session as $session_var => $session_value) { foreach ($session as $session_var => $session_value) {
$_SESSION[$session_var] = $session_value; $_SESSION[$session_var] = $session_value;
} }
/** @var \CoreLibs\ACL\Login&MockObject */ /** @var \CoreLibs\ACL\Login&MockObject */
$login_mock = $this->getMockBuilder(\CoreLibs\ACL\Login::class) $login_mock = $this->getMockBuilder(\CoreLibs\ACL\Login::class)
->setConstructorArgs([self::$db, self::$log, $session_mock, false]) ->setConstructorArgs([
->onlyMethods(['loginTerminate', 'loginReadPageName', 'loginPrintLogin']) self::$db,
self::$log,
$session_mock,
[
'auto_login' => false,
'default_acl_level' => 80,
'logout_target' => '',
'site_locale' => 'en_US.UTF-8',
'site_domain' => 'admin',
'site_encoding' => 'UTF-8',
'locale_path' => __DIR__ . DIRECTORY_SEPARATOR
. 'includes' . DIRECTORY_SEPARATOR
. 'locale' . DIRECTORY_SEPARATOR,
]
])
->onlyMethods(['loginTerminate', 'loginReadPageName', 'loginPrintLogin', 'loginEnhanceHttpSecurity'])
->getMock(); ->getMock();
$login_mock->expects($this->any()) $login_mock->expects($this->any())
->method('loginTerminate') ->method('loginTerminate')
->will( ->will(
$this->returnCallback(function ($code) { $this->returnCallback(function ($message, $code) {
throw new \Exception('', $code); throw new \Exception('', $code);
}) })
); );
@@ -1125,6 +1222,10 @@ final class CoreLibsACLLoginTest extends TestCase
->method('loginPrintLogin') ->method('loginPrintLogin')
->willReturnCallback(function () { ->willReturnCallback(function () {
}); });
$login_mock->expects($this->any())
->method('loginEnhanceHttpSecurity')
->willReturnCallback(function () {
});
// if mock_settings: enabled OFF // if mock_settings: enabled OFF
// run DB update and set off // run DB update and set off
@@ -1206,7 +1307,11 @@ final class CoreLibsACLLoginTest extends TestCase
$login_mock->loginSetMaxLoginErrorCount($mock_settings['max_login_error_count']); $login_mock->loginSetMaxLoginErrorCount($mock_settings['max_login_error_count']);
// temporary wrong password // temporary wrong password
$_POST['login_password'] = 'wrong'; $_POST['login_password'] = 'wrong';
for ($run = 1, $max_run = $login_mock->loginGetMaxLoginErrorCount(); $run <= $max_run; $run++) { for (
$run = 1, $max_run = $login_mock->loginGetMaxLoginErrorCount();
$run <= $max_run;
$run++
) {
try { try {
$login_mock->loginMainCall(); $login_mock->loginMainCall();
} catch (\Exception $e) { } catch (\Exception $e) {
@@ -1338,6 +1443,19 @@ final class CoreLibsACLLoginTest extends TestCase
// run test // run test
try { try {
// preset, we cannot set that in the provider
if (
isset($expected['check_access_cuid']) &&
$expected['check_access_cuid'] == 'SET_EDIT_ACCESS_CUID_IN_TEST'
) {
$expected['check_access_cuid'] = self::$edit_access_cuid;
}
if (
isset($mock_settings['edit_access_cuid']) &&
$mock_settings['edit_access_cuid'] == 'SET_EDIT_ACCESS_CUID_IN_TEST'
) {
$mock_settings['edit_access_cuid'] = self::$edit_access_cuid;
}
// if ajax call // if ajax call
// check if parameter, or globals (old type) // check if parameter, or globals (old type)
// else normal call // else normal call
@@ -1396,6 +1514,31 @@ final class CoreLibsACLLoginTest extends TestCase
$login_mock->loginCheckAccessPage($mock_settings['page_access']), $login_mock->loginCheckAccessPage($mock_settings['page_access']),
'Assert page access' 'Assert page access'
); );
// - loginCheckEditAccessCuid
$this->assertEquals(
$expected['check_access'],
$login_mock->loginCheckEditAccessCuid($mock_settings['edit_access_cuid']),
'Assert check access'
);
// - loginCheckEditAccessValidCuid
$this->assertEquals(
$expected['check_access_cuid'],
$login_mock->loginCheckEditAccessValidCuid($mock_settings['edit_access_cuid']),
'Assert check access cuid valid'
);
// - loginGetEditAccessCuidFromUid
$this->assertEquals(
$expected['check_access_cuid'],
$login_mock->loginGetEditAccessCuidFromUid($mock_settings['edit_access_uid']),
'Assert check access uid to cuid valid'
);
// - loginGetEditAccessCuidFromId
$this->assertEquals(
$expected['check_access_cuid'],
$login_mock->loginGetEditAccessCuidFromUid($mock_settings['edit_access_id']),
'Assert check access id to cuid valid'
);
// Deprecated
// - loginCheckEditAccess // - loginCheckEditAccess
$this->assertEquals( $this->assertEquals(
$expected['check_access'], $expected['check_access'],
@@ -1418,7 +1561,7 @@ final class CoreLibsACLLoginTest extends TestCase
$this->assertEquals( $this->assertEquals(
$expected['check_access_data'], $expected['check_access_data'],
$login_mock->loginGetEditAccessData( $login_mock->loginGetEditAccessData(
$mock_settings['edit_access_id'], $mock_settings['edit_access_uid'],
$mock_settings['edit_access_data'] $mock_settings['edit_access_data']
), ),
'Assert check access id data value valid' 'Assert check access id data value valid'
@@ -1449,15 +1592,16 @@ final class CoreLibsACLLoginTest extends TestCase
// - loginCheckPermissions // - loginCheckPermissions
// - loginGetPermissionOkay // - loginGetPermissionOkay
} catch (\Exception $e) { } catch (\Exception $e) {
// print "[E]: " . $e->getCode() . ", ERROR: " . $login_mock->loginGetLastErrorCode() . "/" /* print "[E]: " . $e->getCode() . ", ERROR: " . $login_mock->loginGetLastErrorCode() . "/"
// . ($expected['login_error'] ?? 0) . "\n"; . ($expected['login_error'] ?? 0) . "\n";
// print "AJAX: " . $login_mock->loginGetAjaxFlag() . "\n"; print "AJAX: " . $login_mock->loginGetAjaxFlag() . "\n";
// print "AJAX GLOBAL: " . ($GLOBALS['AJAX_PAGE'] ?? '{f}') . "\n"; print "AJAX GLOBAL: " . ($GLOBALS['AJAX_PAGE'] ?? '{f}') . "\n";
// print "Login error expext: " . ($expected['login_error'] ?? '{0}') . "\n"; print "Login error expext: " . ($expected['login_error'] ?? '{0}') . "\n";
// if this is 3000, then we do further error checks print "POST exit: " . ($_POST['login_exit'] ?? '{0}') . "\n"; */
// if this is 100, then we do further error checks
if ( if (
$e->getCode() == 3000 || $e->getCode() == 100 ||
!empty($_POST['login_exit']) && $_POST['login_exit'] == 3000 !empty($_POST['login_exit']) && $_POST['login_exit'] == 100
) { ) {
$this->assertEquals( $this->assertEquals(
$expected['login_error'], $expected['login_error'],
@@ -1729,7 +1873,7 @@ final class CoreLibsACLLoginTest extends TestCase
], ],
20 20
], ],
'invalud search' => [ 'invalid search' => [
12, 12,
'foo', 'foo',
[], [],
@@ -1761,9 +1905,9 @@ final class CoreLibsACLLoginTest extends TestCase
/** @var \CoreLibs\Create\Session&MockObject */ /** @var \CoreLibs\Create\Session&MockObject */
$session_mock = $this->createPartialMock( $session_mock = $this->createPartialMock(
\CoreLibs\Create\Session::class, \CoreLibs\Create\Session::class,
['startSession', 'checkActiveSession', 'sessionDestroy'] ['getSessionId', 'checkActiveSession', 'sessionDestroy']
); );
$session_mock->method('startSession')->willReturn('ACLLOGINTEST34'); $session_mock->method('getSessionId')->willReturn('ACLLOGINTEST34');
$session_mock->method('checkActiveSession')->willReturn(true); $session_mock->method('checkActiveSession')->willReturn(true);
$session_mock->method('sessionDestroy')->will( $session_mock->method('sessionDestroy')->will(
$this->returnCallback(function () { $this->returnCallback(function () {
@@ -1774,13 +1918,28 @@ final class CoreLibsACLLoginTest extends TestCase
); );
/** @var \CoreLibs\ACL\Login&MockObject */ /** @var \CoreLibs\ACL\Login&MockObject */
$login_mock = $this->getMockBuilder(\CoreLibs\ACL\Login::class) $login_mock = $this->getMockBuilder(\CoreLibs\ACL\Login::class)
->setConstructorArgs([self::$db, self::$log, $session_mock, false]) ->setConstructorArgs([
self::$db,
self::$log,
$session_mock,
[
'auto_login' => false,
'default_acl_level' => 80,
'logout_target' => '',
'site_locale' => 'en_US.UTF-8',
'site_domain' => 'admin',
'site_encoding' => 'UTF-8',
'locale_path' => __DIR__ . DIRECTORY_SEPARATOR
. 'includes' . DIRECTORY_SEPARATOR
. 'locale' . DIRECTORY_SEPARATOR,
]
])
->onlyMethods(['loginTerminate']) ->onlyMethods(['loginTerminate'])
->getMock(); ->getMock();
$login_mock->expects($this->any()) $login_mock->expects($this->any())
->method('loginTerminate') ->method('loginTerminate')
->will( ->will(
$this->returnCallback(function ($code) { $this->returnCallback(function ($message, $code) {
throw new \Exception('', $code); throw new \Exception('', $code);
}) })
); );
@@ -1860,9 +2019,9 @@ final class CoreLibsACLLoginTest extends TestCase
/** @var \CoreLibs\Create\Session&MockObject */ /** @var \CoreLibs\Create\Session&MockObject */
$session_mock = $this->createPartialMock( $session_mock = $this->createPartialMock(
\CoreLibs\Create\Session::class, \CoreLibs\Create\Session::class,
['startSession', 'checkActiveSession', 'sessionDestroy'] ['getSessionId', 'checkActiveSession', 'sessionDestroy']
); );
$session_mock->method('startSession')->willReturn('ACLLOGINTEST34'); $session_mock->method('getSessionId')->willReturn('ACLLOGINTEST34');
$session_mock->method('checkActiveSession')->willReturn(true); $session_mock->method('checkActiveSession')->willReturn(true);
$session_mock->method('sessionDestroy')->will( $session_mock->method('sessionDestroy')->will(
$this->returnCallback(function () { $this->returnCallback(function () {
@@ -1873,13 +2032,28 @@ final class CoreLibsACLLoginTest extends TestCase
); );
/** @var \CoreLibs\ACL\Login&MockObject */ /** @var \CoreLibs\ACL\Login&MockObject */
$login_mock = $this->getMockBuilder(\CoreLibs\ACL\Login::class) $login_mock = $this->getMockBuilder(\CoreLibs\ACL\Login::class)
->setConstructorArgs([self::$db, self::$log, $session_mock, false]) ->setConstructorArgs([
self::$db,
self::$log,
$session_mock,
[
'auto_login' => false,
'default_acl_level' => 80,
'logout_target' => '',
'site_locale' => 'en_US.UTF-8',
'site_domain' => 'admin',
'site_encoding' => 'UTF-8',
'locale_path' => __DIR__ . DIRECTORY_SEPARATOR
. 'includes' . DIRECTORY_SEPARATOR
. 'locale' . DIRECTORY_SEPARATOR,
]
])
->onlyMethods(['loginTerminate']) ->onlyMethods(['loginTerminate'])
->getMock(); ->getMock();
$login_mock->expects($this->any()) $login_mock->expects($this->any())
->method('loginTerminate') ->method('loginTerminate')
->will( ->will(
$this->returnCallback(function ($code) { $this->returnCallback(function ($message, $code) {
throw new \Exception('', $code); throw new \Exception('', $code);
}) })
); );
@@ -1933,9 +2107,9 @@ final class CoreLibsACLLoginTest extends TestCase
/** @var \CoreLibs\Create\Session&MockObject */ /** @var \CoreLibs\Create\Session&MockObject */
$session_mock = $this->createPartialMock( $session_mock = $this->createPartialMock(
\CoreLibs\Create\Session::class, \CoreLibs\Create\Session::class,
['startSession', 'checkActiveSession', 'sessionDestroy'] ['getSessionId', 'checkActiveSession', 'sessionDestroy']
); );
$session_mock->method('startSession')->willReturn('ACLLOGINTEST34'); $session_mock->method('getSessionId')->willReturn('ACLLOGINTEST34');
$session_mock->method('checkActiveSession')->willReturn(true); $session_mock->method('checkActiveSession')->willReturn(true);
$session_mock->method('sessionDestroy')->will( $session_mock->method('sessionDestroy')->will(
$this->returnCallback(function () { $this->returnCallback(function () {
@@ -1946,13 +2120,28 @@ final class CoreLibsACLLoginTest extends TestCase
); );
/** @var \CoreLibs\ACL\Login&MockObject */ /** @var \CoreLibs\ACL\Login&MockObject */
$login_mock = $this->getMockBuilder(\CoreLibs\ACL\Login::class) $login_mock = $this->getMockBuilder(\CoreLibs\ACL\Login::class)
->setConstructorArgs([self::$db, self::$log, $session_mock, false]) ->setConstructorArgs([
self::$db,
self::$log,
$session_mock,
[
'auto_login' => false,
'default_acl_level' => 80,
'logout_target' => '',
'site_locale' => 'en_US.UTF-8',
'site_domain' => 'admin',
'site_encoding' => 'UTF-8',
'locale_path' => __DIR__ . DIRECTORY_SEPARATOR
. 'includes' . DIRECTORY_SEPARATOR
. 'locale' . DIRECTORY_SEPARATOR,
]
])
->onlyMethods(['loginTerminate']) ->onlyMethods(['loginTerminate'])
->getMock(); ->getMock();
$login_mock->expects($this->any()) $login_mock->expects($this->any())
->method('loginTerminate') ->method('loginTerminate')
->will( ->will(
$this->returnCallback(function ($code) { $this->returnCallback(function ($message, $code) {
throw new \Exception('', $code); throw new \Exception('', $code);
}) })
); );
@@ -2014,9 +2203,9 @@ final class CoreLibsACLLoginTest extends TestCase
/** @var \CoreLibs\Create\Session&MockObject */ /** @var \CoreLibs\Create\Session&MockObject */
$session_mock = $this->createPartialMock( $session_mock = $this->createPartialMock(
\CoreLibs\Create\Session::class, \CoreLibs\Create\Session::class,
['startSession', 'checkActiveSession', 'sessionDestroy'] ['getSessionId', 'checkActiveSession', 'sessionDestroy']
); );
$session_mock->method('startSession')->willReturn('ACLLOGINTEST34'); $session_mock->method('getSessionId')->willReturn('ACLLOGINTEST34');
$session_mock->method('checkActiveSession')->willReturn(true); $session_mock->method('checkActiveSession')->willReturn(true);
$session_mock->method('sessionDestroy')->will( $session_mock->method('sessionDestroy')->will(
$this->returnCallback(function () { $this->returnCallback(function () {
@@ -2027,13 +2216,28 @@ final class CoreLibsACLLoginTest extends TestCase
); );
/** @var \CoreLibs\ACL\Login&MockObject */ /** @var \CoreLibs\ACL\Login&MockObject */
$login_mock = $this->getMockBuilder(\CoreLibs\ACL\Login::class) $login_mock = $this->getMockBuilder(\CoreLibs\ACL\Login::class)
->setConstructorArgs([self::$db, self::$log, $session_mock, false]) ->setConstructorArgs([
self::$db,
self::$log,
$session_mock,
[
'auto_login' => false,
'default_acl_level' => 80,
'logout_target' => '',
'site_locale' => 'en_US.UTF-8',
'site_domain' => 'admin',
'site_encoding' => 'UTF-8',
'locale_path' => __DIR__ . DIRECTORY_SEPARATOR
. 'includes' . DIRECTORY_SEPARATOR
. 'locale' . DIRECTORY_SEPARATOR,
]
])
->onlyMethods(['loginTerminate']) ->onlyMethods(['loginTerminate'])
->getMock(); ->getMock();
$login_mock->expects($this->any()) $login_mock->expects($this->any())
->method('loginTerminate') ->method('loginTerminate')
->will( ->will(
$this->returnCallback(function ($code) { $this->returnCallback(function ($message, $code) {
throw new \Exception('', $code); throw new \Exception('', $code);
}) })
); );

1
4dev/tests/ACL/includes Symbolic link
View File

@@ -0,0 +1 @@
../AAASetupData/includes

View File

@@ -13,6 +13,11 @@ use PHPUnit\Framework\TestCase;
*/ */
final class CoreLibsCheckColorsTest extends TestCase final class CoreLibsCheckColorsTest extends TestCase
{ {
/**
* Undocumented function
*
* @return array<mixed>
*/
public function validateColorProvider(): array public function validateColorProvider(): array
{ {
/* /*
@@ -321,7 +326,7 @@ final class CoreLibsCheckColorsTest extends TestCase
*/ */
public function testValidateColorException(int $flag): void public function testValidateColorException(int $flag): void
{ {
$this->expectException(\Exception::class); $this->expectException(\UnexpectedValueException::class);
\CoreLibs\Check\Colors::validateColor('#ffffff', $flag); \CoreLibs\Check\Colors::validateColor('#ffffff', $flag);
} }
} }

View File

@@ -28,10 +28,10 @@ final class CoreLibsCheckFileTest extends TestCase
public function filesList(): array public function filesList(): array
{ {
return [ return [
['filename.txt', 'txt', 5], ['filename.txt', 'txt', 5, 'text/plain'],
['filename.csv', 'csv', 15], ['filename.csv', 'csv', 15, 'text/csv'],
['filename.tsv', 'tsv', 0], ['filename.tsv', 'tsv', 0, 'text/plain'],
['file_does_not_exits', '', -1], ['file_does_not_exits', '', -1, ''],
]; ];
} }
@@ -63,6 +63,15 @@ final class CoreLibsCheckFileTest extends TestCase
return $list; return $list;
} }
public function mimeTypeProvider(): array
{
$list = [];
foreach ($this->filesList() as $row) {
$list[$row[0] . ' must be mime type ' . $row[3]] = [$row[0], $row[3]];
}
return $list;
}
/** /**
* Tests if file extension matches * Tests if file extension matches
* *
@@ -115,6 +124,51 @@ final class CoreLibsCheckFileTest extends TestCase
unlink($this->base_folder . $input); unlink($this->base_folder . $input);
} }
} }
/**
* Undocumented function
*
* @covers ::getMimeType
* @dataProvider mimeTypeProvider
* @testdox getMimeType $input must be mime type $expected [$_dataName]
*
* @param string $input
* @param string $expected
* @return void
*/
public function testGetMimeType(string $input, string $expected): void
{
if (!empty($expected)) {
$file = $this->base_folder . $input;
$fp = fopen($file, 'w');
switch ($expected) {
case 'text/csv':
for ($i = 1; $i <= 10; $i++) {
fwrite($fp, '"This is row","' . $expected . '",' . $i . PHP_EOL);
}
break;
case 'text/tsv':
for ($i = 1; $i <= 10; $i++) {
fwrite($fp, "\"This is row\"\t\"" . $expected . "\"\t\"" . $i . PHP_EOL);
}
break;
case 'text/plain':
fwrite($fp, 'This is mime type: ' . $expected . PHP_EOL);
break;
}
fclose($fp);
} else {
$this->expectException(\UnexpectedValueException::class);
}
$this->assertEquals(
$expected,
\CoreLibs\Check\File::getMimeType($this->base_folder . $input)
);
// unlink file
if (is_file($this->base_folder . $input)) {
unlink($this->base_folder . $input);
}
}
} }
// __END__ // __END__

View File

@@ -31,6 +31,7 @@ final class CoreLibsCombinedArrayHandlerTest extends TestCase
4, 4,
'b', 'b',
'c' => 'test', 'c' => 'test',
'single' => 'single',
'same' => 'same', 'same' => 'same',
'deep' => [ 'deep' => [
'sub' => [ 'sub' => [
@@ -107,6 +108,13 @@ final class CoreLibsCombinedArrayHandlerTest extends TestCase
*/ */
public function arraySearchRecursiveAllProvider(): array public function arraySearchRecursiveAllProvider(): array
{ {
/*
0: $needle,
1: array $input,
2: ?string $key_search_for,
3: bool $flag,
4: array $expected
*/
return [ return [
'find value' => [ 'find value' => [
0 => 'bar', 0 => 'bar',
@@ -172,6 +180,13 @@ final class CoreLibsCombinedArrayHandlerTest extends TestCase
*/ */
public function arraySearchSimpleProvider(): array public function arraySearchSimpleProvider(): array
{ {
/*
0: array $input,
1: $key,
2: $value,
3: bool $flag,
4: bool $expected
*/
return [ return [
'key/value exist' => [ 'key/value exist' => [
0 => self::$array, 0 => self::$array,
@@ -274,6 +289,188 @@ final class CoreLibsCombinedArrayHandlerTest extends TestCase
]; ];
} }
/**
* Undocumented function
*
* @return array
*/
public function arraySearchKeyProvider(): array
{
/*
0: search in array
1: search keys
2: flat flag
3: prefix flag
4: expected array
*/
return [
// single
'find single, standard' => [
0 => self::$array,
1 => ['single'],
2 => null,
3 => null,
4 => [
0 => [
'value' => 'single',
'path' => ['single'],
],
],
],
'find single, prefix' => [
0 => self::$array,
1 => ['single'],
2 => null,
3 => true,
4 => [
'single' => [
0 => [
'value' => 'single',
'path' => ['single'],
],
],
],
],
'find single, flat' => [
0 => self::$array,
1 => ['single'],
2 => true,
3 => null,
4 => [
'single',
],
],
'find single, flat, prefix' => [
0 => self::$array,
1 => ['single'],
2 => true,
3 => true,
4 => [
'single' => [
'single',
],
],
],
// not found
'not found, standard' => [
0 => self::$array,
1 => ['NOT FOUND'],
2 => null,
3 => null,
4 => [],
],
'not found, standard, prefix' => [
0 => self::$array,
1 => ['NOT FOUND'],
2 => null,
3 => true,
4 => [
'NOT FOUND' => [],
],
],
'not found, flat' => [
0 => self::$array,
1 => ['NOT FOUND'],
2 => true,
3 => null,
4 => [],
],
'not found, flat, prefix' => [
0 => self::$array,
1 => ['NOT FOUND'],
2 => true,
3 => true,
4 => [
'NOT FOUND' => [],
],
],
// multi
'multiple found, standard' => [
0 => self::$array,
1 => ['same'],
2 => null,
3 => null,
4 => [
[
'value' => 'same',
'path' => ['a', 'same', ],
],
[
'value' => 'same',
'path' => ['same', ],
],
[
'value' => 'same',
'path' => ['deep', 'sub', 'same', ],
],
]
],
'multiple found, flat' => [
0 => self::$array,
1 => ['same'],
2 => true,
3 => null,
4 => ['same', 'same', 'same', ],
],
// search with multiple
'search multiple, standard' => [
0 => self::$array,
1 => ['single', 'nested'],
2 => null,
3 => null,
4 => [
[
'value' => 'single',
'path' => ['single'],
],
[
'value' => 'bar',
'path' => ['deep', 'sub', 'nested', ],
],
],
],
'search multiple, prefix' => [
0 => self::$array,
1 => ['single', 'nested'],
2 => null,
3 => true,
4 => [
'single' => [
[
'value' => 'single',
'path' => ['single'],
],
],
'nested' => [
[
'value' => 'bar',
'path' => ['deep', 'sub', 'nested', ],
],
],
],
],
'search multiple, flat' => [
0 => self::$array,
1 => ['single', 'nested'],
2 => true,
3 => null,
4 => [
'single', 'bar',
],
],
'search multiple, flat, prefix' => [
0 => self::$array,
1 => ['single', 'nested'],
2 => true,
3 => true,
4 => [
'single' => ['single', ],
'nested' => ['bar', ],
],
],
];
}
/** /**
* provides array listing for the merge test * provides array listing for the merge test
* *
@@ -321,17 +518,20 @@ final class CoreLibsCombinedArrayHandlerTest extends TestCase
return [ return [
// error <2 arguments // error <2 arguments
'too view arguments' => [ 'too view arguments' => [
'ArgumentCountError',
'arrayMergeRecursive needs two or more array arguments', 'arrayMergeRecursive needs two or more array arguments',
[1] [1]
], ],
// error <2 arrays // error <2 arrays
'only one array' => [ 'only one array' => [
'ArgumentCountError',
'arrayMergeRecursive needs two or more array arguments', 'arrayMergeRecursive needs two or more array arguments',
[1], [1],
true, true,
], ],
// error element is not array // error element is not array
'non array between array' => [ 'non array between array' => [
'TypeError',
'arrayMergeRecursive encountered a non array argument', 'arrayMergeRecursive encountered a non array argument',
[1], [1],
'string', 'string',
@@ -665,7 +865,7 @@ final class CoreLibsCombinedArrayHandlerTest extends TestCase
* *
* @param array $input * @param array $input
* @param string|int $key * @param string|int $key
* @param string|int $value * @param string|int|bool $value
* @param bool $expected * @param bool $expected
* @return void * @return void
*/ */
@@ -677,6 +877,44 @@ final class CoreLibsCombinedArrayHandlerTest extends TestCase
); );
} }
/**
* Undocumented function
*
* @covers::arraySearchKey
* @dataProvider arraySearchKeyProvider
* @testdox arraySearchKey Search array with keys and flat: $flat, prefix: $prefix [$_dataName]
*
* @param array $input
* @param array $needles
* @param bool|null $flat
* @param bool|null $prefix
* @param array $expected
* @return void
*/
public function testArraySearchKey(
array $input,
array $needles,
?bool $flat,
?bool $prefix,
array $expected
): void {
if ($flat === null && $prefix === null) {
$result = \CoreLibs\Combined\ArrayHandler::arraySearchKey($input, $needles);
} elseif ($flat === null) {
$result = \CoreLibs\Combined\ArrayHandler::arraySearchKey($input, $needles, prefix: $prefix);
} elseif ($prefix === null) {
$result = \CoreLibs\Combined\ArrayHandler::arraySearchKey($input, $needles, flat: $flat);
} else {
$result = \CoreLibs\Combined\ArrayHandler::arraySearchKey($input, $needles, $flat, $prefix);
}
// print "E: " . print_r($expected, true) . "\n";
// print "R: " . print_r($result, true) . "\n";
$this->assertEquals(
$expected,
$result
);
}
/** /**
* Undocumented function * Undocumented function
* *
@@ -712,19 +950,21 @@ final class CoreLibsCombinedArrayHandlerTest extends TestCase
*/ */
public function testArrayMergeRecursiveWarningA(): void public function testArrayMergeRecursiveWarningA(): void
{ {
set_error_handler( // set_error_handler(
static function (int $errno, string $errstr): never { // static function (int $errno, string $errstr): never {
throw new Exception($errstr, $errno); // throw new Exception($errstr, $errno);
}, // },
E_USER_WARNING // E_USER_WARNING
); // );
$arrays = func_get_args(); $arrays = func_get_args();
// first is expected warning // first is expected warning
$exception = array_shift($arrays);
$warning = array_shift($arrays); $warning = array_shift($arrays);
// phpunit 10.0 compatible // phpunit 10.0 compatible
$this->expectExceptionMessage(($warning)); $this->expectException($exception);
$this->expectExceptionMessage($warning);
\CoreLibs\Combined\ArrayHandler::arrayMergeRecursive(...$arrays); \CoreLibs\Combined\ArrayHandler::arrayMergeRecursive(...$arrays);
@@ -858,16 +1098,306 @@ final class CoreLibsCombinedArrayHandlerTest extends TestCase
* @testdox arrayFlatForKey array $input will be $expected [$_dataName] * @testdox arrayFlatForKey array $input will be $expected [$_dataName]
* *
* @param array $input * @param array $input
* @param string $search
* @param array $expected * @param array $expected
* @return void * @return void
*/ */
public function testArrayFlatForKey(array $input, $search, array $expected): void public function testArrayFlatForKey(array $input, string $search, array $expected): void
{ {
$this->assertEquals( $this->assertEquals(
$expected, $expected,
\CoreLibs\Combined\ArrayHandler::arrayFlatForKey($input, $search) \CoreLibs\Combined\ArrayHandler::arrayFlatForKey($input, $search)
); );
} }
/**
* Undocumented function
*
* @return array
*/
public function providerArrayGetNextPrevKey(): array
{
return [
'find, ok' => [
'input' => [
'a' => 'First',
'b' => 'Second',
'c' => 'Third',
],
'b',
'a',
'c'
],
'find, first' => [
'input' => [
'a' => 'First',
'b' => 'Second',
'c' => 'Third',
],
'a',
null,
'b'
],
'find, last' => [
'input' => [
'a' => 'First',
'b' => 'Second',
'c' => 'Third',
],
'c',
'b',
null
],
'find, not found' => [
'input' => [
'a' => 'First',
'b' => 'Second',
'c' => 'Third',
],
'z',
null,
null
],
'int, index' => [
'input' => [
'a',
'b',
'c'
],
1,
0,
2
]
];
}
/**
* Undocumented function
*
* @covers ::arrayGetPrevKey, ::arrayGetNextKey
* @dataProvider providerArrayGetNextPrevKey
* @testdox arrayGetNextPrevKey get next/prev key for $search wtih $expected_prev/$expected_next [$_dataName]
*
* @param array $input
* @param int|string $search
* @param int|string|null $expected_prev
* @param int|string|null $expected_next
* @return void
*/
public function testArrayGetNextPrevKey(
array $input,
int|string $search,
int|string|null $expected_prev,
int|string|null $expected_next
): void {
$this->assertEquals(
$expected_prev,
\CoreLibs\Combined\ArrayHandler::arrayGetPrevKey($input, $search),
'Find prev key in array'
);
$this->assertEquals(
$expected_next,
\CoreLibs\Combined\ArrayHandler::arrayGetNextKey($input, $search),
'Find next key in array'
);
}
public function providerReturnMatchingKeyOnley(): array
{
return [
'limited entries' => [
[
'a' => 'foo',
'b' => 'bar',
'c' => 'foobar'
],
[
'a', 'b'
],
[
'a' => 'foo',
'b' => 'bar',
],
],
'limited entries, with one wrong key' => [
[
'a' => 'foo',
'b' => 'bar',
'c' => 'foobar'
],
[
'a', 'b', 'f'
],
[
'a' => 'foo',
'b' => 'bar',
],
],
'wrong keys only' => [
[
'a' => 'foo',
'b' => 'bar',
'c' => 'foobar'
],
[
'f', 'f'
],
[
],
],
'empty keys' => [
[
'a' => 'foo',
'b' => 'bar',
'c' => 'foobar'
],
[],
[
'a' => 'foo',
'b' => 'bar',
'c' => 'foobar'
],
],
];
}
/**
* Undocumented function
*
* @covers ::arrayReturnMatchingKeyOnly
* @dataProvider providerReturnMatchingKeyOnley
* @testdox arrayReturnMatchingKeyOnly get only selected key entries from array [$_dataName]
*
* @param array $input
* @param array $key_list
* @param array $expected
* @return void
*/
public function testArrayReturnMatchingKeyOnly(
array $input,
array $key_list,
array $expected
): void {
$this->assertEquals(
$expected,
\CoreLibs\Combined\ArrayHandler::arrayReturnMatchingKeyOnly(
$input,
$key_list
)
);
}
/**
* provider for arrayModifyKey
*
* @return array<string,array<mixed>>
*/
public function providerArrayModifyKey(): array
{
return [
'prefix and suffix add' => [
'array' => [
'a' => 'foo',
'b' => 'bar',
'c' => 'foobar',
],
'prefix' => 'Prefix: ',
'suffix' => '.suffix',
'expected' => [
'Prefix: a.suffix' => 'foo',
'Prefix: b.suffix' => 'bar',
'Prefix: c.suffix' => 'foobar',
],
],
'prefix add only' => [
'array' => [
'a' => 'foo',
'b' => 'bar',
'c' => 'foobar',
],
'prefix' => 'Prefix: ',
'suffix' => '',
'expected' => [
'Prefix: a' => 'foo',
'Prefix: b' => 'bar',
'Prefix: c' => 'foobar',
],
],
'suffix add only' => [
'array' => [
'a' => 'foo',
'b' => 'bar',
'c' => 'foobar',
],
'prefix' => '',
'suffix' => '.suffix',
'expected' => [
'a.suffix' => 'foo',
'b.suffix' => 'bar',
'c.suffix' => 'foobar',
],
],
'empty array' => [
'array' => [],
'prefix' => '',
'suffix' => '.suffix',
'expected' => [],
],
'no suffix or prefix' => [
'array' => [
'a' => 'foo',
'b' => 'bar',
'c' => 'foobar',
],
'prefix' => '',
'suffix' => '',
'expected' => [
'a' => 'foo',
'b' => 'bar',
'c' => 'foobar',
],
],
'integer index mixed' => [
'array' => [
'a' => 'foo',
'b' => 'bar',
3 => 'foobar',
],
'prefix' => '',
'suffix' => '.suffix',
'expected' => [
'a.suffix' => 'foo',
'b.suffix' => 'bar',
'3.suffix' => 'foobar',
],
]
];
}
/**
* Undocumented function
*
* @covers ::arrayModifyKey
* @dataProvider providerArrayModifyKey
* @testdox arrayModifyKey check that key is correctly modified with $key_mod_prefix and $key_mod_suffix [$_dataName]
*
* @param array<mixed> $in_array
* @param string $key_mod_prefix
* @param string $key_mod_suffix
* @param array<mixed> $expected
* @return void
*/
public function testArrayModifyKey(
array $in_array,
string $key_mod_prefix,
string $key_mod_suffix,
array $expected
): void {
$this->assertEquals(
\CoreLibs\Combined\ArrayHandler::arrayModifyKey($in_array, $key_mod_prefix, $key_mod_suffix),
$expected
);
}
} }
// __END__ // __END__

File diff suppressed because it is too large Load Diff

View File

@@ -40,7 +40,7 @@ final class CoreLibsConvertByteTest extends TestCase
4 => '1.00 KB', 4 => '1.00 KB',
5 => '1.02KiB', 5 => '1.02KiB',
], ],
'invalud string number' => [ 'invalid string number' => [
0 => '1024 MB', 0 => '1024 MB',
1 => '1024 MB', 1 => '1024 MB',
2 => '1024 MB', 2 => '1024 MB',
@@ -253,7 +253,8 @@ final class CoreLibsConvertByteTest extends TestCase
*/ */
public function testHumanReadableByteFormatException(int $flag): void public function testHumanReadableByteFormatException(int $flag): void
{ {
$this->expectException(\Exception::class); $this->expectException(\InvalidArgumentException::class);
$this->expectExceptionCode(1);
\CoreLibs\Convert\Byte::humanReadableByteFormat(12, $flag); \CoreLibs\Convert\Byte::humanReadableByteFormat(12, $flag);
} }
@@ -272,7 +273,8 @@ final class CoreLibsConvertByteTest extends TestCase
*/ */
public function testStringByteFormatException(int $flag): void public function testStringByteFormatException(int $flag): void
{ {
$this->expectException(\Exception::class); $this->expectException(\InvalidArgumentException::class);
$this->expectExceptionCode(1);
\CoreLibs\Convert\Byte::stringByteFormat(12, $flag); \CoreLibs\Convert\Byte::stringByteFormat(12, $flag);
} }
} }

File diff suppressed because it is too large Load Diff

View File

@@ -9,7 +9,7 @@ use PHPUnit\Framework\TestCase;
/** /**
* Test class for Convert\Colors * Test class for Convert\Colors
* @coversDefaultClass \CoreLibs\Convert\Colors * @coversDefaultClass \CoreLibs\Convert\Colors
* @testdox \CoreLibs\Convert\Colors method tests * @testdox \CoreLibs\Convert\Colors legacy method tests
*/ */
final class CoreLibsConvertColorsTest extends TestCase final class CoreLibsConvertColorsTest extends TestCase
{ {
@@ -21,7 +21,7 @@ final class CoreLibsConvertColorsTest extends TestCase
* *
* @return array * @return array
*/ */
public function rgb2hexColorProvider(): array public function providerRgb2hexColor(): array
{ {
return [ return [
'color' => [ 'color' => [
@@ -59,6 +59,27 @@ final class CoreLibsConvertColorsTest extends TestCase
3 => false, 3 => false,
4 => false 4 => false
], ],
'invalid color red ' => [
0 => -12,
1 => 12,
2 => 12,
3 => false,
4 => false
],
'invalid color green ' => [
0 => 12,
1 => -12,
2 => 12,
3 => false,
4 => false
],
'invalid color blue ' => [
0 => 12,
1 => 12,
2 => -12,
3 => false,
4 => false
],
]; ];
} }
@@ -67,7 +88,7 @@ final class CoreLibsConvertColorsTest extends TestCase
* *
* @return array * @return array
*/ */
public function hex2rgbColorProvider(): array public function providerHex2rgbColor(): array
{ {
return [ return [
'color' => [ 'color' => [
@@ -150,10 +171,40 @@ final class CoreLibsConvertColorsTest extends TestCase
'valid' => true, 'valid' => true,
], ],
// invalid values // invalid values
'invalid color' => [ 'invalid color r/h/h low' => [
'rgb' => [-12, 300, 12], 'rgb' => [-1, 12, 12],
'hsb' => [-12, 300, 12], 'hsb' => [-1, 50, 50],
'hsl' => [-12, 300, 12], 'hsl' => [-1, 50, 50],
'valid' => false,
],
'invalid color r/h/h high' => [
'rgb' => [256, 12, 12],
'hsb' => [361, 50, 50],
'hsl' => [361, 50, 50],
'valid' => false,
],
'invalid color g/s/s low' => [
'rgb' => [12, -1, 12],
'hsb' => [1, -1, 50],
'hsl' => [1, -1, 50],
'valid' => false,
],
'invalid color g/s/s high' => [
'rgb' => [12, 256, 12],
'hsb' => [1, 101, 50],
'hsl' => [1, 101, 50],
'valid' => false,
],
'invalid color b/b/l low' => [
'rgb' => [12, 12, -1],
'hsb' => [1, 50, -1],
'hsl' => [1, 50, -1],
'valid' => false,
],
'invalid color b/b/l high' => [
'rgb' => [12, 12, 256],
'hsb' => [1, 50, 101],
'hsl' => [1, 50, 101],
'valid' => false, 'valid' => false,
], ],
]; ];
@@ -164,7 +215,7 @@ final class CoreLibsConvertColorsTest extends TestCase
* *
* @return array * @return array
*/ */
public function rgb2hsbColorProvider(): array public function providerRgb2hsbColor(): array
{ {
$list = []; $list = [];
foreach ($this->rgb2hslAndhsbList() as $name => $values) { foreach ($this->rgb2hslAndhsbList() as $name => $values) {
@@ -183,7 +234,7 @@ final class CoreLibsConvertColorsTest extends TestCase
* *
* @return array * @return array
*/ */
public function hsb2rgbColorProvider(): array public function providerHsb2rgbColor(): array
{ {
$list = []; $list = [];
foreach ($this->rgb2hslAndhsbList() as $name => $values) { foreach ($this->rgb2hslAndhsbList() as $name => $values) {
@@ -202,7 +253,7 @@ final class CoreLibsConvertColorsTest extends TestCase
* *
* @return array * @return array
*/ */
public function rgb2hslColorProvider(): array public function providerRgb2hslColor(): array
{ {
$list = []; $list = [];
foreach ($this->rgb2hslAndhsbList() as $name => $values) { foreach ($this->rgb2hslAndhsbList() as $name => $values) {
@@ -221,7 +272,7 @@ final class CoreLibsConvertColorsTest extends TestCase
* *
* @return array * @return array
*/ */
public function hsl2rgbColorProvider(): array public function providerHsl2rgbColor(): array
{ {
$list = []; $list = [];
foreach ($this->rgb2hslAndhsbList() as $name => $values) { foreach ($this->rgb2hslAndhsbList() as $name => $values) {
@@ -240,17 +291,28 @@ final class CoreLibsConvertColorsTest extends TestCase
* TODO: add cross convert check * TODO: add cross convert check
* *
* @covers ::rgb2hex * @covers ::rgb2hex
* @dataProvider rgb2hexColorProvider * @dataProvider providerRgb2hexColor
* @testdox rgb2hex $input_r,$input_g,$input_b will be $expected [$_dataName] * @testdox rgb2hex $input_r,$input_g,$input_b will be $expected [$_dataName]
* *
* @param int $input_r * @param int $input_r
* @param int $input_g * @param int $input_g
* @param int $input_b * @param int $input_b
* @param string|bool $expected_hash
* @param string|bool $expected * @param string|bool $expected
* @return void * @return void
*/ */
public function testRgb2hex(int $input_r, int $input_g, int $input_b, $expected_hash, $expected) public function testRgb2hex(
{ int $input_r,
int $input_g,
int $input_b,
string|bool $expected_hash,
string|bool $expected
) {
// if expected hash is or expected is false, we need to check for
// LengthException
if ($expected_hash === false || $expected === false) {
$this->expectException(\LengthException::class);
}
// with # // with #
$this->assertEquals( $this->assertEquals(
$expected_hash, $expected_hash,
@@ -280,7 +342,7 @@ final class CoreLibsConvertColorsTest extends TestCase
* Undocumented function * Undocumented function
* *
* @covers ::hex2rgb * @covers ::hex2rgb
* @dataProvider hex2rgbColorProvider * @dataProvider providerHex2rgbColor
* @testdox hex2rgb $input will be $expected, $expected_str str[,], $expected_str_sep str[$separator] [$_dataName] * @testdox hex2rgb $input will be $expected, $expected_str str[,], $expected_str_sep str[$separator] [$_dataName]
* *
* @param string $input * @param string $input
@@ -292,11 +354,19 @@ final class CoreLibsConvertColorsTest extends TestCase
*/ */
public function testHex2rgb( public function testHex2rgb(
string $input, string $input,
$expected, array|bool $expected,
$expected_str, string|bool $expected_str,
string $separator, string $separator,
$expected_str_sep string|bool $expected_str_sep
): void { ): void {
if ($expected === false || $expected_str === false || $expected_str_sep === false) {
$hex_string = preg_replace("/[^0-9A-Fa-f]/", '', $input);
if (!is_string($hex_string)) {
$this->expectException(\InvalidArgumentException::class);
} else {
$this->expectException(\UnexpectedValueException::class);
}
}
$this->assertEquals( $this->assertEquals(
$expected, $expected,
\CoreLibs\Convert\Colors::hex2rgb($input) \CoreLibs\Convert\Colors::hex2rgb($input)
@@ -315,7 +385,7 @@ final class CoreLibsConvertColorsTest extends TestCase
* Undocumented function * Undocumented function
* *
* @covers ::rgb2hsb * @covers ::rgb2hsb
* @dataProvider rgb2hsbColorProvider * @dataProvider providerRgb2hsbColor
* @testdox rgb2hsb $input_r,$input_g,$input_b will be $expected [$_dataName] * @testdox rgb2hsb $input_r,$input_g,$input_b will be $expected [$_dataName]
* *
* @param integer $input_r * @param integer $input_r
@@ -324,8 +394,11 @@ final class CoreLibsConvertColorsTest extends TestCase
* @param array|bool $expected * @param array|bool $expected
* @return void * @return void
*/ */
public function testRgb2hsb(int $input_r, int $input_g, int $input_b, $expected): void public function testRgb2hsb(int $input_r, int $input_g, int $input_b, array|bool $expected): void
{ {
if ($expected === false) {
$this->expectException(\LengthException::class);
}
$this->assertEquals( $this->assertEquals(
$expected, $expected,
\CoreLibs\Convert\Colors::rgb2hsb($input_r, $input_g, $input_b) \CoreLibs\Convert\Colors::rgb2hsb($input_r, $input_g, $input_b)
@@ -336,7 +409,7 @@ final class CoreLibsConvertColorsTest extends TestCase
* Undocumented function * Undocumented function
* *
* @covers ::hsb2rgb * @covers ::hsb2rgb
* @dataProvider hsb2rgbColorProvider * @dataProvider providerHsb2rgbColor
* @testdox hsb2rgb $input_h,$input_s,$input_b will be $expected [$_dataName] * @testdox hsb2rgb $input_h,$input_s,$input_b will be $expected [$_dataName]
* *
* @param float $input_h * @param float $input_h
@@ -345,8 +418,12 @@ final class CoreLibsConvertColorsTest extends TestCase
* @param array|bool $expected * @param array|bool $expected
* @return void * @return void
*/ */
public function testHsb2rgb(float $input_h, float $input_s, float $input_b, $expected): void public function testHsb2rgb(float $input_h, float $input_s, float $input_b, array|bool $expected): void
{ {
if ($expected === false) {
$this->expectException(\LengthException::class);
$expected = [];
}
$this->assertEquals( $this->assertEquals(
$expected, $expected,
\CoreLibs\Convert\Colors::hsb2rgb($input_h, $input_s, $input_b) \CoreLibs\Convert\Colors::hsb2rgb($input_h, $input_s, $input_b)
@@ -357,7 +434,7 @@ final class CoreLibsConvertColorsTest extends TestCase
* Undocumented function * Undocumented function
* *
* @covers ::rgb2hsl * @covers ::rgb2hsl
* @dataProvider rgb2hslColorProvider * @dataProvider providerRgb2hslColor
* @testdox rgb2hsl $input_r,$input_g,$input_b will be $expected [$_dataName] * @testdox rgb2hsl $input_r,$input_g,$input_b will be $expected [$_dataName]
* *
* @param integer $input_r * @param integer $input_r
@@ -366,8 +443,11 @@ final class CoreLibsConvertColorsTest extends TestCase
* @param array|bool $expected * @param array|bool $expected
* @return void * @return void
*/ */
public function testRgb2hsl(int $input_r, int $input_g, int $input_b, $expected): void public function testRgb2hsl(int $input_r, int $input_g, int $input_b, array|bool $expected): void
{ {
if ($expected === false) {
$this->expectException(\LengthException::class);
}
$this->assertEquals( $this->assertEquals(
$expected, $expected,
\CoreLibs\Convert\Colors::rgb2hsl($input_r, $input_g, $input_b) \CoreLibs\Convert\Colors::rgb2hsl($input_r, $input_g, $input_b)
@@ -378,7 +458,7 @@ final class CoreLibsConvertColorsTest extends TestCase
* Undocumented function * Undocumented function
* *
* @covers ::hsl2rgb * @covers ::hsl2rgb
* @dataProvider hsl2rgbColorProvider * @dataProvider providerHsl2rgbColor
* @testdox hsl2rgb $input_h,$input_s,$input_l will be $expected [$_dataName] * @testdox hsl2rgb $input_h,$input_s,$input_l will be $expected [$_dataName]
* *
* @param integer|float $input_h * @param integer|float $input_h
@@ -387,8 +467,11 @@ final class CoreLibsConvertColorsTest extends TestCase
* @param array|bool $expected * @param array|bool $expected
* @return void * @return void
*/ */
public function testHsl2rgb($input_h, float $input_s, float $input_l, $expected): void public function testHsl2rgb(int|float $input_h, float $input_s, float $input_l, array|bool $expected): void
{ {
if ($expected === false) {
$this->expectException(\LengthException::class);
}
$this->assertEquals( $this->assertEquals(
$expected, $expected,
\CoreLibs\Convert\Colors::hsl2rgb($input_h, $input_s, $input_l) \CoreLibs\Convert\Colors::hsl2rgb($input_h, $input_s, $input_l)
@@ -406,11 +489,11 @@ final class CoreLibsConvertColorsTest extends TestCase
*/ */
public function testHslHsb360hue(): void public function testHslHsb360hue(): void
{ {
$this->assertNotFalse( $this->assertIsArray(
\CoreLibs\Convert\Colors::hsl2rgb(360.0, 90.5, 41.2), \CoreLibs\Convert\Colors::hsl2rgb(360.0, 90.5, 41.2),
'HSL to RGB with 360 hue' 'HSL to RGB with 360 hue'
); );
$this->assertNotFalse( $this->assertIsArray(
\CoreLibs\Convert\Colors::hsb2rgb(360, 95, 78.0), \CoreLibs\Convert\Colors::hsb2rgb(360, 95, 78.0),
'HSB to RGB with 360 hue' 'HSB to RGB with 360 hue'
); );

View File

@@ -16,7 +16,7 @@ final class CoreLibsConvertJsonTest extends TestCase
/** /**
* test list for json convert tests * test list for json convert tests
* *
* @return array * @return array<mixed>
*/ */
public function jsonProvider(): array public function jsonProvider(): array
{ {
@@ -54,10 +54,36 @@ final class CoreLibsConvertJsonTest extends TestCase
]; ];
} }
/**
* Undocumented function
*
* @return array<mixed>
*/
public function jsonArrayProvider(): array
{
return [
'valid json' => [
[
'm' => 2,
'f' => 'sub_2'
],
'{"m":2,"f":"sub_2"}',
],
'empty json array' => [
[],
'[]'
],
'empty json hash' => [
['' => ''],
'{"":""}'
]
];
}
/** /**
* json error list * json error list
* *
* @return array JSON error list * @return array<mixed> JSON error list
*/ */
public function jsonErrorProvider(): array public function jsonErrorProvider(): array
{ {
@@ -127,7 +153,7 @@ final class CoreLibsConvertJsonTest extends TestCase
* *
* @param string|null $input * @param string|null $input
* @param bool $flag * @param bool $flag
* @param array $expected * @param array<mixed> $expected
* @return void * @return void
*/ */
public function testJsonConvertToArray(?string $input, bool $flag, array $expected): void public function testJsonConvertToArray(?string $input, bool $flag, array $expected): void
@@ -146,7 +172,8 @@ final class CoreLibsConvertJsonTest extends TestCase
* @testdox jsonGetLastError $input will be $expected_i/$expected_s [$_dataName] * @testdox jsonGetLastError $input will be $expected_i/$expected_s [$_dataName]
* *
* @param string|null $input * @param string|null $input
* @param string $expected * @param int $expected_i
* @param string $expected_s
* @return void * @return void
*/ */
public function testJsonGetLastError(?string $input, int $expected_i, string $expected_s): void public function testJsonGetLastError(?string $input, int $expected_i, string $expected_s): void
@@ -161,6 +188,25 @@ final class CoreLibsConvertJsonTest extends TestCase
\CoreLibs\Convert\Json::jsonGetLastError(true) \CoreLibs\Convert\Json::jsonGetLastError(true)
); );
} }
/**
* Undocumented function
*
* @covers ::jsonConvertArrayTo
* @dataProvider jsonArrayProvider
* @testdox jsonConvertArrayTo $input (Override: $flag) will be $expected [$_dataName]
*
* @param array<mixed> $input
* @param string $expected
* @return void
*/
public function testJsonConvertArrayto(array $input, string $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Convert\Json::jsonConvertArrayTo($input)
);
}
} }
// __END__ // __END__

View File

@@ -0,0 +1,500 @@
<?php
declare(strict_types=1);
namespace tests;
use PHPUnit\Framework\TestCase;
/**
* Undocumented class
* @coversDefaultClass \CoreLibs\Convert\Math
* @testdox \CoreLibs\Convert\Math method tests
*/
final class CoreLibsConvertMathTest extends TestCase
{
/**
* Undocumented function
*
* @return array<mixed>
*/
public function providerFceil(): array
{
return [
'5.5 must be 6' => [5.5, 6],
'5.1234567890 with 5 must be 6' => [5.1234567890, 6],
'6 must be 6' => [6, 6]
];
}
/**
* Undocumented function
*
* @covers ::fceil
* @dataProvider providerFceil
* @testdox fceil: Input $input must be $expected
*
* @param float $input
* @param int $expected
* @return void
*/
public function testMathFceilValue(float $input, int $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Convert\Math::fceil($input)
);
}
/**
* Undocumented function
*
* @return array<mixed>
*/
public function providerFloor(): array
{
return [
'5123456 with -3 must be 5123000' => [5123456, -3, 5123000],
'5123456 with -10 must be 5000000' => [5123456, -10, 5000000]
];
}
/**
* Undocumented function
*
* @covers ::floorp
* @dataProvider providerFloor
* @testdox floor: Input $input with cutoff $cutoff must be $expected
*
* @param int $input
* @param int $cutoff
* @param int $expected
* @return void
*/
public function testMathFloorValue(int $input, int $cutoff, int $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Convert\Math::floorp($input, $cutoff)
);
}
/**
* Undocumented function
*
* @return array<mixed>
*/
public function providerInitNumeric(): array
{
return [
'5 must be 5' => [5, 5, 'int'],
'5.123 must be 5.123' => [5.123, 5.123, 'float'],
"'5' must be 5" => ['5', 5, 'string'],
"'5.123' must be 5.123" => ['5.123', 5.123, 'string'],
];
}
/**
* Undocumented function
*
* @covers ::initNumeric
* @dataProvider providerInitNumeric
* @testdox initNumeric: Input $info $input must match $expected [$_dataName]
*
* @param int|float|string $input
* @param float $expected
* @param string $info
* @return void
*/
public function testMathInitNumericValue($input, float $expected, string $info): void
{
$this->assertEquals(
$expected,
\CoreLibs\Convert\Math::initNumeric($input)
);
}
/**
* Undocumented function
*
* @return array
*/
public function providerCbrt(): array
{
return [
'cube root of 2' => [2, 1.25992, 5],
'cube root of 3' => [3, 1.44225, 5],
'cube root of -1' => [-1, 'NAN', 0],
];
}
/**
* Undocumented function
*
* @covers ::cbrt
* @dataProvider providerCbrt
* @testdox initNumeric: Input $input must match $expected [$_dataName]
*
* @param float|int $number
* @param float $expected
* @param int $round_to
* @return void
*/
public function testCbrt(float|int $number, float|string $expected, int $round_to): void
{
$this->assertEquals(
$expected,
round(\CoreLibs\Convert\Math::cbrt($number), $round_to)
);
}
/**
* Undocumented function
*
* @return array
*/
public function providerMultiplyMatrices(): array
{
return [
'[3] x [3] => [3x1]' => [
[1, 2, 3],
[1, 2, 3],
[14]
],
'[3] x [3x1]' => [
[1, 2, 3],
[[1], [2], [3]],
[14]
],
'[3] x [3x1]' => [
[1, 2, 3],
[[1], [2], [3]],
[14]
],
'[1x3L] x [3x1]' => [
[[1, 2, 3]],
[[1], [2], [3]],
[14]
],
'[1x3] x [3x1]' => [
[[1], [2], [3]],
[[1], [2], [3]],
[1, 2, 3]
],
'[2x3] x [3] => [3x1]' => [
[
[1, 2, 3],
[1, 2, 3]
],
[1, 2, 3],
[
14,
14
]
],
'[2x3] x [3x1]' => [
[
[1, 2, 3],
[1, 2, 3]
],
[[1], [2], [3]],
[
14,
14
]
],
'[2x3] x [2x3] => [3x3]' => [
[
[1, 2, 3],
[1, 2, 3],
],
[
[1, 2, 3],
[1, 2, 3],
],
[
[3, 6, 9],
[3, 6, 9]
]
],
'[2x3] x [3x3]' => [
[
[1, 2, 3],
[1, 2, 3],
],
[
[1, 2, 3],
[1, 2, 3],
[0, 0, 0],
],
[
[3, 6, 9],
[3, 6, 9]
]
],
'[2x3] x [3x2]' => [
'a' => [
[1, 2, 3],
[1, 2, 3],
],
'b' => [
[1, 1],
[2, 2],
[3, 3],
],
'prod' => [
[14, 14],
[14, 14],
]
],
'[3x3] x [3] => [1x3]' => [
[
[1, 2, 3],
[1, 2, 3],
[1, 2, 3],
],
[1, 2, 3],
[
14,
14,
14
]
],
'[3x3] x [2x3] => [3x3]' => [
[
[1, 2, 3],
[1, 2, 3],
[1, 2, 3],
],
[
[1, 2, 3],
[1, 2, 3],
],
[
[3, 6, 9],
[3, 6, 9],
[3, 6, 9],
]
],
'[3x3] x [3x3]' => [
[
[1, 2, 3],
[1, 2, 3],
[1, 2, 3],
],
[
[1, 2, 3],
[1, 2, 3],
// [0, 0, 0],
],
[
[3, 6, 9],
[3, 6, 9],
[3, 6, 9],
]
],
'[3] x [3x3]' => [
[1, 2, 3],
[
[1, 2, 3],
[1, 2, 3],
[1, 2, 3],
],
[
[6, 12, 18],
]
],
'[2x3] x [3x3]' => [
[
[1, 2, 3],
[1, 2, 3],
],
[
[1, 2, 3],
[1, 2, 3],
[1, 2, 3],
],
[
[6, 12, 18],
[6, 12, 18],
]
],
'inblanaced [2x2,3] x [3x2]' => [
'a' => [
[1, 2, 3],
[4, 5]
],
'b' => [
[6, 7],
[8, 9],
[10, 11]
],
'result' => [
[52, 58],
[64, 73],
]
],
'inblanaced [2x3] x [3x1,2]' => [
'a' => [
[1, 2, 3],
[4, 5, 7]
],
'b' => [
[7, 8],
[9, 10],
[11]
],
'result' => [
[58, 28],
[150, 82],
]
],
];
}
/**
* Undocumented function
*
* @covers ::multiplyMatrices
* @dataProvider providerMultiplyMatrices
* @testdox initNumeric: Input $input_a x $input_b must match $expected [$_dataName]
*
* @param array $input_a
* @param array $input_b
* @param array $expected
* @return void
*/
public function testMultiplyMatrices(array $input_a, array $input_b, array $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Convert\Math::multiplyMatrices($input_a, $input_b)
);
}
/**
* Undocumented function
*
* @return array
*/
public function providerEqualWithEpsilon(): array
{
return [
'equal' => [
'a' => 0.000000000000000222,
'b' => 0.000000000000000222,
'epsilon' => PHP_FLOAT_EPSILON,
'equal' => true,
],
'almost equal' => [
'a' => 0.000000000000000222,
'b' => 0.000000000000000232,
'epsilon' => PHP_FLOAT_EPSILON,
'equal' => true,
],
'not equal' => [
'a' => 0.000000000000000222,
'b' => 0.000000000000004222,
'epsilon' => PHP_FLOAT_EPSILON,
'equal' => false,
],
'equal, different epsilon' => [
'a' => 0.000000000000000222,
'b' => 0.000000000000004222,
'epsilon' => 0.0001,
'equal' => true,
],
'not equal, different epsilon' => [
'a' => 0.0001,
'b' => 0.0002,
'epsilon' => 0.0001,
'equal' => false,
]
];
}
/**
* Undocumented function
*
* @covers ::equalWithEpsilon
* @dataProvider providerEqualWithEpsilon
* @testdox equalWithEpsilon with $a and $b and Epsilon: $epsilon must be equal: $equal [$_dataName]
*
* @return void
*/
public function testEqualWithEpsilon(float $a, float $b, float $epsilon, bool $equal): void
{
$this->assertEquals(
$equal,
\CoreLibs\Convert\Math::equalWithEpsilon($a, $b, $epsilon)
);
}
/**
* Undocumented function
*
* @return array
*/
public function providerCompareWithEpsilon(): array
{
return [
'smaller, true' => [
'value' => 0.0001,
'compare' => '<',
'limit' => 0.0002,
'epsilon' => 0.00001,
'match' => true,
],
'smaller, false' => [
'value' => 0.0001,
'compare' => '<',
'limit' => 0.0001,
'epsilon' => 0.00001,
'match' => false,
],
'bigger, true' => [
'value' => 0.0002,
'compare' => '>',
'limit' => 0.0001,
'epsilon' => 0.00001,
'match' => true,
],
'bigger, false' => [
'value' => 0.0001,
'compare' => '>',
'limit' => 0.0001,
'epsilon' => 0.00001,
'match' => false,
],
];
}
/**
* Undocumented function
*
* @covers ::compareWithEpsilon
* @dataProvider providerCompareWithEpsilon
* @testdox compareWithEpsilon $value $compare $limit with $epsilon must match: $match [$_dataName]
*
* @param float $value
* @param string $compare
* @param float $limit
* @param float $epslion
* @param bool $match
* @return void
*/
public function testCompareWithEpsilon(
float $value,
string $compare,
float $limit,
float $epsilon,
bool $match
): void {
$this->assertEquals(
$match,
\CoreLibs\Convert\Math::compareWithEpsilon($value, $compare, $limit, $epsilon)
);
}
}
// __END__

View File

@@ -33,15 +33,14 @@ final class CoreLibsConvertMimeEncodeTest extends TestCase
'The quick brown fox jumps over the lazy sheep that sleeps in the ravine ' 'The quick brown fox jumps over the lazy sheep that sleeps in the ravine '
. 'and has no idea what is going on here', . 'and has no idea what is going on here',
'UTF-8', 'UTF-8',
'The quick brown fox jumps over the lazy sheep that sleeps in the ravine ' "The quick brown fox jumps over the lazy sheep that sleeps in the ravine and\r\n"
. 'and has no idea what is going on here' . ' has no idea what is going on here'
], ],
'standard with special chars UTF-8' => [ 'standard with special chars UTF-8' => [
'This is ümläßtと漢字もカタカナ!^$%&', 'This is ümläßtと漢字もカタカナ!^$%&',
'UTF-8', 'UTF-8',
'This is =?UTF-8?B?w7xtbMOkw59044Go5ryi5a2X44KC44Kr44K/44Kr44OK77yBIV4k?=' "This is =?UTF-8?B?w7xtbMOkw59044Go5ryi5a2X44KC44Kr44K/44Kr44OK77yBIV4k?=\r\n"
. "\r\n" . ' =?UTF-8?B?JSY=?='
. ' =?UTF-8?B?JQ==?=&'
], ],
'35 chars and space at the end UTF-8' => [ '35 chars and space at the end UTF-8' => [
'12345678901234567890123456789012345 ' '12345678901234567890123456789012345 '
@@ -62,9 +61,8 @@ final class CoreLibsConvertMimeEncodeTest extends TestCase
. 'is there a space?', . 'is there a space?',
'UTF-8', 'UTF-8',
"=?UTF-8?B?44Kr44K/44Kr44OK44Kr44K/44Kr44OK44GL44Gq44Kr44K/44Kr44OK44Kr?=\r\n" "=?UTF-8?B?44Kr44K/44Kr44OK44Kr44K/44Kr44OK44GL44Gq44Kr44K/44Kr44OK44Kr?=\r\n"
. " =?UTF-8?B?44K/44Kr44OK?=\r\n" . " =?UTF-8?B?44K/44Kr44OK44GL44Gq44Kr44K/44Kr44OK44Kr44K/44Kr44OK44GL44Gq?=\r\n"
. " =?UTF-8?B?44GL44Gq44Kr44K/44Kr44OK44Kr44K/44Kr44OK44GL44Gq44Kr44K/44Kr?=\r\n" . " =?UTF-8?B?44Kr44K/44Kr44OK44Kr44K/IGlzIHRoZXJlIGEgc3BhY2U/?="
. " =?UTF-8?B?44OK44Kr44K/?= is there a =?UTF-8?B?c3BhY2U/?="
] ]
]; ];
} }
@@ -85,16 +83,28 @@ final class CoreLibsConvertMimeEncodeTest extends TestCase
// print "MIME: -" . $encoded . "-\n"; // print "MIME: -" . $encoded . "-\n";
$this->assertEquals( $this->assertEquals(
$expected, $expected,
$encoded $encoded,
"__mbMimeEncode"
); );
$decoded = mb_decode_mimeheader($encoded); $decoded = mb_decode_mimeheader($encoded);
// print "INPUT : " . $input . "\n"; // print "ENCODED: " . $encoded . "\n";
// print "DECODED: " . $decoded . "\n"; // print "INPUT : " . $input . " | " . mb_strlen($input) . "\n";
// print "DECODED: " . $decoded . " | " . mb_strlen($decoded) . "\n";
// $test_enc = mb_encode_mimeheader($input, $encoding);
// $test_dec = mb_decode_mimeheader($test_enc);
// print "TEST ENC: " . $test_enc . "\n";
// back compare decoded // back compare decoded
$this->assertEquals( $this->assertEquals(
$input, $input,
$decoded $decoded,
"mb_decode_mimeheader"
); );
// $this->assertEquals(
// $input,
// $test_dec,
// 'mb_encode_to_decode'
// );
} }
} }

View File

@@ -43,12 +43,17 @@ final class CoreLibsConvertSetVarTypeNullTest extends TestCase
'int, no override' => [ 'int, no override' => [
1, 1,
null, null,
null '1'
], ],
'int, override set' => [ 'int, override set' => [
1, 1,
'not int', 'not int',
'not int' '1'
],
'array, override set' => [
[1, 2],
null,
null
] ]
]; ];
} }
@@ -201,7 +206,7 @@ final class CoreLibsConvertSetVarTypeNullTest extends TestCase
'float' => [ 'float' => [
1.5, 1.5,
null, null,
null 1
] ]
]; ];
} }
@@ -349,7 +354,7 @@ final class CoreLibsConvertSetVarTypeNullTest extends TestCase
'int' => [ 'int' => [
1, 1,
null, null,
null 1.0
] ]
]; ];
} }

View File

@@ -43,11 +43,16 @@ final class CoreLibsConvertSetVarTypeTest extends TestCase
'int, no override' => [ 'int, no override' => [
1, 1,
null, null,
'' '1'
], ],
'int, override set' => [ 'int, override set' => [
1, 1,
'not int', 'not int',
'1'
],
'array, override set' => [
[1, 2],
'not int',
'not int' 'not int'
] ]
]; ];
@@ -189,7 +194,7 @@ final class CoreLibsConvertSetVarTypeTest extends TestCase
'float' => [ 'float' => [
1.5, 1.5,
null, null,
0 1
] ]
]; ];
} }
@@ -330,7 +335,7 @@ final class CoreLibsConvertSetVarTypeTest extends TestCase
'int' => [ 'int' => [
1, 1,
null, null,
0.0 1.0
] ]
]; ];
} }
@@ -341,7 +346,7 @@ final class CoreLibsConvertSetVarTypeTest extends TestCase
* @dataProvider varSetTypeFloatProvider * @dataProvider varSetTypeFloatProvider
* @testdox setFloat $input with override $default will be $expected [$_dataName] * @testdox setFloat $input with override $default will be $expected [$_dataName]
* *
* @param mixed $input * @param mixed $input
* @param float|null $default * @param float|null $default
* @param float $expected * @param float $expected
* @return void * @return void

View File

@@ -13,6 +13,8 @@ use PHPUnit\Framework\TestCase;
*/ */
final class CoreLibsConvertStringsTest extends TestCase final class CoreLibsConvertStringsTest extends TestCase
{ {
private const DATA_FOLDER = __DIR__ . DIRECTORY_SEPARATOR . 'data' . DIRECTORY_SEPARATOR;
/** /**
* Undocumented function * Undocumented function
* *
@@ -256,6 +258,126 @@ final class CoreLibsConvertStringsTest extends TestCase
$output $output
); );
} }
/**
* provider for testStripMultiplePathSlashes
*
* @return array<mixed>
*/
public function stripMultiplePathSlashesProvider(): array
{
return [
'no slahses' => [
'input' => 'string_abc',
'expected' => 'string_abc',
],
'one slash' => [
'input' => 'some/foo',
'expected' => 'some/foo',
],
'two slashes' => [
'input' => 'some//foo',
'expected' => 'some/foo',
],
'three slashes' => [
'input' => 'some///foo',
'expected' => 'some/foo',
],
'slashes in front' => [
'input' => '/foo',
'expected' => '/foo',
],
'two slashes in front' => [
'input' => '//foo',
'expected' => '/foo',
],
'thee slashes in front' => [
'input' => '///foo',
'expected' => '/foo',
],
'slashes in back' => [
'input' => 'foo/',
'expected' => 'foo/',
],
'two slashes in back' => [
'input' => 'foo//',
'expected' => 'foo/',
],
'thee slashes in back' => [
'input' => 'foo///',
'expected' => 'foo/',
],
'multiple slashes' => [
'input' => '/foo//bar///string/end_times',
'expected' => '/foo/bar/string/end_times',
]
];
}
/**
* test multiple slashes clean up
*
* @covers ::stripMultiplePathSlashes
* @dataProvider stripMultiplePathSlashesProvider
* @testdox stripMultiplePathSlashes $input will be $expected [$_dataName]
*
* @param string $input
* @param string $expected
* @return void
*/
public function testStripMultiplePathSlashes(string $input, string $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Convert\Strings::stripMultiplePathSlashes($input)
);
}
/**
* Undocumented function
*
* @return array
*/
public function providerStripUTF8BomBytes(): array
{
return [
"utf8-bom" => [
"file" => "UTF8BOM.csv",
"expect" => "Asset Type,Epic,File Name\n",
],
"utf8" => [
"file" => "UTF8.csv",
"expect" => "Asset Type,Epic,File Name\n",
],
];
}
/**
* test utf8 bom remove
*
* @covers ::stripUTF8BomBytes
* @dataProvider providerStripUTF8BomBytes
* @testdox stripUTF8BomBytes $file will be $expected [$_dataName]
*
* @param string $file
* @param string $expected
* @return void
*/
public function testStripUTF8BomBytes(string $file, string $expected): void
{
// load sample file
if (!is_file(self::DATA_FOLDER . $file)) {
$this->markTestSkipped('File: ' . $file . ' could not be opened');
}
$file = file_get_contents(self::DATA_FOLDER . $file);
if ($file === false) {
$this->markTestSkipped('File: ' . $file . ' could not be read');
}
$this->assertEquals(
$expected,
\CoreLibs\Convert\Strings::stripUTF8BomBytes($file)
);
}
} }
// __END__ // __END__

View File

@@ -0,0 +1 @@
Asset Type,Epic,File Name
1 Asset Type Epic File Name

View File

@@ -0,0 +1 @@
Asset Type,Epic,File Name
1 Asset Type Epic File Name

View File

@@ -1,785 +0,0 @@
<?php
declare(strict_types=1);
namespace tests;
use PHPUnit\Framework\TestCase;
/**
* Test class for Combined\DateTime
* @coversDefaultClass \CoreLibs\Combined\DateTime
* @testdox \CoreLibs\Combined\DateTime method tests
*/
final class CoreLibsCombinedDateTimeTest extends TestCase
{
/**
* timestamps
*
* @return array
*/
public function timestampProvider(): array
{
return [
'valid timestamp no microtime' => [
1641515890,
false,
false,
'2022-01-07 09:38:10',
],
'valid timestamp with microtime' => [
1641515890,
true,
false,
'2022-01-07 09:38:10',
],
'valid timestamp with microtime float' => [
1641515890,
true,
true,
'2022-01-07 09:38:10',
],
'valid micro timestamp with microtime' => [
1641515890.123456,
true,
false,
'2022-01-07 09:38:10 1235ms',
],
'valid micro timestamp with microtime float' => [
1641515890.123456,
true,
true,
'2022-01-07 09:38:10.1235',
],
'valid micro timestamp no microtime' => [
1641515890.123456,
false,
false,
'2022-01-07 09:38:10',
],
'invalid timestamp' => [
-123123,
false,
false,
'1969-12-30 22:47:57',
],
];
}
/**
* interval for both directions
*
* @return array
*/
public function intervalProvider(): array
{
return [
'interval no microtime' => [
1641515890,
false,
'18999d 0h 38m 10s',
],
'interval with microtime' => [
1641515890,
true,
'18999d 0h 38m 10s',
],
'micro interval no microtime' => [
1641515890.123456,
false,
'18999d 0h 38m 10s',
],
'micro interval with microtime' => [
1641515890.123456,
true,
'18999d 0h 38m 10s 1235ms',
],
'negative interval no microtime' => [
-1641515890,
false,
'-18999d 0h 38m 10s',
],
// short for mini tests
'microtime only' => [
0.123456,
true,
'0s 1235ms',
],
'seconds only' => [
30.123456,
true,
'30s 1235ms',
],
'minutes only' => [
90.123456,
true,
'1m 30s 1235ms',
],
'hours only' => [
3690.123456,
true,
'1h 1m 30s 1235ms',
],
'days only' => [
90090.123456,
true,
'1d 1h 1m 30s 1235ms',
],
'already set' => [
'1d 1h 1m 30s 1235ms',
true,
'1d 1h 1m 30s 1235ms',
],
'invalid data' => [
'xyz',
true,
'0s',
],
'out of bounds timestamp' => [
999999999999999,
false,
'1s'
]
];
}
/**
* Undocumented function
*
* @return array
*/
public function reverseIntervalProvider(): array
{
return [
'interval no microtime' => [
'18999d 0h 38m 10s',
1641515890,
],
'micro interval with microtime' => [
'18999d 0h 38m 10s 1235ms',
1641515890.1235,
],
'micro interval with microtime' => [
'18999d 0h 38m 10s 1234567890ms',
1641515890.1234567,
],
'negative interval no microtime' => [
'-18999d 0h 38m 10s',
-1641515890,
],
// short for mini tests
'microtime only' => [
'0s 1235ms',
0.1235,
],
'seconds only' => [
'30s 1235ms',
30.1235,
],
'minutes only' => [
'1m 30s 1235ms',
90.1235,
],
'hours only' => [
'1h 1m 30s 1235ms',
3690.1235,
],
'days only' => [
'1d 1h 1m 30s 1235ms',
90090.1235,
],
'already set' => [
1641515890,
1641515890,
],
'invalid data' => [
'xyz',
'xyz',
],
'out of bound data' => [
'99999999999999999999d',
8.64E+24
],
];
}
/**
* Undocumented function
*
* @return array
*/
public function dateProvider(): array
{
return [
'valid date with -' => [
'2021-12-12',
true,
],
'valid date with /' => [
'2021/12/12',
true,
],
'valid date time with -' => [
'2021-12-12 12:12:12',
true,
],
'invalid date' => [
'2021-31-31',
false,
],
'invalid date string' => [
'xyz',
false,
],
'out of bound date' => [
'9999-12-31',
true
]
];
}
/**
* Undocumented function
*
* @return array
*/
public function dateTimeProvider(): array
{
return [
'valid date time with -' => [
'2021-12-12 12:12:12',
true,
],
'valid date time with /' => [
'2021/12/12 12:12:12',
true,
],
'vald date time with hour/min' => [
'2021/12/12 12:12',
true,
],
'valid date missing time' => [
'2021-12-12',
false,
],
'valid date invalid time string' => [
'2021-12-12 ab:cd',
false,
],
'invalid hour +' => [
'2021-12-12 35:12',
false,
],
'invalid hour -' => [
'2021-12-12 -12:12',
false,
],
'invalid minute +' => [
'2021-12-12 23:65:12',
false,
],
'invalid minute -' => [
'2021-12-12 23:-12:12',
false,
],
'invalid seconds +' => [
'2021-12-12 23:12:99',
false,
],
'invalid seconds -' => [
'2021-12-12 23:12:-12',
false,
],
'invalid seconds string' => [
'2021-12-12 23:12:ss',
false,
],
];
}
/**
* Undocumented function
*
* @return array
*/
public function dateCompareProvider(): array
{
return [
'first date smaller' => [
'2020-12-12',
'2021-12-12',
-1,
],
'dates equal' => [
'2020-12-12',
'2020-12-12',
0,
],
'second date smaller' => [
'2021-12-12',
'2020-12-12',
1
],
'dates equal with different time' => [
'2020-12-12 12:12:12',
'2020-12-12 13:13:13',
0,
],
'invalid dates --' => [
'--',
'--',
false
],
'empty dates' => [
'',
'',
false
],
'invalid dates' => [
'not a date',
'not a date either',
false,
],
'out of bound dates' => [
'1900-1-1',
'9999-12-31',
-1
]
];
}
public function dateTimeCompareProvider(): array
{
return [
'first date smaller no time' => [
'2020-12-12',
'2021-12-12',
-1,
],
'dates equal no timestamp' => [
'2020-12-12',
'2020-12-12',
0,
],
'second date smaller no timestamp' => [
'2021-12-12',
'2020-12-12',
1
],
'date equal first time smaller' => [
'2020-12-12 12:12:12',
'2020-12-12 13:13:13',
-1,
],
'date equal time equal' => [
'2020-12-12 12:12:12',
'2020-12-12 12:12:12',
0,
],
'date equal second time smaller' => [
'2020-12-12 13:13:13',
'2020-12-12 12:12:12',
1,
],
'valid date invalid time' => [
'2020-12-12 13:99:13',
'2020-12-12 12:12:99',
false,
],
'invalid datetimes --' => [
'--',
'--',
false,
],
'empty datetimess' => [
'',
'',
false,
],
'invalid datetimes' => [
'not a date',
'not a date either',
false,
],
];
}
/**
* Undocumented function
*
* @return array
*/
public function daysIntervalProvider(): array
{
return [
'valid interval /, not named array' => [
'2020/1/1',
'2020/1/30',
false,
[29, 22, 8],
],
'valid interval /, named array' => [
'2020/1/1',
'2020/1/30',
true,
['overall' => 29, 'weekday' => 22, 'weekend' => 8],
],
'valid interval -' => [
'2020-1-1',
'2020-1-30',
false,
[29, 22, 8],
],
'valid interval switched' => [
'2020/1/30',
'2020/1/1',
false,
[28, 0, 0],
],
'valid interval with time' => [
'2020/1/1 12:12:12',
'2020/1/30 13:13:13',
false,
[28, 21, 8],
],
'invalid dates' => [
'abc',
'xyz',
false,
[0, 0, 0]
],
// this test will take a long imte
'out of bound dates' => [
'1900-1-1',
'9999-12-31',
false,
[2958463,2113189,845274],
],
];
}
/**
* date string convert test
*
* @covers ::dateStringFormat
* @dataProvider timestampProvider
* @testdox dateStringFormat $input (microtime $flag) will be $expected [$_dataName]
*
* @param int|float $input
* @param bool $flag
* @param string $expected
* @return void
*/
public function testDateStringFormat(
$input,
bool $flag_show_micro,
bool $flag_micro_as_float,
string $expected
): void {
$this->assertEquals(
$expected,
\CoreLibs\Combined\DateTime::dateStringFormat(
$input,
$flag_show_micro,
$flag_micro_as_float
)
);
}
/**
* interval convert test
*
* @covers ::timeStringFormat
* @dataProvider intervalProvider
* @testdox timeStringFormat $input (microtime $flag) will be $expected [$_dataName]
*
* @param int|float $input
* @param bool $flag
* @param string $expected
* @return void
*/
public function testTimeStringFormat($input, bool $flag, string $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Combined\DateTime::timeStringFormat($input, $flag)
);
}
/**
* Undocumented function
*
* @covers ::stringToTime
* @dataProvider reverseIntervalProvider
* @testdox stringToTime $input will be $expected [$_dataName]
*
* @param string|int|float $input
* @param string|int|float $expected
* @return void
*/
public function testStringToTime($input, $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Combined\DateTime::stringToTime($input)
);
}
/**
* Undocumented function
*
* @covers ::checkDate
* @dataProvider dateProvider
* @testdox checkDate $input will be $expected [$_dataName]
*
* @param string $input
* @param bool $expected
* @return void
*/
public function testCheckDate(string $input, bool $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Combined\DateTime::checkDate($input)
);
}
/**
* Undocumented function
*
* @covers ::checkDateTime
* @dataProvider dateTimeProvider
* @testdox checkDateTime $input will be $expected [$_dataName]
*
* @param string $input
* @param bool $expected
* @return void
*/
public function testCheckDateTime(string $input, bool $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Combined\DateTime::checkDateTime($input)
);
}
/**
* Undocumented function
*
* @covers ::compareDate
* @dataProvider dateCompareProvider
* @testdox compareDate $input_a compared to $input_b will be $expected [$_dataName]
*
* @param string $input_a
* @param string $input_b
* @param int|bool $expected
* @return void
*/
public function testCompareDate(string $input_a, string $input_b, $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Combined\DateTime::compareDate($input_a, $input_b)
);
}
/**
* Undocumented function
*
* @covers ::compareDateTime
* @dataProvider dateTimeCompareProvider
* @testdox compareDateTime $input_a compared to $input_b will be $expected [$_dataName]
*
* @param string $input_a
* @param string $input_b
* @param int|bool $expected
* @return void
*/
public function testCompareDateTime(string $input_a, string $input_b, $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Combined\DateTime::compareDateTime($input_a, $input_b)
);
}
/**
* Undocumented function
*
* @covers ::calcDaysInterval
* @dataProvider daysIntervalProvider
* @testdox calcDaysInterval $input_a compared to $input_b will be $expected [$_dataName]
* @medium
*
* @param string $input_a
* @param string $input_b
* @param bool $flag
* @param array $expected
* @return void
*/
public function testCalcDaysInterval(
string $input_a,
string $input_b,
bool $flag,
$expected
): void {
$this->assertEquals(
$expected,
\CoreLibs\Combined\DateTime::calcDaysInterval($input_a, $input_b, $flag)
);
}
/**
* Undocumented function
*
* @return array
*/
public function weekdayNumberProvider(): array
{
return [
'0 invalid' => [0, null, 'Inv',],
'0 invalid long' => [0, true, 'Invalid',],
'1 short' => [1, null, 'Mon',],
'1 long' => [1, true, 'Monday',],
'2 short' => [2, null, 'Tue',],
'2 long' => [2, true, 'Tuesday',],
'3 short' => [3, null, 'Wed',],
'3 long' => [3, true, 'Wednesday',],
'4 short' => [4, null, 'Thu',],
'4 long' => [4, true, 'Thursday',],
'5 short' => [5, null, 'Fri',],
'5 long' => [5, true, 'Friday',],
'6 short' => [6, null, 'Sat',],
'6 long' => [6, true, 'Saturday',],
'7 short' => [7, null, 'Sun',],
'7 long' => [7, true, 'Sunday',],
'8 invalid' => [8, null, 'Inv',],
'8 invalid long' => [8, true, 'Invalid',],
];
}
/**
* int weekday number to string weekday
*
* @covers ::setWeekdayNameFromIsoDow
* @dataProvider weekdayNumberProvider
* @testdox weekdayListProvider $input (short $flag) will be $expected [$_dataName]
*
* @param int $input
* @param bool|null $flag
* @param string $expected
* @return void
*/
public function testSetWeekdayNameFromIsoDow(
int $input,
?bool $flag,
string $expected
): void {
if ($flag === null) {
$output = \CoreLibs\Combined\DateTime::setWeekdayNameFromIsoDow($input);
} else {
$output = \CoreLibs\Combined\DateTime::setWeekdayNameFromIsoDow($input, $flag);
}
$this->assertEquals(
$expected,
$output
);
}
/**
* Undocumented function
*
* @return array
*/
public function weekdayDateProvider(): array
{
return [
'invalid date' => ['2022-02-31', -1],
'1: monday' => ['2022-07-25', 1],
'2: tuesday' => ['2022-07-26', 2],
'3: wednesday' => ['2022-07-27', 3],
'4: thursday' => ['2022-07-28', 4],
'5: friday' => ['2022-07-29', 5],
'6: saturday' => ['2022-07-30', 6],
'7: sunday' => ['2022-07-31', 7],
];
}
/**
* date to weekday number
*
* @covers ::setWeekdayNumberFromDate
* @dataProvider weekdayDateProvider
* @testdox setWeekdayNumberFromDate $input will be $expected [$_dataName]
*
* @param string $input
* @param int $expected
* @return void
*/
public function testSetWeekdayNumberFromDate(
string $input,
int $expected
): void {
$this->assertEquals(
$expected,
\CoreLibs\Combined\DateTime::setWeekdayNumberFromDate($input)
);
}
/**
* Undocumented function
*
* @return array
*/
public function weekdayDateNameProvider(): array
{
return [
'invalid date short' => ['2022-02-31', null, 'Inv'],
'invalid date long' => ['2022-02-31', true, 'Invalid'],
'Mon short' => ['2022-07-25', null, 'Mon'],
'Monday long' => ['2022-07-25', true, 'Monday'],
'Tue short' => ['2022-07-26', null, 'Tue'],
'Tuesday long' => ['2022-07-26', true, 'Tuesday'],
'Wed short' => ['2022-07-27', null, 'Wed'],
'Wednesday long' => ['2022-07-27', true, 'Wednesday'],
'Thu short' => ['2022-07-28', null, 'Thu'],
'Thursday long' => ['2022-07-28', true, 'Thursday'],
'Fri short' => ['2022-07-29', null, 'Fri'],
'Friday long' => ['2022-07-29', true, 'Friday'],
'Sat short' => ['2022-07-30', null, 'Sat'],
'Saturday long' => ['2022-07-30', true, 'Saturday'],
'Sun short' => ['2022-07-31', null, 'Sun'],
'Sunday long' => ['2022-07-31', true, 'Sunday'],
];
}
/**
* date to weekday name
*
* @covers ::setWeekdayNameFromDate
* @dataProvider weekdayDateNameProvider
* @testdox setWeekdayNameFromDate $input (short $flag) will be $expected [$_dataName]
*
* @param string $input
* @param bool|null $flag
* @param string $expected
* @return void
*/
public function testSetWeekdayNameFromDate(
string $input,
?bool $flag,
string $expected
): void {
if ($flag === null) {
$output = \CoreLibs\Combined\DateTime::setWeekdayNameFromDate($input);
} else {
$output = \CoreLibs\Combined\DateTime::setWeekdayNameFromDate($input, $flag);
}
$this->assertEquals(
$expected,
$output
);
}
}
// __END__

View File

@@ -1,118 +0,0 @@
<?php
declare(strict_types=1);
namespace tests;
use PHPUnit\Framework\TestCase;
/**
* Undocumented class
* @coversDefaultClass \CoreLibs\Convert\Math
* @testdox \CoreLibs\Convert\Math method tests
*/
final class CoreLibsConvertMathTest extends TestCase
{
/**
* Undocumented function
*
* @return array<mixed>
*/
public function fceilProvider(): array
{
return [
'5.5 must be 6' => [5.5, 6],
'5.1234567890 with 5 must be 6' => [5.1234567890, 6],
'6 must be 6' => [6, 6]
];
}
/**
* Undocumented function
*
* @covers ::fceil
* @dataProvider fceilProvider
* @testdox fceil: Input $input must be $expected
*
* @param float $input
* @param int $expected
* @return void
*/
public function testMathFceilValue(float $input, int $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Convert\Math::fceil($input)
);
}
/**
* Undocumented function
*
* @return array<mixed>
*/
public function floorProvider(): array
{
return [
'5123456 with -3 must be 5123000' => [5123456, -3, 5123000],
'5123456 with -10 must be 5000000' => [5123456, -10, 5000000]
];
}
/**
* Undocumented function
*
* @covers ::floorp
* @dataProvider floorProvider
* @testdox floor: Input $input with cutoff $cutoff must be $expected
*
* @param int $input
* @param int $cutoff
* @param int $expected
* @return void
*/
public function testMathFloorValue(int $input, int $cutoff, int $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Convert\Math::floorp($input, $cutoff)
);
}
/**
* Undocumented function
*
* @return array<mixed>
*/
public function initNumericProvider(): array
{
return [
'5 must be 5' => [5, 5, 'int'],
'5.123 must be 5.123' => [5.123, 5.123, 'float'],
"'5' must be 5" => ['5', 5, 'string'],
"'5.123' must be 5.123" => ['5.123', 5.123, 'string'],
];
}
/**
* Undocumented function
*
* @covers ::initNumeric
* @dataProvider initNumericProvider
* @testdox initNumeric: Input $info $input must match $expected [$_dataName]
*
* @param int|float|string $input
* @param float $expected
* @param string $info
* @return void
*/
public function testMathInitNumericValue($input, float $expected, string $info): void
{
$this->assertEquals(
$expected,
\CoreLibs\Convert\Math::initNumeric($input)
);
}
}
// __END__

View File

@@ -1,212 +0,0 @@
<?php
declare(strict_types=1);
namespace tests;
use PHPUnit\Framework\TestCase;
/**
* Test class for Create\Hash
* @coversDefaultClass \CoreLibs\Create\Hash
* @testdox \CoreLibs\Create\Hash method tests
*/
final class CoreLibsCreateHashTest extends TestCase
{
/**
* Undocumented function
*
* @return array
*/
public function hashData(): array
{
return [
'any string' => [
'text' => 'Some String Text',
'crc32b_reverse' => 'c5c21d91', // crc32b (in revere)
'sha1Short' => '4d2bc9ba0', // sha1Short
// via hash
'crc32b' => '911dc2c5', // hash: crc32b
'adler32' => '31aa05f1', // hash: alder32
'fnv132' => '9df444f9', // hash: fnv132
'fnv1a32' => '2c5f91b9', // hash: fnv1a32
'joaat' => '50dab846', // hash: joaat
]
];
}
/**
* Undocumented function
*
* @return array
*/
public function crc32bProvider(): array
{
$list = [];
foreach ($this->hashData() as $name => $values) {
$list[$name . ' to crc32b reverse'] = [
0 => $values['text'],
1 => $values['crc32b_reverse'],
];
}
return $list;
}
/**
* Undocumented function
*
* @return array
*/
public function sha1ShortProvider(): array
{
$list = [];
foreach ($this->hashData() as $name => $values) {
$list[$name . ' to sha1 short'] = [
0 => $values['text'],
1 => $values['crc32b_reverse'],
2 => $values['sha1Short'],
];
}
return $list;
}
/**
* test all hash functions
* NOTE: if we add new hash functions in the __hash method
* they need to be added here too (and in the master hashData array too)
*
* @return array
*/
public function hashProvider(): array
{
$list = [];
foreach ($this->hashData() as $name => $values) {
foreach ([null, 'crc32b', 'adler32', 'fnv132', 'fnv1a32', 'joaat'] as $_hash_type) {
// default value test
if ($_hash_type === null) {
$hash_type = \CoreLibs\Create\Hash::STANDARD_HASH_SHORT;
} else {
$hash_type = $_hash_type;
}
$list[$name . ' to ' . $hash_type] = [
0 => $values['text'],
1 => $_hash_type,
2 => $values[$hash_type]
];
}
}
return $list;
}
/**
* Undocumented function
*
* @return array
*/
public function hashLongProvider(): array
{
$hash_source = 'Some String Text';
return [
'Long Hash check: ' . \CoreLibs\Create\Hash::STANDARD_HASH_LONG => [
$hash_source,
hash(\CoreLibs\Create\Hash::STANDARD_HASH_LONG, $hash_source)
],
];
}
/**
* Undocumented function
*
* @covers ::__crc32b
* @dataProvider crc32bProvider
* @testdox __crc32b $input will be $expected [$_dataName]
*
* @param string $input
* @param string $expected
* @return void
*/
public function testCrc32b(string $input, string $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__crc32b($input)
);
}
/**
* Undocumented function
*
* @covers ::__sha1Short
* @dataProvider sha1ShortProvider
* @testdox __sha1Short $input will be $expected (crc32b) and $expected_sha1 (sha1 short) [$_dataName]
*
* @param string $input
* @param string $expected
* @return void
*/
public function testSha1Short(string $input, string $expected, string $expected_sha1): void
{
// uses crc32b
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__sha1Short($input)
);
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__sha1Short($input, false)
);
// sha1 type
$this->assertEquals(
$expected_sha1,
\CoreLibs\Create\Hash::__sha1Short($input, true)
);
}
/**
* Undocumented function
*
* @covers ::__hash
* @dataProvider hashProvider
* @testdox __hash $input with $hash_type will be $expected [$_dataName]
*
* @param string $input
* @param string|null $hash_type
* @param string $expected
* @return void
*/
public function testHash(string $input, ?string $hash_type, string $expected): void
{
if ($hash_type === null) {
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__hash($input)
);
} else {
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__hash($input, $hash_type)
);
}
}
/**
* Undocumented function
*
* @covers ::__hashLong
* @dataProvider hashLongProvider
* @testdox __hashLong $input will be $expected [$_dataName]
*
* @param string $input
* @param string $expected
* @return void
*/
public function testHashLong(string $input, string $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__hashLong($input)
);
}
}
// __END__

View File

@@ -1,310 +0,0 @@
<?php // phpcs:disable Generic.Files.LineLength
declare(strict_types=1);
namespace tests;
use PHPUnit\Framework\TestCase;
/**
* Test class for Language\GetLocale
*
* @coversDefaultClass \CoreLibs\Language\GetLocale
* @testdox \CoreLibs\Language\GetLocale method tests
*/
final class CoreLibsLanguageGetLocaleTest extends TestCase
{
/**
* set all constant variables that must be set before call
*
* @return void
*/
public static function setUpBeforeClass(): void
{
// default web page encoding setting
if (!defined('DEFAULT_ENCODING')) {
define('DEFAULT_ENCODING', 'UTF-8');
}
if (!defined('DEFAULT_LOCALE')) {
// default lang + encoding
define('DEFAULT_LOCALE', 'en_US.UTF-8');
}
// site
if (!defined('SITE_ENCODING')) {
define('SITE_ENCODING', DEFAULT_ENCODING);
}
if (!defined('SITE_LOCALE')) {
define('SITE_LOCALE', DEFAULT_LOCALE);
}
// just set
if (!defined('BASE')) {
define('BASE', str_replace('/configs', '', __DIR__) . DIRECTORY_SEPARATOR);
}
if (!defined('INCLUDES')) {
define('INCLUDES', 'includes' . DIRECTORY_SEPARATOR);
}
if (!defined('LANG')) {
define('LANG', 'lang' . DIRECTORY_SEPARATOR);
}
if (!defined('LOCALE')) {
define('LOCALE', 'locale' . DIRECTORY_SEPARATOR);
}
if (!defined('CONTENT_PATH')) {
define('CONTENT_PATH', 'frontend' . DIRECTORY_SEPARATOR);
}
// array session
$_SESSION = [];
global $_SESSION;
}
/**
* all the test data
*
* @return array
*/
public function setLocaleProvider(): array
{
return [
// 0: locale
// 1: domain
// 2: encoding
// 3: path
// 4: SESSION: DEFAULT_LOCALE
// 5: SESSION: DEFAULT_CHARSET
// 6: expected array
'no params, all default constants' => [
// lang, domain, encoding, path
null, null, null, null,
// SESSION DEFAULT_LOCALE, SESSION: DEFAULT_CHARSET
null, null,
// return array
[
'locale' => 'en_US.UTF-8',
'lang' => 'en_US',
'domain' => 'frontend',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?includes\/locale\/$/",
],
],
'no params, session charset and lang' => [
// lang, domain, encoding, path
null, null, null, null,
// SESSION DEFAULT_LOCALE, SESSION: DEFAULT_CHARSET
'ja_JP', 'UTF-8',
// return array
[
'locale' => 'ja_JP',
'lang' => 'ja_JP',
'domain' => 'frontend',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?includes\/locale\/$/",
],
],
'no params, session charset and lang short' => [
// lang, domain, encoding, path
null, null, null, null,
// SESSION DEFAULT_LOCALE, SESSION: DEFAULT_CHARSET
'ja', 'UTF-8',
// return array
[
'locale' => 'ja',
'lang' => 'ja',
'domain' => 'frontend',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?includes\/locale\/$/",
],
],
// param lang (no sessions)
'locale param only, no sessions' => [
// lang, domain, encoding, path
'ja.UTF-8', null, null, null,
// SESSION DEFAULT_LOCALE, SESSION: DEFAULT_CHARSET
null, null,
// return array
[
'locale' => 'ja.UTF-8',
'lang' => 'ja',
'domain' => 'frontend',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?includes\/locale\/$/",
],
],
// different locale setting
'locale complex param only, no sessions' => [
// lang, domain, encoding, path
'ja_JP.SJIS', null, null, null,
// SESSION DEFAULT_LOCALE, SESSION: DEFAULT_CHARSET
null, null,
// return array
[
'locale' => 'ja_JP.SJIS',
'lang' => 'ja_JP',
'domain' => 'frontend',
'encoding' => 'SJIS',
'path' => "/^\/(.*\/)?includes\/locale\/$/",
],
],
// param lang and domain (no override)
'locale, domain params, no sessions' => [
// lang, domain, encoding, path
'ja.UTF-8', 'admin', null, null,
// SESSION DEFAULT_LOCALE, SESSION: DEFAULT_CHARSET
null, null,
// return array
[
'locale' => 'ja.UTF-8',
'lang' => 'ja',
'domain' => 'admin',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?includes\/locale\/$/",
],
],
// param lang and domain (no override)
'locale, domain, encoding params, no sessions' => [
// lang, domain, encoding, path
'ja.UTF-8', 'admin', 'UTF-8', null,
// SESSION DEFAULT_LOCALE, SESSION: DEFAULT_CHARSET
null, null,
// return array
[
'locale' => 'ja.UTF-8',
'lang' => 'ja',
'domain' => 'admin',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?includes\/locale\/$/",
],
],
// lang, domain, path (no override)
'locale, domain and path, no sessions' => [
// lang, domain, encoding, path
'ja.UTF-8', 'admin', '', __DIR__ . '/locale_other/',
// SESSION DEFAULT_LOCALE, SESSION: DEFAULT_CHARSET
null, null,
// return array
[
'locale' => 'ja.UTF-8',
'lang' => 'ja',
'domain' => 'admin',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?locale_other\/$/",
],
],
// all params set (no override)
'all parameter, no sessions' => [
// lang, domain, encoding, path
'ja', 'admin', 'UTF-8', __DIR__ . '/locale_other/',
// SESSION DEFAULT_LOCALE, SESSION: DEFAULT_CHARSET
null, null,
// return array
[
'locale' => 'ja',
'lang' => 'ja',
'domain' => 'admin',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?locale_other\/$/",
],
],
// param lang and domain (no override)
'long locale, domain, encoding params, no sessions' => [
// lang, domain, encoding, path
'de_CH.UTF-8@euro', 'admin', 'UTF-8', null,
// SESSION DEFAULT_LOCALE, SESSION: DEFAULT_CHARSET
null, null,
// return array
[
'locale' => 'de_CH.UTF-8@euro',
'lang' => 'de_CH',
'domain' => 'admin',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?includes\/locale\/$/",
],
],
// TODO invalid params (bad path) (no override)
// TODO param calls, but with override set
];
}
/**
* Undocumented function
*
* @covers ::setLocale
* @dataProvider setLocaleProvider
* @testdox lang settings lang $language, domain $domain, encoding $encoding, path $path; session lang: $SESSION_DEFAULT_LOCALE, session char: $SESSION_DEFAULT_CHARSET [$_dataName]
*
* @return void
*/
public function testsetLocale(
?string $language,
?string $domain,
?string $encoding,
?string $path,
?string $SESSION_DEFAULT_LOCALE,
?string $SESSION_DEFAULT_CHARSET,
array $expected
): void {
$return_lang_settings = [];
global $_SESSION;
// set override
if ($SESSION_DEFAULT_LOCALE !== null) {
$_SESSION['DEFAULT_LOCALE'] = $SESSION_DEFAULT_LOCALE;
}
if ($SESSION_DEFAULT_CHARSET !== null) {
$_SESSION['DEFAULT_CHARSET'] = $SESSION_DEFAULT_CHARSET;
}
// function call
if ($language === null && $domain === null && $encoding === null && $path === null) {
$return_lang_settings = \CoreLibs\Language\GetLocale::setLocale();
} elseif ($language !== null && $domain === null && $encoding === null && $path === null) {
$return_lang_settings = \CoreLibs\Language\GetLocale::setLocale(
$language
);
} elseif ($language !== null && $domain !== null && $encoding === null && $path === null) {
$return_lang_settings = \CoreLibs\Language\GetLocale::setLocale(
$language,
$domain
);
} elseif ($language !== null && $domain !== null && $encoding !== null && $path === null) {
$return_lang_settings = \CoreLibs\Language\GetLocale::setLocale(
$language,
$domain,
$encoding
);
} else {
$return_lang_settings = \CoreLibs\Language\GetLocale::setLocale(
$language,
$domain,
$encoding,
$path
);
}
// print "RETURN: " . print_r($return_lang_settings, true) . "\n";
foreach (
[
'locale', 'lang', 'domain', 'encoding', 'path'
] as $key
) {
$value = $expected[$key];
if (strpos($value, "/") === 0) {
// this is regex
$this->assertMatchesRegularExpression(
$value,
$return_lang_settings[$key],
'assert regex failed for ' . $key
);
} else {
// assert equal
$this->assertEquals(
$value,
$return_lang_settings[$key],
'assert equal failed for ' . $key
);
}
}
// unset all vars
$_SESSION = [];
unset($GLOBALS['OVERRIDE_LANG']);
}
}
// __END__

View File

@@ -1,33 +0,0 @@
<?php
declare(strict_types=1);
namespace tests;
use PHPUnit\Framework\TestCase;
/**
* Test class for Output\Image
* @coversDefaultClass \CoreLibs\Output\Image
* @testdox \CoreLibs\Output\Image method tests
*/
final class CoreLibsOutputImageTest extends TestCase
{
/**
* Undocumented function
*
* @testdox Output\Image Class tests
*
* @return void
*/
public function testOutputImage()
{
// $this->assertTrue(true, 'Output Image Tests not implemented');
$this->markTestIncomplete(
'Output\Image Tests have not yet been implemented'
);
// $this->markTestSkipped('No implementation for Output\Image at the moment');
}
}
// __END__

View File

@@ -22,12 +22,9 @@ final class CoreLibsCreateEmailTest extends TestCase
*/ */
public static function setUpBeforeClass(): void public static function setUpBeforeClass(): void
{ {
self::$log = new \CoreLibs\Debug\Logging([ self::$log = new \CoreLibs\Logging\Logging([
'log_folder' => DIRECTORY_SEPARATOR . 'tmp', 'log_folder' => DIRECTORY_SEPARATOR . 'tmp',
'file_id' => 'CoreLibs-Create-Email-Test', 'log_file_id' => 'CoreLibs-Create-Email-Test',
'debug_all' => true,
'echo_all' => false,
'print_all' => true,
]); ]);
} }
@@ -624,7 +621,7 @@ final class CoreLibsCreateEmailTest extends TestCase
// force new set for each run // force new set for each run
self::$log->setLogUniqueId(true); self::$log->setLogUniqueId(true);
// set on of unique log id // set on of unique log id
self::$log->setLogPer('run', true); self::$log->setLogFlag(\CoreLibs\Logging\Logger\Flag::per_run);
// init logger // init logger
$status = \CoreLibs\Create\Email::sendEmail( $status = \CoreLibs\Create\Email::sendEmail(
$subject, $subject,
@@ -646,7 +643,9 @@ final class CoreLibsCreateEmailTest extends TestCase
// assert content: must load JSON from log file // assert content: must load JSON from log file
if ($status == 2) { if ($status == 2) {
// open file, get last entry with 'SEND EMAIL JSON' key // open file, get last entry with 'SEND EMAIL JSON' key
$file = file_get_contents(self::$log->getLogFileName()); $file = file_get_contents(
self::$log->getLogFolder() . self::$log->getLogFile()
);
if ($file !== false) { if ($file !== false) {
// extract SEND EMAIL JSON line // extract SEND EMAIL JSON line
$found = preg_match_all("/^.* <SEND EMAIL JSON> - (.*)$/m", $file, $matches); $found = preg_match_all("/^.* <SEND EMAIL JSON> - (.*)$/m", $file, $matches);

View File

@@ -0,0 +1,426 @@
<?php
declare(strict_types=1);
namespace tests;
use PHPUnit\Framework\TestCase;
/**
* Test class for Create\Hash
* @coversDefaultClass \CoreLibs\Create\Hash
* @testdox \CoreLibs\Create\Hash method tests
*/
final class CoreLibsCreateHashTest extends TestCase
{
/**
* Undocumented function
*
* @return array
*/
public function hashData(): array
{
return [
'hash tests' => [
// this is the string
'text' => 'Some String Text',
// hash list special
'crc32b_reverse' => 'c5c21d91', // crc32b (in revere)
'sha1Short' => '4d2bc9ba0', // sha1Short
// via hash
'crc32b' => '911dc2c5', // hash: crc32b
'adler32' => '31aa05f1', // hash: alder32
'fnv132' => '9df444f9', // hash: fnv132
'fnv1a32' => '2c5f91b9', // hash: fnv1a32
'joaat' => '50dab846', // hash: joaat
'ripemd160' => 'aeae3f041b20136451519edd9361570909300342', // hash: ripemd160,
'sha256' => '9055080e022f224fa835929b80582b3c71c672206fa3a49a87412c25d9d42ceb', // hash: sha256
]
];
}
/**
* Undocumented function
*
* @return array
*/
public function crc32bProvider(): array
{
$list = [];
foreach ($this->hashData() as $name => $values) {
$list[$name . ' to crc32b reverse'] = [
0 => $values['text'],
1 => $values['crc32b_reverse'],
];
}
return $list;
}
/**
* Undocumented function
*
* @return array
*/
public function sha1ShortProvider(): array
{
$list = [];
foreach ($this->hashData() as $name => $values) {
$list[$name . ' to sha1 short'] = [
0 => $values['text'],
1 => $values['crc32b_reverse'],
2 => $values['sha1Short'],
];
}
return $list;
}
/**
* test all hash functions
* NOTE: if we add new hash functions in the __hash method
* they need to be added here too (and in the master hashData array too)
*
* @return array
*/
public function hashProvider(): array
{
$list = [];
foreach ($this->hashData() as $name => $values) {
foreach ([null, 'crc32b', 'adler32', 'fnv132', 'fnv1a32', 'joaat', 'ripemd160', 'sha256'] as $_hash_type) {
// default value test
if ($_hash_type === null) {
$hash_type = \CoreLibs\Create\Hash::STANDARD_HASH_SHORT;
} else {
$hash_type = $_hash_type;
}
$list[$name . ' to ' . $hash_type] = [
0 => $values['text'],
1 => $_hash_type,
2 => $values[$hash_type]
];
}
}
return $list;
}
/**
* Undocumented function
*
* @return array
*/
public function hashLongProvider(): array
{
$hash_source = 'Some String Text';
return [
'Long Hash check: ' . \CoreLibs\Create\Hash::STANDARD_HASH_LONG => [
$hash_source,
hash(\CoreLibs\Create\Hash::STANDARD_HASH_LONG, $hash_source)
],
];
}
/**
* Undocumented function
*
* @return array
*/
public function hashStandardProvider(): array
{
$hash_source = 'Some String Text';
return [
'Long Hash check: ' . \CoreLibs\Create\Hash::STANDARD_HASH => [
$hash_source,
hash(\CoreLibs\Create\Hash::STANDARD_HASH, $hash_source)
],
];
}
/**
* Undocumented function
*
* @covers ::__crc32b
* @dataProvider crc32bProvider
* @testdox __crc32b $input will be $expected [$_dataName]
*
* @param string $input
* @param string $expected
* @return void
*/
public function testCrc32b(string $input, string $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__crc32b($input)
);
}
/**
* Undocumented function
*
* phpcs:disable Generic.Files.LineLength
* @covers ::__sha1Short
* @covers ::__crc32b
* @covers ::sha1Short
* @dataProvider sha1ShortProvider
* @testdox __sha1Short/__crc32b/sha1short $input will be $expected (crc32b) and $expected_sha1 (sha1 short) [$_dataName]
* phpcs:enable Generic.Files.LineLength
*
* @param string $input
* @param string $expected
* @return void
*/
public function testSha1Short(string $input, string $expected, string $expected_sha1): void
{
// uses crc32b
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__sha1Short($input),
'__sha1Short depreacted'
);
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__sha1Short($input, false),
'__sha1Short (false) depreacted'
);
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__crc32b($input),
'__crc32b'
);
// sha1 type
$this->assertEquals(
$expected_sha1,
\CoreLibs\Create\Hash::__sha1Short($input, true),
'__sha1Short (true) depreacted'
);
$this->assertEquals(
$expected_sha1,
\CoreLibs\Create\Hash::sha1Short($input),
'sha1Short'
);
}
/**
* Undocumented function
*
* @covers ::__hash
* @covers ::hashShort
* @covers ::hashShort
* @dataProvider hashProvider
* @testdox __hash/hashShort/hash $input with $hash_type will be $expected [$_dataName]
*
* @param string $input
* @param string|null $hash_type
* @param string $expected
* @return void
*/
public function testHash(string $input, ?string $hash_type, string $expected): void
{
if ($hash_type === null) {
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__hash($input),
'__hash'
);
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::hashShort($input),
'hashShort'
);
} else {
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__hash($input, $hash_type),
'__hash with hash type'
);
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::hash($input, $hash_type),
'hash with hash type'
);
}
}
/**
* Undocumented function
*
* @covers ::__hashLong
* @covers ::hashLong
* @dataProvider hashLongProvider
* @testdox __hashLong/hashLong $input will be $expected [$_dataName]
*
* @param string $input
* @param string $expected
* @return void
*/
public function testHashLong(string $input, string $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::__hashLong($input)
);
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::hashLong($input)
);
}
/**
* Undocumented function
*
* @covers ::hash
* @covers ::hashStd
* @dataProvider hashStandardProvider
* @testdox hash/hashStd $input will be $expected [$_dataName]
*
* @param string $input
* @param string $expected
* @return void
*/
public function testHashStandard(string $input, string $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::hashStd($input)
);
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::hash($input)
);
}
/**
* Undocumented function
*
* @covers ::hash
* @testdox hash with invalid type
*
* @return void
*/
public function testInvalidHashType(): void
{
$hash_source = 'Some String Text';
$expected = hash(\CoreLibs\Create\Hash::STANDARD_HASH, $hash_source);
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::hash($hash_source, 'DOES_NOT_EXIST')
);
}
/**
* Note: this only tests default sha256
*
* @covers ::hashHmac
* @testdox hash hmac test
*
* @return void
*/
public function testHashMac(): void
{
$hash_key = 'FIX KEY';
$hash_source = 'Some String Text';
$expected = '16479b3ef6fa44e1cdd8b2dcfaadf314d1a7763635e8738f1e7996d714d9b6bf';
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::hashHmac($hash_source, $hash_key)
);
}
/**
* Undocumented function
*
* @covers ::hashHmac
* @testdox hash hmac with invalid type
*
* @return void
*/
public function testInvalidHashMacType(): void
{
$hash_key = 'FIX KEY';
$hash_source = 'Some String Text';
$expected = hash_hmac(\CoreLibs\Create\Hash::STANDARD_HASH, $hash_source, $hash_key);
$this->assertEquals(
$expected,
\CoreLibs\Create\Hash::hashHmac($hash_source, $hash_key, 'DOES_NOT_EXIST')
);
}
/**
* Undocumented function
*
* @return array<mixed>
*/
public function providerHashTypes(): array
{
return [
'Hash crc32b' => [
'crc32b',
true,
false,
],
'Hash adler32' => [
'adler32',
true,
false,
],
'HAsh fnv132' => [
'fnv132',
true,
false,
],
'Hash fnv1a32' => [
'fnv1a32',
true,
false,
],
'Hash: joaat' => [
'joaat',
true,
false,
],
'Hash: ripemd160' => [
'ripemd160',
true,
true,
],
'Hash: sha256' => [
'sha256',
true,
true,
],
'Hash: invalid' => [
'invalid',
false,
false
]
];
}
/**
* Undocumented function
*
* @covers ::isValidHashType
* @covers ::isValidHashHmacType
* @dataProvider providerHashTypes
* @testdox check if $hash_type is valid for hash $hash_ok and hash hmac $hash_hmac_ok [$_dataName]
*
* @param string $hash_type
* @param bool $hash_ok
* @param bool $hash_hmac_ok
* @return void
*/
public function testIsValidHashAndHashHmacTypes(string $hash_type, bool $hash_ok, bool $hash_hmac_ok): void
{
$this->assertEquals(
$hash_ok,
\CoreLibs\Create\Hash::isValidHashType($hash_type),
'hash valid'
);
$this->assertEquals(
$hash_hmac_ok,
\CoreLibs\Create\Hash::isValidHashHmacType($hash_type),
'hash hmac valid'
);
}
}
// __END__

View File

@@ -22,7 +22,6 @@ final class CoreLibsCreateSessionTest extends TestCase
public function sessionProvider(): array public function sessionProvider(): array
{ {
// 0: session name as parameter or for GLOBAL value // 0: session name as parameter or for GLOBAL value
// 1: type p: parameter, g: global, d: php.ini default
// 2: mock data as array // 2: mock data as array
// checkCliStatus: true/false, // checkCliStatus: true/false,
// getSessionStatus: PHP_SESSION_DISABLED for abort, // getSessionStatus: PHP_SESSION_DISABLED for abort,
@@ -30,12 +29,11 @@ final class CoreLibsCreateSessionTest extends TestCase
// setSessionName: true/false, // setSessionName: true/false,
// checkActiveSession: true/false, [1st call, 2nd call] // checkActiveSession: true/false, [1st call, 2nd call]
// getSessionId: string or false // getSessionId: string or false
// 3: exepcted name (session) // 3: exepcted name (session)]
// 4: expected error string // 4: auto write close flag
return [ return [
'session parameter' => [ 'session parameter' => [
'sessionNameParameter', 'sessionNameParameter',
'p',
[ [
'checkCliStatus' => false, 'checkCliStatus' => false,
'getSessionStatus' => PHP_SESSION_NONE, 'getSessionStatus' => PHP_SESSION_NONE,
@@ -44,11 +42,10 @@ final class CoreLibsCreateSessionTest extends TestCase
'getSessionId' => '1234abcd4567' 'getSessionId' => '1234abcd4567'
], ],
'sessionNameParameter', 'sessionNameParameter',
'' null,
], ],
'session globals' => [ 'session globals' => [
'sessionNameGlobals', 'sessionNameGlobals',
'g',
[ [
'checkCliStatus' => false, 'checkCliStatus' => false,
'getSessionStatus' => PHP_SESSION_NONE, 'getSessionStatus' => PHP_SESSION_NONE,
@@ -57,11 +54,12 @@ final class CoreLibsCreateSessionTest extends TestCase
'getSessionId' => '1234abcd4567' 'getSessionId' => '1234abcd4567'
], ],
'sessionNameGlobals', 'sessionNameGlobals',
'' [
'auto_write_close' => false,
],
], ],
'session name default' => [ 'auto write close' => [
'', 'sessionNameAutoWriteClose',
'd',
[ [
'checkCliStatus' => false, 'checkCliStatus' => false,
'getSessionStatus' => PHP_SESSION_NONE, 'getSessionStatus' => PHP_SESSION_NONE,
@@ -69,95 +67,10 @@ final class CoreLibsCreateSessionTest extends TestCase
'checkActiveSession' => [false, true], 'checkActiveSession' => [false, true],
'getSessionId' => '1234abcd4567' 'getSessionId' => '1234abcd4567'
], ],
'', 'sessionNameAutoWriteClose',
''
],
// error checks
// 1: we are in cli
'on cli error' => [
'',
'd',
[ [
'checkCliStatus' => true, 'auto_write_close' => true,
'getSessionStatus' => PHP_SESSION_NONE,
'setSessionName' => true,
'checkActiveSession' => [false, true],
'getSessionId' => '1234abcd4567'
], ],
'',
'[SESSION] No sessions in php cli'
],
// 2: session disabled
'session disabled error' => [
'',
'd',
[
'checkCliStatus' => false,
'getSessionStatus' => PHP_SESSION_DISABLED,
'setSessionName' => true,
'checkActiveSession' => [false, true],
'getSessionId' => '1234abcd4567'
],
'',
'[SESSION] Sessions are disabled'
],
// 3: invalid session name: string
'invalid name chars error' => [
'1invalid$session#;',
'p',
[
'checkCliStatus' => false,
'getSessionStatus' => PHP_SESSION_NONE,
'setSessionName' => false,
'checkActiveSession' => [false, true],
'getSessionId' => '1234abcd4567'
],
'',
'[SESSION] Invalid session name: 1invalid$session#;'
],
// 3: invalid session name: only numbers
'invalid name numbers only error' => [
'123',
'p',
[
'checkCliStatus' => false,
'getSessionStatus' => PHP_SESSION_NONE,
'setSessionName' => false,
'checkActiveSession' => [false, true],
'getSessionId' => '1234abcd4567'
],
'',
'[SESSION] Invalid session name: 123'
],
// 3: invalid session name: invalid name short
// 3: invalid session name: too long (128)
// 4: failed to start session (2nd false on check active session)
'invalid name numbers only error' => [
'',
'd',
[
'checkCliStatus' => false,
'getSessionStatus' => PHP_SESSION_NONE,
'setSessionName' => true,
'checkActiveSession' => [false, false],
'getSessionId' => '1234abcd4567'
],
'',
'[SESSION] Failed to activate session'
],
// 5: get session id return false
'invalid name numbers only error' => [
'',
'd',
[
'checkCliStatus' => false,
'getSessionStatus' => PHP_SESSION_NONE,
'setSessionName' => true,
'checkActiveSession' => [false, true],
'getSessionId' => false
],
'',
'[SESSION] getSessionId did not return a session id'
], ],
]; ];
} }
@@ -170,29 +83,24 @@ final class CoreLibsCreateSessionTest extends TestCase
* @testdox startSession $input name for $type will be $expected (error: $expected_error) [$_dataName] * @testdox startSession $input name for $type will be $expected (error: $expected_error) [$_dataName]
* *
* @param string $input * @param string $input
* @param string $type
* @param array<mixed> $mock_data * @param array<mixed> $mock_data
* @param string $expected * @param string $expected
* @param string $expected_error * @param array<string,mixed> $options
* @return void * @return void
*/ */
public function testStartSession( public function testStartSession(
string $input, string $input,
string $type,
array $mock_data, array $mock_data,
string $expected, string $expected,
string $expected_error ?array $options,
): void { ): void {
// override expected
if ($type == 'd') {
$expected = ini_get('session.name');
}
/** @var \CoreLibs\Create\Session&MockObject $session_mock */ /** @var \CoreLibs\Create\Session&MockObject $session_mock */
$session_mock = $this->createPartialMock( $session_mock = $this->createPartialMock(
\CoreLibs\Create\Session::class, \CoreLibs\Create\Session::class,
[ [
'checkCliStatus', 'getSessionStatus', 'checkActiveSession', 'checkCliStatus',
'setSessionName', 'startSessionCall', 'getSessionId', 'getSessionStatus', 'checkActiveSession',
'getSessionId',
'getSessionName' 'getSessionName'
] ]
); );
@@ -211,12 +119,8 @@ final class CoreLibsCreateSessionTest extends TestCase
$mock_data['checkActiveSession'][0], $mock_data['checkActiveSession'][0],
$mock_data['checkActiveSession'][1], $mock_data['checkActiveSession'][1],
); );
// dummy set for session name
$session_mock->method('setSessionName')->with($input)->willReturn($mock_data['setSessionName']);
// set session name & return bsed on request data // set session name & return bsed on request data
$session_mock->method('getSessionName')->willReturn($expected); $session_mock->method('getSessionName')->willReturn($expected);
// will not return anything
$session_mock->method('startSessionCall');
// in test case only return string // in test case only return string
// false: will return false // false: will return false
$session_mock->method('getSessionId')->willReturn($mock_data['getSessionId']); $session_mock->method('getSessionId')->willReturn($mock_data['getSessionId']);
@@ -224,20 +128,7 @@ final class CoreLibsCreateSessionTest extends TestCase
// regex for session id // regex for session id
$ression_id_regex = "/^\w+$/"; $ression_id_regex = "/^\w+$/";
unset($GLOBALS['SET_SESSION_NAME']); $session_id = $session_mock->getSessionId();
$session_id = '';
switch ($type) {
case 'p':
$session_id = $session_mock->startSession($input);
break;
case 'g':
$GLOBALS['SET_SESSION_NAME'] = $input;
$session_id = $session_mock->startSession();
break;
case 'd':
$session_id = $session_mock->startSession();
break;
}
// asert checks // asert checks
if (!empty($session_id)) { if (!empty($session_id)) {
$this->assertMatchesRegularExpression( $this->assertMatchesRegularExpression(
@@ -253,16 +144,82 @@ final class CoreLibsCreateSessionTest extends TestCase
$expected, $expected,
$session_mock->getSessionName() $session_mock->getSessionName()
); );
} else {
// false checks
$this->assertEquals(
$expected_error,
$session_mock->getErrorStr(),
'error assert'
);
} }
} }
/**
* Undocumented function
*
* @return array
*/
public function providerSessionException(): array
{
return [
'not cli' => [
'TEST_EXCEPTION',
\RuntimeException::class,
1,
'/^\[SESSION\] No sessions in php cli$/',
],
/* 'session disabled ' => [
'TEST_EXCEPTION',
\RuntimeException::class,
2,
'/^\[SESSION\] Sessions are disabled/'
],
'invalid session name' => [
'--#as^-292p-',
\UnexpectedValueException::class,
3,
'/^\[SESSION\] Invalid session name: /'
],
'failed to activate session' => [
'TEST_EXCEPTION',
\RuntimeException::class,
4,
'/^\[SESSION\] Failed to activate session/'
],
'expired session' => [
\RuntimeException::class,
5,
'/^\[SESSION\] Expired session found/'
],
'not a valid session id returned' => [
\UnexpectedValueException::class,
6,
'/^\[SESSION\] getSessionId did not return a session id/'
], */
];
}
/**
* exception checks
*
* @covers ::initSession
* @dataProvider providerSessionException
* @testdox create session $session_name with exception $exception ($exception_code) [$_dataName]
*
* @param string $session_name
* @param string $exception
* @param int $exception_code
* @param string $expected_error
* @return void
*/
public function testSessionException(
string $session_name,
string $exception,
int $exception_code,
string $expected_error,
): void {
//
// throws only on new Object creation
$this->expectException($exception);
$this->expectExceptionCode($exception_code);
$this->expectExceptionMessageMatches($expected_error);
// cannot set ini after header sent, plus we are on command line there are no headers
new \CoreLibs\Create\Session($session_name, ['session_strict' => false]);
}
/** /**
* provider for session name check * provider for session name check
* *
@@ -326,109 +283,147 @@ final class CoreLibsCreateSessionTest extends TestCase
* *
* @return array * @return array
*/ */
public function sessionDataProvider(): array public function providerSessionData(): array
{ {
return [ return [
'test' => [ 'test' => [
'foo', 'foo',
'bar', 'bar',
'bar', 'bar',
null,
], ],
'int key test' => [ 'int key test' => [
123, 123,
'bar', 'bar',
'bar', 'bar',
\UnexpectedValueException::class
], ],
// more complex value tests // more complex value tests
'array values' => [ 'array values' => [
'array', 'array',
[1, 2, 3], [1, 2, 3],
[1, 2, 3], [1, 2, 3],
null,
] ]
]; ];
} }
// NOTE: with auto start session, we cannot test this in the command line
/** /**
* method call test * method call test
* *
* @covers ::setS * @covers ::set
* @covers ::getS * @covers ::get
* @covers ::issetS * @covers ::isset
* @covers ::unsetS * @covers ::unset
* @dataProvider sessionDataProvider * @dataProvider providerSessionData
* @testdox setS/getS/issetS/unsetS $name with $input is $expected [$_dataName] * @testdox set/get/isset/unset $name with $input is $expected ($exception) [$_dataName]
* *
* @param string|int $name * @param string|int $name
* @param mixed $input * @param mixed $input
* @param mixed $expected * @param mixed $expected
* @param ?mixed $exception
* @return void * @return void
*/ */
public function testMethodSetGet($name, $input, $expected): void public function testMethodSetGet($name, $input, $expected, $exception): void
{ {
$session = new \CoreLibs\Create\Session(); if (\CoreLibs\Get\System::checkCLI()) {
$session->setS($name, $input); $this->markTestSkipped('Cannot run testMethodSetGet in CLI');
}
$session = new \CoreLibs\Create\Session('TEST_METHOD');
if ($expected !== null) {
$this->expectException($exception);
}
$session->set($name, $input);
$this->assertEquals( $this->assertEquals(
$expected, $expected,
$session->getS($name), $session->get($name),
'method set assert' 'method set assert'
); );
// isset true // isset true
$this->assertTrue( $this->assertTrue(
$session->issetS($name), $session->isset($name),
'method isset assert ok' 'method isset assert ok'
); );
$session->unsetS($name); $session->unset($name);
$this->assertEquals( $this->assertEquals(
'', '',
$session->getS($name), $session->get($name),
'method unset assert' 'method unset assert'
); );
// iset false // isset false
$this->assertFalse( $this->assertFalse(
$session->issetS($name), $session->isset($name),
'method isset assert false' 'method isset assert false'
); );
} }
/** /**
* magic call test * Undocumented function
* *
* @covers ::__set * @return array
* @covers ::__get */
* @covers ::__isset public function providerSessionDataMany(): array
* @covers ::__unset {
* @dataProvider sessionDataProvider return [
* @testdox __set/__get/__iseet/__unset $name with $input is $expected [$_dataName] 'valid set' => [
[
'foo 1' => 'bar 1',
'foo 2' => 'bar 1',
],
[
'foo 1' => 'bar 1',
'foo 2' => 'bar 1',
],
null,
],
'invalid entry' => [
[
'foo 1' => 'bar 1',
123 => 'bar 1',
],
[
'foo 1' => 'bar 1',
],
\UnexpectedValueException::class
]
];
}
/**
* Undocumented function
* *
* @param string|int $name * @covers ::setMany
* @param mixed $input * @covers ::getMany
* @param mixed $expected * @dataProvider providerSessionDataMany
* @testdox setMany/getMany/unsetMany $set is $expected ($exception) [$_dataName]
*
* @param array<string|int,mixed> $set
* @param array<string,mixed> $expected
* @param ?mixed $exception
* @return void * @return void
*/ */
public function testMagicSetGet($name, $input, $expected): void public function testMany($set, $expected, $exception): void
{ {
$session = new \CoreLibs\Create\Session(); if (\CoreLibs\Get\System::checkCLI()) {
$session->$name = $input; $this->markTestSkipped('Cannot run testMethodSetGet in CLI');
}
$session = new \CoreLibs\Create\Session('TEST_METHOD');
if ($expected !== null) {
$this->expectException($exception);
}
$session->setMany($set);
$this->assertEquals( $this->assertEquals(
$expected, $expected,
$session->$name, $session->getMany(array_keys($set)),
'magic set assert' 'set many failed'
); );
// isset true $session->unsetMany(array_keys($set));
$this->assertTrue(
isset($session->$name),
'magic isset assert ok'
);
unset($session->$name);
$this->assertEquals( $this->assertEquals(
'', [],
$session->$name, $session->getMany(array_keys($set)),
'magic unset assert' 'unset many failed'
);
// isset true
$this->assertFalse(
isset($session->$name),
'magic isset assert false'
); );
} }
@@ -442,27 +437,30 @@ final class CoreLibsCreateSessionTest extends TestCase
*/ */
public function testUnsetAll(): void public function testUnsetAll(): void
{ {
if (\CoreLibs\Get\System::checkCLI()) {
$this->markTestSkipped('Cannot run testUnsetAll in CLI');
}
$test_values = [ $test_values = [
'foo' => 'abc', 'foo' => 'abc',
'bar' => '123' 'bar' => '123'
]; ];
$session = new \CoreLibs\Create\Session(); $session = new \CoreLibs\Create\Session('TEST_UNSET');
foreach ($test_values as $name => $value) { foreach ($test_values as $name => $value) {
$session->setS($name, $value); $session->set($name, $value);
// confirm set // confirm set
$this->assertEquals( $this->assertEquals(
$value, $value,
$session->getS($name), $session->get($name),
'set assert: ' . $name 'set assert: ' . $name
); );
} }
// unset all // unset all
$session->unsetAllS(); $session->clear();
// check unset // check unset
foreach (array_keys($test_values) as $name) { foreach (array_keys($test_values) as $name) {
$this->assertEquals( $this->assertEquals(
'', '',
$session->getS($name), $session->get($name),
'unsert assert: ' . $name 'unsert assert: ' . $name
); );
} }

View File

@@ -21,45 +21,83 @@ final class CoreLibsCreateUidsTest extends TestCase
public function uniqIdProvider(): array public function uniqIdProvider(): array
{ {
return [ return [
// number length
'too short' => [
0 => 1,
1 => 4,
2 => null
],
'valid length: 10' => [
0 => 10,
1 => 10,
2 => null
],
'valid length: 9, auto length' => [
0 => 9,
1 => 8,
2 => null
],
'valid length: 9, force length' => [
0 => 9,
1 => 9,
2 => true,
],
'very long: 512' => [
0 => 512,
1 => 512,
2 => null
],
// below is all legacy
'md5 hash' => [ 'md5 hash' => [
0 => 'md5', 0 => 'md5',
1 => 32, 1 => 32,
2 => null
], ],
'sha256 hash' => [ 'sha256 hash' => [
0 => 'sha256', 0 => 'sha256',
1 => 64 1 => 64,
2 => null
], ],
'ripemd160 hash' => [ 'ripemd160 hash' => [
0 => 'ripemd160', 0 => 'ripemd160',
1 => 40 1 => 40,
2 => null
], ],
'adler32 hash' => [ 'adler32 hash' => [
0 => 'adler32', 0 => 'adler32',
1 => 8 1 => 8,
2 => null
], ],
'not in list hash but valid' => [ 'not in list, set default length' => [
0 => 'sha3-512', 0 => 'sha3-512',
1 => strlen(hash('sha3-512', 'A')) 1 => 64,
2 => null
], ],
'default hash not set' => [ 'default hash not set' => [
0 => null, 0 => null,
1 => 64, 1 => 64,
2 => null
], ],
'invalid name' => [ 'invalid name' => [
0 => 'iamnotavalidhash', 0 => 'iamnotavalidhash',
1 => 64, 1 => 64,
2 => null
], ],
'auto: ' . \CoreLibs\Create\Uids::DEFAULT_HASH => [ // auto calls
0 => \CoreLibs\Create\Uids::DEFAULT_HASH, 'auto: ' . \CoreLibs\Create\Uids::DEFAULT_UNNIQ_ID_LENGTH => [
1 => strlen(hash(\CoreLibs\Create\Uids::DEFAULT_HASH, 'A')) 0 => \CoreLibs\Create\Uids::DEFAULT_UNNIQ_ID_LENGTH,
1 => 64,
2 => null
], ],
'auto: ' . \CoreLibs\Create\Uids::STANDARD_HASH_LONG => [ 'auto: ' . \CoreLibs\Create\Uids::STANDARD_HASH_LONG => [
0 => \CoreLibs\Create\Uids::STANDARD_HASH_LONG, 0 => \CoreLibs\Create\Uids::STANDARD_HASH_LONG,
1 => strlen(hash(\CoreLibs\Create\Uids::STANDARD_HASH_LONG, 'A')) 1 => strlen(hash(\CoreLibs\Create\Uids::STANDARD_HASH_LONG, 'A')),
2 => null
], ],
'auto: ' . \CoreLibs\Create\Uids::STANDARD_HASH_SHORT => [ 'auto: ' . \CoreLibs\Create\Uids::STANDARD_HASH_SHORT => [
0 => \CoreLibs\Create\Uids::STANDARD_HASH_SHORT, 0 => \CoreLibs\Create\Uids::STANDARD_HASH_SHORT,
1 => strlen(hash(\CoreLibs\Create\Uids::STANDARD_HASH_SHORT, 'A')) 1 => strlen(hash(\CoreLibs\Create\Uids::STANDARD_HASH_SHORT, 'A')),
2 => null
], ],
]; ];
} }
@@ -83,6 +121,7 @@ final class CoreLibsCreateUidsTest extends TestCase
* must match 7e78fe0d-59b8-4637-af7f-e88d221a7d1e * must match 7e78fe0d-59b8-4637-af7f-e88d221a7d1e
* *
* @covers ::uuidv4 * @covers ::uuidv4
* @covers ::validateUuidv4
* @testdox uuidv4 check that return is matching regex [$_dataName] * @testdox uuidv4 check that return is matching regex [$_dataName]
* *
* @return void * @return void
@@ -91,13 +130,18 @@ final class CoreLibsCreateUidsTest extends TestCase
{ {
$uuid = \CoreLibs\Create\Uids::uuidv4(); $uuid = \CoreLibs\Create\Uids::uuidv4();
$this->assertMatchesRegularExpression( $this->assertMatchesRegularExpression(
'/^[a-z0-9]{8}-[a-z0-9]{4}-[a-z0-9]{4}-[a-z0-9]{4}-[a-z0-9]{12}$/', '/^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/',
$uuid $uuid,
'Failed regex check'
);
$this->assertTrue(
\CoreLibs\Create\Uids::validateUuuidv4($uuid),
'Failed validate regex method'
);
$this->assertFalse(
\CoreLibs\Create\Uids::validateUuuidv4('not-a-uuidv4'),
'Failed wrong uuid validated as true'
); );
// $this->assertStringMatchesFormat(
// '%4s%4s-%4s-%4s-%4s-%4s%4s%4s',
// $uuid
// );
} }
/** /**
@@ -105,25 +149,26 @@ final class CoreLibsCreateUidsTest extends TestCase
* *
* @covers ::uniqId * @covers ::uniqId
* @dataProvider uniqIdProvider * @dataProvider uniqIdProvider
* @testdox uniqId $input will be length $expected [$_dataName] * @testdox uniqId $input will be length $expected (Force $flag) [$_dataName]
* *
* @param string|null $input * @param int|string|null $input
* @param string $expected * @param string $expected
* @param bool|null $flag
* @return void * @return void
*/ */
public function testUniqId(?string $input, int $expected): void public function testUniqId(int|string|null $input, int $expected, ?bool $flag): void
{ {
if ($input === null) { if ($input === null) {
$this->assertEquals( $uniq_id_length = strlen(\CoreLibs\Create\Uids::uniqId());
$expected, } elseif ($flag === null) {
strlen(\CoreLibs\Create\Uids::uniqId()) $uniq_id_length = strlen(\CoreLibs\Create\Uids::uniqId($input));
);
} else { } else {
$this->assertEquals( $uniq_id_length = strlen(\CoreLibs\Create\Uids::uniqId($input, $flag));
$expected,
strlen(\CoreLibs\Create\Uids::uniqId($input))
);
} }
$this->assertEquals(
$expected,
$uniq_id_length
);
} }
/** /**

View File

@@ -10,7 +10,6 @@ use PHPUnit\Framework\TestCase;
* Test class for DB\Extended\ArrayIO * Test class for DB\Extended\ArrayIO
* This will only test the PgSQL parts * This will only test the PgSQL parts
* @coversDefaultClass \CoreLibs\DB\Extended\ArrayIO * @coversDefaultClass \CoreLibs\DB\Extended\ArrayIO
* @coversDefaultClass \CoreLibs\DB\Extended\ArrayIO
* @testdox \CoreLibs\Extended\ArrayIO method tests for extended DB interface * @testdox \CoreLibs\Extended\ArrayIO method tests for extended DB interface
*/ */
final class CoreLibsDBExtendedArrayIOTest extends TestCase final class CoreLibsDBExtendedArrayIOTest extends TestCase

View File

@@ -10,11 +10,13 @@ use PHPUnit\Framework\TestCase;
/** /**
* Test class for Debug\Logging * Test class for Debug\Logging
* @coversDefaultClass \CoreLibs\Debug\Logging * @coversDefaultClass \CoreLibs\Debug\LoggingLegacy
* @testdox \CoreLibs\Debug\Logging method tests * @testdox \CoreLibs\Debug\LoggingLegacy method tests
*/ */
final class CoreLibsDebugLoggingTest extends TestCase final class CoreLibsDebugLoggingLegacyTest extends TestCase
{ {
private const LOG_FOLDER = __DIR__ . DIRECTORY_SEPARATOR . 'log' . DIRECTORY_SEPARATOR;
/** /**
* test set for options BASIC * test set for options BASIC
* *
@@ -23,7 +25,7 @@ final class CoreLibsDebugLoggingTest extends TestCase
* 1: expected * 1: expected
* 2: override * 2: override
* override: * override:
* - constant for COSNTANTS * - constant for CONSTANTS
* - global for _GLOBALS * - global for _GLOBALS
* *
* @return array * @return array
@@ -33,17 +35,20 @@ final class CoreLibsDebugLoggingTest extends TestCase
return [ return [
'log folder set' => [ 'log folder set' => [
[ [
'log_folder' => '/tmp' 'log_folder' => DIRECTORY_SEPARATOR . 'tmp',
'file_id' => 'testClassInit'
], ],
[ [
'log_folder' => '/tmp/', 'log_folder' => DIRECTORY_SEPARATOR . 'tmp' . DIRECTORY_SEPARATOR,
'debug_all' => false, 'debug_all' => false,
'print_all' => false, 'print_all' => false,
], ],
[] []
], ],
'nothing set' => [ 'nothing set' => [
null, [
'file_id' => 'testClassInit'
],
[ [
'log_folder' => getcwd() . DIRECTORY_SEPARATOR, 'log_folder' => getcwd() . DIRECTORY_SEPARATOR,
'debug_all' => false, 'debug_all' => false,
@@ -51,30 +56,33 @@ final class CoreLibsDebugLoggingTest extends TestCase
], ],
[] []
], ],
'no options set, constant set' => [ 'no options set, constant set [DEPRECATED]' => [
null,
[ [
'log_folder' => str_replace('/configs', '', __DIR__) 'file_id' => 'testClassInit'
. DIRECTORY_SEPARATOR . 'log/', ],
[
'log_folder' => str_replace(DIRECTORY_SEPARATOR . 'configs', '', __DIR__)
. DIRECTORY_SEPARATOR . 'log' . DIRECTORY_SEPARATOR,
'debug_all' => false, 'debug_all' => false,
'print_all' => false, 'print_all' => false,
], ],
[ [
'constant' => [ 'constant' => [
'BASE' => str_replace('/configs', '', __DIR__) 'BASE' => str_replace(DIRECTORY_SEPARATOR . 'configs', '', __DIR__)
. DIRECTORY_SEPARATOR, . DIRECTORY_SEPARATOR,
'LOG' => 'log/' 'LOG' => 'log' . DIRECTORY_SEPARATOR
] ]
] ]
], ],
'standard test set' => [ 'standard test set' => [
[ [
'log_folder' => '/tmp', 'log_folder' => DIRECTORY_SEPARATOR . 'tmp',
'file_id' => 'testClassInit',
'debug_all' => true, 'debug_all' => true,
'print_all' => true, 'print_all' => true,
], ],
[ [
'log_folder' => '/tmp/', 'log_folder' => DIRECTORY_SEPARATOR . 'tmp' . DIRECTORY_SEPARATOR,
'debug_all' => true, 'debug_all' => true,
'print_all' => true, 'print_all' => true,
], ],
@@ -89,35 +97,66 @@ final class CoreLibsDebugLoggingTest extends TestCase
* @dataProvider optionsProvider * @dataProvider optionsProvider
* @testdox init test [$_dataName] * @testdox init test [$_dataName]
* *
* @param array|null $options * @param array $options
* @param array $expected * @param array $expected
* @param array $override * @param array $override
* @return void * @return void
*/ */
public function testClassInit(?array $options, array $expected, array $override): void public function testClassInit(array $options, array $expected, array $override): void
{ {
if (!empty($override['constant'])) { if (!empty($override['constant'])) {
foreach ($override['constant'] as $var => $value) { foreach ($override['constant'] as $var => $value) {
define($var, $value); if (!defined($var)) {
define($var, $value);
}
}
// for deprecated no log_folder set
// if base is defined and it does have AAASetupData set
// change the log_folder "Debug" to "AAASetupData"
if (
defined('BASE') &&
strpos(BASE, DIRECTORY_SEPARATOR . 'AAASetupData') !== false
) {
$expected['log_folder'] = str_replace(
DIRECTORY_SEPARATOR . 'Debug',
DIRECTORY_SEPARATOR . 'AAASetupData',
$expected['log_folder']
);
} }
} }
if ($options === null) { // if not log folder and constant set -> expect E_USER_DEPRECATION
$log = new \CoreLibs\Debug\Logging(); if (!empty($override['constant']) && empty($options['log_folder'])) {
} else { // the deprecation message
$log = new \CoreLibs\Debug\Logging($options); $deprecation_message = 'options: log_folder must be set. '
. 'Setting via BASE and LOG constants is deprecated';
// convert E_USER_DEPRECATED to a exception
set_error_handler(
static function (int $errno, string $errstr): never {
throw new \Exception($errstr, $errno);
},
E_USER_DEPRECATED
);
// catch this with the message
$this->expectExceptionMessage($deprecation_message);
} }
$log = new \CoreLibs\Debug\LoggingLegacy($options);
// reset error handler
restore_error_handler();
// check that settings match // check that settings match
$this->assertEquals( $this->assertEquals(
$expected['log_folder'], $expected['log_folder'],
$log->getSetting('log_folder') $log->getSetting('log_folder'),
'log folder not matching'
); );
$this->assertEquals( $this->assertEquals(
$expected['debug_all'], $expected['debug_all'],
$log->getSetting('debug_output_all') $log->getSetting('debug_output_all'),
'debug all flag not matching'
); );
$this->assertEquals( $this->assertEquals(
$expected['print_all'], $expected['print_all'],
$log->getSetting('print_output_all') $log->getSetting('print_output_all'),
'print all flag not matching'
); );
// print "LOG: " . $log->getSetting('log_folder') . "\n"; // print "LOG: " . $log->getSetting('log_folder') . "\n";
// print "DEBUG: " . $log->getSetting('debug_output_all') . "\n"; // print "DEBUG: " . $log->getSetting('debug_output_all') . "\n";
@@ -134,17 +173,23 @@ final class CoreLibsDebugLoggingTest extends TestCase
// 0: options // 0: options
// 1: expected // 1: expected
// 2: override // 2: override
// 3: exception message
return [ return [
'no log id set' => [ 'no log id set' => [
null, [
'log_folder' => self::LOG_FOLDER,
],
[ [
'log_file_id' => '' 'log_file_id' => ''
], ],
[] [],
null
], ],
// set log id manually afterwards // set log id manually afterwards
'set log id manually' => [ 'set log id manually' => [
null, [
'log_folder' => self::LOG_FOLDER,
],
[ [
'log_file_id' => '', 'log_file_id' => '',
'set_log_file_id' => 'abc123', 'set_log_file_id' => 'abc123',
@@ -154,21 +199,26 @@ final class CoreLibsDebugLoggingTest extends TestCase
'values' => [ 'values' => [
'log_file_id' => 'abc123' 'log_file_id' => 'abc123'
] ]
] ],
null
], ],
// set log id from options // set log id from options
'set log id via options' => [ 'set log id via options' => [
[ [
'file_id' => 'abc456', 'file_id' => 'abc456',
'log_folder' => self::LOG_FOLDER,
], ],
[ [
'log_file_id' => 'abc456' 'log_file_id' => 'abc456'
], ],
[] [],
null
], ],
// set log id from GLOBALS [DEPRECATED] // set log id from GLOBALS [DEPRECATED]
'set log id via globals' => [ 'set log id via globals [DEPRECATED]' => [
null, [
'log_folder' => self::LOG_FOLDER,
],
[ [
'log_file_id' => 'def123' 'log_file_id' => 'def123'
], ],
@@ -176,11 +226,14 @@ final class CoreLibsDebugLoggingTest extends TestCase
'globals' => [ 'globals' => [
'LOG_FILE_ID' => 'def123' 'LOG_FILE_ID' => 'def123'
] ]
] ],
'options: file_id must be set. Setting via LOG_FILE_ID global variable is deprecated'
], ],
// set log id from CONSTANT [DEPRECATED] // set log id from CONSTANT [DEPRECATED]
'set log id via constant' => [ 'set log id via constant [DEPRECATED]' => [
null, [
'log_folder' => self::LOG_FOLDER,
],
[ [
'log_file_id' => 'ghi123' 'log_file_id' => 'ghi123'
], ],
@@ -192,12 +245,14 @@ final class CoreLibsDebugLoggingTest extends TestCase
'constant' => [ 'constant' => [
'LOG_FILE_ID' => 'ghi123' 'LOG_FILE_ID' => 'ghi123'
] ]
] ],
'options: file_id must be set. Setting via LOG_FILE_ID constant is deprecated'
], ],
// invalid, keep previous set // invalid, keep previous set
'invalid log id' => [ 'invalid log id' => [
[ [
'file_id' => 'jkl456' 'file_id' => 'jkl456',
'log_folder' => self::LOG_FOLDER,
], ],
[ [
'log_file_id' => 'jkl456', 'log_file_id' => 'jkl456',
@@ -207,7 +262,8 @@ final class CoreLibsDebugLoggingTest extends TestCase
'values' => [ 'values' => [
'log_file_id' => './#' 'log_file_id' => './#'
] ]
] ],
null
] ]
]; ];
} }
@@ -219,13 +275,18 @@ final class CoreLibsDebugLoggingTest extends TestCase
* @dataProvider logIdOptionsProvider * @dataProvider logIdOptionsProvider
* @testdox log id set/get tests [$_dataName] * @testdox log id set/get tests [$_dataName]
* *
* @param array|null $options * @param array $options
* @param array $expected * @param array $expected
* @param array $override * @param array $override
* @param string|null $deprecation_message until we remove the old code
* @return void * @return void
*/ */
public function testLogId(?array $options, array $expected, array $override): void public function testLogId(
{ array $options,
array $expected,
array $override,
?string $deprecation_message
): void {
// we need to set with file_id option, globals LOG_FILE_ID, constant LOG_FILE_ID // we need to set with file_id option, globals LOG_FILE_ID, constant LOG_FILE_ID
if (!empty($override['constant'])) { if (!empty($override['constant'])) {
foreach ($override['constant'] as $var => $value) { foreach ($override['constant'] as $var => $value) {
@@ -237,11 +298,20 @@ final class CoreLibsDebugLoggingTest extends TestCase
$GLOBALS[$var] = $value; $GLOBALS[$var] = $value;
} }
} }
if ($options === null) { if (!empty($override['constant']) || !empty($override['globals'])) {
$log = new \CoreLibs\Debug\Logging(); // convert E_USER_DEPRECATED to a exception
} else { set_error_handler(
$log = new \CoreLibs\Debug\Logging($options); static function (int $errno, string $errstr): never {
throw new \Exception($errstr, $errno);
},
E_USER_DEPRECATED
);
// catch this with the message
$this->expectExceptionMessage($deprecation_message);
} }
$log = new \CoreLibs\Debug\LoggingLegacy($options);
// reset error handler
restore_error_handler();
// check current // check current
$this->assertEquals( $this->assertEquals(
$log->getLogId(), $log->getLogId(),
@@ -316,7 +386,10 @@ final class CoreLibsDebugLoggingTest extends TestCase
bool $expected_get bool $expected_get
): void { ): void {
// neutral start with default // neutral start with default
$log = new \CoreLibs\Debug\Logging(); $log = new \CoreLibs\Debug\LoggingLegacy([
'file_id' => 'testSetGetLogLevelAll',
'log_folder' => self::LOG_FOLDER
]);
// set and check // set and check
$this->assertEquals( $this->assertEquals(
$log->setLogLevelAll($type, $flag), $log->setLogLevelAll($type, $flag),
@@ -438,7 +511,10 @@ final class CoreLibsDebugLoggingTest extends TestCase
$expected_get $expected_get
): void { ): void {
// neutral start with default // neutral start with default
$log = new \CoreLibs\Debug\Logging(); $log = new \CoreLibs\Debug\LoggingLegacy([
'file_id' => 'testSetGetLogLevel',
'log_folder' => self::LOG_FOLDER
]);
// set // set
$this->assertEquals( $this->assertEquals(
$log->setLogLevel($type, $flag, $debug_on), $log->setLogLevel($type, $flag, $debug_on),
@@ -517,7 +593,10 @@ final class CoreLibsDebugLoggingTest extends TestCase
bool $expected_get bool $expected_get
): void { ): void {
// neutral start with default // neutral start with default
$log = new \CoreLibs\Debug\Logging(); $log = new \CoreLibs\Debug\LoggingLegacy([
'file_id' => 'testSetGetLogPer',
'log_folder' => self::LOG_FOLDER
]);
// set and check // set and check
$this->assertEquals( $this->assertEquals(
$log->setLogPer($type, $set), $log->setLogPer($type, $set),
@@ -546,7 +625,10 @@ final class CoreLibsDebugLoggingTest extends TestCase
public function testSetGetLogPrintFileDate(bool $input, bool $expected_set, bool $expected_get): void public function testSetGetLogPrintFileDate(bool $input, bool $expected_set, bool $expected_get): void
{ {
// neutral start with default // neutral start with default
$log = new \CoreLibs\Debug\Logging(); $log = new \CoreLibs\Debug\LoggingLegacy([
'file_id' => 'testSetGetLogPrintFileDate',
'log_folder' => self::LOG_FOLDER
]);
// set and check // set and check
$this->assertEquals( $this->assertEquals(
$log->setGetLogPrintFileDate($input), $log->setGetLogPrintFileDate($input),
@@ -612,7 +694,10 @@ final class CoreLibsDebugLoggingTest extends TestCase
*/ */
public function testPrAr(array $input, string $expected): void public function testPrAr(array $input, string $expected): void
{ {
$log = new \CoreLibs\Debug\Logging(); $log = new \CoreLibs\Debug\LoggingLegacy([
'file_id' => 'testPrAr',
'log_folder' => self::LOG_FOLDER
]);
$this->assertEquals( $this->assertEquals(
$log->prAr($input), $log->prAr($input),
$expected $expected
@@ -673,7 +758,10 @@ final class CoreLibsDebugLoggingTest extends TestCase
*/ */
public function testPrBl(bool $input, ?string $true, ?string $false, string $expected): void public function testPrBl(bool $input, ?string $true, ?string $false, string $expected): void
{ {
$log = new \CoreLibs\Debug\Logging(); $log = new \CoreLibs\Debug\LoggingLegacy([
'file_id' => 'testPrBl',
'log_folder' => self::LOG_FOLDER
]);
$return = ''; $return = '';
if ($true === null && $false === null) { if ($true === null && $false === null) {
$return = $log->prBl($input); $return = $log->prBl($input);
@@ -845,7 +933,7 @@ final class CoreLibsDebugLoggingTest extends TestCase
// remove any files named /tmp/error_log_TestDebug*.log // remove any files named /tmp/error_log_TestDebug*.log
array_map('unlink', glob($options['log_folder'] . 'error_msg_' . $options['file_id'] . '*.log')); array_map('unlink', glob($options['log_folder'] . 'error_msg_' . $options['file_id'] . '*.log'));
// init logger // init logger
$log = new \CoreLibs\Debug\Logging($options); $log = new \CoreLibs\Debug\LoggingLegacy($options);
// * debug (A/B) // * debug (A/B)
// NULL check for strip/prefix // NULL check for strip/prefix
$this->assertEquals( $this->assertEquals(
@@ -959,9 +1047,16 @@ final class CoreLibsDebugLoggingTest extends TestCase
public function testLogUniqueId(bool $option, bool $override): void public function testLogUniqueId(bool $option, bool $override): void
{ {
if ($option === true) { if ($option === true) {
$log = new \CoreLibs\Debug\Logging(['per_run' => $option]); $log = new \CoreLibs\Debug\LoggingLegacy([
'file_id' => 'testLogUniqueId',
'log_folder' => self::LOG_FOLDER,
'per_run' => $option
]);
} else { } else {
$log = new \CoreLibs\Debug\Logging(); $log = new \CoreLibs\Debug\LoggingLegacy([
'file_id' => 'testLogUniqueId',
'log_folder' => self::LOG_FOLDER
]);
$log->setLogUniqueId(); $log->setLogUniqueId();
} }
$per_run_id = $log->getLogUniqueId(); $per_run_id = $log->getLogUniqueId();

View File

@@ -5,6 +5,7 @@ declare(strict_types=1);
namespace tests; namespace tests;
use PHPUnit\Framework\TestCase; use PHPUnit\Framework\TestCase;
use CoreLibs\Debug\Support;
/** /**
* Test class for Debug\Support * Test class for Debug\Support
@@ -40,6 +41,32 @@ final class CoreLibsDebugSupportTest extends TestCase
]; ];
} }
/**
* Undocumented function
*
* @cover ::printTime
* @dataProvider printTimeProvider
* @testdox printTime test with $microtime and match to regex [$_dataName]
*
* @param int|null $mircrotime
* @param string $expected
* @return void
*/
public function testPrintTime(?int $microtime, string $regex): void
{
if ($microtime === null) {
$this->assertMatchesRegularExpression(
$regex,
Support::printTime()
);
} else {
$this->assertMatchesRegularExpression(
$regex,
Support::printTime($microtime)
);
}
}
/** /**
* Undocumented function * Undocumented function
* *
@@ -50,18 +77,55 @@ final class CoreLibsDebugSupportTest extends TestCase
return [ return [
'empty array' => [ 'empty array' => [
0 => [], 0 => [],
1 => "<pre>Array\n(\n)\n</pre>" 1 => "<pre>Array\n(\n)\n</pre>",
2 => "Array\n(\n)\n",
], ],
'simple array' => [ 'simple array' => [
0 => ['a', 'b'], 0 => ['a', 'b'],
1 => "<pre>Array\n(\n" 1 => "<pre>Array\n(\n"
. " [0] => a\n" . " [0] => a\n"
. " [1] => b\n" . " [1] => b\n"
. ")\n</pre>" . ")\n</pre>",
2 => "Array\n(\n"
. " [0] => a\n"
. " [1] => b\n"
. ")\n",
], ],
]; ];
} }
/**
* Undocumented function
*
* @cover ::printAr
* @cover ::printArray
* @dataProvider printArrayProvider
* @testdox printAr/printArray $input will be $expected [$_dataName]
*
* @param array $input
* @param string $expected
* @param string $expected_strip
* @return void
*/
public function testPrintAr(array $input, string $expected, string $expected_strip): void
{
$this->assertEquals(
$expected,
Support::printAr($input),
'assert printAr'
);
$this->assertEquals(
$expected,
Support::printArray($input),
'assert printArray'
);
$this->assertEquals(
$expected_strip,
Support::prAr($input),
'assert prAr'
);
}
/** /**
* Undocumented function * Undocumented function
* *
@@ -73,27 +137,31 @@ final class CoreLibsDebugSupportTest extends TestCase
'true input default' => [ 'true input default' => [
0 => true, 0 => true,
1 => [], 1 => [],
2 => 'true' 2 => 'true',
3 => 'true',
], ],
'false input default' => [ 'false input default' => [
0 => false, 0 => false,
1 => [], 1 => [],
2 => 'false' 2 => 'false',
3 => 'false'
], ],
'false input param name' => [ 'false input param name' => [
0 => false, 0 => false,
1 => [ 1 => [
'name' => 'param test' 'name' => 'param test'
], ],
2 => '<b>param test</b>: false' 2 => '<b>param test</b>: false',
3 => 'false'
], ],
'true input param name, true override' => [ 'true input param name, true override' => [
0 => true, 0 => true,
1 => [ 1 => [
'name' => 'param test', 'name' => 'param test',
'true' => 'ok' 'true' => 'ok',
], ],
2 => '<b>param test</b>: ok' 2 => '<b>param test</b>: ok',
3 => 'ok',
], ],
'false input param name, true override, false override' => [ 'false input param name, true override, false override' => [
0 => false, 0 => false,
@@ -102,11 +170,77 @@ final class CoreLibsDebugSupportTest extends TestCase
'true' => 'ok', 'true' => 'ok',
'false' => 'not', 'false' => 'not',
], ],
2 => '<b>param test</b>: not' 2 => '<b>param test</b>: not',
3 => 'not'
], ],
]; ];
} }
/**
* Undocumented function
*
* @cover ::printBool
* @dataProvider printBoolProvider
* @testdox printBool $input will be $expected [$_dataName]
*
* @param bool $input
* @param array $params
* @param string $expected
* @param string $expected_strip
* @return void
*/
public function testPrintBool(bool $input, array $params, string $expected, string $expected_strip): void
{
if (
isset($params['name']) &&
isset($params['true']) &&
isset($params['false'])
) {
$string = Support::printBool(
$input,
$params['name'],
$params['true'],
$params['false']
);
$string_strip = Support::prBl(
$input,
$params['true'],
$params['false']
);
} elseif (isset($params['name']) && isset($params['true'])) {
$string = Support::printBool(
$input,
$params['name'],
$params['true']
);
$string_strip = Support::prBl(
$input,
$params['true'],
);
} elseif (isset($params['name'])) {
$string = Support::printBool(
$input,
$params['name']
);
$string_strip = Support::prBl(
$input
);
} else {
$string = Support::printBool($input);
$string_strip = Support::prBl($input);
}
$this->assertEquals(
$expected,
$string,
'assert printBool'
);
$this->assertEquals(
$expected_strip,
$string_strip,
'assert prBl'
);
}
/** /**
* Undocumented function * Undocumented function
* *
@@ -169,12 +303,10 @@ final class CoreLibsDebugSupportTest extends TestCase
'an array, no html' => [ 'an array, no html' => [
['a', 'b'], ['a', 'b'],
true, true,
"##HTMLPRE##" "Array\n(\n"
. "Array\n(\n"
. " [0] => a\n" . " [0] => a\n"
. " [1] => b\n" . " [1] => b\n"
. ")\n" . ")\n",
. "##/HTMLPRE##",
], ],
// resource // resource
'a resource' => [ 'a resource' => [
@@ -191,6 +323,333 @@ final class CoreLibsDebugSupportTest extends TestCase
]; ];
} }
/**
* Undocumented function
*
* @cover ::printToString
* @dataProvider printToStringProvider
* @testdox printToString $input with $flag will be $expected [$_dataName]
*
* @param mixed $input anything
* @param boolean|null $flag html flag, only for string and array
* @param string $expected always string
* @return void
*/
public function testPrintToString(mixed $input, ?bool $flag, string $expected): void
{
if ($flag === null) {
// if expected starts with / and ends with / then this is a regex compare
if (
substr($expected, 0, 1) == '/' &&
substr($expected, -1, 1) == '/'
) {
$this->assertMatchesRegularExpression(
$expected,
Support::printToString($input)
);
} else {
$this->assertEquals(
$expected,
Support::printToString($input)
);
}
} else {
$this->assertEquals(
$expected,
Support::printToString($input, $flag)
);
}
}
/**
* Undocumented function
*
* @return array
*/
public function providerDumpExportVar(): array
{
return [
'string' => [
'input' => 'string',
'flag' => null,
'expected_dump' => 'string(6) "string"' . "\n",
'expected_export' => "<pre>'string'</pre>",
],
'string, no html' => [
'input' => 'string',
'flag' => true,
'expected_dump' => 'string(6) "string"' . "\n",
'expected_export' => "'string'",
],
// int
'int' => [
'input' => 6,
'flag' => null,
'expected_dump' => 'int(6)' . "\n",
'expected_export' => "<pre>6</pre>",
],
// float
'float' => [
'input' => 1.6,
'flag' => null,
'expected_dump' => 'float(1.6)' . "\n",
'expected_export' => "<pre>1.6</pre>",
],
// bool
'bool' => [
'input' => true,
'flag' => null,
'expected_dump' => 'bool(true)' . "\n",
'expected_export' => "<pre>true</pre>",
],
// array
'array' => [
'input' => ['string', true],
'flag' => null,
'expected_dump' => "array(2) {\n"
. " [0]=>\n"
. " string(6) \"string\"\n"
. " [1]=>\n"
. " bool(true)\n"
. "}\n",
'expected_export' => "<pre>array (\n"
. " 0 => 'string',\n"
. " 1 => true,\n"
. ")</pre>",
],
// more
];
}
/**
* Undocumented function
*
* @cover ::dumpVar
* @cover ::exportVar
* @dataProvider providerDumpExportVar
* @testdox dump/exportVar $input with $flag will be $expected_dump / $expected_export [$_dataName]
*
* @param mixed $input
* @param bool|null $flag
* @param string $expected_dump
* @param string $expected_export
* @return void
*/
public function testDumpExportVar(mixed $input, ?bool $flag, string $expected_dump, string $expected_export): void
{
if ($flag === null) {
$dump = Support::dumpVar($input);
$export = Support::exportVar($input);
} else {
$dump = Support::dumpVar($input, $flag);
$export = Support::exportVar($input, $flag);
}
$this->assertEquals(
$expected_dump,
$dump,
'assert dumpVar'
);
$this->assertEquals(
$expected_export,
$export,
'assert dumpVar'
);
}
/**
* Undocumented function
*
* @cover ::getCallerFileLine
* @testWith ["vendor/phpunit/phpunit/src/Framework/TestCase.php:6434","phar:///home/clemens/.phive/phars/phpunit-9.6.13.phar/phpunit/Framework/TestCase.php:6434"]
* @testdox getCallerFileLine check based on regex .../Framework/TestCase.php:\d+ [$_dataName]
*
* @param string $expected
* @return void
*/
public function testGetCallerFileLine(): void
{
// regex prefix with path "/../" and then fixed vendor + \d+
// or phar start if phiev installed
// phar:///home/clemens/.phive/phars/phpunit-9.6.13.phar/phpunit/Framework/TestCase.php
$regex = "/^("
. "\/.*\/vendor\/phpunit\/phpunit\/src"
. "|"
. "phar:\/\/\/.*\.phive\/phars\/phpunit-\d+\.\d+\.\d+\.phar\/phpunit"
. ")"
. "\/Framework\/TestCase.php:\d+$/";
$this->assertMatchesRegularExpression(
$regex,
Support::getCallerFileLine()
);
}
/**
* Undocumented function
*
* @cover ::getCallerMethod
* @testWith ["testGetCallerMethod"]
* @testdox getCallerMethod check if it returns $expected [$_dataName]
*
* @return void
*/
public function testGetCallerMethod(string $expected): void
{
$this->assertEquals(
$expected,
Support::getCallerMethod()
);
}
/**
* Undocumented function
*
* @cover ::getCallerMethodList
* @testWith [["main", "run", "run", "run", "run", "run", "run", "runBare", "runTest", "testGetCallerMethodList"]]
* @testdox getCallerMethodList check if it returns $expected [$_dataName]
*
* @param array $expected
* @return void
*/
public function testGetCallerMethodList(array $expected): void
{
$compare = Support::getCallerMethodList();
// 10: legacy
// 11: direct
// 12: full call
switch (count($compare)) {
case 10:
// add nothing
$this->assertEquals(
$expected,
$compare,
'assert expected 10'
);
break;
case 11:
if ($compare[0] == 'include') {
// add include at first
array_splice(
$expected,
0,
0,
['include']
);
} else {
array_splice(
$expected,
6,
0,
['run']
);
}
$this->assertEquals(
$expected,
$compare,
'assert expected 11'
);
break;
case 12:
// add two "run" before "runBare"
array_splice(
$expected,
7,
0,
['run']
);
array_splice(
$expected,
0,
0,
['include']
);
$this->assertEquals(
$expected,
$compare,
'assert expected 12'
);
break;
default:
$this->assertTrue(true, 'Default fallback as true');
break;
}
}
/**
* Undocumented function
*
* @cover ::getCallStack
* @testdox getCallStack check if it returns data [$_dataName]
*
* @return void
*/
public function testGetCallStack(): void
{
$call_stack = Support::getCallStack();
// print "Get CALL: " . print_r(Support::getCallStack(), true) . "\n";
if ($call_stack < 8) {
$this->assertFalse(true, 'getCallStack too low: 8');
} else {
$this->assertTrue(true, 'getCallSteck ok');
}
// just test top entry
$first = array_shift($call_stack);
$this->assertStringEndsWith(
':tests\CoreLibsDebugSupportTest->testGetCallStack',
$first,
);
}
/**
* test the lowest one (one above base)
*
* @cover ::getCallerClass
* @testWith ["tests\\CoreLibsDebugSupportTest"]
* @testdox getCallerClass check if it returns $expected [$_dataName]
*
* @return void
*/
public function testGetCallerClass(string $expected): void
{
$this->assertEquals(
$expected,
Support::getCallerClass()
);
}
/**
* test highest return (top level)
*
* @cover ::getCallerTopLevelClass
* @testWith ["PHPUnit\\TextUI\\Command"]
* @testdox getCallerTopLevelClass check if it returns $expected [$_dataName]
*
* @return void
*/
public function testGetCallerTopLevelClass(string $expected): void
{
$this->assertEquals(
$expected,
Support::getCallerTopLevelClass()
);
}
/**
* test highest return (top level)
*
* @cover ::getCallerClassMethod
* @testWith ["tests\\CoreLibsDebugSupportTest->testGetCallerClassMethod"]
* @testdox getCallerClassMethod check if it returns $expected [$_dataName]
*
* @return void
*/
public function testGetCallerClassMethod(string $expected): void
{
$this->assertEquals(
$expected,
Support::getCallerClassMethod()
);
}
/** /**
* Undocumented function * Undocumented function
* *
@@ -236,205 +695,6 @@ final class CoreLibsDebugSupportTest extends TestCase
]; ];
} }
/**
* Undocumented function
*
* @cover ::printTime
* @dataProvider printTimeProvider
* @testdox printTime test with $microtime and match to regex [$_dataName]
*
* @param int|null $mircrotime
* @param string $expected
* @return void
*/
public function testPrintTime(?int $microtime, string $regex): void
{
if ($microtime === null) {
$this->assertMatchesRegularExpression(
$regex,
\CoreLibs\Debug\Support::printTime()
);
} else {
$this->assertMatchesRegularExpression(
$regex,
\CoreLibs\Debug\Support::printTime($microtime)
);
}
}
/**
* Undocumented function
*
* @cover ::printAr
* @cover ::printArray
* @dataProvider printArrayProvider
* @testdox printAr/printArray $input will be $expected [$_dataName]
*
* @param array $input
* @param string $expected
* @return void
*/
public function testPrintAr(array $input, string $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Debug\Support::printAr($input),
'assert printAr'
);
$this->assertEquals(
$expected,
\CoreLibs\Debug\Support::printArray($input),
'assert printArray'
);
}
/**
* Undocumented function
*
* @cover ::printBool
* @dataProvider printBoolProvider
* @testdox printBool $input will be $expected [$_dataName]
*
* @param bool $input
* @param array $params
* @param string $expected
* @return void
*/
public function testPrintBool(bool $input, array $params, string $expected): void
{
if (
isset($params['name']) &&
isset($params['true']) &&
isset($params['false'])
) {
$string = \CoreLibs\Debug\Support::printBool(
$input,
$params['name'],
$params['true'],
$params['false']
);
} elseif (isset($params['name']) && isset($params['true'])) {
$string = \CoreLibs\Debug\Support::printBool(
$input,
$params['name'],
$params['true']
);
} elseif (isset($params['name'])) {
$string = \CoreLibs\Debug\Support::printBool(
$input,
$params['name']
);
} else {
$string = \CoreLibs\Debug\Support::printBool($input);
}
$this->assertEquals(
$expected,
$string,
'assert printBool'
);
}
/**
* Undocumented function
*
* @cover ::printToString
* @dataProvider printToStringProvider
* @testdox printToString $input with $flag will be $expected [$_dataName]
*
* @param mixed $input anything
* @param boolean|null $flag html flag, only for string and array
* @param string $expected always string
* @return void
*/
public function testPrintToString(mixed $input, ?bool $flag, string $expected): void
{
if ($flag === null) {
// if expected starts with / and ends with / then this is a regex compare
if (
substr($expected, 0, 1) == '/' &&
substr($expected, -1, 1) == '/'
) {
$this->assertMatchesRegularExpression(
$expected,
\CoreLibs\Debug\Support::printToString($input)
);
} else {
$this->assertEquals(
$expected,
\CoreLibs\Debug\Support::printToString($input)
);
}
} else {
$this->assertEquals(
$expected,
\CoreLibs\Debug\Support::printToString($input, $flag)
);
}
}
/**
* Undocumented function
*
* @cover ::getCallerMethod
* @testWith ["testGetCallerMethod"]
* @testdox getCallerMethod check if it returns $expected [$_dataName]
*
* @return void
*/
public function testGetCallerMethod(string $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Debug\Support::getCallerMethod()
);
}
/**
* Undocumented function
*
* @cover ::getCallerMethodList
* @testWith [["main", "run", "run", "run", "run", "run", "run", "runBare", "runTest", "testGetCallerMethodList"],["include", "main", "run", "run", "run", "run", "run", "run", "run", "runBare", "runTest", "testGetCallerMethodList"]]
* @testdox getCallerMethodList check if it returns $expected [$_dataName]
*
* @param array $expected
* @return void
*/
public function testGetCallerMethodList(array $expected, array $expected_group): void
{
$compare = \CoreLibs\Debug\Support::getCallerMethodList();
// if we direct call we have 10, if we call as folder we get 11
if (count($compare) == 10) {
$this->assertEquals(
$expected,
\CoreLibs\Debug\Support::getCallerMethodList(),
'assert expected 10'
);
} else {
$this->assertEquals(
$expected_group,
\CoreLibs\Debug\Support::getCallerMethodList(),
'assert expected group'
);
}
}
/**
* Undocumented function
*
* @cover ::getCallerClass
* @testWith ["PHPUnit\\TextUI\\Command"]
* @testdox getCallerClass check if it returns $expected [$_dataName]
*
* @return void
*/
public function testGetCallerClass(string $expected): void
{
$this->assertEquals(
$expected,
\CoreLibs\Debug\Support::getCallerClass()
);
}
/** /**
* Undocumented function * Undocumented function
* *
@@ -453,19 +713,19 @@ final class CoreLibsDebugSupportTest extends TestCase
if ($replace === null && $flag === null) { if ($replace === null && $flag === null) {
$this->assertEquals( $this->assertEquals(
$expected, $expected,
\CoreLibs\Debug\Support::debugString($input), Support::debugString($input),
'assert all default' 'assert all default'
); );
} elseif ($flag === null) { } elseif ($flag === null) {
$this->assertEquals( $this->assertEquals(
$expected, $expected,
\CoreLibs\Debug\Support::debugString($input, $replace), Support::debugString($input, $replace),
'assert flag default' 'assert flag default'
); );
} else { } else {
$this->assertEquals( $this->assertEquals(
$expected, $expected,
\CoreLibs\Debug\Support::debugString($input, $replace, $flag), Support::debugString($input, $replace, $flag),
'assert all set' 'assert all set'
); );
} }

3
4dev/tests/Debug/log/.gitignore vendored Normal file
View File

@@ -0,0 +1,3 @@
*log
*LOG
!.gitignore

View File

@@ -77,21 +77,24 @@ final class CoreLibsGetDotEnvTest extends TestCase
'file' => 'cannot_read.env', 'file' => 'cannot_read.env',
'status' => 2, 'status' => 2,
'content' => [], 'content' => [],
'chmod' => '000', // 0000
'chmod' => '100000',
], ],
'empty file' => [ 'empty file' => [
'folder' => __DIR__ . DIRECTORY_SEPARATOR . 'dotenv', 'folder' => __DIR__ . DIRECTORY_SEPARATOR . 'dotenv',
'file' => 'empty.env', 'file' => 'empty.env',
'status' => 1, 'status' => 1,
'content' => [], 'content' => [],
'chmod' => null, // 0664
'chmod' => '100664',
], ],
'override all' => [ 'override all' => [
'folder' => __DIR__ . DIRECTORY_SEPARATOR . 'dotenv', 'folder' => __DIR__ . DIRECTORY_SEPARATOR . 'dotenv',
'file' => 'test.env', 'file' => 'test.env',
'status' => 0, 'status' => 0,
'content' => $dot_env_content, 'content' => $dot_env_content,
'chmod' => null, // 0664
'chmod' => '100664',
], ],
'override directory' => [ 'override directory' => [
'folder' => __DIR__ . DIRECTORY_SEPARATOR . 'dotenv', 'folder' => __DIR__ . DIRECTORY_SEPARATOR . 'dotenv',
@@ -124,6 +127,16 @@ final class CoreLibsGetDotEnvTest extends TestCase
array $expected_env, array $expected_env,
?string $chmod ?string $chmod
): void { ): void {
if (
!empty($chmod) &&
$chmod == '100000' &&
getmyuid() == 0
) {
$this->markTestSkipped(
"Skip cannot read file test because run user is root"
);
return;
}
// if we have file + chmod set // if we have file + chmod set
$old_chmod = null; $old_chmod = null;
if ( if (
@@ -134,6 +147,20 @@ final class CoreLibsGetDotEnvTest extends TestCase
$old_chmod = fileperms($folder . DIRECTORY_SEPARATOR . $file); $old_chmod = fileperms($folder . DIRECTORY_SEPARATOR . $file);
chmod($folder . DIRECTORY_SEPARATOR . $file, octdec($chmod)); chmod($folder . DIRECTORY_SEPARATOR . $file, octdec($chmod));
} }
$message = '\CoreLibs\Get\DotEnv is deprecated in favor for '
. 'composer package gullevek\dotenv which is a copy of this';
// convert E_USER_DEPRECATED to a exception
set_error_handler(
static function (int $errno, string $errstr): never {
throw new \Exception($errstr, $errno);
},
E_USER_DEPRECATED
);
// tests are never run -> deprecated
if (is_file($folder . DIRECTORY_SEPARATOR . $file)) {
chmod($folder . DIRECTORY_SEPARATOR . $file, 0664);
}
$this->expectExceptionMessage($message);
if ($folder !== null && $file !== null) { if ($folder !== null && $file !== null) {
$status = DotEnv::readEnvFile($folder, $file); $status = DotEnv::readEnvFile($folder, $file);
} elseif ($folder !== null) { } elseif ($folder !== null) {
@@ -141,6 +168,7 @@ final class CoreLibsGetDotEnvTest extends TestCase
} else { } else {
$status = DotEnv::readEnvFile(); $status = DotEnv::readEnvFile();
} }
restore_error_handler();
$this->assertEquals( $this->assertEquals(
$status, $status,
$expected_status, $expected_status,
@@ -153,8 +181,9 @@ final class CoreLibsGetDotEnvTest extends TestCase
'Assert _ENV correct' 'Assert _ENV correct'
); );
// if we have file and chmod unset // if we have file and chmod unset
if ($old_chmod !== null) { print "Write mode: $old_chmod\n";
chmod($folder . DIRECTORY_SEPARATOR . $file, $old_chmod); if ($old_chmod !== null && $chmod == '100000') {
chmod($folder . DIRECTORY_SEPARATOR . $file, 0664);
} }
} }
} }

View File

@@ -67,17 +67,17 @@ final class CoreLibsGetSystemTest extends TestCase
'original set' => [ 'original set' => [
0 => null, 0 => null,
1 => 'NOHOST', 1 => 'NOHOST',
2 => 'NOPORT', 2 => 0,
], ],
'override set no port' => [ 'override set no port' => [
0 => 'foo.org', 0 => 'foo.org',
1 => 'foo.org', 1 => 'foo.org',
2 => '80' 2 => 80
], ],
'override set with port' => [ 'override set with port' => [
0 => 'foo.org:443', 0 => 'foo.org:443',
1 => 'foo.org', 1 => 'foo.org',
2 => '443' 2 => 443
] ]
]; ];
} }
@@ -99,7 +99,7 @@ final class CoreLibsGetSystemTest extends TestCase
1 => 'phpunit', 1 => 'phpunit',
2 => 'phpunit', 2 => 'phpunit',
// NOTE: this can change, so it is a regex check // NOTE: this can change, so it is a regex check
3 => "/^(\/?.*\/?)?vendor\/bin\/phpunit$/", 3 => "/^(\/?.*\/?)?(vendor\/bin|tools)\/phpunit$/",
], ],
'some path with extension' => [ 'some path with extension' => [
0 => '/some/path/to/file.txt', 0 => '/some/path/to/file.txt',
@@ -138,10 +138,10 @@ final class CoreLibsGetSystemTest extends TestCase
* *
* @param string|null $input * @param string|null $input
* @param string $expected_host * @param string $expected_host
* @param string $expected_port * @param int $expected_port
* @return void * @return void
*/ */
public function testGetHostNanme(?string $input, string $expected_host, string $expected_port): void public function testGetHostNanme(?string $input, string $expected_host, int $expected_port): void
{ {
// print "HOSTNAME: " . $_SERVER['HTTP_HOST'] . "<br>"; // print "HOSTNAME: " . $_SERVER['HTTP_HOST'] . "<br>";
// print "SERVER: " . print_r($_SERVER, true) . "\n"; // print "SERVER: " . print_r($_SERVER, true) . "\n";
@@ -216,6 +216,29 @@ final class CoreLibsGetSystemTest extends TestCase
); );
} }
} }
/**
* Undocumented function
*
* @covers ::getIpAddresses
* @testdox getIpAddresses check
*
* @return void
*/
public function testGetIpAddresses()
{
// response must have "REMOTE_ADDR" entry, others are optional
// NOTE: we have no IP addresses on command line
$this->assertTrue(
true,
"We do not have REMOTE_ADDR on command line"
);
// $this->assertContains(
// 'REMOTE_ADDR',
// array_keys(\CoreLibs\Get\System::getIpAddresses()),
// 'failed REMOTE_ADDR assert'
// );
}
} }
// __END__ // __END__

View File

@@ -0,0 +1,233 @@
<?php // phpcs:disable Generic.Files.LineLength
declare(strict_types=1);
namespace tests;
use PHPUnit\Framework\TestCase;
/**
* Test class for Language\GetLocale
*
* @coversDefaultClass \CoreLibs\Language\GetLocale
* @testdox \CoreLibs\Language\GetLocale method tests
*/
final class CoreLibsLanguageGetLocaleTest extends TestCase
{
public const SITE_ENCODING = 'UTF-8';
public const SITE_LOCALE = 'en_US.UTF-8';
public const SITE_DOMAIN = 'admin';
public const LOCALE_PATH = __DIR__ . DIRECTORY_SEPARATOR
. 'includes' . DIRECTORY_SEPARATOR
. 'locale' . DIRECTORY_SEPARATOR;
/**
* all the test data
*
* @return array<mixed>
*/
public function setLocaleFromSessionProvider(): array
{
return [
// 0: locale
// 1: domain
// 2: encoding
// 3: path
// 4: SESSION: DEFAULT_LOCALE
// 5: SESSION: DEFAULT_CHARSET
// 5: SESSION: DEFAULT_DOMAIN
// 6: SESSION: LOCALE_PATH
// 6: expected array
// 7: deprecation message
'all session vars set' => [
// lang, domain, encoding, path
self::SITE_LOCALE, self::SITE_DOMAIN, self::SITE_ENCODING, self::LOCALE_PATH,
// SESSION SETTINGS: locale, charset, domain, path
'ja_JP.UTF-8', 'UTF-8', 'admin', __DIR__ . '/locale_other/',
// return array
[
'locale' => 'ja_JP.UTF-8',
'lang' => 'ja_JP',
'domain' => 'admin',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?locale_other\/$/",
],
],
// param lang and domain (no override)
'no session set, only parameters' => [
// lang, domain, encoding, path
self::SITE_LOCALE, self::SITE_DOMAIN, self::SITE_ENCODING, self::LOCALE_PATH,
// SESSION SETTINGS: locale, charset, domain, path
null, null, null, null,
// return array
[
'locale' => 'en_US.UTF-8',
'lang' => 'en_US',
'domain' => 'admin',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?includes\/locale\/$/",
],
],
// special parse session check for locales
'all session vars set, short lang' => [
// lang, domain, encoding, path
self::SITE_LOCALE, self::SITE_DOMAIN, self::SITE_ENCODING, self::LOCALE_PATH,
// SESSION SETTINGS: locale, charset, domain, path
'ja', 'UTF-8', 'admin', __DIR__ . '/locale_other/',
// return array
[
'locale' => 'ja',
'lang' => 'ja',
'domain' => 'admin',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?locale_other\/$/",
],
],
// lang with modifier
// param lang and domain (no override)
'long locale, domain, encoding params, no sessions' => [
// lang, domain, encoding, path
self::SITE_LOCALE, self::SITE_DOMAIN, self::SITE_ENCODING, self::LOCALE_PATH,
// SESSION SETTINGS: locale, charset, domain, path
'de_CH.UTF-8@euro', 'admin', 'UTF-8', __DIR__ . '/includes/locale/',
// return array
[
'locale' => 'de_CH.UTF-8@euro',
'lang' => 'de_CH',
'domain' => 'admin',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?includes\/locale\/$/",
],
],
// missing session values check
// special parse session check for locales
'session missing encoding, set from parameters' => [
// lang, domain, encoding, path
self::SITE_LOCALE, self::SITE_DOMAIN, self::SITE_ENCODING, self::LOCALE_PATH,
// SESSION SETTINGS: locale, charset, domain, path
'ja', null, 'admin', __DIR__ . '/locale_other/',
// return array
[
'locale' => 'ja',
'lang' => 'ja',
'domain' => 'admin',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?locale_other\/$/",
],
],
// null return check for invalid entries
'no session set, only parameters, all invalid' => [
// lang, domain, encoding, path
'###', '&&&&', '$$$$', 'foo_bar_path',
// SESSION SETTINGS: locale, charset, domain, path
null, null, null, null,
// return array
[
'locale' => null,
'lang' => null,
'domain' => null,
'encoding' => null,
'path' => null,
],
],
// invalid session names, fall backup
'all session vars are invalid, fallback' => [
// lang, domain, encoding, path
self::SITE_LOCALE, self::SITE_DOMAIN, self::SITE_ENCODING, self::LOCALE_PATH,
// SESSION SETTINGS: locale, charset, domain, path
'###', '&&&&', '$$$$', 'foo_bar_path',
// return array
[
'locale' => 'en_US.UTF-8',
'lang' => 'en_US',
'domain' => 'admin',
'encoding' => 'UTF-8',
'path' => "/^\/(.*\/)?includes\/locale\/$/",
],
],
];
}
/**
* Undocumented function
*
* @covers ::setLocale
* @dataProvider setLocaleFromSessionProvider
* @testdox lang settings lang $language, domain $domain, encoding $encoding, path $path; session lang: $SESSION_DEFAULT_LOCALE, session char: $SESSION_DEFAULT_CHARSET [$_dataName]
*
* @param string| $language
* @param string| $domain
* @param string| $encoding
* @param string| $path
* @param string|null $SESSION_DEFAULT_LOCALE
* @param string|null $SESSION_DEFAULT_CHARSET
* @param string|null $SESSION_DEFAULT_DOMAIN
* @param string|null $SESSION_LOCALE_PATH
* @param array<mixed> $expected
* @return void
*/
public function testsetLocaleFromSession(
string $language,
string $domain,
string $encoding,
string $path,
?string $SESSION_DEFAULT_LOCALE,
?string $SESSION_DEFAULT_CHARSET,
?string $SESSION_DEFAULT_DOMAIN,
?string $SESSION_LOCALE_PATH,
array $expected,
): void {
$return_lang_settings = [];
global $_SESSION;
// set override
if ($SESSION_DEFAULT_LOCALE !== null) {
$_SESSION['DEFAULT_LOCALE'] = $SESSION_DEFAULT_LOCALE;
}
if ($SESSION_DEFAULT_CHARSET !== null) {
$_SESSION['DEFAULT_CHARSET'] = $SESSION_DEFAULT_CHARSET;
}
if ($SESSION_DEFAULT_DOMAIN !== null) {
$_SESSION['DEFAULT_DOMAIN'] = $SESSION_DEFAULT_DOMAIN;
}
if ($SESSION_LOCALE_PATH !== null) {
$_SESSION['LOCALE_PATH'] = $SESSION_LOCALE_PATH;
}
$return_lang_settings = \CoreLibs\Language\GetLocale::setLocaleFromSession(
$language,
$domain,
$encoding,
$path
);
// print "RETURN: " . print_r($return_lang_settings, true) . "\n";
foreach (
[
'locale', 'lang', 'domain', 'encoding', 'path'
] as $key
) {
$value = $expected[$key];
if (
!empty($value) &&
strpos($value, "/") === 0
) {
// this is regex
$this->assertMatchesRegularExpression(
$value,
$return_lang_settings[$key] ?? '',
'assert regex failed for ' . $key
);
} else {
// assert equal
$this->assertEquals(
$value,
$return_lang_settings[$key],
'assert equal failed for ' . $key
);
}
}
// unset all vars
$_SESSION = [];
unset($GLOBALS['OVERRIDE_LANG']);
}
}
// __END__

View File

@@ -22,37 +22,16 @@ final class CoreLibsLanguageL10nTest extends TestCase
*/ */
public static function setUpBeforeClass(): void public static function setUpBeforeClass(): void
{ {
// default web page encoding setting // for deprecation test only, will be removed
if (!defined('DEFAULT_ENCODING')) {
define('DEFAULT_ENCODING', 'UTF-8');
}
if (!defined('DEFAULT_LOCALE')) {
// default lang + encoding
define('DEFAULT_LOCALE', 'en_US.UTF-8');
}
// site
if (!defined('SITE_ENCODING')) {
define('SITE_ENCODING', DEFAULT_ENCODING);
}
if (!defined('SITE_LOCALE')) {
define('SITE_LOCALE', DEFAULT_LOCALE);
}
// just set
if (!defined('BASE')) { if (!defined('BASE')) {
define('BASE', str_replace('/configs', '', __DIR__) . DIRECTORY_SEPARATOR); define('BASE', str_replace(DIRECTORY_SEPARATOR . 'configs', '', __DIR__) . DIRECTORY_SEPARATOR);
} }
if (!defined('INCLUDES')) { if (!defined('INCLUDES')) {
define('INCLUDES', 'includes' . DIRECTORY_SEPARATOR); define('INCLUDES', 'includes' . DIRECTORY_SEPARATOR);
} }
if (!defined('LANG')) {
define('LANG', 'lang' . DIRECTORY_SEPARATOR);
}
if (!defined('LOCALE')) { if (!defined('LOCALE')) {
define('LOCALE', 'locale' . DIRECTORY_SEPARATOR); define('LOCALE', 'locale' . DIRECTORY_SEPARATOR);
} }
if (!defined('CONTENT_PATH')) {
define('CONTENT_PATH', 'frontend' . DIRECTORY_SEPARATOR);
}
} }
/** /**
@@ -105,77 +84,163 @@ final class CoreLibsLanguageL10nTest extends TestCase
{ {
return [ return [
// 0: locale // 0: locale
// 1: domain // 1: encoding
// 2: encoding // 2: domain
// 3: path // 3: path
// 4: locale expected // 4: locale expected
// 5: locale set expected // 5: locale set expected
// 6: domain exepcted // 6: lang expected
// 7: context (null for none) // 7: lang short expected
// 8: test string in // 8: encoding expected
// 9: test translated // 9: domain exepcted
// 10: context (null for none)
// 11: test string in
// 12: test translated
// 13: deprecation message (until removed)
// new style load // new style load
'gettext load en' => [ 'gettext load en' => [
'en_US.UTF-8', 'en_US.UTF-8',
'UTF-8',
'frontend', 'frontend',
__DIR__ . 'includes/locale/', __DIR__ . DIRECTORY_SEPARATOR . 'includes' . DIRECTORY_SEPARATOR . 'locale' . DIRECTORY_SEPARATOR,
// // 4, 5, 6, 7, 8, 9
'en_US.UTF-8', 'en_US.UTF-8',
'en_US', 'en_US',
'en_US',
'en',
'UTF-8',
'frontend', 'frontend',
// 10
null, null,
// 11, 12
'Original', 'Original',
'Translated frontend en_US', 'Translated frontend en_US',
// 13
null,
], ],
'gettext load en' => [ 'gettext load en' => [
'en_US.UTF-8', 'en_US.UTF-8',
'UTF-8',
'frontend', 'frontend',
__DIR__ . 'includes/locale/', __DIR__ . DIRECTORY_SEPARATOR . 'includes' . DIRECTORY_SEPARATOR . 'locale' . DIRECTORY_SEPARATOR,
// //
'en_US.UTF-8', 'en_US.UTF-8',
'en_US', 'en_US',
'en_US',
'en',
'UTF-8',
'frontend', 'frontend',
//
'context', 'context',
//
'Original', 'Original',
'Original context frontend en_US', 'Original context frontend en_US',
//
null,
], ],
'gettext load ja' => [ 'gettext load ja' => [
'ja_JP.UTF-8', 'ja_JP.UTF-8',
'UTF-8',
'admin', 'admin',
__DIR__ . 'includes/locale/', __DIR__ . DIRECTORY_SEPARATOR . 'includes' . DIRECTORY_SEPARATOR . 'locale' . DIRECTORY_SEPARATOR,
// //
'ja_JP.UTF-8', 'ja_JP.UTF-8',
'ja_JP', 'ja_JP',
'ja_JP',
'ja',
'UTF-8',
'admin', 'admin',
//
null, null,
//
'Original', 'Original',
'Translated admin ja_JP', 'Translated admin ja_JP',
//
null,
], ],
// mixed path and domain // load short locale with different encoding
'mixed path and domain' => [ 'gettext load short ja no encoding' => [
'ja',
'SJIS',
'admin',
__DIR__ . DIRECTORY_SEPARATOR . 'includes' . DIRECTORY_SEPARATOR . 'locale' . DIRECTORY_SEPARATOR,
//
'ja',
'ja',
'ja',
'ja',
'SJIS',
'admin',
//
null,
//
'Original',
'Translated admin ja_JP',
//
null,
],
// mixed path and domain [DEPRECATED]
'mixed path and domain [DEPRECATED]' => [
'en_US.UTF-8', 'en_US.UTF-8',
__DIR__ . 'includes/locale/', 'UTF-8',
__DIR__ . DIRECTORY_SEPARATOR . 'includes' . DIRECTORY_SEPARATOR . 'locale' . DIRECTORY_SEPARATOR,
'frontend', 'frontend',
// //
'en_US.UTF-8', 'en_US.UTF-8',
'en_US', 'en_US',
'en_US',
'en',
'UTF-8',
'frontend', 'frontend',
//
'context', 'context',
//
'Original', 'Original',
'Original context frontend en_US', 'Original context frontend en_US',
//
'L10n constructor parameter switch is no longer supported. domain is 2nd, path is 3rd parameter'
],
// unset path
'unset path with locale and domain [DEPRECATED]' => [
'ja_JP.UTF-8',
'UTF-8',
'admin',
null,
//
'ja_JP.UTF-8',
'ja_JP',
'ja_JP',
'ja',
'UTF-8',
'admin',
//
null,
//
'Original',
'Translated admin ja_JP',
//
'Empty path parameter is no longer allowed if locale and domain are set',
], ],
// null set // null set
'empty load new ' => [ 'empty load new ' => [
'', '',
'', '',
'', '',
'',
// //
'', '',
'', '',
'', '',
'',
'', // unset on empty call
'',
//
null, null,
//
'Original', 'Original',
'Original', 'Original',
//
null,
] ]
]; ];
} }
@@ -188,37 +253,62 @@ final class CoreLibsLanguageL10nTest extends TestCase
* @testdox check l10n init with Locale $locale, Path $path, Domain $domain, Legacy: $legacy with $context [$_dataName] * @testdox check l10n init with Locale $locale, Path $path, Domain $domain, Legacy: $legacy with $context [$_dataName]
* *
* @param string|null $locale * @param string|null $locale
* @param string|null $encoding
* @param string|null $domain * @param string|null $domain
* @param string|null $path * @param string|null $path
* @param string $locale_expected * @param string $locale_expected
* @param string $locale_set_expected * @param string $locale_set_expected
* @param string $lang_expected
* @param string $lang_short_expected
* @param string $encoding_expected
* @param string $domain_expected * @param string $domain_expected
* @param ?string $context * @param string|null $context
* @param string $original * @param string $original
* @param string $translated * @param string $translated
* @param string|null $deprecation_message
* @return void * @return void
*/ */
public function testL10nObject( public function testL10nObject(
?string $locale, ?string $locale,
?string $encoding,
?string $domain, ?string $domain,
?string $path, ?string $path,
string $locale_expected, string $locale_expected,
string $locale_set_expected, string $locale_set_expected,
string $lang_expected,
string $lang_short_expected,
string $encoding_expected,
string $domain_expected, string $domain_expected,
?string $context, ?string $context,
string $original, string $original,
string $translated string $translated,
?string $deprecation_message
): void { ): void {
if ($deprecation_message !== null) {
set_error_handler(
static function (int $errno, string $errstr): never {
throw new \Exception($errstr, $errno);
},
E_USER_DEPRECATED
);
// catch this with the message
$this->expectExceptionMessage($deprecation_message);
}
if ($locale === null) { if ($locale === null) {
$l10n = new \CoreLibs\Language\L10n(); $l10n = new \CoreLibs\Language\L10n();
} elseif ($domain === null) { } elseif ($domain === null) {
// deprecated, locale + domain must be set, handled like empty calls
$l10n = new \CoreLibs\Language\L10n($locale); $l10n = new \CoreLibs\Language\L10n($locale);
} elseif ($path === null) { } elseif ($path === null) {
// deprecated, path must be set, will thow DEPRECATION error, handled like empty
$l10n = new \CoreLibs\Language\L10n($locale, $domain); $l10n = new \CoreLibs\Language\L10n($locale, $domain);
} else { } elseif ($encoding === null) {
// if encoding not found will be UTF-8
$l10n = new \CoreLibs\Language\L10n($locale, $domain, $path); $l10n = new \CoreLibs\Language\L10n($locale, $domain, $path);
} else {
$l10n = new \CoreLibs\Language\L10n($locale, $domain, $path, $encoding);
} }
// print "LOC: " . $locale . ", " . $l10n->getLocale() . ", " . $locale_expected . "\n"; restore_error_handler();
// print "MO: " . $l10n->getMoFile() . "\n"; // print "MO: " . $l10n->getMoFile() . "\n";
$this->assertEquals( $this->assertEquals(
$locale_expected, $locale_expected,
@@ -248,6 +338,20 @@ final class CoreLibsLanguageL10nTest extends TestCase
'Translated string assert failed in context: ' . $context 'Translated string assert failed in context: ' . $context
); );
} }
// test get locel as array
$locale = $l10n->getLocaleAsArray();
$this->assertEquals(
[
'locale' => $locale_expected,
'lang' => $lang_expected,
'lang_short' => $lang_short_expected,
'domain' => $domain_expected,
'encoding' => $encoding_expected,
'path' => $path
],
$locale,
'getLocaleAsArray mismatch'
);
} }
// l10nReloadMOfile and getTranslator // l10nReloadMOfile and getTranslator
@@ -283,7 +387,7 @@ final class CoreLibsLanguageL10nTest extends TestCase
// set 0-2 // set 0-2
'en_US.UTF-8', 'en_US.UTF-8',
'frontend', 'frontend',
__DIR__ . 'includes/locale/', __DIR__ . DIRECTORY_SEPARATOR . 'includes' . DIRECTORY_SEPARATOR . 'locale' . DIRECTORY_SEPARATOR,
// status 3 // status 3
false, false,
// to translate 4 // to translate 4
@@ -296,7 +400,7 @@ final class CoreLibsLanguageL10nTest extends TestCase
// set new 8-10 // set new 8-10
'ja_JP.UTF-8', 'ja_JP.UTF-8',
'frontend', 'frontend',
__DIR__ . 'includes/locale/', __DIR__ . DIRECTORY_SEPARATOR . 'includes' . DIRECTORY_SEPARATOR . 'locale' . DIRECTORY_SEPARATOR,
// status new 11 // status new 11
false, false,
// check new setter 12-14 // check new setter 12-14
@@ -322,7 +426,7 @@ final class CoreLibsLanguageL10nTest extends TestCase
// set new 8-10 // set new 8-10
'en_US.UTF-8', 'en_US.UTF-8',
'frontend', 'frontend',
__DIR__ . 'includes/locale/', __DIR__ . DIRECTORY_SEPARATOR . 'includes' . DIRECTORY_SEPARATOR . 'locale' . DIRECTORY_SEPARATOR,
// status new 11 // status new 11
false, false,
// check new setter 12-14 // check new setter 12-14
@@ -387,12 +491,8 @@ final class CoreLibsLanguageL10nTest extends TestCase
string $domain_expected_b, string $domain_expected_b,
string $translated_b string $translated_b
): void { ): void {
if ($locale === null) { if ($locale === null || $domain === null || $path === null) {
$l10n = new \CoreLibs\Language\L10n(); $l10n = new \CoreLibs\Language\L10n();
} elseif ($domain === null) {
$l10n = new \CoreLibs\Language\L10n($locale);
} elseif ($path === null) {
$l10n = new \CoreLibs\Language\L10n($locale, $domain);
} else { } else {
$l10n = new \CoreLibs\Language\L10n($locale, $domain, $path); $l10n = new \CoreLibs\Language\L10n($locale, $domain, $path);
} }
@@ -494,16 +594,16 @@ final class CoreLibsLanguageL10nTest extends TestCase
{ {
return [ return [
// 0: locale // 0: locale
// 1: path // 1: domain
// 2: domain // 2: path
// 3: context (null for none) // 3: context (null for none)
// 4: single string // 4: single string
// 5: plural string // 5: plural string
// 6: array for each n value expected string // 6: array for each n value expected string
'plural text en' => [ 'plural text en' => [
'en_US', 'en_US',
__DIR__ . 'includes/locale/',
'admin', 'admin',
__DIR__ . DIRECTORY_SEPARATOR . 'includes' . DIRECTORY_SEPARATOR . 'locale' . DIRECTORY_SEPARATOR,
// context // context
null, null,
// text single/multi in // text single/multi in
@@ -518,8 +618,8 @@ final class CoreLibsLanguageL10nTest extends TestCase
], ],
'plural text context en' => [ 'plural text context en' => [
'en_US', 'en_US',
__DIR__ . 'includes/locale/',
'admin', 'admin',
__DIR__ . DIRECTORY_SEPARATOR . 'includes' . DIRECTORY_SEPARATOR . 'locale' . DIRECTORY_SEPARATOR,
// context // context
'context', 'context',
// text single/multi in // text single/multi in
@@ -544,8 +644,8 @@ final class CoreLibsLanguageL10nTest extends TestCase
* @testdox plural string test for locale $locale and domain $domain with $context [$_dataName] * @testdox plural string test for locale $locale and domain $domain with $context [$_dataName]
* *
* @param string $locale * @param string $locale
* @param string $path
* @param string $domain * @param string $domain
* @param string $path
* @param ?string $context * @param ?string $context
* @param string $original_single * @param string $original_single
* @param string $original_plural * @param string $original_plural
@@ -555,8 +655,8 @@ final class CoreLibsLanguageL10nTest extends TestCase
public function testNgettext( public function testNgettext(
// config 0-3 // config 0-3
string $locale, string $locale,
string $path,
string $domain, string $domain,
string $path,
// context string // context string
?string $context, ?string $context,
// input strings // input strings
@@ -565,7 +665,7 @@ final class CoreLibsLanguageL10nTest extends TestCase
// expected // expected
array $expected_strings array $expected_strings
): void { ): void {
$l10n = new \CoreLibs\Language\L10n($locale, $path, $domain, false); $l10n = new \CoreLibs\Language\L10n($locale, $domain, $path);
foreach ($expected_strings as $n => $expected) { foreach ($expected_strings as $n => $expected) {
if (empty($context)) { if (empty($context)) {
@@ -981,7 +1081,7 @@ final class CoreLibsLanguageL10nTest extends TestCase
'standard en' => [ 'standard en' => [
'en_US.UTF-8', 'en_US.UTF-8',
'frontend', 'frontend',
__DIR__ . 'includes/locale/', __DIR__ . DIRECTORY_SEPARATOR . 'includes' . DIRECTORY_SEPARATOR . 'locale' . DIRECTORY_SEPARATOR,
'UTF-8', 'UTF-8',
'Original', 'Original',
'Translated frontend en_US', 'Translated frontend en_US',
@@ -989,7 +1089,7 @@ final class CoreLibsLanguageL10nTest extends TestCase
'standard ja' => [ 'standard ja' => [
'ja_JP.UTF-8', 'ja_JP.UTF-8',
'admin', 'admin',
__DIR__ . 'includes/locale/', __DIR__ . DIRECTORY_SEPARATOR . 'includes' . DIRECTORY_SEPARATOR . 'locale' . DIRECTORY_SEPARATOR,
'UTF-8', 'UTF-8',
'Original', 'Original',
'Translated admin ja_JP', 'Translated admin ja_JP',
@@ -1030,6 +1130,7 @@ final class CoreLibsLanguageL10nTest extends TestCase
_textdomain($domain); _textdomain($domain);
_bindtextdomain($domain, $path); _bindtextdomain($domain, $path);
_bind_textdomain_codeset($domain, $encoding); _bind_textdomain_codeset($domain, $encoding);
$this->assertEquals( $this->assertEquals(
$translated, $translated,
__($original), __($original),

View File

@@ -0,0 +1 @@
ja_JP

Some files were not shown because too many files have changed in this diff Show More