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

Merge pull request #5592 from weseek/feat/90993-security-setting-ui

feat: SecuritySetting UI
Yuki Takei 4 лет назад
Родитель
Сommit
090cfebfa6

+ 3 - 4
packages/app/resource/locales/en_US/translation.json

@@ -669,13 +669,12 @@
     "page_listing_2_desc": "Show pages that are restricted by User group when listing/searching",
     "page_access_rights": "Page access",
     "page_delete_rights": "Delete rights",
-    "deletion": "Restrict trashing of the selected single page",
+    "page_delete": "Page Delete",
+    "page_delete_completely": "Page Delete Completely",
+    "other_options": "Other options",
     "deletion_explain": "Restricts users who can trash the selected single page.",
-    "complete_deletion": "Restrict complete deletion of the selected single page",
     "complete_deletion_explain": "Restricts users who can completely delete  selected single page.",
-    "recursive_deletion": "Restrict trashing of pages including descendants",
     "recursive_deletion_explain": "Restricts users who can trash pages including descendants.",
-    "recursive_complete_deletion": "Restrict complete deletion of pages including descendants",
     "recursive_complete_deletion_explain": "Restricts users who can completely delete pages including descendants.",
     "inherit": "Inherit(Use the same setting as for a single page)",
     "admin_only": "Admin only",

+ 3 - 4
packages/app/resource/locales/ja_JP/translation.json

@@ -668,13 +668,12 @@
     "page_listing_2_desc": "ページのリスト表示や検索結果において、特定グループにのみ閲覧制限をしているページをアクセス権のないユーザーにも表示します。",
     "page_access_rights": "ページの閲覧権限",
     "page_delete_rights": "ページの削除権限",
-    "deletion": "ページをゴミ箱に入れる(単体のみの操作)",
+    "page_delete": "ゴミ箱に入れる",
+    "page_delete_completely": "完全に削除する",
+    "other_options": "その他のオプション",
     "deletion_explain": "ページをゴミ箱に入れることができるユーザーを制限します。",
-    "complete_deletion": "ページを完全削除する(単体のみの操作)",
     "complete_deletion_explain": "ページを完全削除することができるユーザーを制限します。",
-    "recursive_deletion": "ページをゴミ箱に入れる(子孫を含む操作)",
     "recursive_deletion_explain": "子孫を含めたページをゴミ箱に入れることができるユーザーを制限します。",
-    "recursive_complete_deletion": "ページを完全削除する(子孫を含む操作)",
     "recursive_complete_deletion_explain": "子孫を含めたページを完全削除することができるユーザーを制限します。",
     "inherit": "単体のみと同じ",
     "admin_only": "管理者のみ可能",

+ 3 - 4
packages/app/resource/locales/zh_CN/translation.json

@@ -627,13 +627,12 @@
 		"page_listing_2_desc": "显示列出/搜索时受用户组限制的页面",
     "page_access_rights": "页面访问",
     "page_delete_rights": "删除权限",
-    "deletion": "限制捣毁一个选定的单一页面",
+    "page_delete": "删除",
+    "page_delete_completely": "彻底删除",
+    "other_options": "其他选项",
     "deletion_explain": "限制用户对选定的单一页面进行垃圾处理。",
-    "complete_deletion": "限制完全删除一个选定的单页",
     "complete_deletion_explain": "限制可以完全删除所选单页的用户。",
-    "recursive_deletion": "限制捣毁包括子孙在内的网页",
     "recursive_deletion_explain": "限制用户可以捣毁包括子孙在内的页面。",
-    "recursive_complete_deletion": "限制完全删除包括子孙在内的页面",
     "recursive_complete_deletion_explain": "限制可以完全删除页面的用户,包括子孙。",
     "inherit": "继承(使用与单页相同的设置)。",
 		"admin_only": "仅管理员",

+ 16 - 0
packages/app/src/client/services/AdminGeneralSecurityContainer.js

@@ -30,6 +30,8 @@ export default class AdminGeneralSecurityContainer extends Container {
       currentPageRecursiveDeletionAuthority: PageRecursiveDeleteConfigValue.Inherit,
       currentPageCompleteDeletionAuthority: PageSingleDeleteCompConfigValue.AdminOnly,
       currentPageRecursiveCompleteDeletionAuthority: PageRecursiveDeleteCompConfigValue.Inherit,
+      expandOtherOptionsForDeletion: false,
+      expandOtherOptionsForCompleteDeletion: false,
       isShowRestrictedByOwner: false,
       isShowRestrictedByGroup: false,
       appSiteUrl: appContainer.config.crowi.url || '',
@@ -147,6 +149,20 @@ export default class AdminGeneralSecurityContainer extends Container {
     this.setState({ currentPageRecursiveCompleteDeletionAuthority: val });
   }
 
+  /**
+   * Switch ExpandOtherOptionsForDeletion
+   */
+  switchExpandOtherOptionsForDeletion() {
+    this.setState({ expandOtherOptionsForDeletion:  !this.state.expandOtherOptionsForDeletion });
+  }
+
+  /**
+   * Switch ExpandOtherOptionsForDeletion
+   */
+  switchExpandOtherOptionsForCompleteDeletion() {
+    this.setState({ expandOtherOptionsForCompleteDeletion:  !this.state.expandOtherOptionsForCompleteDeletion });
+  }
+
   /**
    * Switch showRestrictedByOwner
    */

+ 114 - 69
packages/app/src/components/Admin/Security/SecuritySetting.jsx

@@ -1,6 +1,7 @@
 /* eslint-disable react/no-danger */
 import React from 'react';
 import PropTypes from 'prop-types';
+import { Collapse } from 'reactstrap';
 import { withTranslation } from 'react-i18next';
 
 import { validateDeleteConfigs } from '~/utils/page-delete-config';
@@ -64,6 +65,7 @@ class SecuritySetting extends React.Component {
     this.putSecuritySetting = this.putSecuritySetting.bind(this);
     this.getRecursiveDeletionConfigState = this.getRecursiveDeletionConfigState.bind(this);
     this.setDeletionConfigState = this.setDeletionConfigState.bind(this);
+    this.renderPageDeletePermission = this.renderPageDeletePermission.bind(this);
     this.renderPageDeletePermissionDropdown = this.renderPageDeletePermissionDropdown.bind(this);
   }
 
@@ -120,70 +122,120 @@ class SecuritySetting extends React.Component {
 
   renderPageDeletePermissionDropdown(currentState, setState, deletionType, isButtonDisabled) {
     const { t } = this.props;
+    return (
+      <div className="dropdown">
+        <button
+          className="btn btn-outline-secondary dropdown-toggle text-right"
+          type="button"
+          id="dropdownMenuButton"
+          data-toggle="dropdown"
+          aria-haspopup="true"
+          aria-expanded="true"
+        >
+          <span className="float-left">
+            {currentState === PageDeleteConfigValue.Inherit && t('security_setting.inherit')}
+            {(currentState === PageDeleteConfigValue.Anyone || currentState == null) && t('security_setting.anyone')}
+            {currentState === PageDeleteConfigValue.AdminOnly && t('security_setting.admin_only')}
+            {currentState === PageDeleteConfigValue.AdminAndAuthor && t('security_setting.admin_and_author')}
+          </span>
+        </button>
+        <div className="dropdown-menu" aria-labelledby="dropdownMenuButton">
+          {
+            isRecursiveDeletion(deletionType)
+              ? (
+                <button
+                  className="dropdown-item"
+                  type="button"
+                  onClick={() => { this.setDeletionConfigState(PageDeleteConfigValue.Inherit, setState, deletionType) }}
+                >
+                  {t('security_setting.inherit')}
+                </button>
+              )
+              : (
+                <button
+                  className="dropdown-item"
+                  type="button"
+                  onClick={() => { this.setDeletionConfigState(PageDeleteConfigValue.Anyone, setState, deletionType) }}
+                >
+                  {t('security_setting.anyone')}
+                </button>
+              )
+          }
+          <button
+            className={`dropdown-item ${isButtonDisabled ? 'disabled' : ''}`}
+            type="button"
+            onClick={() => { this.setDeletionConfigState(PageDeleteConfigValue.AdminAndAuthor, setState, deletionType) }}
+          >
+            {t('security_setting.admin_and_author')}
+          </button>
+          <button
+            className="dropdown-item"
+            type="button"
+            onClick={() => { this.setDeletionConfigState(PageDeleteConfigValue.AdminOnly, setState, deletionType) }}
+          >
+            {t('security_setting.admin_only')}
+          </button>
+        </div>
+        <p className="form-text text-muted small">
+          {t(`security_setting.${getDeletionTypeForT(deletionType)}_explain`)}
+        </p>
+      </div>
+    );
+  }
+
+  renderPageDeletePermission(currentState, setState, deletionType, isButtonDisabled) {
+    const { t, adminGeneralSecurityContainer } = this.props;
+
+    const expandOtherOptions = isTypeDeletion(deletionType)
+      ? adminGeneralSecurityContainer.state.expandOtherOptionsForDeletion
+      : adminGeneralSecurityContainer.state.expandOtherOptionsForCompleteDeletion;
+
+    const setExpantOtherOptions = () => {
+      if (isTypeDeletion(deletionType)) {
+        adminGeneralSecurityContainer.switchExpandOtherOptionsForDeletion();
+        return;
+      }
+      adminGeneralSecurityContainer.switchExpandOtherOptionsForCompleteDeletion();
+      return;
+    };
 
     return (
-      <div key={`page-delete-permission-dropdown-${deletionType}`} className="row mb-4">
-        <div className="col-md-3 text-md-right mb-2">
-          <strong>{t(`security_setting.${getDeletionTypeForT(deletionType)}`)}</strong>
+      <div key={`page-delete-permission-dropdown-${deletionType}`} className="row">
+
+        <div className="col-md-3 text-md-right">
+          {!isRecursiveDeletion(deletionType) && isTypeDeletion(deletionType) && (
+            <strong>{t('security_setting.page_delete')}</strong>
+          )}
+          {!isRecursiveDeletion(deletionType) && !isTypeDeletion(deletionType) && (
+            <strong>{t('security_setting.page_delete_completely')}</strong>
+          )}
         </div>
+
         <div className="col-md-6">
-          <div className="dropdown">
-            <button
-              className="btn btn-outline-secondary dropdown-toggle text-right col-12 col-md-auto"
-              type="button"
-              id="dropdownMenuButton"
-              data-toggle="dropdown"
-              aria-haspopup="true"
-              aria-expanded="true"
-            >
-              <span className="float-left">
-                {currentState === PageDeleteConfigValue.Inherit && t('security_setting.inherit')}
-                {(currentState === PageDeleteConfigValue.Anyone || currentState == null) && t('security_setting.anyone')}
-                {currentState === PageDeleteConfigValue.AdminOnly && t('security_setting.admin_only')}
-                {currentState === PageDeleteConfigValue.AdminAndAuthor && t('security_setting.admin_and_author')}
-              </span>
-            </button>
-            <div className="dropdown-menu" aria-labelledby="dropdownMenuButton">
-              {
-                isRecursiveDeletion(deletionType)
-                  ? (
-                    <button
-                      className="dropdown-item"
-                      type="button"
-                      onClick={() => { this.setDeletionConfigState(PageDeleteConfigValue.Inherit, setState, deletionType) }}
-                    >
-                      {t('security_setting.inherit')}
-                    </button>
-                  )
-                  : (
-                    <button
-                      className="dropdown-item"
-                      type="button"
-                      onClick={() => { this.setDeletionConfigState(PageDeleteConfigValue.Anyone, setState, deletionType) }}
-                    >
-                      {t('security_setting.anyone')}
-                    </button>
-                  )
-              }
-              <button
-                className={`dropdown-item ${isButtonDisabled ? 'disabled' : ''}`}
-                type="button"
-                onClick={() => { this.setDeletionConfigState(PageDeleteConfigValue.AdminAndAuthor, setState, deletionType) }}
-              >
-                {t('security_setting.admin_and_author')}
-              </button>
-              <button
-                className="dropdown-item"
-                type="button"
-                onClick={() => { this.setDeletionConfigState(PageDeleteConfigValue.AdminOnly, setState, deletionType) }}
-              >
-                {t('security_setting.admin_only')}
-              </button>
-            </div>
-            <p className="form-text text-muted small">
-              {t(`security_setting.${getDeletionTypeForT(deletionType)}_explain`)}
-            </p>
-          </div>
+          {
+            !isRecursiveDeletion(deletionType)
+              ? (
+                <>{this.renderPageDeletePermissionDropdown(currentState, setState, deletionType, isButtonDisabled)}</>
+              )
+              : (
+                <>
+                  <button
+                    type="button"
+                    className="btn btn-link p-0 mb-4"
+                    aria-expanded="false"
+                    onClick={() => setExpantOtherOptions()}
+                  >
+                    <i className={`fa fa-fw fa-arrow-right ${expandOtherOptions ? 'fa-rotate-90' : ''}`}></i>
+                    { t('security_setting.other_options') }
+                  </button>
+                  <Collapse isOpen={expandOtherOptions}>
+                    <div className="pb-4">
+                      {this.renderPageDeletePermissionDropdown(currentState, setState, deletionType, isButtonDisabled)}
+                    </div>
+                  </Collapse>
+                </>
+              )
+          }
         </div>
       </div>
     );
@@ -316,13 +368,6 @@ class SecuritySetting extends React.Component {
         </div>
 
         <h4>{t('security_setting.page_delete_rights')}</h4>
-        <div className="row">
-          <p className="card well col-9">
-            <span className="text-warning">
-              <i className="icon-info"></i> {t('security_setting.page_delete_rights_caution')}
-            </span>
-          </p>
-        </div>
         <div className="row mb-4"></div>
         {/* Render PageDeletePermissionDropdown */}
         {
@@ -330,14 +375,14 @@ class SecuritySetting extends React.Component {
             [currentPageDeletionAuthority, adminGeneralSecurityContainer.changePageDeletionAuthority, DeletionType.Deletion, false],
             // eslint-disable-next-line max-len
             [currentPageRecursiveDeletionAuthority, adminGeneralSecurityContainer.changePageRecursiveDeletionAuthority, DeletionType.RecursiveDeletion, isButtonDisabledForDeletion],
-          ].map(arr => this.renderPageDeletePermissionDropdown(arr[0], arr[1], arr[2], arr[3]))
+          ].map(arr => this.renderPageDeletePermission(arr[0], arr[1], arr[2], arr[3]))
         }
         {
           [
             [currentPageCompleteDeletionAuthority, adminGeneralSecurityContainer.changePageCompleteDeletionAuthority, DeletionType.CompleteDeletion, false],
             // eslint-disable-next-line max-len
             [currentPageRecursiveCompleteDeletionAuthority, adminGeneralSecurityContainer.changePageRecursiveCompleteDeletionAuthority, DeletionType.RecursiveCompleteDeletion, isButtonDisabledForCompleteDeletion],
-          ].map(arr => this.renderPageDeletePermissionDropdown(arr[0], arr[1], arr[2], arr[3]))
+          ].map(arr => this.renderPageDeletePermission(arr[0], arr[1], arr[2], arr[3]))
         }
 
         <h4>{t('security_setting.session')}</h4>