Browse Source

feat(server): 消息

Go 5 years ago
parent
commit
0b880d67e6
100 changed files with 3085 additions and 1612 deletions
  1. 2 0
      front/project/Constant.js
  2. 0 3
      front/project/admin/routes/class/index.js
  3. 15 0
      front/project/admin/routes/course/ask/index.js
  4. 3 0
      front/project/admin/routes/course/ask/index.less
  5. 193 0
      front/project/admin/routes/course/ask/page.js
  6. 15 0
      front/project/admin/routes/course/askDetail/index.js
  7. 3 0
      front/project/admin/routes/course/askDetail/index.less
  8. 192 0
      front/project/admin/routes/course/askDetail/page.js
  9. 1 1
      front/project/admin/routes/class/group.js
  10. 8 0
      front/project/admin/routes/course/index.js
  11. 14 0
      front/project/admin/routes/course/invoice/index.js
  12. 3 0
      front/project/admin/routes/course/invoice/index.less
  13. 12 0
      front/project/admin/routes/course/invoice/page.js
  14. 14 0
      front/project/admin/routes/course/list/index.js
  15. 3 0
      front/project/admin/routes/course/list/index.less
  16. 12 0
      front/project/admin/routes/course/list/page.js
  17. 14 0
      front/project/admin/routes/course/package/index.js
  18. 3 0
      front/project/admin/routes/course/package/index.less
  19. 12 0
      front/project/admin/routes/course/package/page.js
  20. 15 0
      front/project/admin/routes/course/packageDetail/index.js
  21. 3 0
      front/project/admin/routes/course/packageDetail/index.less
  22. 12 0
      front/project/admin/routes/course/packageDetail/page.js
  23. 15 0
      front/project/admin/routes/setting/comment/index.js
  24. 18 0
      front/project/admin/routes/setting/comment/index.less
  25. 208 0
      front/project/admin/routes/setting/comment/page.js
  26. 15 0
      front/project/admin/routes/setting/faq/index.js
  27. 3 0
      front/project/admin/routes/setting/faq/index.less
  28. 208 0
      front/project/admin/routes/setting/faq/page.js
  29. 4 1
      front/project/admin/routes/setting/index.js
  30. 15 0
      front/project/admin/routes/setting/message/index.js
  31. 22 0
      front/project/admin/routes/setting/message/index.less
  32. 250 0
      front/project/admin/routes/setting/message/page.js
  33. 1 1
      front/project/admin/routes/user/ask/page.js
  34. 2 2
      front/project/admin/routes/user/student/page.js
  35. 0 21
      front/project/admin/stores/class.js
  36. 21 0
      front/project/admin/stores/course.js
  37. 2 2
      front/project/admin/stores/index.js
  38. 64 0
      front/project/admin/stores/system.js
  39. 1 1
      front/project/admin/stores/user.js
  40. 6 3
      server/data/src/main/java/com/qxgmat/data/constants/enums/SettingKey.java
  41. 18 0
      server/data/src/main/java/com/qxgmat/data/constants/enums/module/ChannelModule.java
  42. 4 3
      server/data/src/main/java/com/qxgmat/data/constants/enums/user/MessageType.java
  43. 0 7
      server/data/src/main/java/com/qxgmat/data/dao/ClassCourseMapper.java
  44. 0 7
      server/data/src/main/java/com/qxgmat/data/dao/ClassCourseNoMapper.java
  45. 0 7
      server/data/src/main/java/com/qxgmat/data/dao/ClassFaqMapper.java
  46. 7 0
      server/data/src/main/java/com/qxgmat/data/dao/CommentMapper.java
  47. 7 0
      server/data/src/main/java/com/qxgmat/data/dao/CourseArticleMapper.java
  48. 7 0
      server/data/src/main/java/com/qxgmat/data/dao/CourseDataMapper.java
  49. 0 7
      server/data/src/main/java/com/qxgmat/data/dao/CourseFaqMapper.java
  50. 7 0
      server/data/src/main/java/com/qxgmat/data/dao/CoursePackageMapper.java
  51. 7 0
      server/data/src/main/java/com/qxgmat/data/dao/FaqMapper.java
  52. 7 0
      server/data/src/main/java/com/qxgmat/data/dao/MessageMapper.java
  53. 0 7
      server/data/src/main/java/com/qxgmat/data/dao/UserClassMapper.java
  54. 0 7
      server/data/src/main/java/com/qxgmat/data/dao/UserCourseCommentMapper.java
  55. 0 230
      server/data/src/main/java/com/qxgmat/data/dao/entity/ClassCourse.java
  56. 0 265
      server/data/src/main/java/com/qxgmat/data/dao/entity/ClassCourseNo.java
  57. 0 168
      server/data/src/main/java/com/qxgmat/data/dao/entity/ClassFaq.java
  58. 317 0
      server/data/src/main/java/com/qxgmat/data/dao/entity/Comment.java
  59. 63 0
      server/data/src/main/java/com/qxgmat/data/dao/entity/CourseArticle.java
  60. 63 0
      server/data/src/main/java/com/qxgmat/data/dao/entity/CourseData.java
  61. 0 168
      server/data/src/main/java/com/qxgmat/data/dao/entity/CourseFaq.java
  62. 63 0
      server/data/src/main/java/com/qxgmat/data/dao/entity/CoursePackage.java
  63. 335 0
      server/data/src/main/java/com/qxgmat/data/dao/entity/Faq.java
  64. 63 0
      server/data/src/main/java/com/qxgmat/data/dao/entity/Message.java
  65. 0 204
      server/data/src/main/java/com/qxgmat/data/dao/entity/UserClass.java
  66. 0 186
      server/data/src/main/java/com/qxgmat/data/dao/entity/UserCourseComment.java
  67. 0 21
      server/data/src/main/java/com/qxgmat/data/dao/mapping/ClassCourseMapper.xml
  68. 0 19
      server/data/src/main/java/com/qxgmat/data/dao/mapping/ClassFaqMapper.xml
  69. 10 8
      server/data/src/main/java/com/qxgmat/data/dao/mapping/ClassCourseNoMapper.xml
  70. 10 0
      server/data/src/main/java/com/qxgmat/data/dao/mapping/CourseArticleMapper.xml
  71. 10 0
      server/data/src/main/java/com/qxgmat/data/dao/mapping/CourseDataMapper.xml
  72. 0 19
      server/data/src/main/java/com/qxgmat/data/dao/mapping/CourseFaqMapper.xml
  73. 10 0
      server/data/src/main/java/com/qxgmat/data/dao/mapping/CoursePackageMapper.xml
  74. 9 5
      server/data/src/main/java/com/qxgmat/data/dao/mapping/UserCourseCommentMapper.xml
  75. 10 0
      server/data/src/main/java/com/qxgmat/data/dao/mapping/MessageMapper.xml
  76. 0 20
      server/data/src/main/java/com/qxgmat/data/dao/mapping/UserClassMapper.xml
  77. 7 7
      server/gateway-api/src/main/java/com/qxgmat/controller/admin/ClassController.java
  78. 157 9
      server/gateway-api/src/main/java/com/qxgmat/controller/admin/SettingController.java
  79. 66 9
      server/gateway-api/src/main/java/com/qxgmat/controller/admin/UserController.java
  80. 0 97
      server/gateway-api/src/main/java/com/qxgmat/controller/admin/UserFeedbackErrorController.java
  81. 8 8
      server/gateway-api/src/main/java/com/qxgmat/controller/api/CourseController.java
  82. 15 15
      server/gateway-api/src/main/java/com/qxgmat/controller/api/MyController.java
  83. 1 1
      server/gateway-api/src/main/java/com/qxgmat/controller/api/QuestionController.java
  84. 3 3
      server/gateway-api/src/main/java/com/qxgmat/dto/admin/extend/ClassCourseExtendDto.java
  85. 3 3
      server/gateway-api/src/main/java/com/qxgmat/dto/admin/extend/UserClassExtendDto.java
  86. 99 0
      server/gateway-api/src/main/java/com/qxgmat/dto/admin/request/CommentDto.java
  87. 99 0
      server/gateway-api/src/main/java/com/qxgmat/dto/admin/request/FaqDto.java
  88. 69 0
      server/gateway-api/src/main/java/com/qxgmat/dto/admin/request/MessageDto.java
  89. 3 3
      server/gateway-api/src/main/java/com/qxgmat/dto/admin/response/ClassCourseListDto.java
  90. 4 4
      server/gateway-api/src/main/java/com/qxgmat/dto/admin/response/UserDetailDto.java
  91. 4 4
      server/gateway-api/src/main/java/com/qxgmat/dto/admin/response/UserListDto.java
  92. 6 3
      server/gateway-api/src/main/java/com/qxgmat/dto/response/UserClassDetailDto.java
  93. 20 20
      server/gateway-api/src/main/java/com/qxgmat/dto/response/UserStudyDayDto.java
  94. 3 0
      server/gateway-api/src/main/java/com/qxgmat/help/MailHelp.java
  95. 3 3
      server/gateway-api/src/main/java/com/qxgmat/service/UsersService.java
  96. 14 0
      server/gateway-api/src/main/java/com/qxgmat/service/extend/CourseExtendService.java
  97. 58 0
      server/gateway-api/src/main/java/com/qxgmat/service/extend/MessageExtendService.java
  98. 0 30
      server/gateway-api/src/main/java/com/qxgmat/service/extend/MessageService.java
  99. 12 0
      server/gateway-api/src/main/java/com/qxgmat/service/extend/ToolsService.java
  100. 0 0
      server/gateway-api/src/main/java/com/qxgmat/service/extend/TradeService.java

+ 2 - 0
front/project/Constant.js

@@ -6,6 +6,8 @@ export const QuestionType = [{ label: 'SC/语法', value: 'sc', long: 'Sentence
 
 export const TextbookType = [{ label: 'PS/数学', value: 'ps' }, { label: 'DS/数学', value: 'ds' }];
 
+export const ChannelModule = [{ label: '', value: '' }];
+
 export const MoneyRange = [{ label: '0', value: 0 }, { label: '1-1000', value: 1 }, { label: '1000-5000', value: 2 }, { label: '5000-10000', value: 3 }, { label: '10000以上', value: 4 }];
 
 export const AskTarget = [{ label: '题目', value: 'question', title: '题目', key: 'question' }, { label: '官方解析', value: 'official', title: '官方解析', key: 'official' }, { label: '千行解析', value: 'qx', title: '千行解析', key: 'qx' }, { label: '题源联想', value: 'association', title: '题源联想', key: 'association' }, { label: '相关问答', value: 'qa', title: '相关问答', key: 'qa' }];

+ 0 - 3
front/project/admin/routes/class/index.js

@@ -1,3 +0,0 @@
-
-
-export default [];

+ 15 - 0
front/project/admin/routes/course/ask/index.js

@@ -0,0 +1,15 @@
+import module from '../../module';
+import group from '../group';
+
+export default {
+  path: '/course/ask',
+  key: 'course-ask',
+  title: '学生提问',
+  needLogin: true,
+  module,
+  group,
+  index: true,
+  component() {
+    return import('./page');
+  },
+};

+ 3 - 0
front/project/admin/routes/course/ask/index.less

@@ -0,0 +1,3 @@
+@charset "utf-8";
+
+#course-ask {}

+ 193 - 0
front/project/admin/routes/course/ask/page.js

@@ -0,0 +1,193 @@
+import React from 'react';
+import { Link } from 'react-router-dom';
+import './index.less';
+import Page from '@src/containers/Page';
+import Block from '@src/components/Block';
+import FilterLayout from '@src/layouts/FilterLayout';
+import ActionLayout from '@src/layouts/ActionLayout';
+import TableLayout from '@src/layouts/TableLayout';
+import { getMap, bindSearch, formatDate } from '@src/services/Tools';
+import { asyncSMessage, asyncDelConfirm } from '@src/services/AsyncTools';
+import { QuestionType, AskStatus, MoneyRange, SwitchSelect, AskTarget } from '../../../../Constant';
+import { User } from '../../../stores/user';
+import { Course } from '../../../stores/course';
+
+const QuestionTypeMap = getMap(QuestionType, 'value', 'label');
+const AskStatusMap = getMap(AskStatus, 'value', 'label');
+const SwitchSelectMap = getMap(SwitchSelect, 'value', 'label');
+export default class extends Page {
+  init() {
+    this.actionList = [{
+      key: 'ignore',
+      type: 'danger',
+      name: '批量忽略',
+      needSelect: 1,
+    }];
+    this.filterForm = [{
+      key: 'type',
+      type: 'select',
+      allowClear: true,
+      name: '题型',
+      select: QuestionType,
+      placeholder: '请选择',
+      number: true,
+    }, {
+      key: 'status',
+      type: 'select',
+      allowClear: true,
+      name: '状态',
+      select: AskStatus,
+    }, {
+      key: 'money',
+      type: 'select',
+      allowClear: true,
+      name: '消费金额',
+      select: MoneyRange,
+    }, {
+      key: 'showStatus',
+      type: 'select',
+      allowClear: true,
+      name: '展示状态',
+      select: SwitchSelect,
+    }, {
+      key: 'target',
+      type: 'select',
+      allowClear: true,
+      name: '提问内容',
+      select: AskTarget,
+    }, {
+      key: 'questionNoId',
+      type: 'select',
+      allowClear: true,
+      name: '题目ID',
+      select: [],
+      number: true,
+      placeholder: '请输入',
+    }, {
+      key: 'userId',
+      type: 'select',
+      name: '用户',
+      allowClear: true,
+      select: [],
+      number: true,
+      placeholder: '请输入',
+    }];
+    this.columns = [
+      {
+        title: '题型',
+        dataIndex: 'type',
+        render: (text, record) => {
+          return QuestionTypeMap[record.question.type];
+        },
+      },
+      {
+        title: '题目id',
+        dataIndex: 'questionNo.no',
+      },
+      {
+        title: '提问时间',
+        dataIndex: 'createTime',
+        render: (text) => {
+          return formatDate(text);
+        },
+      },
+      {
+        title: '提问摘要',
+        dataIndex: 'content',
+      }, {
+        title: '提问者',
+        dataIndex: 'user.nickname',
+      }, {
+        title: '回答状态',
+        dataIndex: 'answerStatus',
+        render: (text) => {
+          return AskStatusMap[text] || text;
+        },
+      }, {
+        title: '回答者',
+        dataIndex: 'manager.username',
+      }, {
+        title: '回答时间',
+        dataIndex: 'answerTime',
+      }, {
+        title: '展示状态',
+        dataIndex: 'showStatus',
+        render: (text) => {
+          return SwitchSelectMap[text] || text;
+        },
+      }, {
+        title: '操作',
+        dataIndex: 'handler',
+        render: (text, record) => {
+          return <div className="table-button">
+            {(
+              <Link to={`/user/ask/detail/${record.id}`}>编辑</Link>
+            )}
+          </div>;
+        },
+      },
+    ];
+    bindSearch(this.filterForm, 'userId', this, (search) => {
+      return User.list(search);
+    }, (row) => {
+      return {
+        title: `${row.nickname}(${row.mobile})`,
+        value: row.id,
+      };
+    }, this.state.search.userId ? Number(this.state.search.userId) : [], null);
+    bindSearch(this.filterForm, 'questionNoId', this, (search) => {
+      return Question.searchNo(search);
+    }, (row) => {
+      return {
+        title: row.title,
+        value: row.id,
+      };
+    }, this.state.search.questionNoId ? Number(this.state.search.questionNoId) : [], null);
+  }
+
+  initData() {
+    Course.listAsk(this.state.search).then(result => {
+      this.setTableData(result.list, result.total);
+    });
+  }
+
+  ignoreAction() {
+    const { selectedKeys } = this.state;
+    asyncDelConfirm('忽略确认', '是否忽略选中提问?', () => {
+      return Promise.all(selectedKeys.map(row => User.editAsk({ id: row, answerStatus: 2 }))).then(() => {
+        asyncSMessage('操作成功!');
+        this.refresh();
+      });
+    });
+  }
+
+  renderView() {
+    return <Block flex>
+      <FilterLayout
+        show
+        itemList={this.filterForm}
+        data={this.state.search}
+        onChange={data => {
+          if (data.time.length > 0) {
+            data.time = [data.time[0].format('YYYY-MM-DD HH:mm:ss'), data.time[1].format('YYYY-MM-DD HH:mm:ss')];
+          }
+          this.search(data);
+        }} />
+      <ActionLayout
+        itemList={this.actionList}
+        selectedKeys={this.state.selectedKeys}
+        onAction={key => this.onAction(key)}
+      />
+      <TableLayout
+        select
+        columns={this.columns}
+        list={this.state.list}
+        pagination={this.state.page}
+        loading={this.props.core.loading}
+        onChange={(pagination, filters, sorter) => this.tableChange(pagination, filters, sorter)}
+        onSelect={(keys, rows) => this.tableSelect(keys, rows)}
+        selectedKeys={this.state.selectedKeys}
+      />
+    </Block>;
+  }
+}

+ 15 - 0
front/project/admin/routes/course/askDetail/index.js

@@ -0,0 +1,15 @@
+import module from '../../module';
+import group from '../group';
+
+export default {
+  path: '/user/ask/detail/:id?',
+  key: 'user-ask-detail',
+  title: '问答详情',
+  needLogin: true,
+  module,
+  group,
+  showKey: 'user-ask',
+  component() {
+    return import('./page');
+  },
+};

+ 3 - 0
front/project/admin/routes/course/askDetail/index.less

@@ -0,0 +1,3 @@
+@charset "utf-8";
+
+#user-ask-detail {}

+ 192 - 0
front/project/admin/routes/course/askDetail/page.js

@@ -0,0 +1,192 @@
+import React from 'react';
+import { Form, Button, Row, Col, List, Icon, Switch, Typography } from 'antd';
+import './index.less';
+import Editor from '@src/components/Editor';
+import Page from '@src/containers/Page';
+import Block from '@src/components/Block';
+import DragList from '@src/components/DragList';
+// import FileUpload from '@src/components/FileUpload';
+import { formatFormError, formatDate, getMap } from '@src/services/Tools';
+import { asyncSMessage } from '@src/services/AsyncTools';
+import { AskTarget, QuestionType } from '../../../../Constant';
+// import { User } from '../../../stores/user';
+import { Question } from '../../../stores/question';
+
+const QuestionTypeMap = getMap(QuestionType, 'value', 'label');
+const AskTargetMap = getMap(AskTarget, 'value', 'label');
+export default class extends Page {
+  init() {
+    // Exercise.allStruct().then(result => {
+    //   result = result.filter(row => row.level === 2).map(row => { row.title = `${row.titleZh}/${row.titleEn}`; row.value = row.id; return row; });
+    //   this.setState({ exercise: result });
+    // });
+  }
+
+  initData() {
+    const { id } = this.params;
+    let handler;
+    if (id) {
+      handler = Question.getAsk({ id });
+    } else {
+      handler = Promise.resolve({ others: [{ content: 123123123, answer: 123123 }, {}] });
+    }
+    handler
+      .then(result => {
+        const { getFieldDecorator, setFieldsValue } = this.props.form;
+        getFieldDecorator('id');
+        getFieldDecorator('answer');
+        getFieldDecorator('showStatus');
+        setFieldsValue({ id: result.id, answer: result.answer, showStatus: result.showStatus });
+        this.setState({ data: result });
+      });
+  }
+
+  orderQuestion(oldIndex, newIndex) {
+    const { data } = this.state;
+    const { others = [] } = data;
+    const tmp = others[oldIndex];
+    others[oldIndex] = others[newIndex];
+    others[newIndex] = tmp;
+    this.setState({ others });
+  }
+
+  addOrder() {
+    const { data } = this.state;
+    const { others } = data;
+    others.push(data);
+    this.setState({ data });
+  }
+
+  removeOrder() {
+    const { data } = this.state;
+    const { others } = data;
+    data.others = others.filter(row => row.id !== data.id);
+    this.setState({ data });
+  }
+
+  submit() {
+    const { form } = this.props;
+    form.validateFields((err) => {
+      if (!err) {
+        const data = form.getFieldsValue();
+        data.other = this.state.data.others.map(row => row.id);
+        Question.editAsk(data).then(() => {
+          asyncSMessage('保存成功');
+        }).catch((e) => {
+          if (e.result) form.setFields(formatFormError(data, e.result));
+        });
+      }
+    });
+  }
+
+  renderBase() {
+    const { data } = this.state;
+    const { question = {}, questionNo = {} } = data;
+    return <Block>
+      <h1>题目信息</h1>
+      <Form>
+        <Form.Item labelCol={{ span: 5 }} wrapperCol={{ span: 16 }} label='题型'>
+          {QuestionTypeMap[question.type]}
+        </Form.Item>
+        <Form.Item labelCol={{ span: 5 }} wrapperCol={{ span: 16 }} label='题目id'>
+          <a href='' target='_blank'>{questionNo.no}</a>
+        </Form.Item>
+      </Form>
+    </Block>;
+  }
+
+  renderAsk() {
+    const { data } = this.state;
+    const { user = {}, createTime, target, originContent, content } = data;
+    return <Block>
+      <h1>提问信息</h1>
+      <Form>
+        <Form.Item labelCol={{ span: 5 }} wrapperCol={{ span: 16 }} label='用户姓名'>
+          {user.realName}
+        </Form.Item>
+        <Form.Item labelCol={{ span: 5 }} wrapperCol={{ span: 16 }} label='提问时间'>
+          {formatDate(createTime)}
+        </Form.Item>
+        <Form.Item labelCol={{ span: 5 }} wrapperCol={{ span: 16 }} label='提问模块'>
+          {AskTargetMap[target]}
+        </Form.Item>
+        <Form.Item labelCol={{ span: 5 }} wrapperCol={{ span: 16 }} label='提问内容'>
+          {originContent}
+        </Form.Item>
+        <Form.Item labelCol={{ span: 5 }} wrapperCol={{ span: 16 }} label='提问详情'>
+          {content}
+        </Form.Item>
+      </Form>
+    </Block>;
+  }
+
+  renderQuestionList() {
+    return <Block>
+      <h1>该题目的展示中问题</h1>
+      <DragList
+        loading={this.props.core.loading}
+        dataSource={this.state.data.others || []}
+        handle={'.icon'}
+        onMove={(oldIndex, newIndex) => {
+          this.orderQuestion(oldIndex, newIndex);
+        }}
+        renderItem={(item) => (
+          <List.Item actions={[<Icon type='bars' className='icon' />, <Typography.Text copyable={{ text: 'url' }} />]}>
+            <Row style={{ width: '100%' }}>
+              <Col span={11}>问题:{item.content}</Col>
+              <Col span={11} offset={1}>答复:{item.answer}</Col>
+            </Row>
+          </List.Item>
+        )}
+      /></Block>;
+  }
+
+  renderAnswer() {
+    const { getFieldDecorator } = this.props.form;
+    return <Block>
+      <Form>
+        {getFieldDecorator('id')(<input hidden />)}
+        <Form.Item label='教师回复'>
+          {getFieldDecorator('answer', {
+          })(
+            <Editor placeholder='输入内容' />,
+          )}
+        </Form.Item>
+        <Row type="flex" justify="center">
+          <Col span={12}>
+            <Form.Item labelCol={{ span: 12 }} wrapperCol={{ span: 10 }} label='显示状态'>
+              {getFieldDecorator('showStatus', {
+                valuePropName: 'checked',
+              })(
+                <Switch onChange={(value) => {
+                  if (value) {
+                    this.addOrder();
+                  } else {
+                    this.removeOrder();
+                  }
+                }} checkedChildren='on' unCheckedChildren='off' />,
+              )}
+            </Form.Item>
+          </Col>
+        </Row>
+      </Form>
+    </Block>;
+  }
+
+  renderView() {
+    return <div flex>
+      {this.renderBase()}
+      {this.renderAsk()}
+      {this.renderQuestionList()}
+      {this.renderAnswer()}
+
+      <Row type="flex" justify="center">
+        <Col>
+          <Button type="primary" onClick={() => {
+            this.submit();
+          }}>保存</Button>
+        </Col>
+      </Row>
+    </div>;
+  }
+}

+ 1 - 1
front/project/admin/routes/class/group.js

@@ -1,5 +1,5 @@
 export default {
-  key: 'class',
+  key: 'course',
   name: '课程管理',
   icon: 'appstore',
 };

+ 8 - 0
front/project/admin/routes/course/index.js

@@ -0,0 +1,8 @@
+import ask from './ask';
+import askDetail from './askDetail';
+import invoice from './invoice';
+import list from './list';
+import Package from './package';
+import packageDetail from './packageDetail';
+
+export default [ask, askDetail, invoice, list, Package, packageDetail];

+ 14 - 0
front/project/admin/routes/course/invoice/index.js

@@ -0,0 +1,14 @@
+import module from '../../module';
+import group from '../group';
+
+export default {
+  path: '/course/invoice',
+  key: 'course-invoice',
+  title: '发票管理',
+  needLogin: true,
+  module,
+  group,
+  component() {
+    return import('./page');
+  },
+};

+ 3 - 0
front/project/admin/routes/course/invoice/index.less

@@ -0,0 +1,3 @@
+@charset "utf-8";
+
+#course-invoice {}

+ 12 - 0
front/project/admin/routes/course/invoice/page.js

@@ -0,0 +1,12 @@
+import React from 'react';
+import './index.less';
+import Page from '@src/containers/Page';
+
+export default class extends Page {
+  init() {
+  }
+
+  renderView() {
+    return <div />;
+  }
+}

+ 14 - 0
front/project/admin/routes/course/list/index.js

@@ -0,0 +1,14 @@
+import module from '../../module';
+import group from '../group';
+
+export default {
+  path: '/course/list',
+  key: 'course-list',
+  title: '课程管理',
+  needLogin: true,
+  module,
+  group,
+  component() {
+    return import('./page');
+  },
+};

+ 3 - 0
front/project/admin/routes/course/list/index.less

@@ -0,0 +1,3 @@
+@charset "utf-8";
+
+#course-list {}

+ 12 - 0
front/project/admin/routes/course/list/page.js

@@ -0,0 +1,12 @@
+import React from 'react';
+import './index.less';
+import Page from '@src/containers/Page';
+
+export default class extends Page {
+  init() {
+  }
+
+  renderView() {
+    return <div />;
+  }
+}

+ 14 - 0
front/project/admin/routes/course/package/index.js

@@ -0,0 +1,14 @@
+import module from '../../module';
+import group from '../group';
+
+export default {
+  path: '/course/package',
+  key: 'course-package',
+  title: '套餐管理',
+  needLogin: true,
+  module,
+  group,
+  component() {
+    return import('./page');
+  },
+};

+ 3 - 0
front/project/admin/routes/course/package/index.less

@@ -0,0 +1,3 @@
+@charset "utf-8";
+
+#course-package {}

+ 12 - 0
front/project/admin/routes/course/package/page.js

@@ -0,0 +1,12 @@
+import React from 'react';
+import './index.less';
+import Page from '@src/containers/Page';
+
+export default class extends Page {
+  init() {
+  }
+
+  renderView() {
+    return <div />;
+  }
+}

+ 15 - 0
front/project/admin/routes/course/packageDetail/index.js

@@ -0,0 +1,15 @@
+import module from '../../module';
+import group from '../group';
+
+export default {
+  path: '/course/package/detail/:id',
+  key: 'course-package-detail',
+  title: '套餐管理',
+  needLogin: true,
+  module,
+  group,
+  showKey: 'course-package',
+  component() {
+    return import('./page');
+  },
+};

+ 3 - 0
front/project/admin/routes/course/packageDetail/index.less

@@ -0,0 +1,3 @@
+@charset "utf-8";
+
+#course-package-detail {}

+ 12 - 0
front/project/admin/routes/course/packageDetail/page.js

@@ -0,0 +1,12 @@
+import React from 'react';
+import './index.less';
+import Page from '@src/containers/Page';
+
+export default class extends Page {
+  init() {
+  }
+
+  renderView() {
+    return <div />;
+  }
+}

+ 15 - 0
front/project/admin/routes/setting/comment/index.js

@@ -0,0 +1,15 @@
+import module from '../../module';
+import group from '../group';
+
+export default {
+  path: '/setting/comment',
+  key: 'setting-comment',
+  title: '评价设置',
+  needLogin: true,
+  module,
+  group,
+  index: true,
+  component() {
+    return import('./page');
+  },
+};

+ 18 - 0
front/project/admin/routes/setting/comment/index.less

@@ -0,0 +1,18 @@
+@charset "utf-8";
+
+#setting-index {
+  .ant-card.plus {
+    text-align: center;
+    cursor: pointer;
+  }
+
+  .ant-card {
+    margin-bottom: 20px;
+  }
+
+  .delete-button {
+    position: absolute;
+    right: 10px;
+    top: 10px;
+  }
+}

+ 208 - 0
front/project/admin/routes/setting/comment/page.js

@@ -0,0 +1,208 @@
+import React from 'react';
+import './index.less';
+import Page from '@src/containers/Page';
+import Block from '@src/components/Block';
+import FilterLayout from '@src/layouts/FilterLayout';
+import ActionLayout from '@src/layouts/ActionLayout';
+import TableLayout from '@src/layouts/TableLayout';
+import { getMap, bindSearch, formatDate } from '@src/services/Tools';
+import { asyncSMessage, asyncForm } from '@src/services/AsyncTools';
+import { ChannelModule, SwitchSelect } from '../../../../Constant';
+import { System } from '../../../stores/system';
+import { User } from '../../../stores/user';
+
+const SwitchSelectMap = getMap(SwitchSelect, 'value', 'label');
+const ChannelModuleMap = getMap(ChannelModule, 'value', 'label');
+export default class extends Page {
+  init() {
+    this.actionList = [{
+      key: 'add',
+      type: 'primary',
+      name: '创建',
+    }];
+    this.itemList = [{
+      key: 'id',
+      type: 'hidden',
+    }, {
+      key: 'channel',
+      type: 'select',
+      allowClear: true,
+      name: '频道',
+      select: ChannelModule,
+      placeholder: '请选择',
+    }, {
+      key: 'position',
+      type: 'select',
+      allowClear: true,
+      name: '位置',
+      select: ChannelModule,
+      placeholder: '请选择',
+    }, {
+      key: 'nickname',
+      type: 'input',
+      name: '学员昵称',
+    }, {
+      key: 'avatar',
+      type: 'upload',
+      name: '学员头像',
+      image: true,
+    }, {
+      key: 'content',
+      type: 'textarea',
+      name: '评价内容',
+    }];
+    this.filterForm = [{
+      key: 'channel',
+      type: 'select',
+      allowClear: true,
+      name: '频道',
+      select: ChannelModule,
+      placeholder: '请选择',
+    }, {
+      key: 'position',
+      type: 'select',
+      allowClear: true,
+      name: '位置',
+      select: ChannelModule,
+      placeholder: '请选择',
+    }, {
+      key: 'userId',
+      type: 'select',
+      allowClear: true,
+      name: '用户',
+      select: [],
+      number: true,
+      placeholder: '请输入',
+    }, {
+      key: '精选',
+      type: 'select',
+      allowClear: true,
+      name: '展示状态',
+      select: SwitchSelect,
+    }];
+    this.columns = [
+      {
+        title: '频道',
+        dataIndex: 'channel',
+        render: (text, record) => {
+          return ChannelModuleMap[record.channel];
+        },
+      },
+      {
+        title: '位置',
+        dataIndex: 'position',
+      },
+      {
+        title: '内容',
+        dataIndex: 'content',
+      },
+      {
+        title: '用户',
+        dataIndex: 'user',
+        render: (text, record) => {
+          return text ? text.nickname : record.nickname;
+        },
+      }, {
+        title: '时间',
+        dataIndex: 'createTime',
+        render: (text) => {
+          return formatDate(text);
+        },
+      }, {
+        title: '精选',
+        dataIndex: 'isSpecial',
+        render: (text) => {
+          return SwitchSelectMap[text] || text;
+        },
+      }, {
+        title: '操作',
+        dataIndex: 'handler',
+        render: (text, record) => {
+          return <div className="table-button">
+            {(
+              <a onClick={() => {
+                this.editAction(record);
+              }}>编辑</a>
+            )}
+            {!!record.isSpecial && (
+              <a onClick={() => {
+                this.special(record, 0);
+              }}>取消精选</a>
+            )}
+            {!record.isSpecial && (
+              <a onClick={() => {
+                this.special(record, 1);
+              }}>精选</a>
+            )}
+          </div>;
+        },
+      },
+    ];
+    bindSearch(this.filterForm, 'userId', this, (search) => {
+      return User.list(search);
+    }, (row) => {
+      return {
+        title: `${row.nickname}(${row.mobile})`,
+        value: row.id,
+      };
+    }, this.state.search.userId ? Number(this.state.search.userId) : [], null);
+  }
+
+  initData() {
+    System.listComment(this.state.search).then(result => {
+      this.setTableData(result.list, result.total);
+    });
+  }
+
+  addAction() {
+    asyncForm('创建评价', this.itemList, {}, data => {
+      return System.addComment(data).then(() => {
+        asyncSMessage('添加成功!');
+        this.refresh();
+      });
+    });
+  }
+
+  editAction(row) {
+    asyncForm('编辑', this.itemList, row, data => {
+      return System.editComment(data).then(() => {
+        asyncSMessage('编辑成功!');
+        this.refresh();
+      });
+    });
+  }
+
+  special(row, isSpecial) {
+    System.editComment({ id: row.id, isSpecial }).then(() => {
+      asyncSMessage('编辑成功!');
+      this.refresh();
+    });
+  }
+
+  renderView() {
+    return <Block flex>
+      <FilterLayout
+        show
+        itemList={this.filterForm}
+        data={this.state.search}
+        onChange={data => {
+          this.search(data);
+        }} />
+      <ActionLayout
+        itemList={this.actionList}
+        selectedKeys={this.state.selectedKeys}
+        onAction={key => this.onAction(key)}
+      />
+      <TableLayout
+        select
+        columns={this.columns}
+        list={this.state.list}
+        pagination={this.state.page}
+        loading={this.props.core.loading}
+        onChange={(pagination, filters, sorter) => this.tableChange(pagination, filters, sorter)}
+        onSelect={(keys, rows) => this.tableSelect(keys, rows)}
+        selectedKeys={this.state.selectedKeys}
+      />
+    </Block>;
+  }
+}

+ 15 - 0
front/project/admin/routes/setting/faq/index.js

@@ -0,0 +1,15 @@
+import module from '../../module';
+import group from '../group';
+
+export default {
+  path: '/setting/faq',
+  key: 'setting-faq',
+  title: 'FAQ设置',
+  needLogin: true,
+  module,
+  group,
+  index: true,
+  component() {
+    return import('./page');
+  },
+};

+ 3 - 0
front/project/admin/routes/setting/faq/index.less

@@ -0,0 +1,3 @@
+@charset "utf-8";
+
+#setting-faq {}

+ 208 - 0
front/project/admin/routes/setting/faq/page.js

@@ -0,0 +1,208 @@
+import React from 'react';
+import './index.less';
+import Page from '@src/containers/Page';
+import Block from '@src/components/Block';
+import FilterLayout from '@src/layouts/FilterLayout';
+import ActionLayout from '@src/layouts/ActionLayout';
+import TableLayout from '@src/layouts/TableLayout';
+import { getMap, bindSearch, formatDate } from '@src/services/Tools';
+import { asyncSMessage, asyncForm } from '@src/services/AsyncTools';
+import { ChannelModule, SwitchSelect } from '../../../../Constant';
+import { System } from '../../../stores/system';
+import { User } from '../../../stores/user';
+
+const SwitchSelectMap = getMap(SwitchSelect, 'value', 'label');
+const ChannelModuleMap = getMap(ChannelModule, 'value', 'label');
+export default class extends Page {
+  init() {
+    this.actionList = [{
+      key: 'add',
+      type: 'primary',
+      name: '创建',
+    }];
+    this.itemList = [{
+      key: 'id',
+      type: 'hidden',
+    }, {
+      key: 'channel',
+      type: 'select',
+      allowClear: true,
+      name: '频道',
+      select: ChannelModule,
+      placeholder: '请选择',
+    }, {
+      key: 'position',
+      type: 'select',
+      allowClear: true,
+      name: '位置',
+      select: ChannelModule,
+      placeholder: '请选择',
+    }, {
+      key: 'nickname',
+      type: 'input',
+      name: '学员昵称',
+    }, {
+      key: 'avatar',
+      type: 'upload',
+      name: '学员头像',
+      image: true,
+    }, {
+      key: 'content',
+      type: 'textarea',
+      name: '评价内容',
+    }];
+    this.filterForm = [{
+      key: 'channel',
+      type: 'select',
+      allowClear: true,
+      name: '频道',
+      select: ChannelModule,
+      placeholder: '请选择',
+    }, {
+      key: 'position',
+      type: 'select',
+      allowClear: true,
+      name: '位置',
+      select: ChannelModule,
+      placeholder: '请选择',
+    }, {
+      key: 'userId',
+      type: 'select',
+      allowClear: true,
+      name: '用户',
+      select: [],
+      number: true,
+      placeholder: '请输入',
+    }, {
+      key: '精选',
+      type: 'select',
+      allowClear: true,
+      name: '展示状态',
+      select: SwitchSelect,
+    }];
+    this.columns = [
+      {
+        title: '频道',
+        dataIndex: 'channel',
+        render: (text, record) => {
+          return ChannelModuleMap[record.channel];
+        },
+      },
+      {
+        title: '位置',
+        dataIndex: 'position',
+      },
+      {
+        title: '内容',
+        dataIndex: 'content',
+      },
+      {
+        title: '用户',
+        dataIndex: 'user',
+        render: (text, record) => {
+          return text ? text.nickname : record.nickname;
+        },
+      }, {
+        title: '时间',
+        dataIndex: 'createTime',
+        render: (text) => {
+          return formatDate(text);
+        },
+      }, {
+        title: '精选',
+        dataIndex: 'isSpecial',
+        render: (text) => {
+          return SwitchSelectMap[text] || text;
+        },
+      }, {
+        title: '操作',
+        dataIndex: 'handler',
+        render: (text, record) => {
+          return <div className="table-button">
+            {(
+              <a onClick={() => {
+                this.editAction(record);
+              }}>编辑</a>
+            )}
+            {!!record.isSpecial && (
+              <a onClick={() => {
+                this.special(record, 0);
+              }}>取消精选</a>
+            )}
+            {!record.isSpecial && (
+              <a onClick={() => {
+                this.special(record, 1);
+              }}>精选</a>
+            )}
+          </div>;
+        },
+      },
+    ];
+    bindSearch(this.filterForm, 'userId', this, (search) => {
+      return User.list(search);
+    }, (row) => {
+      return {
+        title: `${row.nickname}(${row.mobile})`,
+        value: row.id,
+      };
+    }, this.state.search.userId ? Number(this.state.search.userId) : [], null);
+  }
+
+  initData() {
+    System.listFAQ(this.state.search).then(result => {
+      this.setTableData(result.list, result.total);
+    });
+  }
+
+  addAction() {
+    asyncForm('创建评价', this.itemList, {}, data => {
+      return System.addFAQ(data).then(() => {
+        asyncSMessage('添加成功!');
+        this.refresh();
+      });
+    });
+  }
+
+  editAction(row) {
+    asyncForm('编辑', this.itemList, row, data => {
+      return System.editFAQ(data).then(() => {
+        asyncSMessage('编辑成功!');
+        this.refresh();
+      });
+    });
+  }
+
+  special(row, isSpecial) {
+    System.editFAQ({ id: row.id, isSpecial }).then(() => {
+      asyncSMessage('编辑成功!');
+      this.refresh();
+    });
+  }
+
+  renderView() {
+    return <Block flex>
+      <FilterLayout
+        show
+        itemList={this.filterForm}
+        data={this.state.search}
+        onChange={data => {
+          this.search(data);
+        }} />
+      <ActionLayout
+        itemList={this.actionList}
+        selectedKeys={this.state.selectedKeys}
+        onAction={key => this.onAction(key)}
+      />
+      <TableLayout
+        select
+        columns={this.columns}
+        list={this.state.list}
+        pagination={this.state.page}
+        loading={this.props.core.loading}
+        onChange={(pagination, filters, sorter) => this.tableChange(pagination, filters, sorter)}
+        onSelect={(keys, rows) => this.tableSelect(keys, rows)}
+        selectedKeys={this.state.selectedKeys}
+      />
+    </Block>;
+  }
+}

+ 4 - 1
front/project/admin/routes/setting/index.js

@@ -4,5 +4,8 @@ import service from './service';
 import index from './index/';
 import place from './place';
 import time from './time';
+import comment from './comment';
+import faq from './faq';
+import message from './message';
 
-export default [struct, tips, service, index, place, time];
+export default [struct, tips, service, index, place, time, comment, faq, message];

+ 15 - 0
front/project/admin/routes/setting/message/index.js

@@ -0,0 +1,15 @@
+import module from '../../module';
+import group from '../group';
+
+export default {
+  path: '/setting/message',
+  key: 'setting-message',
+  title: '消息',
+  needLogin: true,
+  module,
+  group,
+  index: true,
+  component() {
+    return import('./page');
+  },
+};

+ 22 - 0
front/project/admin/routes/setting/message/index.less

@@ -0,0 +1,22 @@
+@charset "utf-8";
+
+#setting-place {
+  .block {
+    margin-bottom: 20px;
+  }
+
+  .ant-card.plus {
+    text-align: center;
+    cursor: pointer;
+  }
+
+  .ant-card {
+    margin-bottom: 20px;
+  }
+
+  .delete-button {
+    position: absolute;
+    right: 10px;
+    top: 10px;
+  }
+}

+ 250 - 0
front/project/admin/routes/setting/message/page.js

@@ -0,0 +1,250 @@
+import React from 'react';
+import { Button, Tabs, Row, Col, Form, Input } from 'antd';
+import './index.less';
+import Page from '@src/containers/Page';
+import Block from '@src/components/Block';
+import ActionLayout from '@src/layouts/ActionLayout';
+import TableLayout from '@src/layouts/TableLayout';
+import { formatFormError, formatDate } from '@src/services/Tools';
+import { asyncSMessage, asyncForm } from '@src/services/AsyncTools';
+import { System } from '../../../stores/system';
+
+export default class extends Page {
+  init() {
+    this.itemList = [{
+      key: 'id',
+      type: 'hidden',
+    }, {
+      key: 'title',
+      type: 'input',
+      name: '标题',
+    }, {
+      key: 'content',
+      type: 'textarea',
+      name: '内容',
+    }, {
+      key: 'link',
+      type: 'input',
+      name: '链接地址',
+    }, {
+      key: 'sendTime',
+      type: 'date',
+      name: '发送时间',
+    }];
+
+    this.columns = [{
+      title: '消息标题',
+      dataIndex: 'title',
+    }, {
+      title: '消息内容',
+      dataIndex: 'content',
+    }, {
+      title: '发送时间',
+      dataIndex: 'sendTime',
+      render: (text) => {
+        return formatDate(text);
+      },
+    }, {
+      title: '操作',
+      dataIndex: 'handler',
+      render: (text, record) => {
+        return <div className="table-button">
+          {(
+            <a onClick={() => {
+              this.editAction(record);
+            }}>编辑</a>
+          )}
+        </div>;
+      },
+    }];
+
+    this.actionList = [{
+      key: 'add',
+      name: '增加',
+    }];
+
+    this.state.tab = 'template';
+  }
+
+  initData() {
+    this.refresh(this.state.tab);
+  }
+
+  refresh(tab) {
+    if (tab === 'template') {
+      return this.refreshTemplate();
+    }
+    if (tab === 'custom') {
+      return this.refreshCustom();
+    }
+    return Promise.reject();
+  }
+
+  refreshTemplate() {
+    return System.getMessageTemplate().then(result => {
+      this.setState({ template: result || {} });
+    });
+  }
+
+  refreshCustom() {
+    return System.listMessage().then((result) => {
+      this.setState({ list: result.list, total: result.total });
+    });
+  }
+
+  submit(tab) {
+    let handler;
+    if (tab === 'template') {
+      handler = this.submitTemplate();
+    }
+    handler.then(() => {
+      asyncSMessage('保存成功');
+    });
+  }
+
+  submitTemplate() {
+    const { form } = this.props;
+    form.validateFields((err) => {
+      if (!err) {
+        const data = form.getFieldsValue();
+        System.setMessageTemplate(data)
+          .then(() => {
+            this.setState(data);
+            asyncSMessage('保存成功');
+          }).catch((e) => {
+            form.setFields(formatFormError(data, e.result));
+          });
+      }
+    });
+  }
+
+  submitCustom() {
+    const { exercise } = this.state;
+    return System.setExerciseTime(exercise);
+  }
+
+  addAction() {
+    asyncForm('创建消息', this.itemList, {}, data => {
+      return System.addMessage(data).then(() => {
+        asyncSMessage('添加成功!');
+        this.refresh('custom');
+      });
+    });
+  }
+
+  editAction(row) {
+    asyncForm('编辑消息', this.itemList, row, data => {
+      return System.editMessage(data).then(() => {
+        asyncSMessage('编辑成功!');
+        this.refresh('custom');
+      });
+    });
+  }
+
+  renderTemplate() {
+    const { getFieldDecorator } = this.props.form;
+    return <div>
+      <Block>
+        <h1>购买消息</h1>
+        <Form>
+          <Form.Item help='可插入自定义字段' />
+          <Form.Item>
+            {getFieldDecorator('pay.content', {
+              rules: [
+                { required: false, message: '请输入购买消息内容' },
+              ],
+            })(
+              <Input.TextArea />,
+            )}
+          </Form.Item>
+          <Form.Item label='链接地址'>
+            {getFieldDecorator('pay.link')(
+              <Input placeholder='请输入跳转地址' />,
+            )}
+          </Form.Item>
+        </Form>
+      </Block>
+      <Block>
+        <h1>换库消息</h1>
+        <Form>
+          <Form.Item help='可插入自定义字段' />
+          <Form.Item>
+            {getFieldDecorator('library.content', {
+              rules: [
+                { required: false, message: '请输入换库消息内容' },
+              ],
+            })(
+              <Input.TextArea />,
+            )}
+          </Form.Item>
+          <Form.Item label='链接地址'>
+            {getFieldDecorator('library.link')(
+              <Input placeholder='请输入跳转地址' />,
+            )}
+          </Form.Item>
+        </Form>
+      </Block>
+      <Block>
+        <h1>课程消息</h1>
+        <Form>
+          <Form.Item help='可插入自定义字段' />
+          <Form.Item>
+            {getFieldDecorator('course.content', {
+              rules: [
+                { required: false, message: '请输入课程消息内容' },
+              ],
+            })(
+              <Input.TextArea />,
+            )}
+          </Form.Item>
+          <Form.Item label='链接地址'>
+            {getFieldDecorator('course.link')(
+              <Input placeholder='请输入跳转地址' />,
+            )}
+          </Form.Item>
+        </Form>
+      </Block>
+    </div>;
+  }
+
+  renderCustom() {
+    return <Block flex>
+      <ActionLayout
+        itemList={this.actionList}
+        selectedKeys={this.state.selectedKeys}
+        onAction={key => this.onAction(key)}
+      />
+      <TableLayout
+        columns={this.columns}
+        list={this.state.list}
+        pagination={false}
+        loading={this.props.core.loading}
+      />
+    </Block>;
+  }
+
+  renderView() {
+    const { tab } = this.state;
+    return <div>
+      <Tabs activeKey={tab} onChange={(value) => {
+        this.setState({ tab: value, selectedKeys: [], checkedKeys: [] });
+        this.refresh(value);
+      }}>
+        <Tabs.TabPane tab="模版消息" key="template">
+          {this.renderTemplate()}
+        </Tabs.TabPane>
+        <Tabs.TabPane tab="自定义消息" key="custom">
+          {this.renderCustom()}
+        </Tabs.TabPane>
+      </Tabs>
+      {tab !== 'custom' && <Row type="flex" justify="center">
+        <Col>
+          <Button type="primary" onClick={() => {
+            this.submit(tab);
+          }}>保存</Button>
+        </Col>
+      </Row>}
+
+    </div>;
+  }
+}

+ 1 - 1
front/project/admin/routes/user/ask/page.js

@@ -154,7 +154,7 @@ export default class extends Page {
   ignoreAction() {
     const { selectedKeys } = this.state;
     asyncDelConfirm('忽略确认', '是否忽略选中提问?', () => {
-      return Promise.all(selectedKeys.map(row => User.editAsk({ id: row, answerStatus: 2 }))).then(() => {
+      return Promise.all(selectedKeys.map(row => Question.editAsk({ id: row, answerStatus: 2 }))).then(() => {
         asyncSMessage('操作成功!');
         this.refresh();
       });

+ 2 - 2
front/project/admin/routes/user/student/page.js

@@ -9,7 +9,7 @@ import TableLayout from '@src/layouts/TableLayout';
 import { getMap, formatDate } from '@src/services/Tools';
 // import { SwitchSelect, ServiceKey } from '../../../../Constant';
 import { User } from '../../../stores/user';
-import { Class } from '../../../stores/class';
+import { Course } from '../../../stores/course';
 
 export default class extends Page {
   constructor(props) {
@@ -81,7 +81,7 @@ export default class extends Page {
         },
       },
     ];
-    Class.listCourse({ size: 100 }).then(result => {
+    Course.list({ size: 100 }).then(result => {
       this.filterForm[1].select = result.list.map(row => {
         return {
           title: row.title,

+ 0 - 21
front/project/admin/stores/class.js

@@ -1,21 +0,0 @@
-import BaseStore from '@src/stores/base';
-
-export default class ClassStore extends BaseStore {
-  listCourse(params) {
-    return this.apiGet('/class/course/list', params);
-  }
-
-  listAsk(params) {
-    return this.apiGet('/class/ask/list', params);
-  }
-
-  editAsk(params) {
-    return this.apiPut('/class/ask/edit', params);
-  }
-
-  getAsk(params) {
-    return this.apiGet('/class/ask/detail', params);
-  }
-}
-
-export const Class = new ClassStore({ key: 'class' });

+ 21 - 0
front/project/admin/stores/course.js

@@ -0,0 +1,21 @@
+import BaseStore from '@src/stores/base';
+
+export default class CourseStore extends BaseStore {
+  list(params) {
+    return this.apiGet('/course/list', params);
+  }
+
+  listAsk(params) {
+    return this.apiGet('/course/ask/list', params);
+  }
+
+  editAsk(params) {
+    return this.apiPut('/course/ask/edit', params);
+  }
+
+  getAsk(params) {
+    return this.apiGet('/course/ask/detail', params);
+  }
+}
+
+export const Course = new CourseStore({ key: 'course' });

+ 2 - 2
front/project/admin/stores/index.js

@@ -6,7 +6,7 @@ import { Textbook } from './textbook';
 import { User } from './user';
 import { Sentence } from './sentence';
 import { Question } from './question';
-import { Class } from './class';
+import { Course } from './course';
 import { Slient } from './slient';
 
-export default [System, Examination, Exercise, Preview, Textbook, User, Sentence, Question, Class, Slient];
+export default [System, Examination, Exercise, Preview, Textbook, User, Sentence, Question, Course, Slient];

+ 64 - 0
front/project/admin/stores/system.js

@@ -29,6 +29,14 @@ export default class SystemStore extends BaseStore {
     return this.apiPut('/setting/index', params);
   }
 
+  getMessageTemplate() {
+    return this.apiGet('/setting/message_template');
+  }
+
+  setMessageTemplate(params) {
+    return this.apiPut('/setting/message_template', params);
+  }
+
   getPlace() {
     return this.apiGet('/setting/place');
   }
@@ -117,6 +125,14 @@ export default class SystemStore extends BaseStore {
     return this.apiPut('/setting/service_qx_cat', params);
   }
 
+  getCourseIndex() {
+    return this.apiGet('/setting/course_index');
+  }
+
+  setCourseIndex(params) {
+    return this.apiPut('/setting/course_index', params);
+  }
+
   getTips() {
     return this.apiGet('/setting/tips');
   }
@@ -145,6 +161,54 @@ export default class SystemStore extends BaseStore {
     return this.apiForm('/setting/rank/import', params);
   }
 
+  listComment(params) {
+    return this.apiGet('/setting/comment/list', params);
+  }
+
+  addComment(params) {
+    return this.apiPost('/setting/comment/add', params);
+  }
+
+  editComment(params) {
+    return this.apiPut('/setting/comment/edit', params);
+  }
+
+  delComment(params) {
+    return this.apiDel('/setting/comment/delete', params);
+  }
+
+  listFAQ(params) {
+    return this.apiGet('/setting/faq/list', params);
+  }
+
+  addFAQ(params) {
+    return this.apiPost('/setting/faq/add', params);
+  }
+
+  editFAQ(params) {
+    return this.apiPut('/setting/faq/edit', params);
+  }
+
+  delFAQ(params) {
+    return this.apiDel('/setting/faq/delete', params);
+  }
+
+  listMessage(params) {
+    return this.apiGet('/setting/message/list', params);
+  }
+
+  addMessage(params) {
+    return this.apiPost('/setting/message/add', params);
+  }
+
+  editMessage(params) {
+    return this.apiPut('/setting/message/edit', params);
+  }
+
+  delMessage(params) {
+    return this.apiDel('/setting/message/delete', params);
+  }
+
   uploadImage(file) {
     return this.apiForm('/common/upload/image', { file });
   }

+ 1 - 1
front/project/admin/stores/user.js

@@ -42,7 +42,7 @@ export default class UserStore extends BaseStore {
   }
 
   listPreview(params) {
-    return this.apiGet('/user/preview/list', params);
+    return this.apiGet('/preview/list', params);
   }
 
   listPay(params) {

+ 6 - 3
server/data/src/main/java/com/qxgmat/data/constants/enums/SettingKey.java

@@ -9,14 +9,16 @@ import com.qxgmat.data.constants.enums.module.QuestionModule;
 public enum SettingKey {
     INDEX("index"), // 首页设置
     SENTENCE("sentence"), // 长难句目录
-    SENTENCE_PAPER_STATUS("sentence_paper_status"), // 长难句自动组卷状态:process进度,finish时间
+    MESSAGE_TEMPLATE("message_template"), // 消息模版
     PLACE("place"), // 难点设置
     EXERCISE_TIME("exercise_time"), // 练习题目时间
+    EXERCISE_PAPER_AUTO("exercise_paper_auto"), // 自动组卷设置
     EXAMINATION_TIME("examination_time"), // 考试时间
     FILTER_TIME("filter_time"), // 题目剔除时间
-    EXERCISE_PAPER_AUTO("exercise_paper_auto"), // 自动组卷设置
-    EXERCISE_PAPER_STATUS("exercise_paper_status"), // 练习自动组卷状态:process进度,finish时间
     PREPARE_INFO("prepare_info"), // 备考统计信息
+
+    EXERCISE_PAPER_STATUS("exercise_paper_status"), // 练习自动组卷状态:process进度,finish时间
+    SENTENCE_PAPER_STATUS("sentence_paper_status"), // 长难句自动组卷状态:process进度,finish时间
     SENTENCE_TIME("sentence_time"), // 长难句题目时间
     TEXTBOOK_TIME("textbook_time"), // 机经题目时间
     SCORE_SWITCH("score_switch"), // 分数开关
@@ -24,6 +26,7 @@ public enum SettingKey {
     SERVICE_TEXTBOOK("service_textbook"), // 数学机经服务信息
     SERVICE_VIP("service_vip"), // vip服务信息
     COURSE_INDEX("course_index"), // 课程首页设置
+    COURSE_PROMOTE("course_promote"), // 课程促销
 
     TIPS("tips"); // 页面提示信息
 

+ 18 - 0
server/data/src/main/java/com/qxgmat/data/constants/enums/module/ChannelModule.java

@@ -0,0 +1,18 @@
+package com.qxgmat.data.constants.enums.module;
+
+// 频道模块
+public enum ChannelModule {
+    EXERCISE("exercise"),
+    EXAMINATION("examination"),
+    COURSE("course"),
+    ;
+    public String key;
+    private ChannelModule(String key){
+        this.key = key;
+    }
+
+    public static ChannelModule ValueOf(String name){
+        if (name == null) return null;
+        return ChannelModule.valueOf(name.toUpperCase());
+    }
+}

+ 4 - 3
server/data/src/main/java/com/qxgmat/data/constants/enums/user/MessageType.java

@@ -5,9 +5,10 @@ package com.qxgmat.data.constants.enums.user;
  */
 public enum MessageType {
     PAY("pay", "购买"),
-    CHANGE("change", "换库"),
-    CLASS("class", "课程"),
-    OTHER("other", "其他");
+    LIBRARY("library", "换库"),
+    COURSE("course", "课程"),
+
+    ;
     final static public String message = "消息类型";
 
 

+ 0 - 7
server/data/src/main/java/com/qxgmat/data/dao/ClassCourseMapper.java

@@ -1,7 +0,0 @@
-package com.qxgmat.data.dao;
-
-import com.nuliji.tools.mybatis.Mapper;
-import com.qxgmat.data.dao.entity.ClassCourse;
-
-public interface ClassCourseMapper extends Mapper<ClassCourse> {
-}

+ 0 - 7
server/data/src/main/java/com/qxgmat/data/dao/ClassCourseNoMapper.java

@@ -1,7 +0,0 @@
-package com.qxgmat.data.dao;
-
-import com.nuliji.tools.mybatis.Mapper;
-import com.qxgmat.data.dao.entity.ClassCourseNo;
-
-public interface ClassCourseNoMapper extends Mapper<ClassCourseNo> {
-}

+ 0 - 7
server/data/src/main/java/com/qxgmat/data/dao/ClassFaqMapper.java

@@ -1,7 +0,0 @@
-package com.qxgmat.data.dao;
-
-import com.nuliji.tools.mybatis.Mapper;
-import com.qxgmat.data.dao.entity.ClassFaq;
-
-public interface ClassFaqMapper extends Mapper<ClassFaq> {
-}

+ 7 - 0
server/data/src/main/java/com/qxgmat/data/dao/CommentMapper.java

@@ -0,0 +1,7 @@
+package com.qxgmat.data.dao;
+
+import com.nuliji.tools.mybatis.Mapper;
+import com.qxgmat.data.dao.entity.Comment;
+
+public interface CommentMapper extends Mapper<Comment> {
+}

+ 7 - 0
server/data/src/main/java/com/qxgmat/data/dao/CourseArticleMapper.java

@@ -0,0 +1,7 @@
+package com.qxgmat.data.dao;
+
+import com.nuliji.tools.mybatis.Mapper;
+import com.qxgmat.data.dao.entity.CourseArticle;
+
+public interface CourseArticleMapper extends Mapper<CourseArticle> {
+}

+ 7 - 0
server/data/src/main/java/com/qxgmat/data/dao/CourseDataMapper.java

@@ -0,0 +1,7 @@
+package com.qxgmat.data.dao;
+
+import com.nuliji.tools.mybatis.Mapper;
+import com.qxgmat.data.dao.entity.CourseData;
+
+public interface CourseDataMapper extends Mapper<CourseData> {
+}

+ 0 - 7
server/data/src/main/java/com/qxgmat/data/dao/CourseFaqMapper.java

@@ -1,7 +0,0 @@
-package com.qxgmat.data.dao;
-
-import com.nuliji.tools.mybatis.Mapper;
-import com.qxgmat.data.dao.entity.CourseFaq;
-
-public interface CourseFaqMapper extends Mapper<CourseFaq> {
-}

+ 7 - 0
server/data/src/main/java/com/qxgmat/data/dao/CoursePackageMapper.java

@@ -0,0 +1,7 @@
+package com.qxgmat.data.dao;
+
+import com.nuliji.tools.mybatis.Mapper;
+import com.qxgmat.data.dao.entity.CoursePackage;
+
+public interface CoursePackageMapper extends Mapper<CoursePackage> {
+}

+ 7 - 0
server/data/src/main/java/com/qxgmat/data/dao/FaqMapper.java

@@ -0,0 +1,7 @@
+package com.qxgmat.data.dao;
+
+import com.nuliji.tools.mybatis.Mapper;
+import com.qxgmat.data.dao.entity.Faq;
+
+public interface FaqMapper extends Mapper<Faq> {
+}

+ 7 - 0
server/data/src/main/java/com/qxgmat/data/dao/MessageMapper.java

@@ -0,0 +1,7 @@
+package com.qxgmat.data.dao;
+
+import com.nuliji.tools.mybatis.Mapper;
+import com.qxgmat.data.dao.entity.Message;
+
+public interface MessageMapper extends Mapper<Message> {
+}

+ 0 - 7
server/data/src/main/java/com/qxgmat/data/dao/UserClassMapper.java

@@ -1,7 +0,0 @@
-package com.qxgmat.data.dao;
-
-import com.nuliji.tools.mybatis.Mapper;
-import com.qxgmat.data.dao.entity.UserClass;
-
-public interface UserClassMapper extends Mapper<UserClass> {
-}

+ 0 - 7
server/data/src/main/java/com/qxgmat/data/dao/UserCourseCommentMapper.java

@@ -1,7 +0,0 @@
-package com.qxgmat.data.dao;
-
-import com.nuliji.tools.mybatis.Mapper;
-import com.qxgmat.data.dao.entity.UserCourseComment;
-
-public interface UserCourseCommentMapper extends Mapper<UserCourseComment> {
-}

+ 0 - 230
server/data/src/main/java/com/qxgmat/data/dao/entity/ClassCourse.java

@@ -1,230 +0,0 @@
-package com.qxgmat.data.dao.entity;
-
-import java.io.Serializable;
-import java.util.Date;
-import javax.persistence.*;
-
-@Table(name = "class_course")
-public class ClassCourse implements Serializable {
-    @Id
-    @Column(name = "`id`")
-    @GeneratedValue(strategy = GenerationType.IDENTITY)
-    private Integer id;
-
-    /**
-     * 节点id
-     */
-    @Column(name = "`struct_id`")
-    private Integer structId;
-
-    /**
-     * 上级节点id,0为无上级
-     */
-    @Column(name = "`parent_struct_id`")
-    private Integer parentStructId;
-
-    /**
-     * 题型:从struct上获取extend
-     */
-    @Column(name = "`question_type`")
-    private String questionType;
-
-    /**
-     * 课程名称
-     */
-    @Column(name = "`title`")
-    private String title;
-
-    @Column(name = "`create_time`")
-    private Date createTime;
-
-    private static final long serialVersionUID = 1L;
-
-    /**
-     * @return id
-     */
-    public Integer getId() {
-        return id;
-    }
-
-    /**
-     * @param id
-     */
-    public void setId(Integer id) {
-        this.id = id;
-    }
-
-    /**
-     * 获取节点id
-     *
-     * @return struct_id - 节点id
-     */
-    public Integer getStructId() {
-        return structId;
-    }
-
-    /**
-     * 设置节点id
-     *
-     * @param structId 节点id
-     */
-    public void setStructId(Integer structId) {
-        this.structId = structId;
-    }
-
-    /**
-     * 获取上级节点id,0为无上级
-     *
-     * @return parent_struct_id - 上级节点id,0为无上级
-     */
-    public Integer getParentStructId() {
-        return parentStructId;
-    }
-
-    /**
-     * 设置上级节点id,0为无上级
-     *
-     * @param parentStructId 上级节点id,0为无上级
-     */
-    public void setParentStructId(Integer parentStructId) {
-        this.parentStructId = parentStructId;
-    }
-
-    /**
-     * 获取题型:从struct上获取extend
-     *
-     * @return question_type - 题型:从struct上获取extend
-     */
-    public String getQuestionType() {
-        return questionType;
-    }
-
-    /**
-     * 设置题型:从struct上获取extend
-     *
-     * @param questionType 题型:从struct上获取extend
-     */
-    public void setQuestionType(String questionType) {
-        this.questionType = questionType;
-    }
-
-    /**
-     * 获取课程名称
-     *
-     * @return title - 课程名称
-     */
-    public String getTitle() {
-        return title;
-    }
-
-    /**
-     * 设置课程名称
-     *
-     * @param title 课程名称
-     */
-    public void setTitle(String title) {
-        this.title = title;
-    }
-
-    /**
-     * @return create_time
-     */
-    public Date getCreateTime() {
-        return createTime;
-    }
-
-    /**
-     * @param createTime
-     */
-    public void setCreateTime(Date createTime) {
-        this.createTime = createTime;
-    }
-
-    @Override
-    public String toString() {
-        StringBuilder sb = new StringBuilder();
-        sb.append(getClass().getSimpleName());
-        sb.append(" [");
-        sb.append("Hash = ").append(hashCode());
-        sb.append(", id=").append(id);
-        sb.append(", structId=").append(structId);
-        sb.append(", parentStructId=").append(parentStructId);
-        sb.append(", questionType=").append(questionType);
-        sb.append(", title=").append(title);
-        sb.append(", createTime=").append(createTime);
-        sb.append("]");
-        return sb.toString();
-    }
-
-    public static ClassCourse.Builder builder() {
-        return new ClassCourse.Builder();
-    }
-
-    public static class Builder {
-        private ClassCourse obj;
-
-        public Builder() {
-            this.obj = new ClassCourse();
-        }
-
-        /**
-         * @param id
-         */
-        public Builder id(Integer id) {
-            obj.setId(id);
-            return this;
-        }
-
-        /**
-         * 设置节点id
-         *
-         * @param structId 节点id
-         */
-        public Builder structId(Integer structId) {
-            obj.setStructId(structId);
-            return this;
-        }
-
-        /**
-         * 设置上级节点id,0为无上级
-         *
-         * @param parentStructId 上级节点id,0为无上级
-         */
-        public Builder parentStructId(Integer parentStructId) {
-            obj.setParentStructId(parentStructId);
-            return this;
-        }
-
-        /**
-         * 设置题型:从struct上获取extend
-         *
-         * @param questionType 题型:从struct上获取extend
-         */
-        public Builder questionType(String questionType) {
-            obj.setQuestionType(questionType);
-            return this;
-        }
-
-        /**
-         * 设置课程名称
-         *
-         * @param title 课程名称
-         */
-        public Builder title(String title) {
-            obj.setTitle(title);
-            return this;
-        }
-
-        /**
-         * @param createTime
-         */
-        public Builder createTime(Date createTime) {
-            obj.setCreateTime(createTime);
-            return this;
-        }
-
-        public ClassCourse build() {
-            return this.obj;
-        }
-    }
-}

+ 0 - 265
server/data/src/main/java/com/qxgmat/data/dao/entity/ClassCourseNo.java

@@ -1,265 +0,0 @@
-package com.qxgmat.data.dao.entity;
-
-import java.io.Serializable;
-import java.util.Date;
-import javax.persistence.*;
-
-@Table(name = "class_course_no")
-public class ClassCourseNo implements Serializable {
-    @Id
-    @Column(name = "`id`")
-    @GeneratedValue(strategy = GenerationType.IDENTITY)
-    private Integer id;
-
-    /**
-     * 课程id
-     */
-    @Column(name = "`course_id`")
-    private Integer courseId;
-
-    /**
-     * 课时序号
-     */
-    @Column(name = "`no`")
-    private Integer no;
-
-    /**
-     * 资源文件地址
-     */
-    @Column(name = "`resource`")
-    private String resource;
-
-    /**
-     * 课程时长
-     */
-    @Column(name = "`time`")
-    private Integer time;
-
-    @Column(name = "`create_time`")
-    private Date createTime;
-
-    /**
-     * 课时描述
-     */
-    @Column(name = "`content`")
-    private String content;
-
-    private static final long serialVersionUID = 1L;
-
-    /**
-     * @return id
-     */
-    public Integer getId() {
-        return id;
-    }
-
-    /**
-     * @param id
-     */
-    public void setId(Integer id) {
-        this.id = id;
-    }
-
-    /**
-     * 获取课程id
-     *
-     * @return course_id - 课程id
-     */
-    public Integer getCourseId() {
-        return courseId;
-    }
-
-    /**
-     * 设置课程id
-     *
-     * @param courseId 课程id
-     */
-    public void setCourseId(Integer courseId) {
-        this.courseId = courseId;
-    }
-
-    /**
-     * 获取课时序号
-     *
-     * @return no - 课时序号
-     */
-    public Integer getNo() {
-        return no;
-    }
-
-    /**
-     * 设置课时序号
-     *
-     * @param no 课时序号
-     */
-    public void setNo(Integer no) {
-        this.no = no;
-    }
-
-    /**
-     * 获取资源文件地址
-     *
-     * @return resource - 资源文件地址
-     */
-    public String getResource() {
-        return resource;
-    }
-
-    /**
-     * 设置资源文件地址
-     *
-     * @param resource 资源文件地址
-     */
-    public void setResource(String resource) {
-        this.resource = resource;
-    }
-
-    /**
-     * 获取课程时长
-     *
-     * @return time - 课程时长
-     */
-    public Integer getTime() {
-        return time;
-    }
-
-    /**
-     * 设置课程时长
-     *
-     * @param time 课程时长
-     */
-    public void setTime(Integer time) {
-        this.time = time;
-    }
-
-    /**
-     * @return create_time
-     */
-    public Date getCreateTime() {
-        return createTime;
-    }
-
-    /**
-     * @param createTime
-     */
-    public void setCreateTime(Date createTime) {
-        this.createTime = createTime;
-    }
-
-    /**
-     * 获取课时描述
-     *
-     * @return content - 课时描述
-     */
-    public String getContent() {
-        return content;
-    }
-
-    /**
-     * 设置课时描述
-     *
-     * @param content 课时描述
-     */
-    public void setContent(String content) {
-        this.content = content;
-    }
-
-    @Override
-    public String toString() {
-        StringBuilder sb = new StringBuilder();
-        sb.append(getClass().getSimpleName());
-        sb.append(" [");
-        sb.append("Hash = ").append(hashCode());
-        sb.append(", id=").append(id);
-        sb.append(", courseId=").append(courseId);
-        sb.append(", no=").append(no);
-        sb.append(", resource=").append(resource);
-        sb.append(", time=").append(time);
-        sb.append(", createTime=").append(createTime);
-        sb.append(", content=").append(content);
-        sb.append("]");
-        return sb.toString();
-    }
-
-    public static ClassCourseNo.Builder builder() {
-        return new ClassCourseNo.Builder();
-    }
-
-    public static class Builder {
-        private ClassCourseNo obj;
-
-        public Builder() {
-            this.obj = new ClassCourseNo();
-        }
-
-        /**
-         * @param id
-         */
-        public Builder id(Integer id) {
-            obj.setId(id);
-            return this;
-        }
-
-        /**
-         * 设置课程id
-         *
-         * @param courseId 课程id
-         */
-        public Builder courseId(Integer courseId) {
-            obj.setCourseId(courseId);
-            return this;
-        }
-
-        /**
-         * 设置课时序号
-         *
-         * @param no 课时序号
-         */
-        public Builder no(Integer no) {
-            obj.setNo(no);
-            return this;
-        }
-
-        /**
-         * 设置资源文件地址
-         *
-         * @param resource 资源文件地址
-         */
-        public Builder resource(String resource) {
-            obj.setResource(resource);
-            return this;
-        }
-
-        /**
-         * 设置课程时长
-         *
-         * @param time 课程时长
-         */
-        public Builder time(Integer time) {
-            obj.setTime(time);
-            return this;
-        }
-
-        /**
-         * @param createTime
-         */
-        public Builder createTime(Date createTime) {
-            obj.setCreateTime(createTime);
-            return this;
-        }
-
-        /**
-         * 设置课时描述
-         *
-         * @param content 课时描述
-         */
-        public Builder content(String content) {
-            obj.setContent(content);
-            return this;
-        }
-
-        public ClassCourseNo build() {
-            return this.obj;
-        }
-    }
-}

+ 0 - 168
server/data/src/main/java/com/qxgmat/data/dao/entity/ClassFaq.java

@@ -1,168 +0,0 @@
-package com.qxgmat.data.dao.entity;
-
-import java.io.Serializable;
-import javax.persistence.*;
-
-@Table(name = "class_faq")
-public class ClassFaq implements Serializable {
-    @Id
-    @Column(name = "`id`")
-    @GeneratedValue(strategy = GenerationType.IDENTITY)
-    private Integer id;
-
-    /**
-     * 课程id
-     */
-    @Column(name = "`course_id`")
-    private Integer courseId;
-
-    /**
-     * 是否精选:0不是精选,1是精选
-     */
-    @Column(name = "`is_special`")
-    private Integer isSpecial;
-
-    /**
-     * 问答状态:0未回答,1回答,忽略
-     */
-    @Column(name = "`status`")
-    private Integer status;
-
-    private static final long serialVersionUID = 1L;
-
-    /**
-     * @return id
-     */
-    public Integer getId() {
-        return id;
-    }
-
-    /**
-     * @param id
-     */
-    public void setId(Integer id) {
-        this.id = id;
-    }
-
-    /**
-     * 获取课程id
-     *
-     * @return course_id - 课程id
-     */
-    public Integer getCourseId() {
-        return courseId;
-    }
-
-    /**
-     * 设置课程id
-     *
-     * @param courseId 课程id
-     */
-    public void setCourseId(Integer courseId) {
-        this.courseId = courseId;
-    }
-
-    /**
-     * 获取是否精选:0不是精选,1是精选
-     *
-     * @return is_special - 是否精选:0不是精选,1是精选
-     */
-    public Integer getIsSpecial() {
-        return isSpecial;
-    }
-
-    /**
-     * 设置是否精选:0不是精选,1是精选
-     *
-     * @param isSpecial 是否精选:0不是精选,1是精选
-     */
-    public void setIsSpecial(Integer isSpecial) {
-        this.isSpecial = isSpecial;
-    }
-
-    /**
-     * 获取问答状态:0未回答,1回答,忽略
-     *
-     * @return status - 问答状态:0未回答,1回答,忽略
-     */
-    public Integer getStatus() {
-        return status;
-    }
-
-    /**
-     * 设置问答状态:0未回答,1回答,忽略
-     *
-     * @param status 问答状态:0未回答,1回答,忽略
-     */
-    public void setStatus(Integer status) {
-        this.status = status;
-    }
-
-    @Override
-    public String toString() {
-        StringBuilder sb = new StringBuilder();
-        sb.append(getClass().getSimpleName());
-        sb.append(" [");
-        sb.append("Hash = ").append(hashCode());
-        sb.append(", id=").append(id);
-        sb.append(", courseId=").append(courseId);
-        sb.append(", isSpecial=").append(isSpecial);
-        sb.append(", status=").append(status);
-        sb.append("]");
-        return sb.toString();
-    }
-
-    public static ClassFaq.Builder builder() {
-        return new ClassFaq.Builder();
-    }
-
-    public static class Builder {
-        private ClassFaq obj;
-
-        public Builder() {
-            this.obj = new ClassFaq();
-        }
-
-        /**
-         * @param id
-         */
-        public Builder id(Integer id) {
-            obj.setId(id);
-            return this;
-        }
-
-        /**
-         * 设置课程id
-         *
-         * @param courseId 课程id
-         */
-        public Builder courseId(Integer courseId) {
-            obj.setCourseId(courseId);
-            return this;
-        }
-
-        /**
-         * 设置是否精选:0不是精选,1是精选
-         *
-         * @param isSpecial 是否精选:0不是精选,1是精选
-         */
-        public Builder isSpecial(Integer isSpecial) {
-            obj.setIsSpecial(isSpecial);
-            return this;
-        }
-
-        /**
-         * 设置问答状态:0未回答,1回答,忽略
-         *
-         * @param status 问答状态:0未回答,1回答,忽略
-         */
-        public Builder status(Integer status) {
-            obj.setStatus(status);
-            return this;
-        }
-
-        public ClassFaq build() {
-            return this.obj;
-        }
-    }
-}

+ 317 - 0
server/data/src/main/java/com/qxgmat/data/dao/entity/Comment.java

@@ -0,0 +1,317 @@
+package com.qxgmat.data.dao.entity;
+
+import java.io.Serializable;
+import java.util.Date;
+import javax.persistence.*;
+
+@Table(name = "comment")
+public class Comment implements Serializable {
+    @Id
+    @Column(name = "`id`")
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    private Integer id;
+
+    /**
+     * 用户id
+     */
+    @Column(name = "`user_id`")
+    private Integer userId;
+
+    /**
+     * 昵称
+     */
+    @Column(name = "`nickname`")
+    private String nickname;
+
+    /**
+     * 头像
+     */
+    @Column(name = "`avatar`")
+    private String avatar;
+
+    /**
+     * 频道
+     */
+    @Column(name = "`channel`")
+    private String channel;
+
+    /**
+     * 位置
+     */
+    @Column(name = "`position`")
+    private String position;
+
+    @Column(name = "`is_special`")
+    private Integer isSpecial;
+
+    @Column(name = "`create_time`")
+    private Date createTime;
+
+    @Column(name = "`content`")
+    private String content;
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * @return id
+     */
+    public Integer getId() {
+        return id;
+    }
+
+    /**
+     * @param id
+     */
+    public void setId(Integer id) {
+        this.id = id;
+    }
+
+    /**
+     * 获取用户id
+     *
+     * @return user_id - 用户id
+     */
+    public Integer getUserId() {
+        return userId;
+    }
+
+    /**
+     * 设置用户id
+     *
+     * @param userId 用户id
+     */
+    public void setUserId(Integer userId) {
+        this.userId = userId;
+    }
+
+    /**
+     * 获取昵称
+     *
+     * @return nickname - 昵称
+     */
+    public String getNickname() {
+        return nickname;
+    }
+
+    /**
+     * 设置昵称
+     *
+     * @param nickname 昵称
+     */
+    public void setNickname(String nickname) {
+        this.nickname = nickname;
+    }
+
+    /**
+     * 获取头像
+     *
+     * @return avatar - 头像
+     */
+    public String getAvatar() {
+        return avatar;
+    }
+
+    /**
+     * 设置头像
+     *
+     * @param avatar 头像
+     */
+    public void setAvatar(String avatar) {
+        this.avatar = avatar;
+    }
+
+    /**
+     * 获取频道
+     *
+     * @return channel - 频道
+     */
+    public String getChannel() {
+        return channel;
+    }
+
+    /**
+     * 设置频道
+     *
+     * @param channel 频道
+     */
+    public void setChannel(String channel) {
+        this.channel = channel;
+    }
+
+    /**
+     * 获取位置
+     *
+     * @return position - 位置
+     */
+    public String getPosition() {
+        return position;
+    }
+
+    /**
+     * 设置位置
+     *
+     * @param position 位置
+     */
+    public void setPosition(String position) {
+        this.position = position;
+    }
+
+    /**
+     * @return is_special
+     */
+    public Integer getIsSpecial() {
+        return isSpecial;
+    }
+
+    /**
+     * @param isSpecial
+     */
+    public void setIsSpecial(Integer isSpecial) {
+        this.isSpecial = isSpecial;
+    }
+
+    /**
+     * @return create_time
+     */
+    public Date getCreateTime() {
+        return createTime;
+    }
+
+    /**
+     * @param createTime
+     */
+    public void setCreateTime(Date createTime) {
+        this.createTime = createTime;
+    }
+
+    /**
+     * @return content
+     */
+    public String getContent() {
+        return content;
+    }
+
+    /**
+     * @param content
+     */
+    public void setContent(String content) {
+        this.content = content;
+    }
+
+    @Override
+    public String toString() {
+        StringBuilder sb = new StringBuilder();
+        sb.append(getClass().getSimpleName());
+        sb.append(" [");
+        sb.append("Hash = ").append(hashCode());
+        sb.append(", id=").append(id);
+        sb.append(", userId=").append(userId);
+        sb.append(", nickname=").append(nickname);
+        sb.append(", avatar=").append(avatar);
+        sb.append(", channel=").append(channel);
+        sb.append(", position=").append(position);
+        sb.append(", isSpecial=").append(isSpecial);
+        sb.append(", createTime=").append(createTime);
+        sb.append(", content=").append(content);
+        sb.append("]");
+        return sb.toString();
+    }
+
+    public static Comment.Builder builder() {
+        return new Comment.Builder();
+    }
+
+    public static class Builder {
+        private Comment obj;
+
+        public Builder() {
+            this.obj = new Comment();
+        }
+
+        /**
+         * @param id
+         */
+        public Builder id(Integer id) {
+            obj.setId(id);
+            return this;
+        }
+
+        /**
+         * 设置用户id
+         *
+         * @param userId 用户id
+         */
+        public Builder userId(Integer userId) {
+            obj.setUserId(userId);
+            return this;
+        }
+
+        /**
+         * 设置昵称
+         *
+         * @param nickname 昵称
+         */
+        public Builder nickname(String nickname) {
+            obj.setNickname(nickname);
+            return this;
+        }
+
+        /**
+         * 设置头像
+         *
+         * @param avatar 头像
+         */
+        public Builder avatar(String avatar) {
+            obj.setAvatar(avatar);
+            return this;
+        }
+
+        /**
+         * 设置频道
+         *
+         * @param channel 频道
+         */
+        public Builder channel(String channel) {
+            obj.setChannel(channel);
+            return this;
+        }
+
+        /**
+         * 设置位置
+         *
+         * @param position 位置
+         */
+        public Builder position(String position) {
+            obj.setPosition(position);
+            return this;
+        }
+
+        /**
+         * @param isSpecial
+         */
+        public Builder isSpecial(Integer isSpecial) {
+            obj.setIsSpecial(isSpecial);
+            return this;
+        }
+
+        /**
+         * @param createTime
+         */
+        public Builder createTime(Date createTime) {
+            obj.setCreateTime(createTime);
+            return this;
+        }
+
+        /**
+         * @param content
+         */
+        public Builder content(String content) {
+            obj.setContent(content);
+            return this;
+        }
+
+        public Comment build() {
+            return this.obj;
+        }
+    }
+}

+ 63 - 0
server/data/src/main/java/com/qxgmat/data/dao/entity/CourseArticle.java

@@ -0,0 +1,63 @@
+package com.qxgmat.data.dao.entity;
+
+import java.io.Serializable;
+import javax.persistence.*;
+
+@Table(name = "course_article")
+public class CourseArticle implements Serializable {
+    @Id
+    @Column(name = "`id`")
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    private Integer id;
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * @return id
+     */
+    public Integer getId() {
+        return id;
+    }
+
+    /**
+     * @param id
+     */
+    public void setId(Integer id) {
+        this.id = id;
+    }
+
+    @Override
+    public String toString() {
+        StringBuilder sb = new StringBuilder();
+        sb.append(getClass().getSimpleName());
+        sb.append(" [");
+        sb.append("Hash = ").append(hashCode());
+        sb.append(", id=").append(id);
+        sb.append("]");
+        return sb.toString();
+    }
+
+    public static CourseArticle.Builder builder() {
+        return new CourseArticle.Builder();
+    }
+
+    public static class Builder {
+        private CourseArticle obj;
+
+        public Builder() {
+            this.obj = new CourseArticle();
+        }
+
+        /**
+         * @param id
+         */
+        public Builder id(Integer id) {
+            obj.setId(id);
+            return this;
+        }
+
+        public CourseArticle build() {
+            return this.obj;
+        }
+    }
+}

+ 63 - 0
server/data/src/main/java/com/qxgmat/data/dao/entity/CourseData.java

@@ -0,0 +1,63 @@
+package com.qxgmat.data.dao.entity;
+
+import java.io.Serializable;
+import javax.persistence.*;
+
+@Table(name = "course_data")
+public class CourseData implements Serializable {
+    @Id
+    @Column(name = "`id`")
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    private Integer id;
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * @return id
+     */
+    public Integer getId() {
+        return id;
+    }
+
+    /**
+     * @param id
+     */
+    public void setId(Integer id) {
+        this.id = id;
+    }
+
+    @Override
+    public String toString() {
+        StringBuilder sb = new StringBuilder();
+        sb.append(getClass().getSimpleName());
+        sb.append(" [");
+        sb.append("Hash = ").append(hashCode());
+        sb.append(", id=").append(id);
+        sb.append("]");
+        return sb.toString();
+    }
+
+    public static CourseData.Builder builder() {
+        return new CourseData.Builder();
+    }
+
+    public static class Builder {
+        private CourseData obj;
+
+        public Builder() {
+            this.obj = new CourseData();
+        }
+
+        /**
+         * @param id
+         */
+        public Builder id(Integer id) {
+            obj.setId(id);
+            return this;
+        }
+
+        public CourseData build() {
+            return this.obj;
+        }
+    }
+}

+ 0 - 168
server/data/src/main/java/com/qxgmat/data/dao/entity/CourseFaq.java

@@ -1,168 +0,0 @@
-package com.qxgmat.data.dao.entity;
-
-import java.io.Serializable;
-import javax.persistence.*;
-
-@Table(name = "course_faq")
-public class CourseFaq implements Serializable {
-    @Id
-    @Column(name = "`id`")
-    @GeneratedValue(strategy = GenerationType.IDENTITY)
-    private Integer id;
-
-    /**
-     * 课程id
-     */
-    @Column(name = "`course_id`")
-    private Integer courseId;
-
-    /**
-     * 是否精选:0不是精选,1是精选
-     */
-    @Column(name = "`is_special`")
-    private Integer isSpecial;
-
-    /**
-     * 问答状态:0未回答,1回答,忽略
-     */
-    @Column(name = "`status`")
-    private Integer status;
-
-    private static final long serialVersionUID = 1L;
-
-    /**
-     * @return id
-     */
-    public Integer getId() {
-        return id;
-    }
-
-    /**
-     * @param id
-     */
-    public void setId(Integer id) {
-        this.id = id;
-    }
-
-    /**
-     * 获取课程id
-     *
-     * @return course_id - 课程id
-     */
-    public Integer getCourseId() {
-        return courseId;
-    }
-
-    /**
-     * 设置课程id
-     *
-     * @param courseId 课程id
-     */
-    public void setCourseId(Integer courseId) {
-        this.courseId = courseId;
-    }
-
-    /**
-     * 获取是否精选:0不是精选,1是精选
-     *
-     * @return is_special - 是否精选:0不是精选,1是精选
-     */
-    public Integer getIsSpecial() {
-        return isSpecial;
-    }
-
-    /**
-     * 设置是否精选:0不是精选,1是精选
-     *
-     * @param isSpecial 是否精选:0不是精选,1是精选
-     */
-    public void setIsSpecial(Integer isSpecial) {
-        this.isSpecial = isSpecial;
-    }
-
-    /**
-     * 获取问答状态:0未回答,1回答,忽略
-     *
-     * @return status - 问答状态:0未回答,1回答,忽略
-     */
-    public Integer getStatus() {
-        return status;
-    }
-
-    /**
-     * 设置问答状态:0未回答,1回答,忽略
-     *
-     * @param status 问答状态:0未回答,1回答,忽略
-     */
-    public void setStatus(Integer status) {
-        this.status = status;
-    }
-
-    @Override
-    public String toString() {
-        StringBuilder sb = new StringBuilder();
-        sb.append(getClass().getSimpleName());
-        sb.append(" [");
-        sb.append("Hash = ").append(hashCode());
-        sb.append(", id=").append(id);
-        sb.append(", courseId=").append(courseId);
-        sb.append(", isSpecial=").append(isSpecial);
-        sb.append(", status=").append(status);
-        sb.append("]");
-        return sb.toString();
-    }
-
-    public static CourseFaq.Builder builder() {
-        return new CourseFaq.Builder();
-    }
-
-    public static class Builder {
-        private CourseFaq obj;
-
-        public Builder() {
-            this.obj = new CourseFaq();
-        }
-
-        /**
-         * @param id
-         */
-        public Builder id(Integer id) {
-            obj.setId(id);
-            return this;
-        }
-
-        /**
-         * 设置课程id
-         *
-         * @param courseId 课程id
-         */
-        public Builder courseId(Integer courseId) {
-            obj.setCourseId(courseId);
-            return this;
-        }
-
-        /**
-         * 设置是否精选:0不是精选,1是精选
-         *
-         * @param isSpecial 是否精选:0不是精选,1是精选
-         */
-        public Builder isSpecial(Integer isSpecial) {
-            obj.setIsSpecial(isSpecial);
-            return this;
-        }
-
-        /**
-         * 设置问答状态:0未回答,1回答,忽略
-         *
-         * @param status 问答状态:0未回答,1回答,忽略
-         */
-        public Builder status(Integer status) {
-            obj.setStatus(status);
-            return this;
-        }
-
-        public CourseFaq build() {
-            return this.obj;
-        }
-    }
-}

+ 63 - 0
server/data/src/main/java/com/qxgmat/data/dao/entity/CoursePackage.java

@@ -0,0 +1,63 @@
+package com.qxgmat.data.dao.entity;
+
+import java.io.Serializable;
+import javax.persistence.*;
+
+@Table(name = "course_package")
+public class CoursePackage implements Serializable {
+    @Id
+    @Column(name = "`id`")
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    private Integer id;
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * @return id
+     */
+    public Integer getId() {
+        return id;
+    }
+
+    /**
+     * @param id
+     */
+    public void setId(Integer id) {
+        this.id = id;
+    }
+
+    @Override
+    public String toString() {
+        StringBuilder sb = new StringBuilder();
+        sb.append(getClass().getSimpleName());
+        sb.append(" [");
+        sb.append("Hash = ").append(hashCode());
+        sb.append(", id=").append(id);
+        sb.append("]");
+        return sb.toString();
+    }
+
+    public static CoursePackage.Builder builder() {
+        return new CoursePackage.Builder();
+    }
+
+    public static class Builder {
+        private CoursePackage obj;
+
+        public Builder() {
+            this.obj = new CoursePackage();
+        }
+
+        /**
+         * @param id
+         */
+        public Builder id(Integer id) {
+            obj.setId(id);
+            return this;
+        }
+
+        public CoursePackage build() {
+            return this.obj;
+        }
+    }
+}

+ 335 - 0
server/data/src/main/java/com/qxgmat/data/dao/entity/Faq.java

@@ -0,0 +1,335 @@
+package com.qxgmat.data.dao.entity;
+
+import java.io.Serializable;
+import java.util.Date;
+import javax.persistence.*;
+
+@Table(name = "faq")
+public class Faq implements Serializable {
+    @Id
+    @Column(name = "`id`")
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    private Integer id;
+
+    /**
+     * 用户id
+     */
+    @Column(name = "`user_id`")
+    private Integer userId;
+
+    /**
+     * 提问者邮箱
+     */
+    @Column(name = "`email`")
+    private String email;
+
+    /**
+     * 频道
+     */
+    @Column(name = "`channel`")
+    private String channel;
+
+    /**
+     * 位置
+     */
+    @Column(name = "`position`")
+    private String position;
+
+    /**
+     * 是否精选:0不是精选,1是精选
+     */
+    @Column(name = "`is_special`")
+    private Integer isSpecial;
+
+    /**
+     * 问答状态:0未回答,1回答,忽略
+     */
+    @Column(name = "`status`")
+    private Integer status;
+
+    @Column(name = "`create_time`")
+    private Date createTime;
+
+    /**
+     * 提问内容
+     */
+    @Column(name = "`content`")
+    private String content;
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * @return id
+     */
+    public Integer getId() {
+        return id;
+    }
+
+    /**
+     * @param id
+     */
+    public void setId(Integer id) {
+        this.id = id;
+    }
+
+    /**
+     * 获取用户id
+     *
+     * @return user_id - 用户id
+     */
+    public Integer getUserId() {
+        return userId;
+    }
+
+    /**
+     * 设置用户id
+     *
+     * @param userId 用户id
+     */
+    public void setUserId(Integer userId) {
+        this.userId = userId;
+    }
+
+    /**
+     * 获取提问者邮箱
+     *
+     * @return email - 提问者邮箱
+     */
+    public String getEmail() {
+        return email;
+    }
+
+    /**
+     * 设置提问者邮箱
+     *
+     * @param email 提问者邮箱
+     */
+    public void setEmail(String email) {
+        this.email = email;
+    }
+
+    /**
+     * 获取频道
+     *
+     * @return channel - 频道
+     */
+    public String getChannel() {
+        return channel;
+    }
+
+    /**
+     * 设置频道
+     *
+     * @param channel 频道
+     */
+    public void setChannel(String channel) {
+        this.channel = channel;
+    }
+
+    /**
+     * 获取位置
+     *
+     * @return position - 位置
+     */
+    public String getPosition() {
+        return position;
+    }
+
+    /**
+     * 设置位置
+     *
+     * @param position 位置
+     */
+    public void setPosition(String position) {
+        this.position = position;
+    }
+
+    /**
+     * 获取是否精选:0不是精选,1是精选
+     *
+     * @return is_special - 是否精选:0不是精选,1是精选
+     */
+    public Integer getIsSpecial() {
+        return isSpecial;
+    }
+
+    /**
+     * 设置是否精选:0不是精选,1是精选
+     *
+     * @param isSpecial 是否精选:0不是精选,1是精选
+     */
+    public void setIsSpecial(Integer isSpecial) {
+        this.isSpecial = isSpecial;
+    }
+
+    /**
+     * 获取问答状态:0未回答,1回答,忽略
+     *
+     * @return status - 问答状态:0未回答,1回答,忽略
+     */
+    public Integer getStatus() {
+        return status;
+    }
+
+    /**
+     * 设置问答状态:0未回答,1回答,忽略
+     *
+     * @param status 问答状态:0未回答,1回答,忽略
+     */
+    public void setStatus(Integer status) {
+        this.status = status;
+    }
+
+    /**
+     * @return create_time
+     */
+    public Date getCreateTime() {
+        return createTime;
+    }
+
+    /**
+     * @param createTime
+     */
+    public void setCreateTime(Date createTime) {
+        this.createTime = createTime;
+    }
+
+    /**
+     * 获取提问内容
+     *
+     * @return content - 提问内容
+     */
+    public String getContent() {
+        return content;
+    }
+
+    /**
+     * 设置提问内容
+     *
+     * @param content 提问内容
+     */
+    public void setContent(String content) {
+        this.content = content;
+    }
+
+    @Override
+    public String toString() {
+        StringBuilder sb = new StringBuilder();
+        sb.append(getClass().getSimpleName());
+        sb.append(" [");
+        sb.append("Hash = ").append(hashCode());
+        sb.append(", id=").append(id);
+        sb.append(", userId=").append(userId);
+        sb.append(", email=").append(email);
+        sb.append(", channel=").append(channel);
+        sb.append(", position=").append(position);
+        sb.append(", isSpecial=").append(isSpecial);
+        sb.append(", status=").append(status);
+        sb.append(", createTime=").append(createTime);
+        sb.append(", content=").append(content);
+        sb.append("]");
+        return sb.toString();
+    }
+
+    public static Faq.Builder builder() {
+        return new Faq.Builder();
+    }
+
+    public static class Builder {
+        private Faq obj;
+
+        public Builder() {
+            this.obj = new Faq();
+        }
+
+        /**
+         * @param id
+         */
+        public Builder id(Integer id) {
+            obj.setId(id);
+            return this;
+        }
+
+        /**
+         * 设置用户id
+         *
+         * @param userId 用户id
+         */
+        public Builder userId(Integer userId) {
+            obj.setUserId(userId);
+            return this;
+        }
+
+        /**
+         * 设置提问者邮箱
+         *
+         * @param email 提问者邮箱
+         */
+        public Builder email(String email) {
+            obj.setEmail(email);
+            return this;
+        }
+
+        /**
+         * 设置频道
+         *
+         * @param channel 频道
+         */
+        public Builder channel(String channel) {
+            obj.setChannel(channel);
+            return this;
+        }
+
+        /**
+         * 设置位置
+         *
+         * @param position 位置
+         */
+        public Builder position(String position) {
+            obj.setPosition(position);
+            return this;
+        }
+
+        /**
+         * 设置是否精选:0不是精选,1是精选
+         *
+         * @param isSpecial 是否精选:0不是精选,1是精选
+         */
+        public Builder isSpecial(Integer isSpecial) {
+            obj.setIsSpecial(isSpecial);
+            return this;
+        }
+
+        /**
+         * 设置问答状态:0未回答,1回答,忽略
+         *
+         * @param status 问答状态:0未回答,1回答,忽略
+         */
+        public Builder status(Integer status) {
+            obj.setStatus(status);
+            return this;
+        }
+
+        /**
+         * @param createTime
+         */
+        public Builder createTime(Date createTime) {
+            obj.setCreateTime(createTime);
+            return this;
+        }
+
+        /**
+         * 设置提问内容
+         *
+         * @param content 提问内容
+         */
+        public Builder content(String content) {
+            obj.setContent(content);
+            return this;
+        }
+
+        public Faq build() {
+            return this.obj;
+        }
+    }
+}

+ 63 - 0
server/data/src/main/java/com/qxgmat/data/dao/entity/Message.java

@@ -0,0 +1,63 @@
+package com.qxgmat.data.dao.entity;
+
+import java.io.Serializable;
+import javax.persistence.*;
+
+@Table(name = "message")
+public class Message implements Serializable {
+    @Id
+    @Column(name = "`id`")
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    private Integer id;
+
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * @return id
+     */
+    public Integer getId() {
+        return id;
+    }
+
+    /**
+     * @param id
+     */
+    public void setId(Integer id) {
+        this.id = id;
+    }
+
+    @Override
+    public String toString() {
+        StringBuilder sb = new StringBuilder();
+        sb.append(getClass().getSimpleName());
+        sb.append(" [");
+        sb.append("Hash = ").append(hashCode());
+        sb.append(", id=").append(id);
+        sb.append("]");
+        return sb.toString();
+    }
+
+    public static Message.Builder builder() {
+        return new Message.Builder();
+    }
+
+    public static class Builder {
+        private Message obj;
+
+        public Builder() {
+            this.obj = new Message();
+        }
+
+        /**
+         * @param id
+         */
+        public Builder id(Integer id) {
+            obj.setId(id);
+            return this;
+        }
+
+        public Message build() {
+            return this.obj;
+        }
+    }
+}

+ 0 - 204
server/data/src/main/java/com/qxgmat/data/dao/entity/UserClass.java

@@ -1,204 +0,0 @@
-package com.qxgmat.data.dao.entity;
-
-import java.io.Serializable;
-import java.util.Date;
-import javax.persistence.*;
-
-@Table(name = "user_class")
-public class UserClass implements Serializable {
-    @Id
-    @Column(name = "`id`")
-    @GeneratedValue(strategy = GenerationType.IDENTITY)
-    private Integer id;
-
-    /**
-     * 用户id
-     */
-    @Column(name = "`user_id`")
-    private Integer userId;
-
-    /**
-     * 课程id
-     */
-    @Column(name = "`course_id`")
-    private Integer courseId;
-
-    /**
-     * 开通时间
-     */
-    @Column(name = "`start_time`")
-    private Date startTime;
-
-    /**
-     * 到期时间
-     */
-    @Column(name = "`expire_time`")
-    private Date expireTime;
-
-    private static final long serialVersionUID = 1L;
-
-    /**
-     * @return id
-     */
-    public Integer getId() {
-        return id;
-    }
-
-    /**
-     * @param id
-     */
-    public void setId(Integer id) {
-        this.id = id;
-    }
-
-    /**
-     * 获取用户id
-     *
-     * @return user_id - 用户id
-     */
-    public Integer getUserId() {
-        return userId;
-    }
-
-    /**
-     * 设置用户id
-     *
-     * @param userId 用户id
-     */
-    public void setUserId(Integer userId) {
-        this.userId = userId;
-    }
-
-    /**
-     * 获取课程id
-     *
-     * @return course_id - 课程id
-     */
-    public Integer getCourseId() {
-        return courseId;
-    }
-
-    /**
-     * 设置课程id
-     *
-     * @param courseId 课程id
-     */
-    public void setCourseId(Integer courseId) {
-        this.courseId = courseId;
-    }
-
-    /**
-     * 获取开通时间
-     *
-     * @return start_time - 开通时间
-     */
-    public Date getStartTime() {
-        return startTime;
-    }
-
-    /**
-     * 设置开通时间
-     *
-     * @param startTime 开通时间
-     */
-    public void setStartTime(Date startTime) {
-        this.startTime = startTime;
-    }
-
-    /**
-     * 获取到期时间
-     *
-     * @return expire_time - 到期时间
-     */
-    public Date getExpireTime() {
-        return expireTime;
-    }
-
-    /**
-     * 设置到期时间
-     *
-     * @param expireTime 到期时间
-     */
-    public void setExpireTime(Date expireTime) {
-        this.expireTime = expireTime;
-    }
-
-    @Override
-    public String toString() {
-        StringBuilder sb = new StringBuilder();
-        sb.append(getClass().getSimpleName());
-        sb.append(" [");
-        sb.append("Hash = ").append(hashCode());
-        sb.append(", id=").append(id);
-        sb.append(", userId=").append(userId);
-        sb.append(", courseId=").append(courseId);
-        sb.append(", startTime=").append(startTime);
-        sb.append(", expireTime=").append(expireTime);
-        sb.append("]");
-        return sb.toString();
-    }
-
-    public static UserClass.Builder builder() {
-        return new UserClass.Builder();
-    }
-
-    public static class Builder {
-        private UserClass obj;
-
-        public Builder() {
-            this.obj = new UserClass();
-        }
-
-        /**
-         * @param id
-         */
-        public Builder id(Integer id) {
-            obj.setId(id);
-            return this;
-        }
-
-        /**
-         * 设置用户id
-         *
-         * @param userId 用户id
-         */
-        public Builder userId(Integer userId) {
-            obj.setUserId(userId);
-            return this;
-        }
-
-        /**
-         * 设置课程id
-         *
-         * @param courseId 课程id
-         */
-        public Builder courseId(Integer courseId) {
-            obj.setCourseId(courseId);
-            return this;
-        }
-
-        /**
-         * 设置开通时间
-         *
-         * @param startTime 开通时间
-         */
-        public Builder startTime(Date startTime) {
-            obj.setStartTime(startTime);
-            return this;
-        }
-
-        /**
-         * 设置到期时间
-         *
-         * @param expireTime 到期时间
-         */
-        public Builder expireTime(Date expireTime) {
-            obj.setExpireTime(expireTime);
-            return this;
-        }
-
-        public UserClass build() {
-            return this.obj;
-        }
-    }
-}

+ 0 - 186
server/data/src/main/java/com/qxgmat/data/dao/entity/UserCourseComment.java

@@ -1,186 +0,0 @@
-package com.qxgmat.data.dao.entity;
-
-import java.io.Serializable;
-import java.util.Date;
-import javax.persistence.*;
-
-@Table(name = "user_course_comment")
-public class UserCourseComment implements Serializable {
-    @Id
-    @Column(name = "`id`")
-    @GeneratedValue(strategy = GenerationType.IDENTITY)
-    private Integer id;
-
-    /**
-     * 用户id
-     */
-    @Column(name = "`user_id`")
-    private Integer userId;
-
-    /**
-     * 课程id
-     */
-    @Column(name = "`course_id`")
-    private Integer courseId;
-
-    @Column(name = "`create_time`")
-    private Date createTime;
-
-    @Column(name = "`content`")
-    private String content;
-
-    private static final long serialVersionUID = 1L;
-
-    /**
-     * @return id
-     */
-    public Integer getId() {
-        return id;
-    }
-
-    /**
-     * @param id
-     */
-    public void setId(Integer id) {
-        this.id = id;
-    }
-
-    /**
-     * 获取用户id
-     *
-     * @return user_id - 用户id
-     */
-    public Integer getUserId() {
-        return userId;
-    }
-
-    /**
-     * 设置用户id
-     *
-     * @param userId 用户id
-     */
-    public void setUserId(Integer userId) {
-        this.userId = userId;
-    }
-
-    /**
-     * 获取课程id
-     *
-     * @return course_id - 课程id
-     */
-    public Integer getCourseId() {
-        return courseId;
-    }
-
-    /**
-     * 设置课程id
-     *
-     * @param courseId 课程id
-     */
-    public void setCourseId(Integer courseId) {
-        this.courseId = courseId;
-    }
-
-    /**
-     * @return create_time
-     */
-    public Date getCreateTime() {
-        return createTime;
-    }
-
-    /**
-     * @param createTime
-     */
-    public void setCreateTime(Date createTime) {
-        this.createTime = createTime;
-    }
-
-    /**
-     * @return content
-     */
-    public String getContent() {
-        return content;
-    }
-
-    /**
-     * @param content
-     */
-    public void setContent(String content) {
-        this.content = content;
-    }
-
-    @Override
-    public String toString() {
-        StringBuilder sb = new StringBuilder();
-        sb.append(getClass().getSimpleName());
-        sb.append(" [");
-        sb.append("Hash = ").append(hashCode());
-        sb.append(", id=").append(id);
-        sb.append(", userId=").append(userId);
-        sb.append(", courseId=").append(courseId);
-        sb.append(", createTime=").append(createTime);
-        sb.append(", content=").append(content);
-        sb.append("]");
-        return sb.toString();
-    }
-
-    public static UserCourseComment.Builder builder() {
-        return new UserCourseComment.Builder();
-    }
-
-    public static class Builder {
-        private UserCourseComment obj;
-
-        public Builder() {
-            this.obj = new UserCourseComment();
-        }
-
-        /**
-         * @param id
-         */
-        public Builder id(Integer id) {
-            obj.setId(id);
-            return this;
-        }
-
-        /**
-         * 设置用户id
-         *
-         * @param userId 用户id
-         */
-        public Builder userId(Integer userId) {
-            obj.setUserId(userId);
-            return this;
-        }
-
-        /**
-         * 设置课程id
-         *
-         * @param courseId 课程id
-         */
-        public Builder courseId(Integer courseId) {
-            obj.setCourseId(courseId);
-            return this;
-        }
-
-        /**
-         * @param createTime
-         */
-        public Builder createTime(Date createTime) {
-            obj.setCreateTime(createTime);
-            return this;
-        }
-
-        /**
-         * @param content
-         */
-        public Builder content(String content) {
-            obj.setContent(content);
-            return this;
-        }
-
-        public UserCourseComment build() {
-            return this.obj;
-        }
-    }
-}

+ 0 - 21
server/data/src/main/java/com/qxgmat/data/dao/mapping/ClassCourseMapper.xml

@@ -1,21 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
-<mapper namespace="com.qxgmat.data.dao.ClassCourseMapper">
-  <resultMap id="BaseResultMap" type="com.qxgmat.data.dao.entity.ClassCourse">
-    <!--
-      WARNING - @mbg.generated
-    -->
-    <id column="id" jdbcType="INTEGER" property="id" />
-    <result column="struct_id" jdbcType="INTEGER" property="structId" />
-    <result column="parent_struct_id" jdbcType="INTEGER" property="parentStructId" />
-    <result column="question_type" jdbcType="VARCHAR" property="questionType" />
-    <result column="title" jdbcType="VARCHAR" property="title" />
-    <result column="create_time" jdbcType="TIMESTAMP" property="createTime" />
-  </resultMap>
-  <sql id="Base_Column_List">
-    <!--
-      WARNING - @mbg.generated
-    -->
-    `id`, `struct_id`, `parent_struct_id`, `question_type`, `title`, `create_time`
-  </sql>
-</mapper>

+ 0 - 19
server/data/src/main/java/com/qxgmat/data/dao/mapping/ClassFaqMapper.xml

@@ -1,19 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
-<mapper namespace="com.qxgmat.data.dao.ClassFaqMapper">
-  <resultMap id="BaseResultMap" type="com.qxgmat.data.dao.entity.ClassFaq">
-    <!--
-      WARNING - @mbg.generated
-    -->
-    <id column="id" jdbcType="INTEGER" property="id" />
-    <result column="course_id" jdbcType="INTEGER" property="courseId" />
-    <result column="is_special" jdbcType="INTEGER" property="isSpecial" />
-    <result column="status" jdbcType="INTEGER" property="status" />
-  </resultMap>
-  <sql id="Base_Column_List">
-    <!--
-      WARNING - @mbg.generated
-    -->
-    `id`, `course_id`, `is_special`, `status`
-  </sql>
-</mapper>

+ 10 - 8
server/data/src/main/java/com/qxgmat/data/dao/mapping/ClassCourseNoMapper.xml

@@ -1,18 +1,20 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
-<mapper namespace="com.qxgmat.data.dao.ClassCourseNoMapper">
-  <resultMap id="BaseResultMap" type="com.qxgmat.data.dao.entity.ClassCourseNo">
+<mapper namespace="com.qxgmat.data.dao.CommentMapper">
+  <resultMap id="BaseResultMap" type="com.qxgmat.data.dao.entity.Comment">
     <!--
       WARNING - @mbg.generated
     -->
     <id column="id" jdbcType="INTEGER" property="id" />
-    <result column="course_id" jdbcType="INTEGER" property="courseId" />
-    <result column="no" jdbcType="INTEGER" property="no" />
-    <result column="resource" jdbcType="VARCHAR" property="resource" />
-    <result column="time" jdbcType="INTEGER" property="time" />
+    <result column="user_id" jdbcType="INTEGER" property="userId" />
+    <result column="nickname" jdbcType="VARCHAR" property="nickname" />
+    <result column="avatar" jdbcType="VARCHAR" property="avatar" />
+    <result column="channel" jdbcType="VARCHAR" property="channel" />
+    <result column="position" jdbcType="VARCHAR" property="position" />
+    <result column="is_special" jdbcType="INTEGER" property="isSpecial" />
     <result column="create_time" jdbcType="TIMESTAMP" property="createTime" />
   </resultMap>
-  <resultMap extends="BaseResultMap" id="ResultMapWithBLOBs" type="com.qxgmat.data.dao.entity.ClassCourseNo">
+  <resultMap extends="BaseResultMap" id="ResultMapWithBLOBs" type="com.qxgmat.data.dao.entity.Comment">
     <!--
       WARNING - @mbg.generated
     -->
@@ -22,7 +24,7 @@
     <!--
       WARNING - @mbg.generated
     -->
-    `id`, `course_id`, `no`, `resource`, `time`, `create_time`
+    `id`, `user_id`, `nickname`, `avatar`, `channel`, `position`, `is_special`, `create_time`
   </sql>
   <sql id="Blob_Column_List">
     <!--

+ 10 - 0
server/data/src/main/java/com/qxgmat/data/dao/mapping/CourseArticleMapper.xml

@@ -0,0 +1,10 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="com.qxgmat.data.dao.CourseArticleMapper">
+  <resultMap id="BaseResultMap" type="com.qxgmat.data.dao.entity.CourseArticle">
+    <!--
+      WARNING - @mbg.generated
+    -->
+    <id column="id" jdbcType="INTEGER" property="id" />
+  </resultMap>
+</mapper>

+ 10 - 0
server/data/src/main/java/com/qxgmat/data/dao/mapping/CourseDataMapper.xml

@@ -0,0 +1,10 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="com.qxgmat.data.dao.CourseDataMapper">
+  <resultMap id="BaseResultMap" type="com.qxgmat.data.dao.entity.CourseData">
+    <!--
+      WARNING - @mbg.generated
+    -->
+    <id column="id" jdbcType="INTEGER" property="id" />
+  </resultMap>
+</mapper>

+ 0 - 19
server/data/src/main/java/com/qxgmat/data/dao/mapping/CourseFaqMapper.xml

@@ -1,19 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
-<mapper namespace="com.qxgmat.data.dao.CourseFaqMapper">
-  <resultMap id="BaseResultMap" type="com.qxgmat.data.dao.entity.CourseFaq">
-    <!--
-      WARNING - @mbg.generated
-    -->
-    <id column="id" jdbcType="INTEGER" property="id" />
-    <result column="course_id" jdbcType="INTEGER" property="courseId" />
-    <result column="is_special" jdbcType="INTEGER" property="isSpecial" />
-    <result column="status" jdbcType="INTEGER" property="status" />
-  </resultMap>
-  <sql id="Base_Column_List">
-    <!--
-      WARNING - @mbg.generated
-    -->
-    `id`, `course_id`, `is_special`, `status`
-  </sql>
-</mapper>

+ 10 - 0
server/data/src/main/java/com/qxgmat/data/dao/mapping/CoursePackageMapper.xml

@@ -0,0 +1,10 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="com.qxgmat.data.dao.CoursePackageMapper">
+  <resultMap id="BaseResultMap" type="com.qxgmat.data.dao.entity.CoursePackage">
+    <!--
+      WARNING - @mbg.generated
+    -->
+    <id column="id" jdbcType="INTEGER" property="id" />
+  </resultMap>
+</mapper>

+ 9 - 5
server/data/src/main/java/com/qxgmat/data/dao/mapping/UserCourseCommentMapper.xml

@@ -1,16 +1,20 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
-<mapper namespace="com.qxgmat.data.dao.UserCourseCommentMapper">
-  <resultMap id="BaseResultMap" type="com.qxgmat.data.dao.entity.UserCourseComment">
+<mapper namespace="com.qxgmat.data.dao.FaqMapper">
+  <resultMap id="BaseResultMap" type="com.qxgmat.data.dao.entity.Faq">
     <!--
       WARNING - @mbg.generated
     -->
     <id column="id" jdbcType="INTEGER" property="id" />
     <result column="user_id" jdbcType="INTEGER" property="userId" />
-    <result column="course_id" jdbcType="INTEGER" property="courseId" />
+    <result column="email" jdbcType="VARCHAR" property="email" />
+    <result column="channel" jdbcType="VARCHAR" property="channel" />
+    <result column="position" jdbcType="VARCHAR" property="position" />
+    <result column="is_special" jdbcType="INTEGER" property="isSpecial" />
+    <result column="status" jdbcType="INTEGER" property="status" />
     <result column="create_time" jdbcType="TIMESTAMP" property="createTime" />
   </resultMap>
-  <resultMap extends="BaseResultMap" id="ResultMapWithBLOBs" type="com.qxgmat.data.dao.entity.UserCourseComment">
+  <resultMap extends="BaseResultMap" id="ResultMapWithBLOBs" type="com.qxgmat.data.dao.entity.Faq">
     <!--
       WARNING - @mbg.generated
     -->
@@ -20,7 +24,7 @@
     <!--
       WARNING - @mbg.generated
     -->
-    `id`, `user_id`, `course_id`, `create_time`
+    `id`, `user_id`, `email`, `channel`, `position`, `is_special`, `status`, `create_time`
   </sql>
   <sql id="Blob_Column_List">
     <!--

+ 10 - 0
server/data/src/main/java/com/qxgmat/data/dao/mapping/MessageMapper.xml

@@ -0,0 +1,10 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
+<mapper namespace="com.qxgmat.data.dao.MessageMapper">
+  <resultMap id="BaseResultMap" type="com.qxgmat.data.dao.entity.Message">
+    <!--
+      WARNING - @mbg.generated
+    -->
+    <id column="id" jdbcType="INTEGER" property="id" />
+  </resultMap>
+</mapper>

+ 0 - 20
server/data/src/main/java/com/qxgmat/data/dao/mapping/UserClassMapper.xml

@@ -1,20 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
-<mapper namespace="com.qxgmat.data.dao.UserClassMapper">
-  <resultMap id="BaseResultMap" type="com.qxgmat.data.dao.entity.UserClass">
-    <!--
-      WARNING - @mbg.generated
-    -->
-    <id column="id" jdbcType="INTEGER" property="id" />
-    <result column="user_id" jdbcType="INTEGER" property="userId" />
-    <result column="course_id" jdbcType="INTEGER" property="courseId" />
-    <result column="start_time" jdbcType="TIMESTAMP" property="startTime" />
-    <result column="expire_time" jdbcType="TIMESTAMP" property="expireTime" />
-  </resultMap>
-  <sql id="Base_Column_List">
-    <!--
-      WARNING - @mbg.generated
-    -->
-    `id`, `user_id`, `course_id`, `start_time`, `expire_time`
-  </sql>
-</mapper>

+ 7 - 7
server/gateway-api/src/main/java/com/qxgmat/controller/admin/ClassController.java

@@ -16,7 +16,7 @@ import com.qxgmat.dto.admin.response.*;
 import com.qxgmat.help.ShiroHelp;
 import com.qxgmat.service.ManagerService;
 import com.qxgmat.service.UsersService;
-import com.qxgmat.service.inline.ClassCourseService;
+import com.qxgmat.service.inline.CourseService;
 import com.qxgmat.service.inline.ManagerLogService;
 import com.qxgmat.service.inline.UserAskCourseService;
 import io.swagger.annotations.ApiOperation;
@@ -31,13 +31,13 @@ import java.util.Date;
 import java.util.List;
 
 @RestController("AdminClassController")
-@RequestMapping("/admin/class")
-public class ClassController {
+@RequestMapping("/admin/course")
+public class CourseController {
     @Autowired
     private ShiroHelp shiroHelp;
 
     @Autowired
-    private ClassCourseService classCourseService;
+    private CourseService courseService;
 
     @Autowired
     private UserAskCourseService userAskCourseService;
@@ -53,12 +53,12 @@ public class ClassController {
 
     @RequestMapping(value = "/course/list", method = RequestMethod.GET)
     @ApiOperation(value = "课程列表", httpMethod = "GET")
-    public Response<PageMessage<ClassCourseListDto>> list(
+    public Response<PageMessage<CourseListDto>> list(
             @RequestParam(required = false, defaultValue = "1") int page,
             @RequestParam(required = false, defaultValue = "100") int size,
             HttpSession session) {
-        Page<ClassCourse> p = classCourseService.select(page, size);
-        List<ClassCourseListDto> pr = Transform.convert(p, ClassCourseListDto.class);
+        Page<Course> p = courseService.select(page, size);
+        List<CourseListDto> pr = Transform.convert(p, CourseListDto.class);
 
         return ResponseHelp.success(pr, page, size, p.getTotal());
     }

+ 157 - 9
server/gateway-api/src/main/java/com/qxgmat/controller/admin/SettingController.java

@@ -1,15 +1,15 @@
 package com.qxgmat.controller.admin;
 
 import com.alibaba.fastjson.JSONObject;
-import com.nuliji.tools.Response;
-import com.nuliji.tools.ResponseHelp;
-import com.nuliji.tools.Transform;
+import com.github.pagehelper.Page;
+import com.nuliji.tools.*;
 import com.qxgmat.data.constants.enums.SettingKey;
-import com.qxgmat.data.dao.entity.Rank;
-import com.qxgmat.data.dao.entity.Setting;
+import com.qxgmat.data.constants.enums.module.ChannelModule;
+import com.qxgmat.data.dao.entity.*;
+import com.qxgmat.dto.admin.request.CommentDto;
+import com.qxgmat.dto.admin.request.FaqDto;
 import com.qxgmat.dto.admin.request.RankDto;
-import com.qxgmat.service.inline.RankService;
-import com.qxgmat.service.inline.SettingService;
+import com.qxgmat.service.inline.*;
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiOperation;
 import org.apache.poi.hssf.usermodel.HSSFCell;
@@ -26,7 +26,6 @@ import org.springframework.web.bind.annotation.*;
 import org.springframework.web.multipart.MultipartFile;
 
 import java.io.FileInputStream;
-import java.io.FileNotFoundException;
 import java.io.IOException;
 import java.io.InputStream;
 import java.util.ArrayList;
@@ -45,6 +44,15 @@ public class SettingController {
     @Autowired
     private RankService rankService;
 
+    @Autowired
+    private CommentService commentService;
+
+    @Autowired
+    private FaqService faqService;
+
+    @Autowired
+    private MessageService messageService;
+
     @RequestMapping(value = "/index", method = RequestMethod.PUT)
     @ApiOperation(value = "修改首页配置", httpMethod = "PUT")
     private Response<Boolean> editIndex(@RequestBody @Validated JSONObject dto){
@@ -79,6 +87,22 @@ public class SettingController {
         return ResponseHelp.success(entity.getValue());
     }
 
+    @RequestMapping(value = "/message_template", method = RequestMethod.PUT)
+    @ApiOperation(value = "修改消息模版", httpMethod = "PUT")
+    private Response<Boolean> editMessageTemplate(@RequestBody @Validated JSONObject dto){
+        Setting entity = settingService.getByKey(SettingKey.MESSAGE_TEMPLATE);
+        entity.setValue(dto);
+        settingService.edit(entity);
+        return ResponseHelp.success(true);
+    }
+
+    @RequestMapping(value = "/message_template", method = RequestMethod.GET)
+    @ApiOperation(value = "获取消息模版", httpMethod = "GET")
+    private Response<JSONObject> getMessageTemplate(){
+        Setting entity = settingService.getByKey(SettingKey.MESSAGE_TEMPLATE);
+
+        return ResponseHelp.success(entity.getValue());
+    }
 
     @RequestMapping(value = "/sentence", method = RequestMethod.PUT)
     @ApiOperation(value = "修改长难句设置", httpMethod = "PUT")
@@ -97,7 +121,6 @@ public class SettingController {
         return ResponseHelp.success(entity.getValue());
     }
 
-
     @RequestMapping(value = "/exercise_time", method = RequestMethod.PUT)
     @ApiOperation(value = "修改做题时间设置", httpMethod = "PUT")
     private Response<Boolean> editExerciseTime(@RequestBody @Validated JSONObject dto){
@@ -114,6 +137,7 @@ public class SettingController {
 
         return ResponseHelp.success(entity.getValue());
     }
+
     @RequestMapping(value = "/examination_time", method = RequestMethod.PUT)
     @ApiOperation(value = "修改做题时间设置", httpMethod = "PUT")
     private Response<Boolean> editExaminationTime(@RequestBody @Validated JSONObject dto){
@@ -250,6 +274,23 @@ public class SettingController {
         return ResponseHelp.success(entity.getValue());
     }
 
+    @RequestMapping(value = "/course_index", method = RequestMethod.PUT)
+    @ApiOperation(value = "修改课程首页", httpMethod = "PUT")
+    private Response<Boolean> editCourseIndex(@RequestBody @Validated JSONObject dto){
+        Setting entity = settingService.getByKey(SettingKey.COURSE_INDEX);
+        entity.setValue(dto);
+        settingService.edit(entity);
+        return ResponseHelp.success(true);
+    }
+
+    @RequestMapping(value = "/course_index", method = RequestMethod.GET)
+    @ApiOperation(value = "获取课程首页", httpMethod = "GET")
+    private Response<JSONObject> getCourseIndex(){
+        Setting entity = settingService.getByKey(SettingKey.COURSE_INDEX);
+
+        return ResponseHelp.success(entity.getValue());
+    }
+
     @RequestMapping(value = "/tips", method = RequestMethod.PUT)
     @ApiOperation(value = "修改结构说明", httpMethod = "PUT")
     private Response<Boolean> editTips(@RequestBody @Validated JSONObject dto){
@@ -267,6 +308,113 @@ public class SettingController {
         return ResponseHelp.success(entity.getValue());
     }
 
+    @RequestMapping(value = "/comment/add", method = RequestMethod.POST)
+    @ApiOperation(value = "添加评价", httpMethod = "POST")
+    private Response<Boolean> addComment(@RequestBody @Validated CommentDto dto){
+        Comment entity = Transform.dtoToEntity(dto);
+        commentService.add(entity);
+        return ResponseHelp.success(true);
+    }
+
+    @RequestMapping(value = "/comment/edit", method = RequestMethod.PUT)
+    @ApiOperation(value = "修改评价", httpMethod = "PUT")
+    private Response<Boolean> editComment(@RequestBody @Validated CommentDto dto){
+        Comment entity = Transform.dtoToEntity(dto);
+        commentService.edit(entity);
+        return ResponseHelp.success(true);
+    }
+
+    @RequestMapping(value = "/comment/delete", method = RequestMethod.DELETE)
+    @ApiOperation(value = "删除评价", httpMethod = "DELETE")
+    private Response<Boolean> deleteComment(@RequestParam int id){
+        commentService.delete(id);
+        return ResponseHelp.success(true);
+    }
+
+    @RequestMapping(value = "/comment/list", method = RequestMethod.GET)
+    @ApiOperation(value = "获取评价列表", httpMethod = "GET")
+    private Response<PageMessage<Comment>> listComment(
+            @RequestParam(required = false, defaultValue = "1") int page,
+            @RequestParam(required = false, defaultValue = "100") int size,
+            @RequestParam(required = false) String channel,
+            @RequestParam(required = false) String position,
+            @RequestParam(required = false) Integer userId,
+            @RequestParam(required = false) Boolean isSpecial
+    ){
+        Page<Comment> p = commentService.listAdmin(page, size, ChannelModule.ValueOf(channel), position, userId, isSpecial);
+        return ResponseHelp.success(p, page, size, p.getTotal());
+    }
+
+    @RequestMapping(value = "/faq/add", method = RequestMethod.POST)
+    @ApiOperation(value = "添加faq", httpMethod = "POST")
+    private Response<Boolean> addFaq(@RequestBody @Validated FaqDto dto){
+        Faq entity = Transform.dtoToEntity(dto);
+        faqService.add(entity);
+        return ResponseHelp.success(true);
+    }
+
+    @RequestMapping(value = "/faq/edit", method = RequestMethod.PUT)
+    @ApiOperation(value = "修改faq", httpMethod = "PUT")
+    private Response<Boolean> editFaq(@RequestBody @Validated FaqDto dto){
+        Faq entity = Transform.dtoToEntity(dto);
+        faqService.edit(entity);
+        return ResponseHelp.success(true);
+    }
+
+    @RequestMapping(value = "/faq/delete", method = RequestMethod.DELETE)
+    @ApiOperation(value = "删除评价", httpMethod = "DELETE")
+    private Response<Boolean> deleteFaq(@RequestParam int id){
+        faqService.delete(id);
+        return ResponseHelp.success(true);
+    }
+
+    @RequestMapping(value = "/faq/list", method = RequestMethod.GET)
+    @ApiOperation(value = "获取faq列表", httpMethod = "GET")
+    private Response<PageMessage<Faq>> listFaq(
+            @RequestParam(required = false, defaultValue = "1") int page,
+            @RequestParam(required = false, defaultValue = "100") int size,
+            @RequestParam(required = false) String channel,
+            @RequestParam(required = false) String position,
+            @RequestParam(required = false) Integer status,
+            @RequestParam(required = false) Boolean isSpecial
+    ){
+        Page<Faq> p = faqService.listAdmin(page, size, ChannelModule.ValueOf(channel), position, status, isSpecial);
+        return ResponseHelp.success(p, page, size, p.getTotal());
+    }
+
+    @RequestMapping(value = "/message/add", method = RequestMethod.POST)
+    @ApiOperation(value = "添加消息", httpMethod = "POST")
+    private Response<Boolean> addMessage(@RequestBody @Validated FaqDto dto){
+        Faq entity = Transform.dtoToEntity(dto);
+        faqService.add(entity);
+        return ResponseHelp.success(true);
+    }
+
+    @RequestMapping(value = "/message/edit", method = RequestMethod.PUT)
+    @ApiOperation(value = "修改消息", httpMethod = "PUT")
+    private Response<Boolean> editMessage(@RequestBody @Validated FaqDto dto){
+        Faq entity = Transform.dtoToEntity(dto);
+        faqService.edit(entity);
+        return ResponseHelp.success(true);
+    }
+
+    @RequestMapping(value = "/message/delete", method = RequestMethod.DELETE)
+    @ApiOperation(value = "删除消息", httpMethod = "DELETE")
+    private Response<Boolean> deleteMessage(@RequestParam int id){
+        faqService.delete(id);
+        return ResponseHelp.success(true);
+    }
+
+    @RequestMapping(value = "/message/list", method = RequestMethod.GET)
+    @ApiOperation(value = "获取消息列表", httpMethod = "GET")
+    private Response<PageMessage<Message>> listMessage(
+            @RequestParam(required = false, defaultValue = "1") int page,
+            @RequestParam(required = false, defaultValue = "100") int size
+    ){
+        Page<Message> p = messageService.select(page, size);
+        return ResponseHelp.success(p, page, size, p.getTotal());
+    }
+
     @RequestMapping(value = "/rank/add", method = RequestMethod.POST)
     @ApiOperation(value = "添加排行", httpMethod = "POST")
     private Response<Boolean> addRank(@RequestBody @Validated RankDto dto){

+ 66 - 9
server/gateway-api/src/main/java/com/qxgmat/controller/admin/UserController.java

@@ -2,12 +2,14 @@ package com.qxgmat.controller.admin;
 
 import com.github.pagehelper.Page;
 import com.nuliji.tools.*;
+import com.qxgmat.data.constants.enums.module.FeedbackModule;
 import com.qxgmat.data.constants.enums.status.DirectionStatus;
+import com.qxgmat.data.constants.enums.status.FeedbackStatus;
 import com.qxgmat.data.dao.entity.*;
 import com.qxgmat.data.relation.entity.UserPreviewPaperRelation;
 import com.qxgmat.dto.admin.extend.*;
-import com.qxgmat.dto.admin.response.UserListDto;
-import com.qxgmat.dto.admin.response.UserPreviewListDto;
+import com.qxgmat.dto.admin.request.UserFeedbackErrorDto;
+import com.qxgmat.dto.admin.response.*;
 import com.qxgmat.help.ShiroHelp;
 import com.qxgmat.service.ManagerService;
 import com.qxgmat.service.extend.PreviewService;
@@ -17,10 +19,13 @@ import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiOperation;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.http.MediaType;
+import org.springframework.validation.annotation.Validated;
 import org.springframework.web.bind.annotation.*;
 
+import javax.servlet.http.HttpServletRequest;
 import javax.servlet.http.HttpSession;
 import java.util.Collection;
+import java.util.Date;
 import java.util.List;
 import java.util.Map;
 
@@ -47,7 +52,7 @@ public class UserController {
     private UserServiceService userServiceService;
 
     @Autowired
-    private UserClassService userClassService;
+    private UserCourseService userCourseService;
 
     @Autowired
     private UserPayService userPayService;
@@ -61,6 +66,9 @@ public class UserController {
     @Autowired
     private PreviewPaperService previewPaperService;
 
+    @Autowired
+    private UserFeedbackErrorService userFeedbackErrorService;
+
 //    @RequestMapping(value = "/add", method = RequestMethod.POST)
 //    @ApiOperation(value = "添加用户信息", httpMethod = "POST")
 //    public Response<User> add(@RequestBody @Validated UserDto dto, HttpServletRequest request) {
@@ -125,8 +133,8 @@ public class UserController {
         Transform.combine(pr, serviceByUser, UserListDto.class, "id", "services", UserServiceExtendDto.class);
 
         // 绑定用户课程
-        Map<Object, Collection<UserClass>> classByUser = userClassService.mapByUser(userIds, true);
-        Transform.combine(pr, classByUser, UserListDto.class, "id", "classes", UserClassExtendDto.class);
+        Map<Object, Collection<UserCourse>> courseByUser = userCourseService.mapByUser(userIds, true);
+        Transform.combine(pr, courseByUser, UserListDto.class, "id", "classes", UserCourseExtendDto.class);
 
         return ResponseHelp.success(pr, page, size, p.getTotal());
     }
@@ -148,8 +156,8 @@ public class UserController {
         Collection userIds = Transform.getIds(p, User.class, "id");
 
         // 绑定用户课程
-        Map<Object, Collection<UserClass>> classByUser = userClassService.mapByUser(userIds, false);
-        Transform.combine(pr, classByUser, UserListDto.class, "id", "classes", UserClassExtendDto.class);
+        Map<Object, Collection<UserCourse>> courseByUser = userCourseService.mapByUser(userIds, false);
+        Transform.combine(pr, courseByUser, UserListDto.class, "id", "classes", UserCourseExtendDto.class);
 
         return ResponseHelp.success(pr, page, size, p.getTotal());
     }
@@ -172,8 +180,8 @@ public class UserController {
         Transform.combine(pr, serviceByUser, UserListDto.class, "id", "services", UserServiceExtendDto.class);
 
         // 绑定用户课程
-        Map<Object, Collection<UserClass>> classByUser = userClassService.mapByUser(userIds, false);
-        Transform.combine(pr, classByUser, UserListDto.class, "id", "classes", UserClassExtendDto.class);
+        Map<Object, Collection<UserCourse>> courseByUser = userCourseService.mapByUser(userIds, false);
+        Transform.combine(pr, courseByUser, UserListDto.class, "id", "classes", UserCourseExtendDto.class);
 
         return ResponseHelp.success(pr, page, size, p.getTotal());
     }
@@ -205,4 +213,53 @@ public class UserController {
 
         return ResponseHelp.success(pr, page, size, p.getTotal());
     }
+
+    @RequestMapping(value = "/feedback_error/edit", method = RequestMethod.PUT)
+    @ApiOperation(value = "修改勘误信息", httpMethod = "PUT")
+    public Response<Boolean> editFeedbackError(@RequestBody @Validated UserFeedbackErrorDto dto, HttpServletRequest request) {
+        UserFeedbackError entity = Transform.dtoToEntity(dto);
+        UserFeedbackError in = userFeedbackErrorService.get(entity.getId());
+
+        // 处理设定
+        if(in.getHandleTime() == null){
+            entity.setHandleTime(new Date());
+            Manager manager = shiroHelp.getLoginManager();
+            entity.setManagerId(manager.getId());
+        }
+
+        entity = userFeedbackErrorService.edit(entity);
+
+        managerLogService.log(request);
+        return ResponseHelp.success(true);
+    }
+
+    @RequestMapping(value = "/feedback_error/detail", method = RequestMethod.GET)
+    @ApiOperation(value = "勘误详情", httpMethod = "GET")
+    public Response<UserFeedbackErrorDetailDto> detailFeedbackError(@RequestParam int id, HttpServletRequest request) {
+        UserFeedbackError entity = userFeedbackErrorService.get(id);
+        UserFeedbackErrorDetailDto dto = Transform.convert(entity, UserFeedbackErrorDetailDto.class);
+
+        return ResponseHelp.success(dto);
+    }
+
+    @RequestMapping(value = "/feedback_error/list", method = RequestMethod.GET)
+    @ApiOperation(value = "勘误列表", httpMethod = "GET")
+    public Response<PageMessage<UserFeedbackErrorListDto>> listFeedbackError(
+            @RequestParam(required = false, defaultValue = "1") int page,
+            @RequestParam(required = false, defaultValue = "100") int size,
+            @RequestParam(required = false) String module,
+            @RequestParam(required = false) Integer status,
+            @RequestParam(required = false) String keyword,
+            HttpSession session) {
+        Page<UserFeedbackError> p = userFeedbackErrorService.listAdmin(page, size, FeedbackModule.ValueOf(module), FeedbackStatus.ValueOf(status), keyword);
+        List<UserFeedbackErrorListDto> pr = Transform.convert(p, UserFeedbackErrorListDto.class);
+
+        // 绑定用户
+        Collection userIds = Transform.getIds(p, UserAskQuestion.class, "userId");
+        List<User> userList = usersService.select(userIds);
+        List<UserExtendDto> userExtendDtoList = Transform.convert(userList, UserExtendDto.class);
+        Transform.combine(pr, userExtendDtoList, UserAskQuestionListDto.class, "userId", "user", UserExtendDto.class, "id");
+
+        return ResponseHelp.success(pr, page, size, p.getTotal());
+    }
 }

+ 0 - 97
server/gateway-api/src/main/java/com/qxgmat/controller/admin/UserFeedbackErrorController.java

@@ -1,97 +0,0 @@
-package com.qxgmat.controller.admin;
-
-import com.github.pagehelper.Page;
-import com.nuliji.tools.PageMessage;
-import com.nuliji.tools.Response;
-import com.nuliji.tools.ResponseHelp;
-import com.nuliji.tools.Transform;
-import com.qxgmat.data.constants.enums.module.FeedbackModule;
-import com.qxgmat.data.constants.enums.status.FeedbackStatus;
-import com.qxgmat.data.dao.entity.*;
-import com.qxgmat.dto.admin.extend.UserExtendDto;
-import com.qxgmat.dto.admin.request.UserFeedbackErrorDto;
-import com.qxgmat.dto.admin.response.UserFeedbackErrorDetailDto;
-import com.qxgmat.dto.admin.response.UserFeedbackErrorListDto;
-import com.qxgmat.dto.admin.response.UserAskQuestionListDto;
-import com.qxgmat.help.ShiroHelp;
-import com.qxgmat.service.UsersService;
-import com.qxgmat.service.inline.UserFeedbackErrorService;
-import com.qxgmat.service.inline.ManagerLogService;
-import io.swagger.annotations.Api;
-import io.swagger.annotations.ApiOperation;
-import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.http.MediaType;
-import org.springframework.validation.annotation.Validated;
-import org.springframework.web.bind.annotation.*;
-
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpSession;
-import java.util.Collection;
-import java.util.Date;
-import java.util.List;
-
-@RestController("AdminFeedbackErrorController")
-@RequestMapping("/admin/user/feedback_error")
-@Api(tags = "用户勘误接口", description = "用户勘误相关", produces = MediaType.APPLICATION_JSON_VALUE)
-public class UserFeedbackErrorController {
-    @Autowired
-    private ManagerLogService managerLogService;
-    @Autowired
-    private ShiroHelp shiroHelp;
-
-    @Autowired
-    private UserFeedbackErrorService userFeedbackErrorService;
-
-    @Autowired
-    private UsersService usersService;
-
-
-    @RequestMapping(value = "/edit", method = RequestMethod.PUT)
-    @ApiOperation(value = "修改勘误信息", httpMethod = "PUT")
-    public Response<Boolean> edit(@RequestBody @Validated UserFeedbackErrorDto dto, HttpServletRequest request) {
-        UserFeedbackError entity = Transform.dtoToEntity(dto);
-        UserFeedbackError in = userFeedbackErrorService.get(entity.getId());
-
-        // 处理设定
-        if(in.getHandleTime() == null){
-            entity.setHandleTime(new Date());
-            Manager manager = shiroHelp.getLoginManager();
-            entity.setManagerId(manager.getId());
-        }
-
-        entity = userFeedbackErrorService.edit(entity);
-
-        managerLogService.log(request);
-        return ResponseHelp.success(true);
-    }
-
-    @RequestMapping(value = "/detail", method = RequestMethod.GET)
-    @ApiOperation(value = "勘误详情", httpMethod = "GET")
-    public Response<UserFeedbackErrorDetailDto> detail(@RequestParam int id, HttpServletRequest request) {
-        UserFeedbackError entity = userFeedbackErrorService.get(id);
-        UserFeedbackErrorDetailDto dto = Transform.convert(entity, UserFeedbackErrorDetailDto.class);
-
-        return ResponseHelp.success(dto);
-    }
-
-    @RequestMapping(value = "/list", method = RequestMethod.GET)
-    @ApiOperation(value = "勘误列表", httpMethod = "GET")
-    public Response<PageMessage<UserFeedbackErrorListDto>> list(
-            @RequestParam(required = false, defaultValue = "1") int page,
-            @RequestParam(required = false, defaultValue = "100") int size,
-            @RequestParam(required = false) String module,
-            @RequestParam(required = false) Integer status,
-            @RequestParam(required = false) String keyword,
-            HttpSession session) {
-        Page<UserFeedbackError> p = userFeedbackErrorService.listAdmin(page, size, FeedbackModule.ValueOf(module), FeedbackStatus.ValueOf(status), keyword);
-        List<UserFeedbackErrorListDto> pr = Transform.convert(p, UserFeedbackErrorListDto.class);
-
-        // 绑定用户
-        Collection userIds = Transform.getIds(p, UserAskQuestion.class, "userId");
-        List<User> userList = usersService.select(userIds);
-        List<UserExtendDto> userExtendDtoList = Transform.convert(userList, UserExtendDto.class);
-        Transform.combine(pr, userExtendDtoList, UserAskQuestionListDto.class, "userId", "user", UserExtendDto.class, "id");
-
-        return ResponseHelp.success(pr, page, size, p.getTotal());
-    }
-}

+ 8 - 8
server/gateway-api/src/main/java/com/qxgmat/controller/api/CourseController.java

@@ -41,7 +41,7 @@ public class CourseController {
     private QuestionService questionService;
 
     @Autowired
-    private UserClassService userClassService;
+    private UserCourseService userCourseService;
 
     @Autowired
     private UserPayService userPayService;
@@ -49,22 +49,22 @@ public class CourseController {
 
     @RequestMapping(value = "/progress", method = RequestMethod.GET)
     @ApiOperation(value = "获取课程进度", notes = "获取所有课程及状态进度", httpMethod = "GET")
-    public Response<List<UserClassDetailDto>> classProgress()  {
+    public Response<List<UserCourseDetailDto>> progress()  {
         User user = (User) shiroHelp.getLoginUser();
-        List<UserClass> userClassList = userClassService.getByUser(user.getId());
-        List<UserClassDetailDto> dtos = Transform.convert(userClassList, UserClassDetailDto.class);
+        List<UserCourse> userCourseList = userCourseService.getByUser(user.getId());
+        List<UserCourseDetailDto> dtos = Transform.convert(userCourseList, UserCourseDetailDto.class);
 
         // 获取每个科目的最后2次作业
         Map<Object, Collection<UserPreviewPaperRelation>> previewMap = previewService.groupByCategory(user.getId(), 3);
-        Transform.combine(dtos, previewMap, UserClassDetailDto.class, "courseId", "previews", UserPreviewPaperExtendDto.class);
+        Transform.combine(dtos, previewMap, UserCourseDetailDto.class, "courseId", "previews", UserPreviewPaperExtendDto.class);
 
         // 获取课程状态:已购买未开通
         List<UserPay> pays = userPayService.listUnUse(user.getId(), PayModule.CLASS);
-        Collection ids = Transform.getIds(userClassList, UserClass.class, "courseId");
+        Collection ids = Transform.getIds(userCourseList, UserCourse.class, "courseId");
         for(UserPay pay : pays){
-            Integer courseId = Integer.valueOf(0);
+            Integer courseId = 0;
             if (!ids.contains(courseId)){
-                UserClassDetailDto dto = new UserClassDetailDto();
+                UserCourseDetailDto dto = new UserCourseDetailDto();
                 dto.setCourseId(courseId);
                 dto.setPayed(true);
                 dtos.add(dto);

+ 15 - 15
server/gateway-api/src/main/java/com/qxgmat/controller/api/MyController.java

@@ -73,10 +73,10 @@ public class MyController {
     private ExerciseStructService exerciseStructService;
 
     @Autowired
-    private ClassCourseService classCourseService;
+    private CourseService courseService;
 
     @Autowired
-    private ClassCourseNoService classCourseNoService;
+    private CourseNoService courseNoService;
 
     @Autowired
     private QuestionService questionService;
@@ -335,21 +335,21 @@ public class MyController {
         dto.setExaminationExceed(examinationRank);
 
         // 获取课程访问记录 - 按课时
-        Integer classTime = 0;
-        Integer classCourse = 0;
+        Integer courseTime = 0;
+        Integer courseNumber = 0;
         List<UserCourseRecord> userCourseRecordList = userCourseRecordService.getByTime(user.getId(), startTime, endTime);
         Collection courseIds = Transform.getIds(userCourseRecordList, UserCourseRecord.class, "courseId");
         Collection courseNoIds = Transform.getIds(userCourseRecordList, UserCourseRecord.class, "noId");
-        List<ClassCourse> classCourseList = classCourseService.select(courseIds);
-        Map classCourseMap = Transform.getMap(classCourseList, ClassCourse.class, "id", "title");
-        List<ClassCourseNo> classCourseNoList = classCourseNoService.select(courseNoIds);
-        Map classCourseNoMap = Transform.getMap(classCourseNoList, ClassCourseNo.class, "id", "content");
+        List<Course> courseList = courseService.select(courseIds);
+        Map courseMap = Transform.getMap(courseList, Course.class, "id", "title");
+        List<CourseNo> courseNoList = courseNoService.select(courseNoIds);
+        Map classCourseNoMap = Transform.getMap(courseNoList, CourseNo.class, "id", "content");
         List<UserCourseResultExtendDto> courseResultList = new ArrayList<>(userCourseRecordList.size());
         for(UserCourseRecord record:userCourseRecordList){
-            classTime += record.getUserTime();
-            classCourse += 1;
+            courseTime += record.getUserTime();
+            courseNumber += 1;
             UserCourseResultExtendDto d = Transform.convert(record, UserCourseResultExtendDto.class);
-            d.setTitle((String)classCourseMap.get(record.getCourseId()));
+            d.setTitle((String)courseMap.get(record.getCourseId()));
             d.setContent((String)classCourseNoMap.get(record.getCourseNoId()));
             courseResultList.add(d);
         }
@@ -357,10 +357,10 @@ public class MyController {
         UserRankStatRelation classRank = userCourseRecordService.rankByTime(user.getId(), startTime, endTime);
         classRank.setTotal(total);
 
-        dto.setClassTime(classTime);
-        dto.setClassCourse(classCourse);
-        dto.setClassList(courseResultList);
-        dto.setClassExceed(classRank);
+        dto.setCourseTime(courseTime);
+        dto.setCourseNumber(courseNumber);
+        dto.setCourseList(courseResultList);
+        dto.setCourseExceed(classRank);
 
 
         return ResponseHelp.success(dto);

+ 1 - 1
server/gateway-api/src/main/java/com/qxgmat/controller/api/QuestionController.java

@@ -91,7 +91,7 @@ public class QuestionController {
     private UserAskQuestionService userAskQuestionService;
 
     @Autowired
-    private UserClassService userClassService;
+    private UserCourseService userCourseService;
 
     @Autowired
     private UserPayService userPayService;

+ 3 - 3
server/gateway-api/src/main/java/com/qxgmat/dto/admin/extend/ClassCourseExtendDto.java

@@ -1,10 +1,10 @@
 package com.qxgmat.dto.admin.extend;
 
 import com.nuliji.tools.annotation.Dto;
-import com.qxgmat.data.dao.entity.ClassCourse;
+import com.qxgmat.data.dao.entity.Course;
 
-@Dto(entity = ClassCourse.class)
-public class ClassCourseExtendDto {
+@Dto(entity = Course.class)
+public class CourseExtendDto {
     private Integer id;
 
     private String title;

+ 3 - 3
server/gateway-api/src/main/java/com/qxgmat/dto/admin/extend/UserClassExtendDto.java

@@ -1,12 +1,12 @@
 package com.qxgmat.dto.admin.extend;
 
 import com.nuliji.tools.annotation.Dto;
-import com.qxgmat.data.dao.entity.UserClass;
+import com.qxgmat.data.dao.entity.UserCourse;
 
 import java.util.Date;
 
-@Dto(entity = UserClass.class)
-public class UserClassExtendDto {
+@Dto(entity = UserCourse.class)
+public class UserCourseExtendDto {
 
     private Integer id;
     private Integer courseId;

+ 99 - 0
server/gateway-api/src/main/java/com/qxgmat/dto/admin/request/CommentDto.java

@@ -0,0 +1,99 @@
+package com.qxgmat.dto.admin.request;
+
+import com.nuliji.tools.annotation.Dto;
+import com.qxgmat.data.dao.entity.Comment;
+
+import java.util.Date;
+
+@Dto(entity = Comment.class)
+public class CommentDto {
+    private Integer id;
+
+    private String channel;
+
+    private String position;
+
+    private Integer userId;
+
+    private String nickname;
+
+    private String avatar;
+
+    private String content;
+
+    private Integer isSpecial;
+
+    private Date createTime;
+
+    public Integer getId() {
+        return id;
+    }
+
+    public void setId(Integer id) {
+        this.id = id;
+    }
+
+    public String getChannel() {
+        return channel;
+    }
+
+    public void setChannel(String channel) {
+        this.channel = channel;
+    }
+
+    public String getPosition() {
+        return position;
+    }
+
+    public void setPosition(String position) {
+        this.position = position;
+    }
+
+    public Integer getUserId() {
+        return userId;
+    }
+
+    public void setUserId(Integer userId) {
+        this.userId = userId;
+    }
+
+    public String getNickname() {
+        return nickname;
+    }
+
+    public void setNickname(String nickname) {
+        this.nickname = nickname;
+    }
+
+    public String getAvatar() {
+        return avatar;
+    }
+
+    public void setAvatar(String avatar) {
+        this.avatar = avatar;
+    }
+
+    public String getContent() {
+        return content;
+    }
+
+    public void setContent(String content) {
+        this.content = content;
+    }
+
+    public Integer getIsSpecial() {
+        return isSpecial;
+    }
+
+    public void setIsSpecial(Integer isSpecial) {
+        this.isSpecial = isSpecial;
+    }
+
+    public Date getCreateTime() {
+        return createTime;
+    }
+
+    public void setCreateTime(Date createTime) {
+        this.createTime = createTime;
+    }
+}

+ 99 - 0
server/gateway-api/src/main/java/com/qxgmat/dto/admin/request/FaqDto.java

@@ -0,0 +1,99 @@
+package com.qxgmat.dto.admin.request;
+
+import com.nuliji.tools.annotation.Dto;
+import com.qxgmat.data.dao.entity.Faq;
+
+import java.util.Date;
+
+@Dto(entity = Faq.class)
+public class FaqDto {
+    private Integer id;
+
+    private Integer userId;
+
+    private String email;
+
+    private String channel;
+
+    private String position;
+
+    private String content;
+
+    private Integer isSpecial;
+
+    private Integer status;
+
+    private Date createTime;
+
+    public Integer getId() {
+        return id;
+    }
+
+    public void setId(Integer id) {
+        this.id = id;
+    }
+
+    public Integer getUserId() {
+        return userId;
+    }
+
+    public void setUserId(Integer userId) {
+        this.userId = userId;
+    }
+
+    public String getEmail() {
+        return email;
+    }
+
+    public void setEmail(String email) {
+        this.email = email;
+    }
+
+    public String getChannel() {
+        return channel;
+    }
+
+    public void setChannel(String channel) {
+        this.channel = channel;
+    }
+
+    public String getPosition() {
+        return position;
+    }
+
+    public void setPosition(String position) {
+        this.position = position;
+    }
+
+    public String getContent() {
+        return content;
+    }
+
+    public void setContent(String content) {
+        this.content = content;
+    }
+
+    public Integer getIsSpecial() {
+        return isSpecial;
+    }
+
+    public void setIsSpecial(Integer isSpecial) {
+        this.isSpecial = isSpecial;
+    }
+
+    public Integer getStatus() {
+        return status;
+    }
+
+    public void setStatus(Integer status) {
+        this.status = status;
+    }
+
+    public Date getCreateTime() {
+        return createTime;
+    }
+
+    public void setCreateTime(Date createTime) {
+        this.createTime = createTime;
+    }
+}

+ 69 - 0
server/gateway-api/src/main/java/com/qxgmat/dto/admin/request/MessageDto.java

@@ -0,0 +1,69 @@
+package com.qxgmat.dto.admin.request;
+
+import com.nuliji.tools.annotation.Dto;
+import com.qxgmat.data.dao.entity.Message;
+
+import java.util.Date;
+
+@Dto(entity = Message.class)
+public class MessageDto {
+    private Integer id;
+
+    private String title;
+
+    private String content;
+
+    private String link;
+
+    private Date sendTime;
+
+    private Date createTime;
+
+    public Integer getId() {
+        return id;
+    }
+
+    public void setId(Integer id) {
+        this.id = id;
+    }
+
+    public String getTitle() {
+        return title;
+    }
+
+    public void setTitle(String title) {
+        this.title = title;
+    }
+
+    public String getContent() {
+        return content;
+    }
+
+    public void setContent(String content) {
+        this.content = content;
+    }
+
+    public String getLink() {
+        return link;
+    }
+
+    public void setLink(String link) {
+        this.link = link;
+    }
+
+    public Date getSendTime() {
+        return sendTime;
+    }
+
+    public void setSendTime(Date sendTime) {
+        this.sendTime = sendTime;
+    }
+
+    public Date getCreateTime() {
+        return createTime;
+    }
+
+    public void setCreateTime(Date createTime) {
+        this.createTime = createTime;
+    }
+}

+ 3 - 3
server/gateway-api/src/main/java/com/qxgmat/dto/admin/response/ClassCourseListDto.java

@@ -1,10 +1,10 @@
 package com.qxgmat.dto.admin.response;
 
 import com.nuliji.tools.annotation.Dto;
-import com.qxgmat.data.dao.entity.ClassCourse;
+import com.qxgmat.data.dao.entity.Course;
 
-@Dto(entity = ClassCourse.class)
-public class ClassCourseListDto {
+@Dto(entity = Course.class)
+public class CourseListDto {
     private Integer id;
 
     private String title;

+ 4 - 4
server/gateway-api/src/main/java/com/qxgmat/dto/admin/response/UserDetailDto.java

@@ -2,7 +2,7 @@ package com.qxgmat.dto.admin.response;
 
 import com.nuliji.tools.annotation.Dto;
 import com.qxgmat.data.dao.entity.User;
-import com.qxgmat.dto.admin.extend.UserClassExtendDto;
+import com.qxgmat.dto.admin.extend.UserCourseExtendDto;
 import com.qxgmat.dto.admin.extend.UserServiceExtendDto;
 
 import java.math.BigDecimal;
@@ -24,7 +24,7 @@ public class UserDetailDto {
 
     private Collection<UserServiceExtendDto> services;
 
-    private Collection<UserClassExtendDto> classes;
+    private Collection<UserCourseExtendDto> classes;
 
     public Integer getId() {
         return id;
@@ -74,11 +74,11 @@ public class UserDetailDto {
         this.services = services;
     }
 
-    public Collection<UserClassExtendDto> getClasses() {
+    public Collection<UserCourseExtendDto> getClasses() {
         return classes;
     }
 
-    public void setClasses(Collection<UserClassExtendDto> classes) {
+    public void setClasses(Collection<UserCourseExtendDto> classes) {
         this.classes = classes;
     }
 }

+ 4 - 4
server/gateway-api/src/main/java/com/qxgmat/dto/admin/response/UserListDto.java

@@ -2,7 +2,7 @@ package com.qxgmat.dto.admin.response;
 
 import com.nuliji.tools.annotation.Dto;
 import com.qxgmat.data.dao.entity.User;
-import com.qxgmat.dto.admin.extend.UserClassExtendDto;
+import com.qxgmat.dto.admin.extend.UserCourseExtendDto;
 import com.qxgmat.dto.admin.extend.UserServiceExtendDto;
 
 import java.math.BigDecimal;
@@ -28,7 +28,7 @@ public class UserListDto {
 
     private Collection<UserServiceExtendDto> services;
 
-    private Collection<UserClassExtendDto> classes;
+    private Collection<UserCourseExtendDto> classes;
 
     public Integer getId() {
         return id;
@@ -78,11 +78,11 @@ public class UserListDto {
         this.services = services;
     }
 
-    public Collection<UserClassExtendDto> getClasses() {
+    public Collection<UserCourseExtendDto> getClasses() {
         return classes;
     }
 
-    public void setClasses(Collection<UserClassExtendDto> classes) {
+    public void setClasses(Collection<UserCourseExtendDto> classes) {
         this.classes = classes;
     }
 

+ 6 - 3
server/gateway-api/src/main/java/com/qxgmat/dto/response/UserClassDetailDto.java

@@ -1,17 +1,20 @@
 package com.qxgmat.dto.response;
 
 import com.nuliji.tools.annotation.Dto;
-import com.qxgmat.data.dao.entity.UserClass;
+import com.qxgmat.data.dao.entity.UserCourse;
 import com.qxgmat.dto.extend.UserPreviewPaperExtendDto;
 
 import java.util.Date;
 import java.util.List;
 
-@Dto(entity = UserClass.class)
-public class UserClassDetailDto {
+@Dto(entity = UserCourse.class)
+public class UserCourseDetailDto {
     private Integer courseId;
+
     private Date startTime;
+
     private Date expireTime;
+
     private Boolean payed;
 
     private List<UserPreviewPaperExtendDto> papers;

+ 20 - 20
server/gateway-api/src/main/java/com/qxgmat/dto/response/UserStudyDayDto.java

@@ -25,13 +25,13 @@ public class UserStudyDayDto {
 
     private List<UserPaperDetailExtendDto> examinationList;
 
-    private Integer classTime;
+    private Integer courseTime;
 
-    private Integer classCourse;
+    private Integer courseNumber;
 
-    private UserRankStatRelation classExceed;
+    private UserRankStatRelation courseExceed;
 
-    private List<UserCourseResultExtendDto> classList;
+    private List<UserCourseResultExtendDto> courseList;
 
     public Integer getExerciseTime() {
         return exerciseTime;
@@ -97,35 +97,35 @@ public class UserStudyDayDto {
         this.examinationList = examinationList;
     }
 
-    public Integer getClassTime() {
-        return classTime;
+    public Integer getCourseTime() {
+        return courseTime;
     }
 
-    public void setClassTime(Integer classTime) {
-        this.classTime = classTime;
+    public void setCourseTime(Integer courseTime) {
+        this.courseTime = courseTime;
     }
 
-    public Integer getClassCourse() {
-        return classCourse;
+    public Integer getCourseNumber() {
+        return courseNumber;
     }
 
-    public void setClassCourse(Integer classCourse) {
-        this.classCourse = classCourse;
+    public void setCourseNumber(Integer courseNumber) {
+        this.courseNumber = courseNumber;
     }
 
-    public UserRankStatRelation getClassExceed() {
-        return classExceed;
+    public UserRankStatRelation getCourseExceed() {
+        return courseExceed;
     }
 
-    public void setClassExceed(UserRankStatRelation classExceed) {
-        this.classExceed = classExceed;
+    public void setCourseExceed(UserRankStatRelation courseExceed) {
+        this.courseExceed = courseExceed;
     }
 
-    public List<UserCourseResultExtendDto> getClassList() {
-        return classList;
+    public List<UserCourseResultExtendDto> getCourseList() {
+        return courseList;
     }
 
-    public void setClassList(List<UserCourseResultExtendDto> classList) {
-        this.classList = classList;
+    public void setCourseList(List<UserCourseResultExtendDto> courseList) {
+        this.courseList = courseList;
     }
 }

+ 3 - 0
server/gateway-api/src/main/java/com/qxgmat/help/MailHelp.java

@@ -52,6 +52,9 @@ public class MailHelp {
     }
 
     private String replaceBody(String body, Map<String, String> params){
+        for(String key :params.keySet()){
+            body = body.replaceAll("{"+key+"}", params.get(key));
+        }
         return body;
     }
 }

+ 3 - 3
server/gateway-api/src/main/java/com/qxgmat/service/UsersService.java

@@ -19,7 +19,7 @@ import com.qxgmat.data.inline.UserToken;
 import com.qxgmat.data.relation.UserRelationMapper;
 import com.qxgmat.data.relation.entity.UserPrepareRelation;
 import com.qxgmat.help.WechatHelp;
-import com.qxgmat.service.inline.UserClassService;
+import com.qxgmat.service.inline.UserCourseService;
 import com.qxgmat.service.inline.UserMessageService;
 import com.qxgmat.service.inline.UserPayService;
 import com.qxgmat.service.inline.UserServiceService;
@@ -57,7 +57,7 @@ public class UsersService extends AbstractService {
     private UserPayService userPayService;
 
     @Resource
-    private UserClassService userClassService;
+    private UserCourseService userCourseService;
 
     @Resource
     private UserServiceService userServiceService;
@@ -132,7 +132,7 @@ public class UsersService extends AbstractService {
                 // 更新消费记录
                 userPayService.mergeUser(openUser.getId(), user.getId());
                 // 更新课程信息
-                userClassService.mergeUser(openUser.getId(), user.getId());
+                userCourseService.mergeUser(openUser.getId(), user.getId());
                 // 更新服务信息
                 userServiceService.mergeUser(openUser.getId(), user.getId());
 

+ 14 - 0
server/gateway-api/src/main/java/com/qxgmat/service/extend/CourseExtendService.java

@@ -0,0 +1,14 @@
+package com.qxgmat.service.extend;
+
+import com.qxgmat.service.inline.CourseService;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+
+@Service
+public class CourseExtendService {
+
+    @Autowired
+    private CourseService courseService;
+
+
+}

+ 58 - 0
server/gateway-api/src/main/java/com/qxgmat/service/extend/MessageExtendService.java

@@ -0,0 +1,58 @@
+package com.qxgmat.service.extend;
+
+import com.alibaba.fastjson.JSONObject;
+import com.nuliji.tools.MessageHelp;
+import com.nuliji.tools.exception.SystemException;
+import com.qxgmat.data.constants.enums.user.MessageType;
+import com.qxgmat.data.dao.entity.UserMessage;
+import com.qxgmat.service.inline.MessageService;
+import com.qxgmat.service.inline.UserMessageService;
+import org.springframework.stereotype.Service;
+
+import javax.annotation.Resource;
+import java.util.Date;
+import java.util.Map;
+
+@Service
+public class MessageExtendService {
+
+    @Resource
+    private MessageHelp messageHelp;
+
+    @Resource
+    private UserMessageService userMessageService;
+
+    @Resource
+    private MessageService messageService;
+
+    @Resource
+    private ToolsService toolsService;
+
+    public UserMessage send(Integer userId, MessageType type, Map<String, String> params){
+        try {
+            // 根据模版创建
+            JSONObject template = toolsService.messageTemplate(type);
+            String content = template.getString("content");
+            String link = template.getString("link");
+            userMessageService.add(UserMessage.builder()
+                    .userId(userId)
+                    .title(type.title)
+                    .content(replaceBody(content, params))
+                    .link(link)
+                    .type(type.type)
+                    .isRead(0)
+                    .createTime(new Date())
+                    .build());
+            return null;
+        }catch (Exception e){
+            throw new SystemException("Message生成失败", e);
+        }
+    }
+
+    private String replaceBody(String body, Map<String, String> params){
+        for(String key :params.keySet()){
+            body = body.replaceAll("{"+key+"}", params.get(key));
+        }
+        return body;
+    }
+}

+ 0 - 30
server/gateway-api/src/main/java/com/qxgmat/service/extend/MessageService.java

@@ -1,30 +0,0 @@
-package com.qxgmat.service.extend;
-
-import com.nuliji.tools.MessageHelp;
-import com.nuliji.tools.exception.SystemException;
-import com.qxgmat.data.constants.enums.user.MessageType;
-import com.qxgmat.data.dao.entity.UserMessage;
-import com.qxgmat.service.inline.UserMessageService;
-import org.springframework.stereotype.Service;
-
-import javax.annotation.Resource;
-import java.util.Map;
-
-@Service
-public class MessageService {
-
-    @Resource
-    private MessageHelp messageHelp;
-
-    @Resource
-    private UserMessageService userMessageService;
-
-    public UserMessage send(Integer userId, MessageType type, Map<String, String> info){
-        try {
-            // 根据模版创建
-            return null;
-        }catch (Exception e){
-            throw new SystemException("Message生成失败", e);
-        }
-    }
-}

+ 12 - 0
server/gateway-api/src/main/java/com/qxgmat/service/extend/ToolsService.java

@@ -5,6 +5,7 @@ import com.alibaba.fastjson.JSONObject;
 import com.qxgmat.data.constants.enums.QuestionDifficult;
 import com.qxgmat.data.constants.enums.QuestionSubject;
 import com.qxgmat.data.constants.enums.SettingKey;
+import com.qxgmat.data.constants.enums.user.MessageType;
 import com.qxgmat.data.dao.entity.*;
 import com.qxgmat.data.relation.entity.QuestionNoRelation;
 import com.qxgmat.data.relation.entity.SentenceQuestionRelation;
@@ -178,6 +179,17 @@ public class ToolsService {
     }
 
     /**
+     * 获取消息模版
+     * @param messageType
+     * @return
+     */
+    public JSONObject messageTemplate(MessageType messageType){
+        Setting setting = settingService.getByKey(SettingKey.MESSAGE_TEMPLATE);
+        JSONObject value = setting.getValue();
+        return value.getJSONObject(messageType.type);
+    }
+
+    /**
      * 根据考试设置,得到做题时间,做题数量
      *      setting: {subject: { time: "", number: "" }}
      * @param order

+ 0 - 0
server/gateway-api/src/main/java/com/qxgmat/service/extend/TradeService.java


Some files were not shown because too many files changed in this diff