Skip to content

Commit

Permalink
Add deprecation layer for validation of XML mappings (#1814)
Browse files Browse the repository at this point in the history
  • Loading branch information
alcaeus committed Jan 9, 2019
1 parent cb319d6 commit 5ab33e4
Show file tree
Hide file tree
Showing 2 changed files with 65 additions and 42 deletions.
84 changes: 42 additions & 42 deletions doctrine-mongo-mapping.xsd
Original file line number Diff line number Diff line change
Expand Up @@ -14,12 +14,12 @@

<xs:element name="doctrine-mongo-mapping">
<xs:complexType>
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="document" type="odm:document" minOccurs="0" maxOccurs="unbounded" />
<xs:element name="embedded-document" type="odm:document" minOccurs="0" maxOccurs="unbounded" />
<xs:element name="mapped-superclass" type="odm:document" minOccurs="0" maxOccurs="unbounded" />
<xs:element name="query-result-document" type="odm:document" minOccurs="0" maxOccurs="unbounded" />
</xs:sequence>
</xs:choice>
</xs:complexType>
</xs:element>

Expand All @@ -36,7 +36,7 @@
</xs:complexType>

<xs:complexType name="document">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="id" type="odm:id" minOccurs="0" maxOccurs="1"/>
<xs:element name="field" type="odm:field" minOccurs="0" maxOccurs="unbounded"/>
<xs:element name="embed-one" type="odm:embed-one" minOccurs="0" maxOccurs="unbounded"/>
Expand All @@ -51,7 +51,7 @@
<xs:element name="indexes" type="odm:indexes" minOccurs="0"/>
<xs:element name="shard-key" type="odm:shard-key" minOccurs="0"/>
<xs:element name="read-preference" type="odm:read-preference" minOccurs="0" maxOccurs="1"/>
</xs:sequence>
</xs:choice>
<xs:attribute name="db" type="xs:NMTOKEN" />
<xs:attribute name="name" type="xs:string" />
<xs:attribute name="writeConcern" type="xs:string" />
Expand All @@ -68,17 +68,17 @@
</xs:complexType>

<xs:complexType name="read-preference">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="tag-set" type="odm:read-preference-tag-set" minOccurs="0" maxOccurs="unbounded" />
</xs:sequence>
</xs:choice>
<xs:attribute name="mode" type="odm:read-preference-values"/>
</xs:complexType>

<xs:complexType name="field">
<!-- deprecated -->
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="id-generator-option" type="odm:id-generator-option" minOccurs="0" maxOccurs="unbounded" />
</xs:sequence>
</xs:choice>
<!-- deprecated -->
<xs:attribute name="id" type="xs:boolean" default="false" />
<xs:attribute name="name" type="xs:NMTOKEN" />
Expand Down Expand Up @@ -120,11 +120,11 @@
</xs:complexType>

<xs:complexType name="embed-one">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="discriminator-field" type="odm:discriminator-field" minOccurs="0"/>
<xs:element name="discriminator-map" type="odm:discriminator-map" minOccurs="0"/>
<xs:element name="default-discriminator-value" type="odm:default-discriminator-value" minOccurs="0"/>
</xs:sequence>
</xs:choice>
<xs:attribute name="target-document" type="xs:string" />
<xs:attribute name="field" type="xs:NMTOKEN" use="required" />
<xs:attribute name="fieldName" type="xs:NMTOKEN" />
Expand All @@ -134,11 +134,11 @@
</xs:complexType>

<xs:complexType name="embed-many">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="discriminator-field" type="odm:discriminator-field" minOccurs="0"/>
<xs:element name="discriminator-map" type="odm:discriminator-map" minOccurs="0"/>
<xs:element name="default-discriminator-value" type="odm:default-discriminator-value" minOccurs="0"/>
</xs:sequence>
</xs:choice>
<xs:attribute name="target-document" type="xs:string" />
<xs:attribute name="collection-class" type="xs:string" />
<xs:attribute name="field" type="xs:NMTOKEN" use="required" />
Expand All @@ -159,14 +159,14 @@
</xs:simpleType>

<xs:complexType name="reference-one">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="cascade" type="odm:cascade-type" minOccurs="0" />
<xs:element name="discriminator-field" type="odm:discriminator-field" minOccurs="0"/>
<xs:element name="discriminator-map" type="odm:discriminator-map" minOccurs="0"/>
<xs:element name="default-discriminator-value" type="odm:default-discriminator-value" minOccurs="0"/>
<xs:element name="sort" type="odm:sort-map" minOccurs="0" />
<xs:element name="criteria" type="odm:criteria-map" minOccurs="0" />
</xs:sequence>
</xs:choice>
<xs:attribute name="target-document" type="xs:string" />
<xs:attribute name="field" type="xs:NMTOKEN" use="required" />
<xs:attribute name="fieldName" type="xs:NMTOKEN" />
Expand All @@ -183,15 +183,15 @@
</xs:complexType>

<xs:complexType name="reference-many">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="cascade" type="odm:cascade-type" minOccurs="0" />
<xs:element name="discriminator-field" type="odm:discriminator-field" minOccurs="0"/>
<xs:element name="discriminator-map" type="odm:discriminator-map" minOccurs="0"/>
<xs:element name="default-discriminator-value" type="odm:default-discriminator-value" minOccurs="0"/>
<xs:element name="sort" type="odm:sort-map" minOccurs="0" />
<xs:element name="criteria" type="odm:criteria-map" minOccurs="0" />
<xs:element name="prime" type="odm:primers" minOccurs="0" />
</xs:sequence>
</xs:choice>
<xs:attribute name="target-document" type="xs:string" />
<xs:attribute name="collection-class" type="xs:string" />
<xs:attribute name="field" type="xs:NMTOKEN" use="required" />
Expand All @@ -217,9 +217,9 @@
</xs:complexType>

<xs:complexType name="sort-map">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="sort" type="odm:sort-type" minOccurs="1" maxOccurs="unbounded"/>
</xs:sequence>
</xs:choice>
</xs:complexType>

<xs:complexType name="criteria-type">
Expand All @@ -228,15 +228,15 @@
</xs:complexType>

<xs:complexType name="criteria-map">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="criteria" type="odm:criteria-type" minOccurs="1" maxOccurs="unbounded"/>
</xs:sequence>
</xs:choice>
</xs:complexType>

<xs:complexType name="primers">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="field" type="odm:primer-field" minOccurs="1" maxOccurs="unbounded"/>
</xs:sequence>
</xs:choice>
</xs:complexType>

<xs:complexType name="primer-field">
Expand All @@ -246,14 +246,14 @@
<xs:complexType name="emptyType"/>

<xs:complexType name="cascade-type">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="all" type="odm:emptyType" minOccurs="0" maxOccurs="1"/>
<xs:element name="persist" type="odm:emptyType" minOccurs="0" maxOccurs="1"/>
<xs:element name="merge" type="odm:emptyType" minOccurs="0" maxOccurs="1"/>
<xs:element name="remove" type="odm:emptyType" minOccurs="0" maxOccurs="1"/>
<xs:element name="refresh" type="odm:emptyType" minOccurs="0" maxOccurs="1"/>
<xs:element name="detach" type="odm:emptyType" minOccurs="0" maxOccurs="1"/>
</xs:sequence>
</xs:choice>
</xs:complexType>

<xs:simpleType name="inheritance-type">
Expand All @@ -277,9 +277,9 @@
</xs:complexType>

<xs:complexType name="discriminator-map">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="discriminator-mapping" type="odm:discriminator-mapping" minOccurs="1" maxOccurs="unbounded"/>
</xs:sequence>
</xs:choice>
</xs:complexType>

<xs:complexType name="discriminator-field">
Expand Down Expand Up @@ -309,9 +309,9 @@
</xs:complexType>

<xs:complexType name="lifecycle-callbacks">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="lifecycle-callback" type="odm:lifecycle-callback" minOccurs="1" maxOccurs="unbounded"/>
</xs:sequence>
</xs:choice>
</xs:complexType>

<xs:complexType name="index-key">
Expand All @@ -337,18 +337,18 @@
</xs:simpleType>

<xs:complexType name="partial-filter-expression-field">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="field" type="odm:partial-filter-expression-field" minOccurs="0" maxOccurs="unbounded" />
</xs:sequence>
</xs:choice>
<xs:attribute name="name" type="xs:NMTOKEN" use="required"/>
<xs:attribute name="operator" type="odm:partial-filter-expression-operator" use="optional" />
<xs:attribute name="value" type="xs:string" use="optional" />
</xs:complexType>

<xs:complexType name="partial-filter-expression-and">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="field" type="odm:partial-filter-expression-field" minOccurs="1" maxOccurs="unbounded" />
</xs:sequence>
</xs:choice>
</xs:complexType>

<xs:complexType name="partial-filter-expression">
Expand All @@ -359,11 +359,11 @@
</xs:complexType>

<xs:complexType name="index">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="key" type="odm:index-key" minOccurs="1" maxOccurs="unbounded"/>
<xs:element name="option" type="odm:index-option" minOccurs="0" maxOccurs="unbounded"/>
<xs:element name="partial-filter-expression" type="odm:partial-filter-expression" minOccurs="0" maxOccurs="1"/>
</xs:sequence>
</xs:choice>
<xs:attribute name="name" type="xs:NMTOKEN"/>
<xs:attribute name="drop-dups" type="xs:boolean"/>
<xs:attribute name="background" type="xs:boolean"/>
Expand All @@ -373,16 +373,16 @@
</xs:complexType>

<xs:complexType name="indexes">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="index" type="odm:index" minOccurs="1" maxOccurs="unbounded"/>
</xs:sequence>
</xs:choice>
</xs:complexType>

<xs:complexType name="shard-key">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="key" type="odm:shard-key-key" minOccurs="1" maxOccurs="unbounded"/>
<xs:element name="option" type="odm:shard-key-option" minOccurs="0" maxOccurs="unbounded"/>
</xs:sequence>
</xs:choice>
<xs:attribute name="unique" type="xs:boolean"/>
<xs:attribute name="numInitialChunks" type="xs:integer"/>
</xs:complexType>
Expand All @@ -404,9 +404,9 @@


<xs:complexType name="also-load-methods">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="also-load-method" type="odm:also-load-method" minOccurs="1" maxOccurs="unbounded"/>
</xs:sequence>
</xs:choice>
</xs:complexType>

<xs:simpleType name="read-preference-values">
Expand All @@ -420,9 +420,9 @@
</xs:simpleType>

<xs:complexType name="read-preference-tag-set">
<xs:sequence>
<xs:choice minOccurs="0" maxOccurs="unbounded">
<xs:element name="tag" type="read-preference-tag" minOccurs="0" maxOccurs="unbounded" />
</xs:sequence>
</xs:choice>
</xs:complexType>

<xs:complexType name="read-preference-tag">
Expand Down
23 changes: 23 additions & 0 deletions lib/Doctrine/ODM/MongoDB/Mapping/Driver/XmlDriver.php
Original file line number Diff line number Diff line change
Expand Up @@ -23,8 +23,10 @@
use Doctrine\Common\Persistence\Mapping\Driver\FileDriver;
use Doctrine\ODM\MongoDB\Mapping\ClassMetadata as MappingClassMetadata;
use Doctrine\ODM\MongoDB\Utility\CollectionHelper;
use DOMDocument;
use SimpleXMLElement;
use const E_USER_DEPRECATED;
use function libxml_use_internal_errors;
use function sprintf;
use function trigger_error;

Expand Down Expand Up @@ -570,6 +572,9 @@ private function transformReadPreference($xmlReadPreference)
protected function loadMappingFile($file)
{
$result = array();

$this->validateSchema($file);

$xmlElement = simplexml_load_file($file);

foreach (array('document', 'embedded-document', 'mapped-superclass', 'query-result-document') as $type) {
Expand All @@ -583,4 +588,22 @@ protected function loadMappingFile($file)

return $result;
}

private function validateSchema($filename)
{
$document = new DOMDocument();
$document->load($filename);

$previousUseErrors = libxml_use_internal_errors(true);

try {
if ($document->schemaValidate(__DIR__ . '/../../../../../../doctrine-mongo-mapping.xsd')) {
return;
}
} finally {
libxml_use_internal_errors($previousUseErrors);
}

@trigger_error(sprintf('The mapping file "%s" does not follow the mapping schema. Loading invalid files is deprecated and will no longer work in 2.0', $filename), E_USER_DEPRECATED);
}
}

0 comments on commit 5ab33e4

Please sign in to comment.