Просмотр исходного кода

add ID/Pass tab to /admin/security

Yuki Takei 6 лет назад
Родитель
Сommit
856632acc5

+ 0 - 4
src/server/form/admin/securityGeneral.js

@@ -1,13 +1,9 @@
 const form = require('express-form');
 
 const field = form.field;
-const stringToArray = require('../../util/formUtil').stringToArrayFilter;
-const normalizeCRLF = require('../../util/formUtil').normalizeCRLFFilter;
 
 module.exports = form(
   field('settingForm[security:restrictGuestMode]'),
-  field('settingForm[security:registrationMode]').required(),
-  field('settingForm[security:registrationWhiteList]').custom(normalizeCRLF).custom(stringToArray),
   field('settingForm[security:list-policy:hideRestrictedByOwner]').trim().toBooleanStrict(),
   field('settingForm[security:list-policy:hideRestrictedByGroup]').trim().toBooleanStrict(),
   field('settingForm[security:pageCompleteDeletionAuthority]'),

+ 11 - 0
src/server/form/admin/securityPassportLocal.js

@@ -0,0 +1,11 @@
+const form = require('express-form');
+
+const field = form.field;
+const stringToArray = require('../../util/formUtil').stringToArrayFilter;
+const normalizeCRLF = require('../../util/formUtil').normalizeCRLFFilter;
+
+module.exports = form(
+  field('settingForm[security:passport-local:isEnabled]').trim().toBooleanStrict().required(),
+  field('settingForm[security:registrationMode]').required(),
+  field('settingForm[security:registrationWhiteList]').custom(normalizeCRLF).custom(stringToArray),
+);

+ 1 - 0
src/server/form/index.js

@@ -19,6 +19,7 @@ module.exports = {
     importerQiita: require('./admin/importerQiita'),
     plugin: require('./admin/plugin'),
     securityGeneral: require('./admin/securityGeneral'),
+    securityPassportLocal: require('./admin/securityPassportLocal'),
     securityPassportLdap: require('./admin/securityPassportLdap'),
     securityPassportSaml: require('./admin/securityPassportSaml'),
     securityPassportBasic: require('./admin/securityPassportBasic'),

+ 1 - 0
src/server/models/config.js

@@ -49,6 +49,7 @@ module.exports = function(crowi) {
       'security:list-policy:hideRestrictedByGroup' : false,
       'security:pageCompleteDeletionAuthority' : undefined,
 
+      'security:passport-local:isEnabled' : true,
       'security:passport-ldap:isEnabled' : false,
       'security:passport-ldap:serverUrl' : undefined,
       'security:passport-ldap:isUserBind' : undefined,

+ 26 - 0
src/server/routes/admin.js

@@ -918,6 +918,32 @@ module.exports = function(crowi, app) {
     }
   };
 
+  actions.api.securityPassportLocalSetting = async function(req, res) {
+    const form = req.form.settingForm;
+
+    if (!req.form.isValid) {
+      return res.json({ status: false, message: req.form.errors.join('\n') });
+    }
+
+    debug('form content', form);
+
+    try {
+      await configManager.updateConfigsInTheSameNamespace('crowi', form);
+      // reset strategy
+      crowi.passportService.resetLocalStrategy();
+      // setup strategy
+      if (configManager.getConfig('crowi', 'security:passport-local:isEnabled')) {
+        crowi.passportService.setupLocalStrategy(true);
+      }
+    }
+    catch (err) {
+      logger.error(err);
+      return res.json({ status: false, message: err.message });
+    }
+
+    return res.json({ status: true });
+  };
+
   actions.api.securityPassportLdapSetting = async function(req, res) {
     const form = req.form.settingForm;
 

+ 1 - 0
src/server/routes/index.js

@@ -58,6 +58,7 @@ module.exports = function(crowi, app) {
   // security admin
   app.get('/admin/security'                     , loginRequired() , adminRequired , admin.security.index);
   app.post('/_api/admin/security/general'       , loginRequired() , adminRequired , form.admin.securityGeneral, admin.api.securitySetting);
+  app.post('/_api/admin/security/passport-local', loginRequired() , adminRequired , csrf, form.admin.securityPassportLocal, admin.api.securityPassportLocalSetting);
   app.post('/_api/admin/security/passport-ldap' , loginRequired() , adminRequired , csrf, form.admin.securityPassportLdap, admin.api.securityPassportLdapSetting);
   app.post('/_api/admin/security/passport-saml' , loginRequired() , adminRequired , csrf, form.admin.securityPassportSaml, admin.api.securityPassportSamlSetting);
   app.post('/_api/admin/security/passport-basic' , loginRequired() , adminRequired , csrf, form.admin.securityPassportBasic, admin.api.securityPassportBasicSetting);

+ 16 - 30
src/server/views/admin/security.html

@@ -59,27 +59,6 @@
             </div>
           </div>
 
-          <div class="form-group">
-            <label for="settingForm[security:registrationMode]" class="col-xs-3 control-label">{{ t('Register limitation') }}</label>
-            <div class="col-xs-6">
-              <select class="form-control selectpicker" name="settingForm[security:registrationMode]" value="{{ getConfig('crowi', 'security:registrationMode') }}">
-                {% for modeValue, modeLabel in consts.registrationMode %}
-                <option value="{{ t(modeValue) }}" {% if modeValue == getConfig('crowi', 'security:registrationMode') %}selected{% endif %} >{{ t(modeLabel) }}</option>
-                {% endfor %}
-              </select>
-              <p class="help-block small">{{ t('security_setting.Register limitation desc') }}</p>
-            </div>
-          </div>
-
-          <div class="form-group">
-            <label for="settingForm[security:registrationWhiteList]" class="col-xs-3 control-label">{{ t('The whitelist of registration permission E-mail address') }}</label>
-            <div class="col-xs-8">
-              <textarea class="form-control" type="textarea" name="settingForm[security:registrationWhiteList]" placeholder="{{ t('security_setting.example') }}: @growi.org">{{ getConfig('crowi', 'security:registrationWhiteList') | join('&#13') | raw }}</textarea>
-              <p class="help-block small">{{ t("security_setting.restrict_emails") }}{{ t("security_setting.for_instance") }}<code>@growi.org</code>{{ t("security_setting.only_those") }}<br>
-              {{ t("security_setting.insert_single") }}</p>
-            </div>
-          </div>
-
           <div class="form-group">
             {% set configName = 'settingForm[security:list-policy:hideRestrictedByOwner]' %}
             {% set configValue = getConfig('crowi', 'security:list-policy:hideRestrictedByOwner') %}
@@ -170,13 +149,16 @@
         <div class="passport-settings">
           <ul class="nav nav-tabs" role="tablist">
             <li class="active">
-              <a href="#passport-saml" data-toggle="tab" role="tab"><i class="fa fa-key"></i> SAML</a>
+              <a href="#passport-local" data-toggle="tab" role="tab"><i class="fa fa-users"></i> ID/Pass</a>
             </li>
             <li>
-              <a href="#passport-oidc" data-toggle="tab" role="tab"><i class="fa fa-openid"></i> OIDC</a>
+              <a href="#passport-ldap" data-toggle="tab" role="tab"><i class="fa fa-sitemap"></i> LDAP</a>
             </li>
             <li>
-              <a href="#passport-ldap" data-toggle="tab" role="tab"><i class="fa fa-sitemap"></i> LDAP</a>
+              <a href="#passport-saml" data-toggle="tab" role="tab"><i class="fa fa-key"></i> SAML</a>
+            </li>
+            <li>
+              <a href="#passport-oidc" data-toggle="tab" role="tab"><i class="fa fa-openid"></i> OIDC</a>
             </li>
             <li>
               <a href="#passport-basic" data-toggle="tab" role="tab"><i class="fa fa-lock"></i> Basic</a>
@@ -196,7 +178,15 @@
           </ul>
 
           <div class="tab-content p-t-10">
-            <div id="passport-saml" class="tab-pane active" role="tabpanel" >
+            <div id="passport-local" class="tab-pane active" role="tabpanel" >
+              {% include './widget/passport/local.html' %}
+            </div>
+
+            <div id="passport-ldap" class="tab-pane" role="tabpanel" >
+              {% include './widget/passport/ldap.html' with { settingForm: settingForm } %}
+            </div>
+
+            <div id="passport-saml" class="tab-pane" role="tabpanel" >
               {% include './widget/passport/saml.html' %}
             </div>
 
@@ -204,10 +194,6 @@
               {% include './widget/passport/oidc.html' %}
             </div>
 
-            <div id="passport-ldap" class="tab-pane" role="tabpanel" >
-              {% include './widget/passport/ldap.html' with { settingForm: settingForm } %}
-            </div>
-
             <div id="passport-basic" class="tab-pane" role="tabpanel">
               {% include './widget/passport/basic.html' %}
             </div>
@@ -236,7 +222,7 @@
   </div>
 
   <script>
-    $('#generalSetting, #samlSetting, #basicSetting, #googleSetting, #githubSetting, #twitterSetting, #oidcSetting').each(function() {
+    $('#generalSetting, #localSetting, #samlSetting, #basicSetting, #googleSetting, #githubSetting, #twitterSetting, #oidcSetting').each(function() {
       $(this).submit(function()
       {
         function showMessage(formId, msg, status) {

+ 77 - 0
src/server/views/admin/widget/passport/local.html

@@ -0,0 +1,77 @@
+<form action="/_api/admin/security/passport-local" method="post" class="form-horizontal passportStrategy" id="localSetting" role="form"
+    {% if isRestartingServerNeeded %}style="opacity: 0.4;"{% endif %}>
+  <legend class="alert-anchor">{{ t("security_setting.Local.name") }} {{ t("security_setting.configuration") }}</legend>
+
+  {% set nameForIsLocalEnabled = "settingForm[security:passport-local:isEnabled]" %}
+  {% set isLocalEnabled = getConfig('crowi', 'security:passport-local:isEnabled') %}
+
+  <div class="form-group">
+    <label for="{{nameForIsLocalEnabled}}" class="col-xs-3 control-label">{{ t("security_setting.Local.name") }}</label>
+    <div class="col-xs-6">
+      <div class="btn-group btn-toggle" data-toggle="buttons">
+        <label class="btn btn-default btn-rounded btn-outline {% if isLocalEnabled %}active{% endif %}" data-active-class="primary">
+          <input name="{{nameForIsLocalEnabled}}" value="true" type="radio"
+              {% if true === isLocalEnabled %}checked{% endif %}> ON
+        </label>
+        <label class="btn btn-default btn-rounded btn-outline {% if !isLocalEnabled %}active{% endif %}" data-active-class="default">
+          <input name="{{nameForIsLocalEnabled}}" value="false" type="radio"
+              {% if !isLocalEnabled %}checked{% endif %}> OFF
+        </label>
+      </div>
+      <p class="help-block">
+        <small>
+          {{ t("security_setting.Local.desc_1") }}<br>
+          {{ t("security_setting.Local.desc_2") }}
+        </small>
+      </p>
+    </div>
+  </div>
+
+
+  <fieldset id="passport-local-hide-when-disabled" {%if !isLocalEnabled %}style="display: none;"{% endif %}>
+
+    <div class="form-group">
+      <label for="settingForm[security:registrationMode]" class="col-xs-3 control-label">{{ t('Register limitation') }}</label>
+      <div class="col-xs-6">
+        <select class="form-control selectpicker" name="settingForm[security:registrationMode]" value="{{ getConfig('crowi', 'security:registrationMode') }}">
+          {% for modeValue, modeLabel in consts.registrationMode %}
+          <option value="{{ t(modeValue) }}" {% if modeValue == getConfig('crowi', 'security:registrationMode') %}selected{% endif %} >{{ t(modeLabel) }}</option>
+          {% endfor %}
+        </select>
+        <p class="help-block small">{{ t('security_setting.Register limitation desc') }}</p>
+      </div>
+    </div>
+
+    <div class="form-group">
+      <label for="settingForm[security:registrationWhiteList]" class="col-xs-3 control-label">{{ t('The whitelist of registration permission E-mail address') }}</label>
+      <div class="col-xs-8">
+        <textarea class="form-control" type="textarea" name="settingForm[security:registrationWhiteList]" placeholder="{{ t('security_setting.example') }}: @growi.org">{{ getConfig('crowi', 'security:registrationWhiteList') | join('&#13') | raw }}</textarea>
+        <p class="help-block small">{{ t("security_setting.restrict_emails") }}{{ t("security_setting.for_instance") }}<code>@growi.org</code>{{ t("security_setting.only_those") }}<br>
+        {{ t("security_setting.insert_single") }}</p>
+      </div>
+    </div>
+
+  </fieldset>
+
+  <div class="form-group" id="btn-update">
+    <div class="col-xs-offset-3 col-xs-6">
+      <input type="hidden" name="_csrf" value="{{ csrf() }}">
+      <button type="submit" class="btn btn-primary">{{ t('Update') }}</button>
+    </div>
+  </div>
+
+</form>
+
+<script>
+  $('input[name="settingForm[security:passport-local:isEnabled]"]').change(function() {
+    const isEnabled = ($(this).val() === "true");
+
+    if (isEnabled) {
+      $('#passport-local-hide-when-disabled').show(400);
+    }
+    else {
+      $('#passport-local-hide-when-disabled').hide(400);
+    }
+  });
+</script>
+