mizozobu 6 лет назад
Родитель
Сommit
8034b4f041

+ 1 - 2
src/client/js/components/Admin/UserGroup/UserGroupPage.jsx

@@ -155,8 +155,7 @@ class UserGroupPage extends React.Component {
           changePage={this.handlePage}
           totalItemsCount={this.state.totalUserGroups}
           pagingLimit={this.state.pagingLimit}
-        >
-        </PaginationWrapper>
+        />
         <UserGroupDeleteModal
           userGroups={this.state.userGroups}
           deleteUserGroup={this.state.selectedUserGroup}

+ 1 - 0
src/client/js/components/Admin/UserGroupDetail/UserGroupDetailPage.jsx

@@ -40,6 +40,7 @@ class UserGroupDetailPage extends React.Component {
           userGroup={this.state.userGroup}
         />
         <UserGroupPageList
+          userGroup={this.state.userGroup}
           relatedPages={this.state.relatedPages}
         />
       </div>

+ 41 - 2
src/client/js/components/Admin/UserGroupDetail/UserGroupPageList.jsx

@@ -4,20 +4,51 @@ import { withTranslation } from 'react-i18next';
 
 import UserPicture from '../../User/UserPicture';
 import PageListMeta from '../../PageList/PageListMeta';
+import PaginationWrapper from '../../PaginationWrapper';
 import { createSubscribedElement } from '../../UnstatedUtils';
 import AppContainer from '../../../services/AppContainer';
+import { toastError } from '../../../util/apiNotification';
 
 class UserGroupPageList extends React.Component {
 
   constructor(props) {
     super(props);
 
+    this.state = {
+      currentPages: [],
+      activePage: 1,
+      total: props.relatedPages.length,
+      pagingLimit: Infinity,
+    };
+
+    this.handlePageChange = this.handlePageChange.bind(this);
     this.renderPageList = this.renderPageList.bind(this);
   }
 
+  async componentDidMount() {
+    await this.handlePageChange(this.state.activePage);
+  }
+
+  async handlePageChange(pageNum) {
+    const limit = this.state.pagingLimit;
+    const offset = (pageNum - 1) * limit;
+
+    try {
+      const res = await this.props.appContainer.apiv3.get(`/user-groups/${this.props.userGroup._id}/pages`, { limit, offset });
+
+      this.setState({
+        currentPages: res.data.pages,
+        activePage: pageNum,
+      });
+    }
+    catch (err) {
+      toastError(err);
+    }
+  }
+
   renderPageList(page) {
     return (
-      <li>
+      <li key={page._id}>
         <UserPicture user={page.lastUpdateUser} className="picture img-circle" />
         <a
           href={page.path}
@@ -39,10 +70,16 @@ class UserGroupPageList extends React.Component {
         <legend className="m-t-20">{ t('Page') }</legend>
         <div className="page-list">
           <ul className="page-list-ul page-list-ul-flat">
-            {this.props.relatedPages.map((page) => { return this.renderPageList(page) })}
+            {this.state.currentPages.map((page) => { return this.renderPageList(page) })}
           </ul>
           {this.props.relatedPages.length === 0 ? <p>{ t('user_group_management.no_pages') }</p> : null}
         </div>
+        <PaginationWrapper
+          activePage={this.state.activePage}
+          changePage={this.handlePageChange}
+          totalItemsCount={this.state.total}
+          pagingLimit={this.state.pagingLimit}
+        />
       </Fragment>
     );
   }
@@ -51,6 +88,8 @@ class UserGroupPageList extends React.Component {
 
 UserGroupPageList.propTypes = {
   t: PropTypes.func.isRequired, // i18next
+  appContainer: PropTypes.instanceOf(AppContainer).isRequired,
+  userGroup: PropTypes.object.isRequired,
   relatedPages: PropTypes.arrayOf(PropTypes.object).isRequired,
 };
 

+ 1 - 1
src/client/js/components/PaginationWrapper.jsx

@@ -42,7 +42,7 @@ class PaginationWrapper extends React.Component {
 
     let paginationStart = activePage - 2;
     let maxViewPageNum = activePage + 2;
-    // pagiNation Number area size = 5 , pageNuber calculate in here
+    // if pagiNation Number area size = 5 , pageNumber is calculated here
     // activePage Position calculate ex. 4 5 [6] 7 8 (Page8 over is Max), 3 4 5 [6] 7 (Page7 is Max)
     if (paginationStart < 1) {
       const diff = 1 - paginationStart;

+ 1 - 1
src/server/middlewares/ApiV3FormValidator.js

@@ -13,7 +13,7 @@ class ApiV3FormValidator {
       }
 
       const errs = errObjArray.array().map((err) => {
-        logger.error(`${err.param} in ${err.location}: ${err.msg}`);
+        logger.error(`${err.location}.${err.param}: ${err.value} - ${err.msg}`);
         return new ErrorV3(`${err.param}: ${err.msg}`, 'validation_failed');
       });
 

+ 32 - 0
src/server/routes/apiv3/user-group.js

@@ -7,11 +7,14 @@ const express = require('express');
 const router = express.Router();
 
 const { body, param, query } = require('express-validator/check');
+const { sanitizeQuery } = require('express-validator/filter');
 
 const validator = {};
 
 const { ObjectId } = require('mongoose').Types;
 
+const { toPagingLimit, toPagingOffset } = require('../../util/validator');
+
 /**
  * @swagger
  *  tags:
@@ -24,6 +27,7 @@ module.exports = (crowi) => {
     UserGroup,
     UserGroupRelation,
     User,
+    Page,
   } = crowi.models;
   const { ApiV3FormValidator } = crowi.middlewares;
 
@@ -426,5 +430,33 @@ module.exports = (crowi) => {
     }
   });
 
+  validator.pages = {};
+
+  validator.pages.get = [
+    param('id').trim().exists({ checkFalsy: true }),
+    sanitizeQuery('limit').customSanitizer(toPagingLimit),
+    sanitizeQuery('offset').customSanitizer(toPagingOffset),
+  ];
+
+  router.get('/:id/pages', loginRequired(), adminRequired, validator.pages.get, ApiV3FormValidator, async(req, res) => {
+    const { id } = req.params;
+    const { limit, offset } = req.query;
+
+    try {
+      const pages = await Page
+        .find({ grant: Page.GRANT_USER_GROUP, grantedGroup: { $in: [id] } }, null, { skip: offset, limit })
+        .populate('lastUpdateUser', User.USER_PUBLIC_FIELDS)
+        .exec();
+
+      return res.apiv3({ pages });
+    }
+    catch (err) {
+      const msg = `Error occurred in fetching related pages for the user group "${id}"`;
+      logger.error(msg, err);
+      return res.apiv3Err(new ErrorV3(msg, 'user-group-fetch-page-list-failed'));
+    }
+  });
+
+
   return router;
 };

+ 15 - 0
src/server/util/validator.js

@@ -0,0 +1,15 @@
+const validators = {};
+
+validators.toPagingLimit = (_value) => {
+  const value = parseInt(_value);
+  // eslint-disable-next-line no-restricted-globals
+  return !isNaN(value) && isFinite(value) ? value : 20;
+};
+
+validators.toPagingOffset = (_value) => {
+  const value = parseInt(_value);
+  // eslint-disable-next-line no-restricted-globals
+  return !isNaN(value) && isFinite(value) ? value : 0;
+};
+
+module.exports = validators;