Add map element validation to check for valid geometry.

This commit is contained in:
Michael Stenta 2022-06-16 14:42:04 -04:00
parent a5d442ba63
commit ba6000ebc6
2 changed files with 37 additions and 4 deletions

View File

@ -4,6 +4,7 @@ namespace Drupal\farm_map\Element;
use Drupal\Core\Form\FormStateInterface;
use Drupal\Core\Render\Element\FormElement;
use Drupal\geofield\GeoPHP\GeoPHPWrapper;
/**
* Form element that returns WKT rendered in a map.
@ -27,10 +28,9 @@ class FarmMapInput extends FormElement {
'#pre_render' => [
[$class, 'preRenderGroup'],
],
// @todo Add validation.
// '#element_validate' => [
// [$class, 'elementValidate'],
// ],
'#element_validate' => [
[$class, 'elementValidate'],
],
'#theme_wrappers' => ['fieldset'],
// Display descriptions above the map by default.
'#description_display' => 'before',
@ -93,6 +93,34 @@ class FarmMapInput extends FormElement {
return $element;
}
/**
* Validates the form element.
*/
public static function elementValidate(&$element, FormStateInterface $form_state, &$complete_form) {
// Validate that the geometry data is valid by attempting to load it into
// GeoPHP. This uses the same logic and error message as the geofield
// module's validation constraint.
// @see Drupal\geofield\Plugin\Validation\Constraint\GeoConstraint
// @see Drupal\geofield\Plugin\Validation\Constraint\GeoConstraintValidator
$value = $element['value']['#value'];
if (!empty($value)) {
$geophp = new GeoPHPWrapper();
$valid_geometry = TRUE;
try {
if (!$geophp->load($value)) {
$valid_geometry = FALSE;
}
}
catch (\Exception $e) {
$valid_geometry = FALSE;
}
if (!$valid_geometry) {
$form_state->setError($element, t('"@value" is not a valid geospatial content.', ['@value' => $value]));
}
}
}
/**
* {@inheritdoc}
*/

View File

@ -57,6 +57,11 @@ class MapFormTest extends FarmBrowserTestBase {
$log = $logs[2];
$this->assertEquals('POINT(-45.967095060886315 32.77503850904169)', $log->get('geometry')->value);
// Test that submitting an invalid geometry throws a form validation error.
$this->drupalGet('quick/test');
$edit = ['geometry2[value]' => 'POLYGON()'];
$this->submitForm($edit, 'Submit');
$this->assertSession()->pageTextContains($this->t('"POLYGON()" is not a valid geospatial content.'));
}
}