Sfoglia il codice sorgente

Merge pull request #1284 from weseek/reactify-admin/external-accout-api

create container and apiv3
Yuki Takei 6 anni fa
parent
commit
fc01af5e84

+ 14 - 0
src/client/js/app.jsx

@@ -56,6 +56,7 @@ import UserGroupDetailContainer from './services/UserGroupDetailContainer';
 import AdminUsersContainer from './services/AdminUsersContainer';
 import WebsocketContainer from './services/WebsocketContainer';
 import MarkDownSettingContainer from './services/MarkDownSettingContainer';
+import AdminExternalAccountsContainer from './services/AdminExternalAccountsContainer';
 
 const logger = loggerFactory('growi:app');
 
@@ -171,6 +172,19 @@ if (adminUsersElem != null) {
   );
 }
 
+const adminExternalAccountsElem = document.getElementById('admin-external-account');
+if (adminExternalAccountsElem != null) {
+  const adminExternalAccountsContainer = new AdminExternalAccountsContainer(appContainer);
+  ReactDOM.render(
+    <Provider inject={[injectableContainers, adminExternalAccountsContainer]}>
+      <I18nextProvider i18n={i18n}>
+        <ManageExternalAccount />
+      </I18nextProvider>
+    </Provider>,
+    adminExternalAccountsElem,
+  );
+}
+
 const adminUserGroupDetailElem = document.getElementById('admin-user-group-detail');
 if (adminUserGroupDetailElem != null) {
   const userGroupDetailContainer = new UserGroupDetailContainer(appContainer);

+ 2 - 2
src/client/js/components/Admin/Users/ManageExternalAccount.jsx

@@ -10,7 +10,7 @@ class ManageExternalAccount extends React.Component {
 
   constructor(props) {
     super(props);
-
+    // TODO GW-417
     this.state = {
     };
   }
@@ -58,7 +58,7 @@ class ManageExternalAccount extends React.Component {
               <th width="70px"></th>
             </tr>
           </thead>
-          {/* TODO GW-328 */}
+          {/* TODO GW-417 */}
         </table>
       </Fragment>
     );

+ 87 - 0
src/client/js/services/AdminExternalAccountsContainer.js

@@ -0,0 +1,87 @@
+import { Container } from 'unstated';
+
+import loggerFactory from '@alias/logger';
+
+
+// eslint-disable-next-line no-unused-vars
+const logger = loggerFactory('growi:services:UserGroupDetailContainer');
+
+/**
+ * Service container for admin users page (Users.jsx)
+ * @extends {Container} unstated Container
+ */
+export default class AdminExternalAccountContainer extends Container {
+
+  constructor(appContainer) {
+    super();
+
+    this.appContainer = appContainer;
+
+    this.state = {
+      exteranalAccounts: JSON.parse(document.getElementById('admin-external-account-setting').getAttribute('external-account')) || [],
+      totalAccounts: 0,
+      activePage: 1,
+      pagingLimit: Infinity,
+    };
+
+  }
+
+  /**
+   * Workaround for the mangling in production build to break constructor.name
+   */
+  static getClassName() {
+    return 'AdminExternalAccountsContainer';
+  }
+
+  /**
+   * update external-account
+   *
+   * @memberOf AdminExternalAccountsContainer
+   * @param {object} param update param for external account
+   * @return {object} response object
+   */
+  async updateExternalAccount(param) {
+    const res = await this.appContainer.apiv3.put(`/users/external-account/${this.state.externalAccounts._id}`, param);
+    const { exteranalAccounts } = res.data;
+
+    await this.setState({ exteranalAccounts });
+
+    return res;
+  }
+
+  /**
+   * syncExternalAccounts of selectedPage
+   * @memberOf AdminExternalAccountsContainer
+   * @param {number} selectedPage
+   */
+  async retrieveExternalAccountsByPagingNum(selectedPage) {
+
+    const params = { page: selectedPage };
+    const response = await this.appContainer.apiv3.get('/users/external-accounts', params);
+
+    const exteranalAccounts = response.data.externalAccounts;
+    const totalAccounts = response.data.totalAccounts;
+    const pagingLimit = response.data.pagingLimit;
+
+    this.setState({
+      exteranalAccounts,
+      totalAccounts,
+      pagingLimit,
+      activePage: selectedPage,
+    });
+
+  }
+
+  /**
+   * remove external account
+   *
+   * @memberOf AdminExternalAccountsContainer
+   * @param {string} externalAccountId id of the External Account to be removed
+   */
+  async removeExternal(externalAccountId) {
+    const res = await this.appContainer.apiv3.delete(`/users/external-accounts/${externalAccountId}/remove`);
+    const externalAccountData = res.data.exteranalAccount;
+    return externalAccountData;
+  }
+
+}

+ 77 - 0
src/server/routes/apiv3/users.js

@@ -333,5 +333,82 @@ module.exports = (crowi) => {
     }
   });
 
+  /**
+   * @swagger
+   *
+   *  paths:
+   *    /_api/v3/users:
+   *      get:
+   *        tags: [Users]
+   *        description: Get external-account
+   *        responses:
+   *          200:
+   *            description: external-account are fetched
+   *            content:
+   *              application/json:
+   *                schema:
+   *                  properties:
+   *                    external-account:
+   *                      type: object
+   *                      description: a result of `ExternalAccount.find`
+   */
+  router.get('/external-accounts/', loginRequiredStrictly, adminRequired, async(req, res) => {
+    try {
+      const page = parseInt(req.query.page) || 1;
+      const result = await ExternalAccount.findAllWithPagination({ page });
+      const { docs: extenralAccounts, total: totalAccounts, limit: pagingLimit } = result;
+      return res.apiv3({ extenralAccounts, totalAccounts, pagingLimit });
+    }
+    catch (err) {
+      const msg = 'Error occurred in fetching external-account list';
+      logger.error(msg, err);
+      const errMsg = Object.assign(msg, err.message);
+      return res.apiv3Err(new ErrorV3(errMsg, 'external-account-list-fetch-failed'));
+    }
+  });
+
+
+  /**
+   * @swagger
+   *
+   *  paths:
+   *    /_api/v3/users/external-accounts/{id}/remove:
+   *      delete:
+   *        tags: [Users]
+   *        description: Delete ExternalAccount
+   *        parameters:
+   *          - name: id
+   *            in: path
+   *            required: true
+   *            description: id of ExternalAccount
+   *            schema:
+   *              type: string
+   *        responses:
+   *          200:
+   *            description:  External Account is removed
+   *            content:
+   *              application/json:
+   *                schema:
+   *                  properties:
+   *                    externalAccount:
+   *                      type: object
+   *                      description: A result of `ExtenralAccount.findByIdAndRemove`
+   */
+
+  router.delete('/external-accounts/:id/remove', loginRequiredStrictly, adminRequired, ApiV3FormValidator, async(req, res) => {
+    const { id: deleteExtenralAccountId } = req.params.id;
+
+    try {
+      const externalAccount = await ExternalAccount.findByIdAndRemove(deleteExtenralAccountId);
+
+      return res.apiv3({ externalAccount });
+    }
+    catch (err) {
+      const msg = 'Error occurred in deleting a external account';
+      logger.error(msg, err);
+      const errMsg = Object.assign(msg, err.message);
+      return res.apiv3Err(new ErrorV3(errMsg, 'extenral-account-delete-failed'));
+    }
+  });
   return router;
 };

+ 1 - 1
src/server/views/admin/external-accounts.html

@@ -39,7 +39,7 @@
     </div>
 
     <!-- TODO reactify admin -->
-    <div class="col-md-9">
+    <div class="col-md-9" id="admin-external-account-setting">
       <p>
         <a class="btn btn-default" href="/admin/users">
           <i class="icon-fw ti-arrow-left" aria-hidden="true"></i>