Skip to content

Commit 7097abb

Browse files
author
epriestley
committedNov 15, 2016
Add a bunch of Phacility-specific code to the upstream, thinly veiled as generic code
Summary: Ref T9304. This adds a "GuidanceEngine" which can generate "Guidance". In practice, this lets third-party code (rSERVICES) remove and replace instructions in the UI, which is basically only usefulf or us to tell users to go read the documentation in the Phacility cluster. The next diff tailors the help on the "Auth Providers" and "Create New User" pages to say "PHACILITY PHACILITY PHACILITY PHACILITY". Test Plan: Browed to "Auth Providers" and "Create New User" on instanced and non-instanced installs, saw appropriate guidance. Reviewers: chad Reviewed By: chad Maniphest Tasks: T9304 Differential Revision: https://secure.phabricator.com/D16861
1 parent e6c82c0 commit 7097abb

11 files changed

+333
-64
lines changed
 

‎src/__phutil_library_map__.php

+14
Original file line numberDiff line numberDiff line change
@@ -1917,6 +1917,8 @@
19171917
'PhabricatorAuthProviderConfigQuery' => 'applications/auth/query/PhabricatorAuthProviderConfigQuery.php',
19181918
'PhabricatorAuthProviderConfigTransaction' => 'applications/auth/storage/PhabricatorAuthProviderConfigTransaction.php',
19191919
'PhabricatorAuthProviderConfigTransactionQuery' => 'applications/auth/query/PhabricatorAuthProviderConfigTransactionQuery.php',
1920+
'PhabricatorAuthProvidersGuidanceContext' => 'applications/auth/guidance/PhabricatorAuthProvidersGuidanceContext.php',
1921+
'PhabricatorAuthProvidersGuidanceEngineExtension' => 'applications/auth/guidance/PhabricatorAuthProvidersGuidanceEngineExtension.php',
19201922
'PhabricatorAuthQueryPublicKeysConduitAPIMethod' => 'applications/auth/conduit/PhabricatorAuthQueryPublicKeysConduitAPIMethod.php',
19211923
'PhabricatorAuthRegisterController' => 'applications/auth/controller/PhabricatorAuthRegisterController.php',
19221924
'PhabricatorAuthRevokeTokenController' => 'applications/auth/controller/PhabricatorAuthRevokeTokenController.php',
@@ -2728,6 +2730,10 @@
27282730
'PhabricatorGlobalLock' => 'infrastructure/util/PhabricatorGlobalLock.php',
27292731
'PhabricatorGlobalUploadTargetView' => 'applications/files/view/PhabricatorGlobalUploadTargetView.php',
27302732
'PhabricatorGoogleAuthProvider' => 'applications/auth/provider/PhabricatorGoogleAuthProvider.php',
2733+
'PhabricatorGuidanceContext' => 'applications/guides/guidance/PhabricatorGuidanceContext.php',
2734+
'PhabricatorGuidanceEngine' => 'applications/guides/guidance/PhabricatorGuidanceEngine.php',
2735+
'PhabricatorGuidanceEngineExtension' => 'applications/guides/guidance/PhabricatorGuidanceEngineExtension.php',
2736+
'PhabricatorGuidanceMessage' => 'applications/guides/guidance/PhabricatorGuidanceMessage.php',
27312737
'PhabricatorGuideApplication' => 'applications/guides/application/PhabricatorGuideApplication.php',
27322738
'PhabricatorGuideController' => 'applications/guides/controller/PhabricatorGuideController.php',
27332739
'PhabricatorGuideInstallModule' => 'applications/guides/module/PhabricatorGuideInstallModule.php',
@@ -3218,6 +3224,7 @@
32183224
'PhabricatorPeopleApproveController' => 'applications/people/controller/PhabricatorPeopleApproveController.php',
32193225
'PhabricatorPeopleController' => 'applications/people/controller/PhabricatorPeopleController.php',
32203226
'PhabricatorPeopleCreateController' => 'applications/people/controller/PhabricatorPeopleCreateController.php',
3227+
'PhabricatorPeopleCreateGuidanceContext' => 'applications/people/guidance/PhabricatorPeopleCreateGuidanceContext.php',
32213228
'PhabricatorPeopleDatasource' => 'applications/people/typeahead/PhabricatorPeopleDatasource.php',
32223229
'PhabricatorPeopleDeleteController' => 'applications/people/controller/PhabricatorPeopleDeleteController.php',
32233230
'PhabricatorPeopleDetailsProfilePanel' => 'applications/people/profilepanel/PhabricatorPeopleDetailsProfilePanel.php',
@@ -6730,6 +6737,8 @@
67306737
'PhabricatorAuthProviderConfigQuery' => 'PhabricatorCursorPagedPolicyAwareQuery',
67316738
'PhabricatorAuthProviderConfigTransaction' => 'PhabricatorApplicationTransaction',
67326739
'PhabricatorAuthProviderConfigTransactionQuery' => 'PhabricatorApplicationTransactionQuery',
6740+
'PhabricatorAuthProvidersGuidanceContext' => 'PhabricatorGuidanceContext',
6741+
'PhabricatorAuthProvidersGuidanceEngineExtension' => 'PhabricatorGuidanceEngineExtension',
67336742
'PhabricatorAuthQueryPublicKeysConduitAPIMethod' => 'PhabricatorAuthConduitAPIMethod',
67346743
'PhabricatorAuthRegisterController' => 'PhabricatorAuthController',
67356744
'PhabricatorAuthRevokeTokenController' => 'PhabricatorAuthController',
@@ -7687,6 +7696,10 @@
76877696
'PhabricatorGlobalLock' => 'PhutilLock',
76887697
'PhabricatorGlobalUploadTargetView' => 'AphrontView',
76897698
'PhabricatorGoogleAuthProvider' => 'PhabricatorOAuth2AuthProvider',
7699+
'PhabricatorGuidanceContext' => 'Phobject',
7700+
'PhabricatorGuidanceEngine' => 'Phobject',
7701+
'PhabricatorGuidanceEngineExtension' => 'Phobject',
7702+
'PhabricatorGuidanceMessage' => 'Phobject',
76907703
'PhabricatorGuideApplication' => 'PhabricatorApplication',
76917704
'PhabricatorGuideController' => 'PhabricatorController',
76927705
'PhabricatorGuideInstallModule' => 'PhabricatorGuideModule',
@@ -8256,6 +8269,7 @@
82568269
'PhabricatorPeopleApproveController' => 'PhabricatorPeopleController',
82578270
'PhabricatorPeopleController' => 'PhabricatorController',
82588271
'PhabricatorPeopleCreateController' => 'PhabricatorPeopleController',
8272+
'PhabricatorPeopleCreateGuidanceContext' => 'PhabricatorGuidanceContext',
82598273
'PhabricatorPeopleDatasource' => 'PhabricatorTypeaheadDatasource',
82608274
'PhabricatorPeopleDeleteController' => 'PhabricatorPeopleController',
82618275
'PhabricatorPeopleDetailsProfilePanel' => 'PhabricatorProfilePanel',

‎src/applications/auth/controller/config/PhabricatorAuthListController.php

+6-62
Original file line numberDiff line numberDiff line change
@@ -94,58 +94,12 @@ public function handleRequest(AphrontRequest $request) {
9494
$crumbs->addTextCrumb(pht('Auth Providers'));
9595
$crumbs->setBorder(true);
9696

97-
$domains_key = 'auth.email-domains';
98-
$domains_link = $this->renderConfigLink($domains_key);
99-
$domains_value = PhabricatorEnv::getEnvConfig($domains_key);
100-
101-
$approval_key = 'auth.require-approval';
102-
$approval_link = $this->renderConfigLink($approval_key);
103-
$approval_value = PhabricatorEnv::getEnvConfig($approval_key);
104-
105-
$issues = array();
106-
if ($domains_value) {
107-
$issues[] = pht(
108-
'Phabricator is configured with an email domain whitelist (in %s), so '.
109-
'only users with a verified email address at one of these %s '.
110-
'allowed domain(s) will be able to register an account: %s',
111-
$domains_link,
112-
phutil_count($domains_value),
113-
phutil_tag('strong', array(), implode(', ', $domains_value)));
114-
} else {
115-
$issues[] = pht(
116-
'Anyone who can browse to this Phabricator install will be able to '.
117-
'register an account. To add email domain restrictions, configure '.
118-
'%s.',
119-
$domains_link);
120-
}
121-
122-
if ($approval_value) {
123-
$issues[] = pht(
124-
'Administrative approvals are enabled (in %s), so all new users must '.
125-
'have their accounts approved by an administrator.',
126-
$approval_link);
127-
} else {
128-
$issues[] = pht(
129-
'Administrative approvals are disabled, so users who register will '.
130-
'be able to use their accounts immediately. To enable approvals, '.
131-
'configure %s.',
132-
$approval_link);
133-
}
134-
135-
if (!$domains_value && !$approval_value) {
136-
$severity = PHUIInfoView::SEVERITY_WARNING;
137-
$issues[] = pht(
138-
'You can safely ignore this warning if the install itself has '.
139-
'access controls (for example, it is deployed on a VPN) or if all of '.
140-
'the configured providers have access controls (for example, they are '.
141-
'all private LDAP or OAuth servers).');
142-
} else {
143-
$severity = PHUIInfoView::SEVERITY_NOTICE;
144-
}
97+
$guidance_context = new PhabricatorAuthProvidersGuidanceContext();
14598

146-
$warning = id(new PHUIInfoView())
147-
->setSeverity($severity)
148-
->setErrors($issues);
99+
$guidance = id(new PhabricatorGuidanceEngine())
100+
->setViewer($viewer)
101+
->setGuidanceContext($guidance_context)
102+
->newInfoView();
149103

150104
$button = id(new PHUIButtonView())
151105
->setTag('a')
@@ -170,7 +124,7 @@ public function handleRequest(AphrontRequest $request) {
170124
$view = id(new PHUITwoColumnView())
171125
->setHeader($header)
172126
->setFooter(array(
173-
$warning,
127+
$guidance,
174128
$list,
175129
));
176130

@@ -180,14 +134,4 @@ public function handleRequest(AphrontRequest $request) {
180134
->appendChild($view);
181135
}
182136

183-
private function renderConfigLink($key) {
184-
return phutil_tag(
185-
'a',
186-
array(
187-
'href' => '/config/edit/'.$key.'/',
188-
'target' => '_blank',
189-
),
190-
$key);
191-
}
192-
193137
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
<?php
2+
3+
final class PhabricatorAuthProvidersGuidanceContext
4+
extends PhabricatorGuidanceContext {}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,88 @@
1+
<?php
2+
3+
final class PhabricatorAuthProvidersGuidanceEngineExtension
4+
extends PhabricatorGuidanceEngineExtension {
5+
6+
const GUIDANCEKEY = 'core.auth.providers';
7+
8+
public function canGenerateGuidance(PhabricatorGuidanceContext $context) {
9+
return ($context instanceof PhabricatorAuthProvidersGuidanceContext);
10+
}
11+
12+
public function generateGuidance(PhabricatorGuidanceContext $context) {
13+
$domains_key = 'auth.email-domains';
14+
$domains_link = $this->renderConfigLink($domains_key);
15+
$domains_value = PhabricatorEnv::getEnvConfig($domains_key);
16+
17+
$approval_key = 'auth.require-approval';
18+
$approval_link = $this->renderConfigLink($approval_key);
19+
$approval_value = PhabricatorEnv::getEnvConfig($approval_key);
20+
21+
$results = array();
22+
23+
if ($domains_value) {
24+
$message = pht(
25+
'Phabricator is configured with an email domain whitelist (in %s), so '.
26+
'only users with a verified email address at one of these %s '.
27+
'allowed domain(s) will be able to register an account: %s',
28+
$domains_link,
29+
phutil_count($domains_value),
30+
phutil_tag('strong', array(), implode(', ', $domains_value)));
31+
32+
$results[] = $this->newGuidance('core.auth.email-domains.on')
33+
->setMessage($message);
34+
} else {
35+
$message = pht(
36+
'Anyone who can browse to this Phabricator install will be able to '.
37+
'register an account. To add email domain restrictions, configure '.
38+
'%s.',
39+
$domains_link);
40+
41+
$results[] = $this->newGuidance('core.auth.email-domains.off')
42+
->setMessage($message);
43+
}
44+
45+
if ($approval_value) {
46+
$message = pht(
47+
'Administrative approvals are enabled (in %s), so all new users must '.
48+
'have their accounts approved by an administrator.',
49+
$approval_link);
50+
51+
$results[] = $this->newGuidance('core.auth.require-approval.on')
52+
->setMessage($message);
53+
} else {
54+
$message = pht(
55+
'Administrative approvals are disabled, so users who register will '.
56+
'be able to use their accounts immediately. To enable approvals, '.
57+
'configure %s.',
58+
$approval_link);
59+
60+
$results[] = $this->newGuidance('core.auth.require-approval.off')
61+
->setMessage($message);
62+
}
63+
64+
if (!$domains_value && !$approval_value) {
65+
$message = pht(
66+
'You can safely ignore these warnings if the install itself has '.
67+
'access controls (for example, it is deployed on a VPN) or if all of '.
68+
'the configured providers have access controls (for example, they are '.
69+
'all private LDAP or OAuth servers).');
70+
71+
$results[] = $this->newWarning('core.auth.warning')
72+
->setMessage($message);
73+
}
74+
75+
return $results;
76+
}
77+
78+
private function renderConfigLink($key) {
79+
return phutil_tag(
80+
'a',
81+
array(
82+
'href' => '/config/edit/'.$key.'/',
83+
'target' => '_blank',
84+
),
85+
$key);
86+
}
87+
88+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
<?php
2+
3+
abstract class PhabricatorGuidanceContext
4+
extends Phobject {}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,96 @@
1+
<?php
2+
3+
final class PhabricatorGuidanceEngine
4+
extends Phobject {
5+
6+
private $viewer;
7+
private $guidanceContext;
8+
9+
public function setGuidanceContext(
10+
PhabricatorGuidanceContext $guidance_context) {
11+
$this->guidanceContext = $guidance_context;
12+
return $this;
13+
}
14+
15+
public function getGuidanceContext() {
16+
return $this->guidanceContext;
17+
}
18+
19+
public function setViewer(PhabricatorUser $viewer) {
20+
$this->viewer = $viewer;
21+
return $this;
22+
}
23+
24+
public function getViewer() {
25+
return $this->viewer;
26+
}
27+
28+
public function newInfoView() {
29+
$extensions = PhabricatorGuidanceEngineExtension::getAllExtensions();
30+
$context = $this->getGuidanceContext();
31+
32+
$keep = array();
33+
foreach ($extensions as $key => $extension) {
34+
if (!$extension->canGenerateGuidance($context)) {
35+
continue;
36+
}
37+
$keep[$key] = id(clone $extension);
38+
}
39+
40+
$guidance_map = array();
41+
foreach ($keep as $extension) {
42+
$guidance_list = $extension->generateGuidance($context);
43+
foreach ($guidance_list as $guidance) {
44+
$key = $guidance->getKey();
45+
46+
if (isset($guidance_map[$key])) {
47+
throw new Exception(
48+
pht(
49+
'Two guidance extensions generated guidance with the same '.
50+
'key ("%s"). Each piece of guidance must have a unique key.',
51+
$key));
52+
}
53+
54+
$guidance_map[$key] = $guidance;
55+
}
56+
}
57+
58+
foreach ($keep as $extension) {
59+
$guidance_map = $extension->didGenerateGuidance($context, $guidance_map);
60+
}
61+
62+
if (!$guidance_map) {
63+
return null;
64+
}
65+
66+
$guidance_map = msortv($guidance_map, 'getSortVector');
67+
68+
$severity = PhabricatorGuidanceMessage::SEVERITY_NOTICE;
69+
$strength = null;
70+
foreach ($guidance_map as $guidance) {
71+
if ($strength !== null) {
72+
if ($guidance->getSeverityStrength() <= $strength) {
73+
continue;
74+
}
75+
}
76+
77+
$strength = $guidance->getSeverityStrength();
78+
$severity = $guidance->getSeverity();
79+
}
80+
81+
$severity_map = array(
82+
PhabricatorGuidanceMessage::SEVERITY_NOTICE
83+
=> PHUIInfoView::SEVERITY_NOTICE,
84+
PhabricatorGuidanceMessage::SEVERITY_WARNING
85+
=> PHUIInfoView::SEVERITY_WARNING,
86+
);
87+
88+
$messages = mpull($guidance_map, 'getMessage', 'getKey');
89+
90+
return id(new PHUIInfoView())
91+
->setViewer($this->getViewer())
92+
->setSeverity(idx($severity_map, $severity, $severity))
93+
->setErrors($messages);
94+
}
95+
96+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
<?php
2+
3+
abstract class PhabricatorGuidanceEngineExtension
4+
extends Phobject {
5+
6+
final public function getExtensionKey() {
7+
return $this->getPhobjectClassConstant('GUIDANCEKEY', 64);
8+
}
9+
10+
abstract public function canGenerateGuidance(
11+
PhabricatorGuidanceContext $context);
12+
13+
abstract public function generateGuidance(
14+
PhabricatorGuidanceContext $context);
15+
16+
public function didGenerateGuidance(
17+
PhabricatorGuidanceContext $context,
18+
array $guidance) {
19+
return $guidance;
20+
}
21+
22+
final protected function newGuidance($key) {
23+
return id(new PhabricatorGuidanceMessage())
24+
->setKey($key);
25+
}
26+
27+
final protected function newWarning($key) {
28+
return $this->newGuidance($key)
29+
->setSeverity(PhabricatorGuidanceMessage::SEVERITY_WARNING);
30+
}
31+
32+
final public static function getAllExtensions() {
33+
return id(new PhutilClassMapQuery())
34+
->setAncestorClass(__CLASS__)
35+
->setUniqueMethod('getExtensionKey')
36+
->execute();
37+
}
38+
39+
}

0 commit comments

Comments
 (0)
Failed to load comments.