diff --git a/.travis.yml b/.travis.yml
index 8e8fb5782..934d9ef7b 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -21,6 +21,14 @@ matrix:
php: '7.0'
- env: CHECK=phpcs
php: '5.6'
+ - env: CHECK=syntax
+ php: 'nightly'
+ - env: CHECK=syntax
+ php: '7.3'
+ - env: CHECK=syntax
+ php: '7.0'
+ - env: CHECK=syntax
+ php: '5.6'
allow_failures:
- php: nightly
@@ -52,3 +60,4 @@ script:
# also see: modules/test/application/clicommands/PhpCommand.php
- 'if [ "$CHECK" = phpcs ]; then php phpcs.phar; fi'
- 'if [ "$CHECK" = phpunit ]; then php phpunit.phar -c modules/test/phpunit.xml --verbose; fi'
+ - 'if [ "$CHECK" = syntax ]; then php test/check-syntax.php -e "^(\./)?vendor/" -e Icinga/Util/String.php; fi'
diff --git a/phpcs.xml b/phpcs.xml
index e04ad72f8..3a33b6e38 100644
--- a/phpcs.xml
+++ b/phpcs.xml
@@ -8,6 +8,7 @@
test/
vendor/*
+ test/*.php
application/fonts/fontello-ifont/*
diff --git a/test/check-syntax.php b/test/check-syntax.php
new file mode 100755
index 000000000..b8f4afd66
--- /dev/null
+++ b/test/check-syntax.php
@@ -0,0 +1,145 @@
+#!/usr/bin/env php
+&1 >/dev/null", $output, $rc);
+
+ if (! empty($output) || $rc != 0) {
+ stdout('E', '91');
+
+ foreach ($output as $line) {
+ // remove own name from text
+ $line = preg_replace('~ in ' . preg_quote($path) . '~i', '', $line);
+
+ $errors[$path][] = $line;
+ }
+ } else {
+ stdout('.');
+ }
+}
+
+function usage()
+{
+ printf("Usage: %s [--verbose] [--exclude file-regex] [path]\n\n", $_SERVER['argv'][0]);
+}
+
+function main($argv)
+{
+ $fileCount = 0;
+ $verbose = false;
+ $errors = [];
+ $excludes = [];
+ $searchPaths = [];
+
+ for ($i = 1; $i < count($argv); $i++) {
+ $arg = $argv[$i];
+ switch ($arg) {
+ case '-h':
+ case '--help':
+ usage();
+ return 1;
+ case '-v':
+ case '--verbose':
+ $verbose = true;
+ break;
+ case '-e':
+ case '--exclude':
+ $excludes[] = $argv[++$i];
+ break;
+ default:
+ if (substr($arg, 0, 1) === '-') {
+ stderr("Unknown argument: $arg");
+ return 1;
+ } else {
+ $searchPaths[] = $arg;
+ }
+ }
+ }
+
+ if (empty($searchPaths)) {
+ $searchPaths = ['.'];
+ }
+
+ $files = [];
+ foreach ($searchPaths as $basePath) {
+ findPhpFiles($basePath, $files);
+ }
+
+ foreach ($files as $file) {
+ foreach ($excludes as $exclude) {
+ if (preg_match("~$exclude~", $file)) {
+ continue 2;
+ }
+ }
+
+ $fileCount++;
+
+ if ($verbose) {
+ printf("%s\n", $file);
+ }
+ checkFile($file, $errors);
+ }
+
+ $errorCount = count($errors);
+ if ($fileCount === 0) {
+ stderr("error: No files found!\n");
+ return 2;
+ } elseif ($errorCount > 0) {
+ stdout("\n");
+
+ foreach ($errors as $file => $errList) {
+ stderr("\n$file\n " . join("\n ", $errList) . "\n");
+ }
+
+ stderr(sprintf("\nFound syntax errors in %d of %d files! \n", $errorCount, $fileCount));
+ return 1;
+ } else {
+ stdout(sprintf("\n\nChecked %d files successfully! \n", $fileCount));
+ return 0;
+ }
+}
+
+exit(main($_SERVER['argv']));