When showing policy hints, if the Space policy is strictly stronger, show it instead
Summary:
Ref T8449. Before we show a policy hint in the header of an object, compare it to the space policy (if one exists).
If the space policy is strictly stronger (more restrictive -- for example, the Space policy is 'members of X', and the object policy is 'public'), show the space policy instead.
See discussion on T8376.
Test Plan: {F509126}
Reviewers: btrahan
Reviewed By: btrahan
Subscribers: epriestley
Maniphest Tasks: T8449
Differential Revision: https://secure.phabricator.com/D13328
This commit is contained in:
@@ -69,44 +69,115 @@ final class PhabricatorPolicyExplainController
|
||||
$capability_name = $capobj->getCapabilityName();
|
||||
}
|
||||
|
||||
$space_info = null;
|
||||
if ($object instanceof PhabricatorSpacesInterface) {
|
||||
if (PhabricatorSpacesNamespaceQuery::getViewerSpacesExist($viewer)) {
|
||||
$space_phid = PhabricatorSpacesNamespaceQuery::getObjectSpacePHID(
|
||||
$object);
|
||||
$dialog = id(new AphrontDialogView())
|
||||
->setUser($viewer)
|
||||
->setClass('aphront-access-dialog');
|
||||
|
||||
$handles = $viewer->loadHandles(array($space_phid));
|
||||
$this->appendSpaceInformation($dialog, $object, $policy, $capability);
|
||||
|
||||
$space_info = array(
|
||||
pht(
|
||||
'This object is in %s, and can only be seen by users with '.
|
||||
'access to that space.',
|
||||
$handles[$space_phid]->renderLink()),
|
||||
phutil_tag('br'),
|
||||
phutil_tag('br'),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
$content = array(
|
||||
$space_info,
|
||||
pht('Users with the "%s" capability:', $capability_name),
|
||||
$auto_info,
|
||||
);
|
||||
$intro = pht(
|
||||
'Users with the "%s" capability for this object:',
|
||||
$capability_name);
|
||||
|
||||
$object_name = pht(
|
||||
'%s %s',
|
||||
$handle->getTypeName(),
|
||||
$handle->getObjectName());
|
||||
|
||||
$dialog = id(new AphrontDialogView())
|
||||
->setUser($viewer)
|
||||
->setClass('aphront-access-dialog')
|
||||
return $dialog
|
||||
->setTitle(pht('Policy Details: %s', $object_name))
|
||||
->appendChild($content)
|
||||
->appendParagraph($intro)
|
||||
->appendChild($auto_info)
|
||||
->addCancelButton($object_uri, pht('Done'));
|
||||
}
|
||||
|
||||
return id(new AphrontDialogResponse())->setDialog($dialog);
|
||||
private function appendSpaceInformation(
|
||||
AphrontDialogView $dialog,
|
||||
PhabricatorPolicyInterface $object,
|
||||
PhabricatorPolicy $policy,
|
||||
$capability) {
|
||||
$viewer = $this->getViewer();
|
||||
|
||||
if (!($object instanceof PhabricatorSpacesInterface)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!PhabricatorSpacesNamespaceQuery::getSpacesExist($viewer)) {
|
||||
return;
|
||||
}
|
||||
|
||||
// NOTE: We're intentionally letting users through here, even if they only
|
||||
// have access to one space. The intent is to help users in "space jail"
|
||||
// understand who objects they create are visible to:
|
||||
|
||||
$space_phid = PhabricatorSpacesNamespaceQuery::getObjectSpacePHID(
|
||||
$object);
|
||||
|
||||
$handles = $viewer->loadHandles(array($space_phid));
|
||||
$doc_href = PhabricatorEnv::getDoclink('Spaces User Guide');
|
||||
|
||||
$dialog->appendParagraph(
|
||||
array(
|
||||
pht(
|
||||
'This object is in %s, and can only be seen or edited by users with '.
|
||||
'access to view objects in the space.',
|
||||
$handles[$space_phid]->renderLink()),
|
||||
' ',
|
||||
phutil_tag(
|
||||
'strong',
|
||||
array(),
|
||||
phutil_tag(
|
||||
'a',
|
||||
array(
|
||||
'href' => $doc_href,
|
||||
'target' => '_blank',
|
||||
),
|
||||
pht('Learn More'))),
|
||||
));
|
||||
|
||||
$spaces = PhabricatorSpacesNamespaceQuery::getViewerSpaces($viewer);
|
||||
$space = idx($spaces, $space_phid);
|
||||
if (!$space) {
|
||||
return;
|
||||
}
|
||||
|
||||
$space_policies = PhabricatorPolicyQuery::loadPolicies($viewer, $space);
|
||||
$space_policy = idx($space_policies, PhabricatorPolicyCapability::CAN_VIEW);
|
||||
if (!$space_policy) {
|
||||
return;
|
||||
}
|
||||
|
||||
$space_explanation = PhabricatorPolicy::getPolicyExplanation(
|
||||
$viewer,
|
||||
$space_policy->getPHID());
|
||||
$items = array();
|
||||
$items[] = $space_explanation;
|
||||
|
||||
foreach ($items as $key => $item) {
|
||||
$items[$key] = phutil_tag('li', array(), $item);
|
||||
}
|
||||
|
||||
$dialog->appendParagraph(pht('Users who can see objects in this space:'));
|
||||
$dialog->appendChild(phutil_tag('ul', array(), $items));
|
||||
|
||||
$view_capability = PhabricatorPolicyCapability::CAN_VIEW;
|
||||
if ($capability == $view_capability) {
|
||||
$stronger = $space_policy->isStrongerThan($policy);
|
||||
if ($stronger) {
|
||||
$dialog->appendParagraph(
|
||||
pht(
|
||||
'The space this object is in has a more restrictive view '.
|
||||
'policy ("%s") than the object does ("%s"), so the space\'s '.
|
||||
'view policy is shown as a hint instead of the object policy.',
|
||||
$space_policy->getShortName(),
|
||||
$policy->getShortName()));
|
||||
}
|
||||
}
|
||||
|
||||
$dialog->appendParagraph(
|
||||
pht(
|
||||
'After a user passes space policy checks, they must still pass '.
|
||||
'object policy checks.'));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user