Merge branch 'release/1.6.x' into 'main'

1.6.1 Release

See merge request kosit/validator!105
This commit is contained in:
Philip Helger 2026-02-05 12:53:43 +01:00
commit 82fdcabe3d
15 changed files with 506 additions and 66 deletions

6
.gitignore vendored
View file

@ -36,6 +36,7 @@ src/generated
.factorypath
.idea/
.settings/
.externalToolBuilders/
.vscode
*.code-workspace
*.xpr
@ -46,3 +47,8 @@ xrechnung
.DS_Store
andre*-simple.xml
somePrefix*.xml
# 2.0 stuff
api/
cli/
core/

View file

@ -1,8 +1,8 @@
image: maven:latest
variables:
BUILD_PROPS: "-Dbuild.revision=$CI_COMMIT_SHA -Dbuild.branch=$CI_COMMIT_REF_NAME -Dbuild.number=$CI_PIPELINE_IID -Dfile.encoding=UTF-8 -Dhttp.keepAlive=false -Dmaven.wagon.http.pool=false"
MAVEN_OPTS: "-Dmaven.repo.local=$CI_PROJECT_DIR/.m2/repository -Dorg.slf4j.simpleLogger.log.org.apache.maven.cli.transfer.Slf4jMavenTransferListener=WARN -Dorg.slf4j.simpleLogger.showDateTime=true -Djava.awt.headless=true"
MAVEN_OPTS: "-Dmaven.repo.local=$CI_PROJECT_DIR/.m2/repository -Dorg.slf4j.simpleLogger.log.org.apache.maven.cli.transfer.Slf4jMavenTransferListener=WARN -Dorg.slf4j.simpleLogger.showDateTime=true -Djava.awt.headless=true -Xmx6g"
MAVEN_CLI_OPTS: " --batch-mode --update-snapshots --errors --fail-at-end --show-version -s .mvn/settings.xml"
MAVEN_CLI_OPTS_CENTRAL: " --batch-mode --show-version -s .mvn/settings-maven-central.xml"
@ -15,6 +15,7 @@ cache:
paths:
- .m2/repository
# Basic Java build steps
.java:
stage: build
needs:
@ -32,11 +33,6 @@ cache:
- target/surefire-reports/*.xml
- target/failsafe-reports/*.xml
.java_extended:
extends: .java
rules:
- if: $CI_PIPELINE_SOURCE == "schedule"
java-11:
extends: .java
image: maven:3-eclipse-temurin-11-alpine
@ -54,10 +50,6 @@ java-11:
- target/surefire-reports/*.xml
- target/failsafe-reports/*.xml
java-11-openj9:
extends: .java_extended
image: maven:3-jdk-11-openj9
java-17:
extends: .java
image: maven:3-eclipse-temurin-17-alpine
@ -66,14 +58,29 @@ java-21:
extends: .java
image: maven:3-eclipse-temurin-21-alpine
java-24:
extends: .java_extended
image: maven:3-eclipse-temurin-24-alpine
java-25:
extends: .java
image: maven:3-eclipse-temurin-25-alpine
# Rare Java stuff
.java_extended:
extends: .java
rules:
- if: $CI_PIPELINE_SOURCE == "schedule"
# Note: the openj9 images don't exist for Java 17, 21 or 25
# Removed because the latest public image is 11.0.11 which is not comaptible to the Lombok requirement of 11.0.23
#java-11-openj9:
# extends: .java_extended
# image: maven:3-jdk-11-openj9
# Deploy Java 11 build on Maven Central
deploy-java-11-snapshot:
extends: java-11
script:
- mvn $MAVEN_CLI_OPTS_CENTRAL -P release-snapshot deploy
# Deploy Java 11 build to KoSIT repository (manually)
deploy:
stage: deploy
image: maven:3-eclipse-temurin-11-alpine
@ -81,18 +88,14 @@ deploy:
- job: java-11
script:
- export PROJECT_VERSION=$(mvn help:evaluate -Dexpression=project.version -q -DforceStdout)
- mvn $MAVEN_CLI_OPTS deploy:deploy-file -Dfile=target/validator-${PROJECT_VERSION}.zip -DgroupId=kosit -DartifactId=validator -Dclassifier="distribution" -Dversion=${PROJECT_VERSION} -Dpackaging=zip -DrepositoryId="gitlab-maven" -Durl=https://projekte.kosit.org/api/v4/projects/7/packages/maven
- mvn $MAVEN_CLI_OPTS deploy:deploy-file -Dfile=target/validator-${PROJECT_VERSION}.jar -DgroupId=kosit -DartifactId=validator -Dversion=${PROJECT_VERSION} -Dpackaging=jar -DrepositoryId="gitlab-maven" -Durl=https://projekte.kosit.org/api/v4/projects/7/packages/maven
- mvn $MAVEN_CLI_OPTS deploy:deploy-file -Dfile=target/validator-${PROJECT_VERSION}-javadoc.jar -DgroupId=kosit -DartifactId=validator -Dclassifier="javadoc" -Dversion=${PROJECT_VERSION} -Dpackaging=zip -DrepositoryId="gitlab-maven" -Durl=https://projekte.kosit.org/api/v4/projects/7/packages/maven
- mvn $MAVEN_CLI_OPTS deploy:deploy-file -Dfile=target/validator-${PROJECT_VERSION}-standalone.jar -DgroupId=kosit -DartifactId=validator -Dclassifier="standalone" -Dversion=${PROJECT_VERSION} -Dpackaging=jar -DrepositoryId="gitlab-maven" -Durl=https://projekte.kosit.org/api/v4/projects/7/packages/maven
- mvn $MAVEN_CLI_OPTS deploy:deploy-file -Dfile=target/validator-${PROJECT_VERSION}-sources.jar -DgroupId=kosit -DartifactId=validator -Dclassifier="sources" -Dversion=${PROJECT_VERSION} -Dpackaging=jar -DrepositoryId="gitlab-maven" -Durl=https://projekte.kosit.org/api/v4/projects/7/packages/maven
- mvn $MAVEN_CLI_OPTS deploy:deploy-file -Dfile=target/validator-${PROJECT_VERSION}.zip -DgroupId=kosit -DartifactId=validator -Dversion=${PROJECT_VERSION} -Dclassifier="distribution" -Dpackaging=zip -DrepositoryId="gitlab-maven" -Durl=https://projekte.kosit.org/api/v4/projects/7/packages/maven
- mvn $MAVEN_CLI_OPTS deploy:deploy-file -Dfile=target/validator-${PROJECT_VERSION}.jar -DgroupId=kosit -DartifactId=validator -Dversion=${PROJECT_VERSION} -Dpackaging=jar -DrepositoryId="gitlab-maven" -Durl=https://projekte.kosit.org/api/v4/projects/7/packages/maven
- mvn $MAVEN_CLI_OPTS deploy:deploy-file -Dfile=target/validator-${PROJECT_VERSION}-javadoc.jar -DgroupId=kosit -DartifactId=validator -Dversion=${PROJECT_VERSION} -Dclassifier="javadoc" -Dpackaging=zip -DrepositoryId="gitlab-maven" -Durl=https://projekte.kosit.org/api/v4/projects/7/packages/maven
- mvn $MAVEN_CLI_OPTS deploy:deploy-file -Dfile=target/validator-${PROJECT_VERSION}-standalone.jar -DgroupId=kosit -DartifactId=validator -Dversion=${PROJECT_VERSION} -Dclassifier="standalone" -Dpackaging=jar -DrepositoryId="gitlab-maven" -Durl=https://projekte.kosit.org/api/v4/projects/7/packages/maven
- mvn $MAVEN_CLI_OPTS deploy:deploy-file -Dfile=target/validator-${PROJECT_VERSION}-sources.jar -DgroupId=kosit -DartifactId=validator -Dversion=${PROJECT_VERSION} -Dclassifier="sources" -Dpackaging=jar -DrepositoryId="gitlab-maven" -Durl=https://projekte.kosit.org/api/v4/projects/7/packages/maven
when: manual
deploy-snapshot:
extends: java-11
script:
- mvn $MAVEN_CLI_OPTS_CENTRAL -P release-snapshot deploy
# Build Docker images and upload to KoSIT registry
create-build-image:
stage: deploy
image: docker:latest
@ -108,12 +111,22 @@ create-build-image:
changes:
- .mvn/createBuildImages.sh
# Run OWASP checks - expensive so only on main branch
owasp-check:
extends: .java
stage: test
image: maven:3-eclipse-temurin-21-alpine
needs: [ ]
# set job timeout to 1 hour - it's required when new rules are downloaded
timeout: 1h
variables:
RUNNER_SCRIPT_TIMEOUT: 1h
script:
- mvn $MAVEN_CLI_OPTS $BUILD_PROPS $CI_JOB_TIMESTAMP validate -Powasp-check
artifacts:
name: artifacts
reports:
codequality:
- target/dependency-check-report.html
rules:
- if: $CI_PIPELINE_SOURCE == "schedule"
- if: $CI_COMMIT_REF_NAME == "main"

View file

@ -6,8 +6,13 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/)
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
## Unreleased
## 1.6.1 - 2026-02-05
### Changed
- (CORE) [#106](https://projekte.kosit.org/kosit/validator/-/issues/106) The `match` element in `scenarios.xml` is required to have at least one character (per XSD change)
- (BUILD) [#176](https://projekte.kosit.org/kosit/validator/-/issues/176) The Maven Central deployed `pom.xml` properly includes runtime dependencies
- (BUILD) [#175](https://projekte.kosit.org/kosit/validator/-/issues/175) The `.zip` file created from `maven-assembly-plugin` no longer contains the standalone validator, which reduces its size to 50%
## 1.6.0 - 2025-11-07

22
pom.xml
View file

@ -6,7 +6,7 @@
<groupId>org.kosit</groupId>
<artifactId>validator</artifactId>
<version>1.6.1-SNAPSHOT</version>
<version>1.6.2-SNAPSHOT</version>
<description>KoSIT XML Validator against XSD and Schematron based on defined scenarios.</description>
<developers>
@ -80,17 +80,16 @@
<version>${version.lombok}</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>net.sf.saxon</groupId>
<artifactId>Saxon-HE</artifactId>
<version>${version.saxon-he}</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-api</artifactId>
<version>${version.slf4j}</version>
</dependency>
<dependency>
<groupId>net.sf.saxon</groupId>
<artifactId>Saxon-HE</artifactId>
<version>${version.saxon-he}</version>
</dependency>
<dependency>
<groupId>info.picocli</groupId>
<artifactId>picocli</artifactId>
@ -180,7 +179,7 @@
<plugin>
<groupId>org.sonatype.central</groupId>
<artifactId>central-publishing-maven-plugin</artifactId>
<version>0.8.0</version>
<version>0.10.0</version>
<extensions>true</extensions>
<configuration>
<publishingServerId>central</publishingServerId>
@ -275,15 +274,15 @@
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-shade-plugin</artifactId>
<version>3.6.0</version>
<version>3.6.1</version>
<executions>
<execution>
<id>jdk11+</id>
<phase>package</phase>
<goals>
<goal>shade</goal>
</goals>
<configuration>
<createDependencyReducedPom>false</createDependencyReducedPom>
<shadedArtifactAttached>true</shadedArtifactAttached>
<shadedClassifierName>standalone</shadedClassifierName>
<transformers>
@ -626,7 +625,8 @@
<suppressionFiles>
<suppressionFile>${project.basedir}/owasp-suppressions.xml</suppressionFile>
</suppressionFiles>
<!-- ref to CI CD variable -->
<nvdApiKey>${NVD_API_KEY}</nvdApiKey>
</configuration>
<executions>
<execution>

View file

@ -20,6 +20,10 @@
<includes>
<include>validator-*.jar</include>
</includes>
<!-- excludes always win over includes if both patterns match -->
<excludes>
<exclude>*standalone.jar</exclude>
</excludes>
</fileSet>
</fileSets>

View file

@ -47,7 +47,7 @@ public class CollectingErrorEventHandler implements ValidationEventHandler, Erro
private static final int DEFAULT_ABORT_COUNT = 50;
private static final int stopProcessCount = DEFAULT_ABORT_COUNT;
private final int stopProcessCount = DEFAULT_ABORT_COUNT;
private final List<XMLSyntaxError> errors = new ArrayList<>();

View file

@ -23,9 +23,6 @@ import javax.xml.transform.dom.DOMSource;
import org.oclc.purl.dsdl.svrl.SchematronOutput;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import de.kosit.validationtool.impl.CollectingErrorEventHandler;
import de.kosit.validationtool.impl.ConversionService;
import de.kosit.validationtool.impl.Scenario;
@ -33,7 +30,8 @@ import de.kosit.validationtool.impl.Scenario.Transformation;
import de.kosit.validationtool.model.reportInput.CreateReportInput;
import de.kosit.validationtool.model.reportInput.ValidationResultsSchematron;
import de.kosit.validationtool.model.reportInput.ValidationResultsSchematron.Results;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import net.sf.saxon.dom.NodeOverNodeInfo;
import net.sf.saxon.s9api.SaxonApiException;
import net.sf.saxon.s9api.XdmDestination;
@ -71,6 +69,11 @@ public class SchematronValidationAction implements CheckAction {
transformer.setInitialContextNode(document);
transformer.transform();
// If we reach this line, it means no Exception was thrown :-)
if (e.hasErrors()) {
log.error("XSLT errors found: " + e.getErrorDescription());
}
final ValidationResultsSchematron.Results r = new ValidationResultsSchematron.Results();
r.setSchematronOutput(this.conversionService.readDocument(
new DOMSource(NodeOverNodeInfo.wrap(result.getXdmNode().getUnderlyingNode()).getOwnerDocument()),

View file

@ -1,21 +1,4 @@
<?xml version="1.0" encoding="UTF-8" ?>
<!--
~ Copyright 2017-2022 Koordinierungsstelle für IT-Standards (KoSIT)
~
~ Licensed under the Apache License, Version 2.0 (the "License");
~ you may not use this file except in compliance with the License.
~ You may obtain a copy of the License at
~
~ http://www.apache.org/licenses/LICENSE-2.0
~
~ Unless required by applicable law or agreed to in writing, software
~ distributed under the License is distributed on an "AS IS" BASIS,
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
~ See the License for the specific language governing permissions and
~ limitations under the License.
-->
<!-- $Id$ -->
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:s="http://www.xoev.de/de/validator/framework/1/scenarios" targetNamespace="http://www.xoev.de/de/validator/framework/1/scenarios" version="1.1.0" elementFormDefault="qualified" attributeFormDefault="unqualified">
<xs:element name="scenarios">
@ -72,13 +55,19 @@
<xs:simpleType name="Tokens">
<xs:list itemType="xs:token" />
</xs:simpleType>
<xs:simpleType name="NonEmptyString">
<xs:restriction base="xs:string">
<xs:minLength value="1"/>
</xs:restriction>
</xs:simpleType>
<xs:complexType name="ScenarioType">
<xs:sequence>
<xs:element name="name" type="xs:token" />
<xs:element minOccurs="0" name="description" type="s:DescriptionType" />
<xs:element minOccurs="0" maxOccurs="unbounded" name="namespace" type="s:NamespaceType" />
<xs:element name="match" type="xs:string" />
<xs:element name="match" type="s:NonEmptyString" />
<xs:element name="validateWithXmlSchema" type="s:ValidateWithXmlSchema" />
<xs:element name="validateWithSchematron" maxOccurs="unbounded" minOccurs="0" type="s:ValidateWithSchematron" />
<xs:element name="createReport" type="s:CreateReportType" minOccurs="0"/>
@ -138,3 +127,18 @@
</xs:simpleContent>
</xs:complexType>
</xs:schema>
<!--
~ Copyright 2017-2026 Koordinierungsstelle für IT-Standards (KoSIT)
~
~ Licensed under the Apache License, Version 2.0 (the "License");
~ you may not use this file except in compliance with the License.
~ You may obtain a copy of the License at
~
~ http://www.apache.org/licenses/LICENSE-2.0
~
~ Unless required by applicable law or agreed to in writing, software
~ distributed under the License is distributed on an "AS IS" BASIS,
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
~ See the License for the specific language governing permissions and
~ limitations under the License.
-->

View file

@ -139,6 +139,15 @@ public class CommandlineApplicationTest {
assertThat(CommandLine.getErrorOutput()).contains(RESULT_OUTPUT);
}
@Test
public void testValidMinimalConfigurationXSLTRuntimeError() {
final String[] args = { "-s", Paths.get(Simple.SCENARIOS_XSLT_RUNTIME_ERROR).toString(), "-h", "-o",
this.output.toAbsolutePath().toString(), "--serialize-report-input",
Paths.get(Simple.SIMPLE_XSLT_RUNTIME_ERROR).toString() };
CommandLineApplication.mainProgram(args);
assertThat(CommandLine.getErrorOutput()).contains(RESULT_OUTPUT);
}
@Test
public void testValidNamingConfiguration() {
final String[] args = { "-s", Paths.get(Simple.SCENARIOS).toString(), "-r", Paths.get(Simple.REPOSITORY_URI).toString(),
@ -159,7 +168,7 @@ public class CommandlineApplicationTest {
@Test
public void testValidDirectoryInput() {
final String[] args = { "-s", Paths.get(Simple.SCENARIOS).toString(), "-o", this.output.toString(), "-r",
Paths.get(Simple.REPOSITORY_URI).toString(), Paths.get(Simple.EXAMPLES).toString() };
Paths.get(Simple.REPOSITORY_URI).toString(), Paths.get(Simple.INPUT).toString() };
CommandLineApplication.mainProgram(args);
assertThat(CommandLine.getErrorOutput()).contains("Processing 9 object(s) completed");
}

View file

@ -49,15 +49,18 @@ public class Helper {
public static final URI ROOT = EXAMPLES_DIR.resolve("simple/");
public static final URI EXAMPLES = ROOT.resolve("input/");
public static final URI INPUT = ROOT.resolve("input/");
public static final URI SIMPLE_VALID = ROOT.resolve("input/simple.xml");
public static final URI SIMPLE_XSLT_RUNTIME_ERROR = EXAMPLES_DIR
.resolve("invalid/xslt-runtime-error/input/simple-xslt-runtime-error.xml");
public static final URI FOO = ROOT.resolve("input/foo.xml");
public static final URI FOO_SCHEMATRON_INVALID = EXAMPLES.resolve("foo-schematron-invalid.xml");
public static final URI FOO_SCHEMATRON_INVALID = INPUT.resolve("foo-schematron-invalid.xml");
public static final URI FOO_CUSTOM_LEVEL_ERROR = EXAMPLES.resolve("foo-custom-level-error.xml");
public static final URI FOO_CUSTOM_LEVEL_ERROR = INPUT.resolve("foo-custom-level-error.xml");
public static final URI REJECTED = ROOT.resolve("input/withManualReject.xml");
@ -65,6 +68,9 @@ public class Helper {
public static final URI SCENARIOS_WITH_RELATIVE_PATHS = ROOT.resolve("scenarios-with-relative-paths.xml");
public static final URI SCENARIOS_XSLT_RUNTIME_ERROR = EXAMPLES_DIR
.resolve("invalid/xslt-runtime-error/scenarios-with-xslt-runtime-error.xml");
public static final URI OTHER_SCENARIOS = ROOT.resolve("otherScenarios.xml");
public static final URI ERROR_SCENARIOS = ROOT.resolve("scenarios-with-errors.xml");
@ -101,6 +107,7 @@ public class Helper {
public static class Invalid {
// Is the typo in the name on purpose???
public static final URI ROOT = EXAMPLES_DIR.resolve("invaid/");
public static final URI SCENARIOS = ROOT.resolve("scenarios.xml");

View file

@ -0,0 +1,23 @@
<?xml version="1.0" encoding="UTF-8"?>
<simple xmlns="http://validator.kosit.de/test-sample">
<inner>abc</inner>
<inner>def</inner>
<content>
<IDontCare/>
</content>
</simple>
<!--
~ Copyright 2017-2026 Koordinierungsstelle für IT-Standards (KoSIT)
~
~ Licensed under the Apache License, Version 2.0 (the "License");
~ you may not use this file except in compliance with the License.
~ You may obtain a copy of the License at
~
~ http://www.apache.org/licenses/LICENSE-2.0
~
~ Unless required by applicable law or agreed to in writing, software
~ distributed under the License is distributed on an "AS IS" BASIS,
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
~ See the License for the specific language governing permissions and
~ limitations under the License.
-->

View file

@ -0,0 +1,44 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
~ Copyright 2017-2022 Koordinierungsstelle für IT-Standards (KoSIT)
~
~ Licensed under the Apache License, Version 2.0 (the "License");
~ you may not use this file except in compliance with the License.
~ You may obtain a copy of the License at
~
~ http://www.apache.org/licenses/LICENSE-2.0
~
~ Unless required by applicable law or agreed to in writing, software
~ distributed under the License is distributed on an "AS IS" BASIS,
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
~ See the License for the specific language governing permissions and
~ limitations under the License.
-->
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:in="http://www.xoev.de/de/validator/framework/1/createreportinput"
exclude-result-prefixes="xs"
version="2.0">
<xsl:output method="xml" indent="yes" />
<xsl:param name="input-document" as="document-node(element())" required="yes" />
<xsl:template match="in:createReportInput">
<report xmlns="http://validator.kosit.de/test-report">
<input>
<xsl:copy-of select="$input-document" />
</input>
<result>
<xsl:copy-of select="." />
</result>
<text>
<xsl:value-of select="unparsed-text('some.txt','UTF-8')" />
</text>
</report>
</xsl:template>
</xsl:stylesheet>

View file

@ -0,0 +1,231 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
~ Copyright 2017-2022 Koordinierungsstelle für IT-Standards (KoSIT)
~
~ Licensed under the Apache License, Version 2.0 (the "License");
~ you may not use this file except in compliance with the License.
~ You may obtain a copy of the License at
~
~ http://www.apache.org/licenses/LICENSE-2.0
~
~ Unless required by applicable law or agreed to in writing, software
~ distributed under the License is distributed on an "AS IS" BASIS,
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
~ See the License for the specific language governing permissions and
~ limitations under the License.
-->
<xsl:stylesheet
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:s="http://validator.kosit.de/test-sample"
version="2.0"><!--Implementers: please note that overriding process-prolog or process-root is
the preferred method for meta-stylesheets to use where possible. -->
<xsl:param name="archiveDirParameter" />
<xsl:param name="archiveNameParameter" />
<xsl:param name="fileNameParameter" />
<xsl:param name="fileDirParameter" />
<xsl:variable name="document-uri">
<xsl:value-of select="document-uri(/)" />
</xsl:variable>
<!--PHASES-->
<!--PROLOG-->
<xsl:output xmlns:svrl="http://purl.oclc.org/dsdl/svrl"
method="xml"
omit-xml-declaration="no"
standalone="yes"
indent="yes" />
<!--XSD TYPES FOR XSLT2-->
<!--KEYS AND FUNCTIONS-->
<!--DEFAULT RULES-->
<!--MODE: SCHEMATRON-SELECT-FULL-PATH-->
<!--This mode can be used to generate an ugly though full XPath for locators-->
<xsl:template match="*" mode="schematron-select-full-path">
<xsl:apply-templates select="." mode="schematron-get-full-path" />
</xsl:template>
<!--MODE: SCHEMATRON-FULL-PATH-->
<!--This mode can be used to generate an ugly though full XPath for locators-->
<xsl:template match="*" mode="schematron-get-full-path">
<xsl:apply-templates select="parent::*" mode="schematron-get-full-path" />
<xsl:text>/</xsl:text>
<xsl:choose>
<xsl:when test="namespace-uri()=''">
<xsl:value-of select="name()" />
</xsl:when>
<xsl:otherwise>
<xsl:text>*:</xsl:text>
<xsl:value-of select="local-name()" />
<xsl:text>[namespace-uri()='</xsl:text>
<xsl:value-of select="namespace-uri()" />
<xsl:text>']</xsl:text>
</xsl:otherwise>
</xsl:choose>
<xsl:variable name="preceding"
select="count(preceding-sibling::*[local-name()=local-name(current()) and namespace-uri() = namespace-uri(current())])" />
<xsl:text>[</xsl:text>
<xsl:value-of select="1+ $preceding" />
<xsl:text>]</xsl:text>
</xsl:template>
<xsl:template match="@*" mode="schematron-get-full-path">
<xsl:apply-templates select="parent::*" mode="schematron-get-full-path" />
<xsl:text>/</xsl:text>
<xsl:choose>
<xsl:when test="namespace-uri()=''">@<xsl:value-of select="name()" />
</xsl:when>
<xsl:otherwise>
<xsl:text>@*[local-name()='</xsl:text>
<xsl:value-of select="local-name()" />
<xsl:text>' and namespace-uri()='</xsl:text>
<xsl:value-of select="namespace-uri()" />
<xsl:text>']</xsl:text>
</xsl:otherwise>
</xsl:choose>
</xsl:template>
<!--MODE: SCHEMATRON-FULL-PATH-2-->
<!--This mode can be used to generate prefixed XPath for humans-->
<xsl:template match="node() | @*" mode="schematron-get-full-path-2">
<xsl:for-each select="ancestor-or-self::*">
<xsl:text>/</xsl:text>
<xsl:value-of select="name(.)" />
<xsl:if test="preceding-sibling::*[name(.)=name(current())]">
<xsl:text>[</xsl:text>
<xsl:value-of select="count(preceding-sibling::*[name(.)=name(current())])+1" />
<xsl:text>]</xsl:text>
</xsl:if>
</xsl:for-each>
<xsl:if test="not(self::*)">
<xsl:text />/@<xsl:value-of select="name(.)" />
</xsl:if>
</xsl:template>
<!--MODE: SCHEMATRON-FULL-PATH-3-->
<!--This mode can be used to generate prefixed XPath for humans
(Top-level element has index)-->
<xsl:template match="node() | @*" mode="schematron-get-full-path-3">
<xsl:for-each select="ancestor-or-self::*">
<xsl:text>/</xsl:text>
<xsl:value-of select="name(.)" />
<xsl:if test="parent::*">
<xsl:text>[</xsl:text>
<xsl:value-of select="count(preceding-sibling::*[name(.)=name(current())])+1" />
<xsl:text>]</xsl:text>
</xsl:if>
</xsl:for-each>
<xsl:if test="not(self::*)">
<xsl:text />/@<xsl:value-of select="name(.)" />
</xsl:if>
</xsl:template>
<!--MODE: GENERATE-ID-FROM-PATH -->
<xsl:template match="/" mode="generate-id-from-path" />
<xsl:template match="text()" mode="generate-id-from-path">
<xsl:apply-templates select="parent::*" mode="generate-id-from-path" />
<xsl:value-of select="concat('.text-', 1+count(preceding-sibling::text()), '-')" />
</xsl:template>
<xsl:template match="comment()" mode="generate-id-from-path">
<xsl:apply-templates select="parent::*" mode="generate-id-from-path" />
<xsl:value-of select="concat('.comment-', 1+count(preceding-sibling::comment()), '-')" />
</xsl:template>
<xsl:template match="processing-instruction()" mode="generate-id-from-path">
<xsl:apply-templates select="parent::*" mode="generate-id-from-path" />
<xsl:value-of select="concat('.processing-instruction-', 1+count(preceding-sibling::processing-instruction()), '-')" />
</xsl:template>
<xsl:template match="@*" mode="generate-id-from-path">
<xsl:apply-templates select="parent::*" mode="generate-id-from-path" />
<xsl:value-of select="concat('.@', name())" />
</xsl:template>
<xsl:template match="*" mode="generate-id-from-path" priority="-0.5">
<xsl:apply-templates select="parent::*" mode="generate-id-from-path" />
<xsl:text>.</xsl:text>
<xsl:value-of select="concat('.',name(),'-',1+count(preceding-sibling::*[name()=name(current())]),'-')" />
</xsl:template>
<!--MODE: GENERATE-ID-2 -->
<xsl:template match="/" mode="generate-id-2">U</xsl:template>
<xsl:template match="*" mode="generate-id-2" priority="2">
<xsl:text>U</xsl:text>
<xsl:number level="multiple" count="*" />
</xsl:template>
<xsl:template match="node()" mode="generate-id-2">
<xsl:text>U.</xsl:text>
<xsl:number level="multiple" count="*" />
<xsl:text>n</xsl:text>
<xsl:number count="node()" />
</xsl:template>
<xsl:template match="@*" mode="generate-id-2">
<xsl:text>U.</xsl:text>
<xsl:number level="multiple" count="*" />
<xsl:text>_</xsl:text>
<xsl:value-of select="string-length(local-name(.))" />
<xsl:text>_</xsl:text>
<xsl:value-of select="translate(name(),':','.')" />
</xsl:template>
<!--Strip characters-->
<xsl:template match="text()" priority="-1" />
<!--SCHEMA SETUP-->
<xsl:template match="/">
<svrl:schematron-output xmlns:svrl="http://purl.oclc.org/dsdl/svrl"
title="Schematron Simple"
schemaVersion="">
<xsl:comment>
<xsl:value-of select="$archiveDirParameter" />  
<xsl:value-of select="$archiveNameParameter" />  
<xsl:value-of select="$fileNameParameter" />  
<xsl:value-of select="$fileDirParameter" />
</xsl:comment>
<svrl:ns-prefix-in-attribute-values uri="http://www.w3.org/2001/XMLSchema" prefix="xs" />
<svrl:ns-prefix-in-attribute-values uri="http://validator.kosit.de/test-sample" prefix="s" />
<svrl:active-pattern>
<xsl:attribute name="document">
<xsl:value-of select="document-uri(/)" />
</xsl:attribute>
<xsl:apply-templates />
</svrl:active-pattern>
<xsl:apply-templates select="/" mode="M3" />
</svrl:schematron-output>
</xsl:template>
<!--SCHEMATRON PATTERNS-->
<svrl:text xmlns:svrl="http://purl.oclc.org/dsdl/svrl">Schematron Simple</svrl:text>
<!--PATTERN -->
<!--RULE -->
<xsl:template match="s:simple" priority="1001" mode="M3">
<svrl:fired-rule xmlns:svrl="http://purl.oclc.org/dsdl/svrl" context="s:simple" />
<!--ASSERT -->
<xsl:choose>
<xsl:when test="xs:decimal(s:inner) = 1" />
<xsl:otherwise>
<svrl:failed-assert xmlns:svrl="http://purl.oclc.org/dsdl/svrl" test="xs:decimal(s:inner) = 1">
<xsl:attribute name="id">content-2</xsl:attribute>
<xsl:attribute name="location">
<xsl:apply-templates select="." mode="schematron-select-full-path" />
</xsl:attribute>
<svrl:text>The decimal value of s:inner should be 1.</svrl:text>
</svrl:failed-assert>
</xsl:otherwise>
</xsl:choose>
<xsl:apply-templates select="*|comment()|processing-instruction()" mode="M3" />
</xsl:template>
<xsl:template match="text()" priority="-1" mode="M3" />
<xsl:template match="@*|node()" priority="-2" mode="M3">
<xsl:apply-templates select="*|comment()|processing-instruction()" mode="M3" />
</xsl:template>
</xsl:stylesheet>

View file

@ -0,0 +1,30 @@
<?xml version="1.0" encoding="UTF-8"?>
<!--
~ Copyright 2017-2022 Koordinierungsstelle für IT-Standards (KoSIT)
~
~ Licensed under the Apache License, Version 2.0 (the "License");
~ you may not use this file except in compliance with the License.
~ You may obtain a copy of the License at
~
~ http://www.apache.org/licenses/LICENSE-2.0
~
~ Unless required by applicable law or agreed to in writing, software
~ distributed under the License is distributed on an "AS IS" BASIS,
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
~ See the License for the specific language governing permissions and
~ limitations under the License.
-->
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:tns="http://validator.kosit.de/test-sample" version="1.0" xml:lang="en"
targetNamespace="http://validator.kosit.de/test-sample" elementFormDefault="qualified">
<xs:element name="simple" type="tns:SimpleType" />
<xs:element name="foo" type="tns:SimpleType" />
<xs:complexType name="SimpleType">
<xs:sequence>
<xs:element name="inner" type="xs:string" minOccurs="0" maxOccurs="unbounded" />
<xs:element name="content" type="xs:anyType" />
</xs:sequence>
</xs:complexType>
</xs:schema>

View file

@ -0,0 +1,61 @@
<?xml version="1.0" encoding="UTF-8"?>
<scenarios xmlns="http://www.xoev.de/de/validator/framework/1/scenarios" frameworkVersion="1.1.2">
<name>XSLT-Runtime-Error-TestSuite</name>
<author>QA</author>
<date>2026-03-02</date>
<description>
<p>Szenario für Tests</p>
</description>
<scenario>
<name>Simple</name>
<description>
<p>Teste Fehlerfall.</p>
</description>
<namespace prefix="cri">http://www.xoev.de/de/validator/framework/1/createreportinput</namespace>
<namespace prefix="test">http://validator.kosit.de/test-sample</namespace>
<namespace prefix="rpt">http://validator.kosit.de/test-report</namespace>
<match>/</match>
<validateWithXmlSchema>
<resource>
<name>Sample Schema</name>
<location>repository/simple.xsd</location>
</resource>
</validateWithXmlSchema>
<validateWithSchematron>
<resource>
<name>Sample Schematron</name>
<location>repository/simple-xslt-runtime-error.xsl</location>
</resource>
</validateWithSchematron>
<createReport>
<resource>
<name>Report für eRechnung</name>
<location>repository/report.xsl</location>
</resource>
</createReport>
</scenario>
<noScenarioReport>
<resource>
<name>default</name>
<location>repository/report.xsl</location>
</resource>
</noScenarioReport>
</scenarios>
<!--
~ Copyright 2017-2026 Koordinierungsstelle für IT-Standards (KoSIT)
~
~ Licensed under the Apache License, Version 2.0 (the "License");
~ you may not use this file except in compliance with the License.
~ You may obtain a copy of the License at
~
~ http://www.apache.org/licenses/LICENSE-2.0
~
~ Unless required by applicable law or agreed to in writing, software
~ distributed under the License is distributed on an "AS IS" BASIS,
~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
~ See the License for the specific language governing permissions and
~ limitations under the License.
-->