@recaptime-dev's working patches + fork for Phorge, a community fork of Phabricator. (Upstream dev and stable branches are at upstream/main and upstream/stable respectively.) hq.recaptime.dev/wiki/Phorge
phorge phabricator
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Legalpad - add policy rule for legalpad document signatures

Summary:
Ref T3116. This creates a policy rule where you can require a signature on a given legalpad document.

NOTE: signatures must be for the *latest* document version.

Test Plan: made a task have a custom policy requiring a legalpad signature. verified non-signers were locked out.

Reviewers: epriestley

Reviewed By: epriestley

CC: Korvin, epriestley, aran

Maniphest Tasks: T3116

Differential Revision: https://secure.phabricator.com/D7977

+122 -3
+5
resources/sql/autopatches/20140115.legalpadsigkey.sql
··· 1 + ALTER TABLE {$NAMESPACE}_legalpad.legalpad_documentsignature 2 + DROP KEY `key_document`; 3 + 4 + ALTER TABLE {$NAMESPACE}_legalpad.legalpad_documentsignature 5 + ADD KEY `key_document` (`documentPHID`,`signerPHID`, `documentVersion`);
+2
src/__phutil_library_map__.php
··· 1764 1764 'PhabricatorPolicyQuery' => 'applications/policy/query/PhabricatorPolicyQuery.php', 1765 1765 'PhabricatorPolicyRule' => 'applications/policy/rule/PhabricatorPolicyRule.php', 1766 1766 'PhabricatorPolicyRuleAdministrators' => 'applications/policy/rule/PhabricatorPolicyRuleAdministrators.php', 1767 + 'PhabricatorPolicyRuleLegalpadSignature' => 'applications/policy/rule/PhabricatorPolicyRuleLegalpadSignature.php', 1767 1768 'PhabricatorPolicyRuleLunarPhase' => 'applications/policy/rule/PhabricatorPolicyRuleLunarPhase.php', 1768 1769 'PhabricatorPolicyRuleProjects' => 'applications/policy/rule/PhabricatorPolicyRuleProjects.php', 1769 1770 'PhabricatorPolicyRuleUsers' => 'applications/policy/rule/PhabricatorPolicyRuleUsers.php', ··· 4395 4396 'PhabricatorPolicyPHIDTypePolicy' => 'PhabricatorPHIDType', 4396 4397 'PhabricatorPolicyQuery' => 'PhabricatorCursorPagedPolicyAwareQuery', 4397 4398 'PhabricatorPolicyRuleAdministrators' => 'PhabricatorPolicyRule', 4399 + 'PhabricatorPolicyRuleLegalpadSignature' => 'PhabricatorPolicyRule', 4398 4400 'PhabricatorPolicyRuleLunarPhase' => 'PhabricatorPolicyRule', 4399 4401 'PhabricatorPolicyRuleProjects' => 'PhabricatorPolicyRule', 4400 4402 'PhabricatorPolicyRuleUsers' => 'PhabricatorPolicyRule',
+3 -3
src/applications/legalpad/controller/LegalpadDocumentSignController.php
··· 58 58 if ($signer_phid) { 59 59 $signature = id(new LegalpadDocumentSignature()) 60 60 ->loadOneWhere( 61 - 'documentPHID = %s AND documentVersion = %d AND signerPHID = %s', 61 + 'documentPHID = %s AND signerPHID = %s AND documentVersion = %d', 62 62 $document->getPHID(), 63 - $document->getVersions(), 64 - $signer_phid); 63 + $signer_phid, 64 + $document->getVersions()); 65 65 } 66 66 67 67 if (!$signature) {
+27
src/applications/legalpad/query/LegalpadDocumentQuery.php
··· 10 10 private $phids; 11 11 private $creatorPHIDs; 12 12 private $contributorPHIDs; 13 + private $signerPHIDs; 13 14 private $dateCreatedAfter; 14 15 private $dateCreatedBefore; 15 16 ··· 33 34 34 35 public function withContributorPHIDs(array $phids) { 35 36 $this->contributorPHIDs = $phids; 37 + return $this; 38 + } 39 + 40 + public function withSignerPHIDs(array $phids) { 41 + $this->signerPHIDs = $phids; 36 42 return $this; 37 43 } 38 44 ··· 75 81 } 76 82 77 83 protected function willFilterPage(array $documents) { 84 + if ($this->signerPHIDs) { 85 + $document_map = mpull($documents, null, 'getPHID'); 86 + $signatures = id(new LegalpadDocumentSignature()) 87 + ->loadAllWhere( 88 + 'documentPHID IN (%Ls) AND signerPHID IN (%Ls)', 89 + array_keys($document_map), 90 + $this->signerPHIDs); 91 + $signatures = mgroup($signatures, 'getDocumentPHID'); 92 + foreach ($document_map as $document_phid => $document) { 93 + $sigs = idx($signatures, $document_phid, array()); 94 + foreach ($sigs as $index => $sig) { 95 + if ($sig->getDocumentVersion() != $document->getVersions()) { 96 + unset($sigs[$index]); 97 + } 98 + } 99 + $signer_phids = mpull($sigs, 'getSignerPHID'); 100 + if (array_diff($this->signerPHIDs, $signer_phids)) { 101 + unset($documents[$document->getID()]); 102 + } 103 + } 104 + } 78 105 if ($this->needDocumentBodies) { 79 106 $documents = $this->loadDocumentBodies($documents); 80 107 }
+69
src/applications/policy/rule/PhabricatorPolicyRuleLegalpadSignature.php
··· 1 + <?php 2 + 3 + final class PhabricatorPolicyRuleLegalpadSignature 4 + extends PhabricatorPolicyRule { 5 + 6 + private $signatures = array(); 7 + 8 + public function getRuleDescription() { 9 + return pht('signers of legalpad documents'); 10 + } 11 + 12 + public function willApplyRules(PhabricatorUser $viewer, array $values) { 13 + $values = array_unique(array_filter(array_mergev($values))); 14 + if (!$values) { 15 + return; 16 + } 17 + 18 + $documents = id(new LegalpadDocumentQuery()) 19 + ->setViewer(PhabricatorUser::getOmnipotentUser()) 20 + ->withPHIDs($values) 21 + ->withSignerPHIDs(array($viewer->getPHID())) 22 + ->execute(); 23 + $this->signatures = mpull($documents, 'getPHID', 'getPHID'); 24 + } 25 + 26 + public function applyRule(PhabricatorUser $viewer, $value) { 27 + foreach ($value as $document_phid) { 28 + if (!isset($this->signatures[$document_phid])) { 29 + return false; 30 + } 31 + } 32 + return true; 33 + } 34 + 35 + public function getValueControlType() { 36 + return self::CONTROL_TYPE_TOKENIZER; 37 + } 38 + 39 + public function getValueControlTemplate() { 40 + return array( 41 + 'markup' => new AphrontTokenizerTemplateView(), 42 + 'uri' => '/typeahead/common/legalpaddocuments/', 43 + 'placeholder' => pht('Type a document title...'), 44 + ); 45 + } 46 + 47 + public function getRuleOrder() { 48 + return 900; 49 + } 50 + 51 + public function getValueForStorage($value) { 52 + PhutilTypeSpec::newFromString('list<string>')->check($value); 53 + return array_values($value); 54 + } 55 + 56 + public function getValueForDisplay(PhabricatorUser $viewer, $value) { 57 + $handles = id(new PhabricatorHandleQuery()) 58 + ->setViewer($viewer) 59 + ->withPHIDs($value) 60 + ->execute(); 61 + 62 + return mpull($handles, 'getFullName', 'getPHID'); 63 + } 64 + 65 + public function ruleHasEffect($value) { 66 + return (bool)$value; 67 + } 68 + 69 + }
+16
src/applications/typeahead/controller/PhabricatorTypeaheadCommonDatasourceController.php
··· 37 37 $need_jump_objects = false; 38 38 $need_build_plans = false; 39 39 $need_macros = false; 40 + $need_legalpad_documents = false; 40 41 switch ($this->type) { 41 42 case 'mainsearch': 42 43 $need_users = true; ··· 100 101 break; 101 102 case 'macros': 102 103 $need_macros = true; 104 + break; 105 + case 'legalpaddocuments': 106 + $need_legalpad_documents = true; 103 107 break; 104 108 } 105 109 ··· 249 253 $results[] = id(new PhabricatorTypeaheadResult()) 250 254 ->setPHID($phid) 251 255 ->setName($name); 256 + } 257 + } 258 + 259 + if ($need_legalpad_documents) { 260 + $documents = id(new LegalpadDocumentQuery()) 261 + ->setViewer($viewer) 262 + ->execute(); 263 + $documents = mpull($documents, 'getTitle', 'getPHID'); 264 + foreach ($documents as $phid => $title) { 265 + $results[] = id(new PhabricatorTypeaheadResult()) 266 + ->setPHID($phid) 267 + ->setName($title); 252 268 } 253 269 } 254 270