diff --git a/src/applications/differential/customfield/DifferentialCoreCustomField.php b/src/applications/differential/customfield/DifferentialCoreCustomField.php index 6d956ac367..f88ac8836c 100644 --- a/src/applications/differential/customfield/DifferentialCoreCustomField.php +++ b/src/applications/differential/customfield/DifferentialCoreCustomField.php @@ -1,163 +1,122 @@ setFieldError(null); $errors = parent::validateApplicationTransactions( $editor, $type, $xactions); $transaction = null; foreach ($xactions as $xaction) { $value = $xaction->getNewValue(); if ($this->isCoreFieldRequired()) { if ($this->isCoreFieldValueEmpty($value)) { $error = new PhabricatorApplicationTransactionValidationError( $type, pht('Required'), $this->getCoreFieldRequiredErrorString(), $xaction); $error->setIsMissingFieldError(true); $errors[] = $error; $this->setFieldError(pht('Required')); continue; } } - - if (is_string($value)) { - $parser = $this->getFieldParser(); - $result = $parser->parseCorpus($value); - - unset($result['__title__']); - unset($result['__summary__']); - - if ($result) { - $error = new PhabricatorApplicationTransactionValidationError( - $type, - pht('Invalid'), - pht( - 'The value you have entered in "%s" can not be parsed '. - 'unambiguously when rendered in a commit message. Edit the '. - 'message so that keywords like "Summary:" and "Test Plan:" do '. - 'not appear at the beginning of lines. Parsed keys: %s.', - $this->getFieldName(), - implode(', ', array_keys($result))), - $xaction); - $errors[] = $error; - $this->setFieldError(pht('Invalid')); - continue; - } - } } return $errors; } - private function getFieldParser() { - if (!$this->fieldParser) { - $viewer = $this->getViewer(); - $parser = DifferentialCommitMessageParser::newStandardParser($viewer); - - // Set custom title and summary keys so we can detect the presence of - // "Summary:" in, e.g., a test plan. - $parser->setTitleKey('__title__'); - $parser->setSummaryKey('__summary__'); - - $this->fieldParser = $parser; - } - - return $this->fieldParser; - } - public function canDisableField() { return false; } public function shouldAppearInApplicationTransactions() { return true; } public function readValueFromObject(PhabricatorCustomFieldInterface $object) { if ($this->isCoreFieldRequired()) { $this->setFieldError(true); } $this->setValue($this->readValueFromRevision($object)); } public function getOldValueForApplicationTransactions() { return $this->readValueFromRevision($this->getObject()); } public function getNewValueForApplicationTransactions() { return $this->getValue(); } public function applyApplicationTransactionInternalEffects( PhabricatorApplicationTransaction $xaction) { $this->writeValueToRevision($this->getObject(), $xaction->getNewValue()); } public function setFieldError($field_error) { $this->fieldError = $field_error; return $this; } public function getFieldError() { return $this->fieldError; } public function setValue($value) { $this->value = $value; return $this; } public function getValue() { return $this->value; } public function getConduitDictionaryValue() { return $this->getValue(); } } diff --git a/src/applications/differential/field/DifferentialTestPlanCommitMessageField.php b/src/applications/differential/field/DifferentialTestPlanCommitMessageField.php index a477a9036e..178e51d985 100644 --- a/src/applications/differential/field/DifferentialTestPlanCommitMessageField.php +++ b/src/applications/differential/field/DifferentialTestPlanCommitMessageField.php @@ -1,53 +1,60 @@ isCustomFieldEnabled('differential:test-plan'); } public function validateFieldValue($value) { $is_required = PhabricatorEnv::getEnvConfig( 'differential.require-test-plan-field'); if ($is_required && !strlen($value)) { $this->raiseValidationException( pht( 'You must provide a test plan. Describe the actions you performed '. 'to verify the behavior of this change.')); } } public function readFieldValueFromObject(DifferentialRevision $revision) { return $revision->getTestPlan(); } public function getFieldTransactions($value) { return array( array( 'type' => DifferentialRevisionTestPlanTransaction::EDITKEY, 'value' => $value, ), ); } + public function validateTransactions($object, array $xactions) { + return $this->validateCommitMessageCorpusTransactions( + $object, + $xactions, + pht('Test Plan')); + } + } diff --git a/src/applications/differential/xaction/DifferentialRevisionSummaryTransaction.php b/src/applications/differential/xaction/DifferentialRevisionSummaryTransaction.php index a4f1dcafa5..238eb53903 100644 --- a/src/applications/differential/xaction/DifferentialRevisionSummaryTransaction.php +++ b/src/applications/differential/xaction/DifferentialRevisionSummaryTransaction.php @@ -1,57 +1,64 @@ getSummary(); } public function applyInternalEffects($object, $value) { $object->setSummary($value); } public function getTitle() { return pht( '%s edited the summary of this revision.', $this->renderAuthor()); } public function getTitleForFeed() { return pht( '%s updated the summary of %s.', $this->renderAuthor(), $this->renderObject()); } public function hasChangeDetailView() { return true; } public function getMailDiffSectionHeader() { return pht('CHANGES TO REVISION SUMMARY'); } public function newChangeDetailView() { $viewer = $this->getViewer(); return id(new PhabricatorApplicationTransactionTextDiffDetailView()) ->setViewer($viewer) ->setOldText($this->getOldValue()) ->setNewText($this->getNewValue()); } public function newRemarkupChanges() { $changes = array(); $changes[] = $this->newRemarkupChange() ->setOldValue($this->getOldValue()) ->setNewValue($this->getNewValue()); return $changes; } + public function validateTransactions($object, array $xactions) { + return $this->validateCommitMessageCorpusTransactions( + $object, + $xactions, + pht('Summary')); + } + } diff --git a/src/applications/differential/xaction/DifferentialRevisionTransactionType.php b/src/applications/differential/xaction/DifferentialRevisionTransactionType.php index f740d97c74..59b0c7510d 100644 --- a/src/applications/differential/xaction/DifferentialRevisionTransactionType.php +++ b/src/applications/differential/xaction/DifferentialRevisionTransactionType.php @@ -1,4 +1,60 @@ validateMessageCorpus($xaction, $field_name); + if ($error) { + $errors[] = $error; + } + } + + return $errors; + } + + private function validateMessageCorpus($xaction, $field_name) { + $value = $xaction->getNewValue(); + if (!strlen($value)) { + return null; + } + + // Put a placeholder title on the message, because the first line of a + // message is now always parsed as a title. + $value = "\n".$value; + + $viewer = $this->getActor(); + $parser = DifferentialCommitMessageParser::newStandardParser($viewer); + + // Set custom title and summary keys so we can detect the presence of + // "Summary:" in, e.g., a test plan. + $parser->setTitleKey('__title__'); + $parser->setSummaryKey('__summary__'); + + $result = $parser->parseCorpus($value); + + unset($result['__title__']); + unset($result['__summary__']); + + if (!$result) { + return null; + } + + return $this->newInvalidError( + pht( + 'The value you have entered in "%s" can not be parsed '. + 'unambiguously when rendered in a commit message. Edit the '. + 'message so that keywords like "Summary:" and "Test Plan:" do '. + 'not appear at the beginning of lines. Parsed keys: %s.', + $field_name, + implode(', ', array_keys($result))), + $xaction); + } + +}