Files
myep/tests/Service/BpnXmlAnonymizerTest.php
T

534 lines
24 KiB
PHP

<?php
declare(strict_types=1);
namespace App\Tests\Service;
use App\Service\BpnXmlAnonymizer;
use PHPUnit\Framework\TestCase;
class BpnXmlAnonymizerTest extends TestCase
{
public function testAnonymizeReusesIdentityForSamePersonId(): void
{
$xml = <<<'XML'
<?xml version="1.0" encoding="UTF-8"?>
<anfrage>
<anmelder>
<name>Example</name>
<vorname>Ava</vorname>
<geburtsdatum>03.04.1991</geburtsdatum>
<anschrift>
<strasse>Testallee 7</strasse>
<plz>10115</plz>
<ort>Berlin</ort>
</anschrift>
<kommunikation>
<email>[email protected]</email>
<telefonmobil>015500000001</telefonmobil>
</kommunikation>
<idadresseperson>111111</idadresseperson>
</anmelder>
<teilnehmerliste>
<teilnehmer id="1">
<name>Example</name>
<vorname>Ava</vorname>
<geburtsdatum>03.04.1991</geburtsdatum>
<anschrift>
<strasse>Testallee 7</strasse>
<plz>10115</plz>
<ort>Berlin</ort>
</anschrift>
<kommunikation>
<email>[email protected]</email>
<telefonmobil>015500000001</telefonmobil>
</kommunikation>
<idadresseperson>111111</idadresseperson>
</teilnehmer>
<teilnehmer id="2">
<name>Second</name>
<vorname>Ben</vorname>
<geburtsdatum>12.11.1987</geburtsdatum>
<kommunikation>
<email>[email protected]</email>
</kommunikation>
<idadresseperson>222222</idadresseperson>
</teilnehmer>
</teilnehmerliste>
</anfrage>
XML;
$anonymizer = new BpnXmlAnonymizer();
$result = $anonymizer->anonymize($xml);
$document = new \DOMDocument();
$this->assertTrue($document->loadXML($result));
$xpath = new \DOMXPath($document);
$applicantName = trim((string) $xpath->evaluate('string(//anmelder/name)'));
$participantOneName = trim((string) $xpath->evaluate('string(//teilnehmer[1]/name)'));
$participantOneEmail = trim((string) $xpath->evaluate('string(//teilnehmer[1]/kommunikation/email)'));
$applicantMobilePhone = trim((string) $xpath->evaluate('string(//anmelder/kommunikation/telefonmobil)'));
$participantOneMobilePhone = trim((string) $xpath->evaluate('string(//teilnehmer[1]/kommunikation/telefonmobil)'));
$participantTwoName = trim((string) $xpath->evaluate('string(//teilnehmer[2]/name)'));
$applicantBirthDate = trim((string) $xpath->evaluate('string(//anmelder/geburtsdatum)'));
$participantOneBirthDate = trim((string) $xpath->evaluate('string(//teilnehmer[1]/geburtsdatum)'));
$participantTwoBirthDate = trim((string) $xpath->evaluate('string(//teilnehmer[2]/geburtsdatum)'));
$this->assertNotSame('Example', $applicantName);
$this->assertSame($applicantName, $participantOneName);
$this->assertSame('[email protected]', $participantOneEmail);
$this->assertSame('01000000002', $participantOneMobilePhone);
$this->assertSame($applicantMobilePhone, $participantOneMobilePhone);
$this->assertNotSame($participantOneName, $participantTwoName);
$this->assertSame('03.04.1991', $applicantBirthDate);
$this->assertSame('03.04.1991', $participantOneBirthDate);
$this->assertSame('12.11.1987', $participantTwoBirthDate);
$this->assertSame(3, $anonymizer->getLastIdentityCount());
}
public function testAnonymizeReplacesAdressdatenRequestAndResponseConsistently(): void
{
$requestXml = <<<'XML'
<?xml version="1.0" encoding="UTF-8"?>
<anfrage>
<user>portal-user</user>
<key>aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa</key>
<satz typ="KUNDENKONTO"/>
<art>Adressdaten</art>
<email>[email protected]</email>
<passwort>bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb</passwort>
</anfrage>
XML;
$responseXml = <<<'XML'
<?xml version="1.0" encoding="UTF-8"?>
<ergebnis>
<satz typ="KUNDENKONTO"/>
<art>Adressdaten</art>
<idadresse>654321</idadresse>
<idperson>123456</idperson>
<adressdaten>
<name>Input</name>
<vorname>Person</vorname>
<anrede>Herr</anrede>
<titel>Prof.</titel>
<geschlecht>M</geschlecht>
<geburtsdatum>16.04.1972</geburtsdatum>
<nationalitaet>NL</nationalitaet>
<anschrift>
<id>444444</id>
<strasse>Beispielweg 57</strasse>
<plz>42853</plz>
<ort>Musterstadt</ort>
<ortsteil>Innenstadt</ortsteil>
<land>D</land>
</anschrift>
<kommunikation>
<telefonmobil>017700000000</telefonmobil>
<email>[email protected]</email>
<newsletter>False</newsletter>
<telefonprivat>021900000000</telefonprivat>
</kommunikation>
<bankverbindung>
<iban>DE02120300000000202051</iban>
</bankverbindung>
<sonstiges1>179-197</sonstiges1>
<sonstiges2>79-94</sonstiges2>
<sonstiges3>44</sonstiges3>
</adressdaten>
</ergebnis>
XML;
$anonymizer = new BpnXmlAnonymizer();
$anonymizedRequest = $anonymizer->anonymize($requestXml, true);
$anonymizedResponse = $anonymizer->anonymize($responseXml, false);
$requestDocument = new \DOMDocument();
$this->assertTrue($requestDocument->loadXML($anonymizedRequest));
$requestXpath = new \DOMXPath($requestDocument);
$requestUser = trim((string) $requestXpath->evaluate('string(//user)'));
$requestEmail = trim((string) $requestXpath->evaluate('string(//email)'));
$requestKey = trim((string) $requestXpath->evaluate('string(//key)'));
$requestPassword = trim((string) $requestXpath->evaluate('string(//passwort)'));
$responseDocument = new \DOMDocument();
$this->assertTrue($responseDocument->loadXML($anonymizedResponse));
$responseXpath = new \DOMXPath($responseDocument);
$responseEmail = trim((string) $responseXpath->evaluate('string(//adressdaten/kommunikation/email)'));
$responseName = trim((string) $responseXpath->evaluate('string(//adressdaten/name)'));
$responseFirstName = trim((string) $responseXpath->evaluate('string(//adressdaten/vorname)'));
$responseSalutation = trim((string) $responseXpath->evaluate('string(//adressdaten/anrede)'));
$responseTitle = trim((string) $responseXpath->evaluate('string(//adressdaten/titel)'));
$responseGender = trim((string) $responseXpath->evaluate('string(//adressdaten/geschlecht)'));
$responseBirthDate = trim((string) $responseXpath->evaluate('string(//adressdaten/geburtsdatum)'));
$responseNationality = trim((string) $responseXpath->evaluate('string(//adressdaten/nationalitaet)'));
$responseStreet = trim((string) $responseXpath->evaluate('string(//adressdaten/anschrift/strasse)'));
$responsePostalCode = trim((string) $responseXpath->evaluate('string(//adressdaten/anschrift/plz)'));
$responseCity = trim((string) $responseXpath->evaluate('string(//adressdaten/anschrift/ort)'));
$responseDistrict = trim((string) $responseXpath->evaluate('string(//adressdaten/anschrift/ortsteil)'));
$responseCountry = trim((string) $responseXpath->evaluate('string(//adressdaten/anschrift/land)'));
$responseAddressId = trim((string) $responseXpath->evaluate('string(//adressdaten/anschrift/id)'));
$responseMobilePhone = trim((string) $responseXpath->evaluate('string(//adressdaten/kommunikation/telefonmobil)'));
$responsePhone = trim((string) $responseXpath->evaluate('string(//adressdaten/kommunikation/telefonprivat)'));
$responseNewsletter = trim((string) $responseXpath->evaluate('string(//adressdaten/kommunikation/newsletter)'));
$responseIban = trim((string) $responseXpath->evaluate('string(//adressdaten/bankverbindung/iban)'));
$responseHeight = trim((string) $responseXpath->evaluate('string(//adressdaten/sonstiges1)'));
$responseWeight = trim((string) $responseXpath->evaluate('string(//adressdaten/sonstiges2)'));
$responseShoeSize = trim((string) $responseXpath->evaluate('string(//adressdaten/sonstiges3)'));
$responseRootPersonId = trim((string) $responseXpath->evaluate('string(//idperson)'));
$responseRootAddressId = trim((string) $responseXpath->evaluate('string(//idadresse)'));
$this->assertSame('anon-user-1', $requestUser);
$this->assertSame('[email protected]', $requestEmail);
$this->assertSame('00000000000000000000000000000001', $requestKey);
$this->assertSame('00000000000000000000000000000002', $requestPassword);
$this->assertSame($requestEmail, $responseEmail);
$this->assertNotSame('Input', $responseName);
$this->assertNotSame('Person', $responseFirstName);
$this->assertSame('Divers', $responseSalutation);
$this->assertSame('', $responseTitle);
$this->assertSame('D', $responseGender);
$this->assertSame('16.04.1972', $responseBirthDate);
$this->assertSame('XX', $responseNationality);
$this->assertNotSame('Beispielweg 57', $responseStreet);
$this->assertNotSame('42853', $responsePostalCode);
$this->assertNotSame('Musterstadt', $responseCity);
$this->assertSame('', $responseDistrict);
$this->assertSame('XX', $responseCountry);
$this->assertSame('800001', $responseAddressId);
$this->assertSame('01000000001', $responseMobilePhone);
$this->assertSame('02000000001', $responsePhone);
$this->assertSame('False', $responseNewsletter);
$this->assertSame('DE00000000000000000001', $responseIban);
$this->assertSame('170', $responseHeight);
$this->assertSame('70', $responseWeight);
$this->assertSame('42', $responseShoeSize);
$this->assertSame('123456', $responseRootPersonId);
$this->assertSame('654321', $responseRootAddressId);
$this->assertSame(1, $anonymizer->getLastIdentityCount());
}
public function testAnonymizeReplacesKundeAttributes(): void
{
$xml = <<<'XML'
<?xml version="1.0" encoding="utf-8"?>
<ergebnis>
<vorgaenge>
<vorgang>
<kundennamen>
<kunde id="1" art="Anmelder/Teilnehmer" name="Alpha" vorname="Ada"></kunde>
<kunde id="2" art="Teilnehmer" name="Beta" vorname="Ben"></kunde>
</kundennamen>
</vorgang>
</vorgaenge>
</ergebnis>
XML;
$anonymizer = new BpnXmlAnonymizer();
$result = $anonymizer->anonymize($xml);
$document = new \DOMDocument();
$this->assertTrue($document->loadXML($result));
$xpath = new \DOMXPath($document);
$firstCustomerLastName = trim((string) $xpath->evaluate('string(//kundennamen/kunde[1]/@name)'));
$firstCustomerFirstName = trim((string) $xpath->evaluate('string(//kundennamen/kunde[1]/@vorname)'));
$firstCustomerId = trim((string) $xpath->evaluate('string(//kundennamen/kunde[1]/@id)'));
$secondCustomerId = trim((string) $xpath->evaluate('string(//kundennamen/kunde[2]/@id)'));
$this->assertNotSame('Alpha', $firstCustomerLastName);
$this->assertNotSame('Ada', $firstCustomerFirstName);
$this->assertSame('900001', $firstCustomerId);
$this->assertSame('900002', $secondCustomerId);
}
public function testAnonymizePreservesEmptyNodesAndAttributes(): void
{
$xml = <<<'XML'
<?xml version="1.0" encoding="UTF-8"?>
<anfrage>
<user></user>
<key/>
<email> </email>
<passwort></passwort>
<anmelder id="">
<name/>
<vorname> </vorname>
<anrede></anrede>
<geschlecht>W</geschlecht>
<nationalitaet></nationalitaet>
<geburtsdatum/>
<anschrift>
<id></id>
<strasse/>
<plz>12345</plz>
<ort> </ort>
<land></land>
</anschrift>
<kommunikation>
<email></email>
<telefonmobil>01701234567</telefonmobil>
<telefonprivat/>
<newsletter></newsletter>
</kommunikation>
<bankverbindung>
<iban></iban>
</bankverbindung>
<sonstiges1/>
<sonstiges2>75</sonstiges2>
<sonstiges3></sonstiges3>
</anmelder>
<kundennamen>
<kunde id="" art="Teilnehmer" name="" vorname="Ada"/>
</kundennamen>
</anfrage>
XML;
$anonymizer = new BpnXmlAnonymizer();
$result = $anonymizer->anonymize($xml);
$document = new \DOMDocument();
$this->assertTrue($document->loadXML($result));
$xpath = new \DOMXPath($document);
$this->assertSame('', trim((string) $xpath->evaluate('string(/anfrage/user)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(/anfrage/key)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(/anfrage/email)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(/anfrage/passwort)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/@id)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/name)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/vorname)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/anrede)')));
$this->assertSame('D', trim((string) $xpath->evaluate('string(//anmelder/geschlecht)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/nationalitaet)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/geburtsdatum)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/anschrift/id)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/anschrift/strasse)')));
$this->assertNotSame('12345', trim((string) $xpath->evaluate('string(//anmelder/anschrift/plz)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/anschrift/ort)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/anschrift/land)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/kommunikation/email)')));
$this->assertSame('01000000002', trim((string) $xpath->evaluate('string(//anmelder/kommunikation/telefonmobil)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/kommunikation/telefonprivat)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/kommunikation/newsletter)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/bankverbindung/iban)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/sonstiges1)')));
$this->assertSame('70', trim((string) $xpath->evaluate('string(//anmelder/sonstiges2)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//anmelder/sonstiges3)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//kundennamen/kunde/@id)')));
$this->assertSame('', trim((string) $xpath->evaluate('string(//kundennamen/kunde/@name)')));
$this->assertNotSame('Ada', trim((string) $xpath->evaluate('string(//kundennamen/kunde/@vorname)')));
}
public function testAnonymizeThrowsOnInvalidXml(): void
{
$anonymizer = new BpnXmlAnonymizer();
$this->expectException(\InvalidArgumentException::class);
$anonymizer->anonymize('<invalid');
}
public function testAnonymizeLinksApplicantAndParticipantWhenOnlyDataMatches(): void
{
$xml = <<<'XML'
<?xml version="1.0" encoding="UTF-8"?>
<anfrage>
<anmelder>
<name>Shared</name>
<vorname>Casey</vorname>
<anschrift>
<strasse>Sharedstrasse 1</strasse>
<plz>50667</plz>
<ort>Koeln</ort>
</anschrift>
<kommunikation>
<email>[email protected]</email>
</kommunikation>
</anmelder>
<teilnehmerliste>
<teilnehmer id="1">
<name>Shared</name>
<vorname>Casey</vorname>
<anschrift>
<strasse>Sharedstrasse 1</strasse>
<plz>50667</plz>
<ort>Koeln</ort>
</anschrift>
<kommunikation>
<email>[email protected]</email>
</kommunikation>
</teilnehmer>
</teilnehmerliste>
</anfrage>
XML;
$anonymizer = new BpnXmlAnonymizer();
$result = $anonymizer->anonymize($xml);
$document = new \DOMDocument();
$this->assertTrue($document->loadXML($result));
$xpath = new \DOMXPath($document);
$applicantName = trim((string) $xpath->evaluate('string(//anmelder/name)'));
$participantName = trim((string) $xpath->evaluate('string(//teilnehmer[1]/name)'));
$this->assertSame($applicantName, $participantName);
$this->assertSame(2, $anonymizer->getLastIdentityCount());
}
public function testAnonymizeCanReuseIdentityAcrossMultipleXmlDocuments(): void
{
$requestXml = <<<'XML'
<?xml version="1.0" encoding="UTF-8"?>
<anfrage>
<anmelder>
<name>Reusable</name>
<vorname>Riley</vorname>
<kommunikation>
<email>[email protected]</email>
</kommunikation>
<idadresseperson>333333</idadresseperson>
</anmelder>
</anfrage>
XML;
$responseXml = <<<'XML'
<?xml version="1.0" encoding="UTF-8"?>
<ergebnis>
<teilnehmerliste>
<teilnehmer id="1">
<name>Reusable</name>
<vorname>Riley</vorname>
<kommunikation>
<email>[email protected]</email>
</kommunikation>
<idadresseperson>333333</idadresseperson>
</teilnehmer>
</teilnehmerliste>
</ergebnis>
XML;
$anonymizer = new BpnXmlAnonymizer();
$anonymizedRequest = $anonymizer->anonymize($requestXml, true);
$anonymizedResponse = $anonymizer->anonymize($responseXml, false);
$requestDocument = new \DOMDocument();
$this->assertTrue($requestDocument->loadXML($anonymizedRequest));
$requestXpath = new \DOMXPath($requestDocument);
$requestName = trim((string) $requestXpath->evaluate('string(//anmelder/name)'));
$responseDocument = new \DOMDocument();
$this->assertTrue($responseDocument->loadXML($anonymizedResponse));
$responseXpath = new \DOMXPath($responseDocument);
$responseName = trim((string) $responseXpath->evaluate('string(//teilnehmer[1]/name)'));
$this->assertSame($requestName, $responseName);
$this->assertSame(2, $anonymizer->getLastIdentityCount());
}
public function testAnonymizeReplacesAdressdatenBlocksInCustomerResponses(): void
{
$xml = <<<'XML'
<?xml version="1.0" encoding="UTF-8"?>
<ergebnis>
<satz typ="KUNDENKONTO"/>
<art>Adressdaten</art>
<idadresse>654321</idadresse>
<idperson>123456</idperson>
<adressdaten>
<name>Input</name>
<vorname>Person</vorname>
<anrede>Frau</anrede>
<titel>Dr.</titel>
<geschlecht>W</geschlecht>
<geburtsdatum>01.02.1990</geburtsdatum>
<nationalitaet>DE</nationalitaet>
<anschrift>
<id>444444</id>
<strasse>Beispielweg 12</strasse>
<plz>12345</plz>
<ort>Musterstadt</ort>
<ortsteil>Altstadt</ortsteil>
<land>DE</land>
</anschrift>
<kommunikation>
<telefonmobil>01701234567</telefonmobil>
<email>[email protected]</email>
<newsletter>True</newsletter>
<telefonprivat>02101234567</telefonprivat>
</kommunikation>
<bankverbindung>
<iban>DE02120300000000202051</iban>
</bankverbindung>
<sonstiges1>180</sonstiges1>
<sonstiges2>75</sonstiges2>
<sonstiges3>43</sonstiges3>
</adressdaten>
</ergebnis>
XML;
$anonymizer = new BpnXmlAnonymizer();
$result = $anonymizer->anonymize($xml);
$document = new \DOMDocument();
$this->assertTrue($document->loadXML($result));
$xpath = new \DOMXPath($document);
$lastName = trim((string) $xpath->evaluate('string(//adressdaten/name)'));
$firstName = trim((string) $xpath->evaluate('string(//adressdaten/vorname)'));
$salutation = trim((string) $xpath->evaluate('string(//adressdaten/anrede)'));
$title = trim((string) $xpath->evaluate('string(//adressdaten/titel)'));
$gender = trim((string) $xpath->evaluate('string(//adressdaten/geschlecht)'));
$birthDate = trim((string) $xpath->evaluate('string(//adressdaten/geburtsdatum)'));
$nationality = trim((string) $xpath->evaluate('string(//adressdaten/nationalitaet)'));
$street = trim((string) $xpath->evaluate('string(//adressdaten/anschrift/strasse)'));
$postalCode = trim((string) $xpath->evaluate('string(//adressdaten/anschrift/plz)'));
$city = trim((string) $xpath->evaluate('string(//adressdaten/anschrift/ort)'));
$district = trim((string) $xpath->evaluate('string(//adressdaten/anschrift/ortsteil)'));
$country = trim((string) $xpath->evaluate('string(//adressdaten/anschrift/land)'));
$addressId = trim((string) $xpath->evaluate('string(//adressdaten/anschrift/id)'));
$email = trim((string) $xpath->evaluate('string(//adressdaten/kommunikation/email)'));
$mobilePhone = trim((string) $xpath->evaluate('string(//adressdaten/kommunikation/telefonmobil)'));
$phone = trim((string) $xpath->evaluate('string(//adressdaten/kommunikation/telefonprivat)'));
$newsletter = trim((string) $xpath->evaluate('string(//adressdaten/kommunikation/newsletter)'));
$iban = trim((string) $xpath->evaluate('string(//adressdaten/bankverbindung/iban)'));
$height = trim((string) $xpath->evaluate('string(//adressdaten/sonstiges1)'));
$weight = trim((string) $xpath->evaluate('string(//adressdaten/sonstiges2)'));
$shoeSize = trim((string) $xpath->evaluate('string(//adressdaten/sonstiges3)'));
$personId = trim((string) $xpath->evaluate('string(//idperson)'));
$addressIdRoot = trim((string) $xpath->evaluate('string(//idadresse)'));
$this->assertNotSame('Input', $lastName);
$this->assertNotSame('Person', $firstName);
$this->assertSame('Divers', $salutation);
$this->assertSame('', $title);
$this->assertSame('D', $gender);
$this->assertSame('01.02.1990', $birthDate);
$this->assertSame('XX', $nationality);
$this->assertNotSame('Beispielweg 12', $street);
$this->assertNotSame('12345', $postalCode);
$this->assertNotSame('Musterstadt', $city);
$this->assertSame('', $district);
$this->assertSame('XX', $country);
$this->assertSame('800001', $addressId);
$this->assertSame('[email protected]', $email);
$this->assertSame('01000000001', $mobilePhone);
$this->assertSame('02000000001', $phone);
$this->assertSame('False', $newsletter);
$this->assertSame('DE00000000000000000001', $iban);
$this->assertSame('170', $height);
$this->assertSame('70', $weight);
$this->assertSame('42', $shoeSize);
$this->assertSame('123456', $personId);
$this->assertSame('654321', $addressIdRoot);
$this->assertSame(1, $anonymizer->getLastIdentityCount());
}
}