From 0e7ad92b3570f1f61bcb1289187768787b0f328c Mon Sep 17 00:00:00 2001 From: tangjiang <465264938@qq.com> Date: Fri, 10 Jan 2020 14:08:47 +0800 Subject: [PATCH 001/204] add static --- public/react/package.json | 1 + public/react/src/modules/paths/Index.js | 10 +- .../modules/paths/statics/DisplayTableData.js | 26 ++++ .../paths/statics/StaticNumberAndTxt.js | 43 +++++ .../react/src/modules/paths/statics/index.js | 147 ++++++++++++++++++ .../src/modules/paths/statics/index.scss | 92 +++++++++++ 6 files changed, 316 insertions(+), 3 deletions(-) create mode 100644 public/react/src/modules/paths/statics/DisplayTableData.js create mode 100644 public/react/src/modules/paths/statics/StaticNumberAndTxt.js create mode 100644 public/react/src/modules/paths/statics/index.js create mode 100644 public/react/src/modules/paths/statics/index.scss diff --git a/public/react/package.json b/public/react/package.json index 6828a43c4..39067977d 100644 --- a/public/react/package.json +++ b/public/react/package.json @@ -71,6 +71,7 @@ "rc-tree": "^1.7.11", "rc-upload": "^2.5.1", "react": "^16.9.0", + "react-base-table": "^1.9.1", "react-beautiful-dnd": "^10.0.4", "react-codemirror": "^1.0.0", "react-codemirror2": "^6.0.0", diff --git a/public/react/src/modules/paths/Index.js b/public/react/src/modules/paths/Index.js index 7a1c3d301..67ef9125b 100644 --- a/public/react/src/modules/paths/Index.js +++ b/public/react/src/modules/paths/Index.js @@ -17,10 +17,14 @@ const PathsNew = Loadable({ loader: () => import('./PathNew'), loading:Loading, }) +// const Statistics = Loadable({ +// loader: () => import('./SchoolStatistics/Statistics'), +// loading:Loading +// }) const Statistics = Loadable({ - loader: () => import('./SchoolStatistics/Statistics'), - loading:Loading -}) + loader: () => import('./statics'), + loading: Loading +}); const ShixunPaths = Loadable({ loader: () => import('./ShixunPaths'), diff --git a/public/react/src/modules/paths/statics/DisplayTableData.js b/public/react/src/modules/paths/statics/DisplayTableData.js new file mode 100644 index 000000000..59c4f092a --- /dev/null +++ b/public/react/src/modules/paths/statics/DisplayTableData.js @@ -0,0 +1,26 @@ +/* + * @Description: 展示表格数据 + * @Author: tangjiang + * @Github: + * @Date: 2020-01-10 13:46:30 + * @LastEditors : tangjiang + * @LastEditTime : 2020-01-10 13:48:54 + */ +import React from 'react'; +// import { Table } from 'antd'; + +const DisplayTableData = ({ + columns, + datas +}) => { + + return ( + + ); +} + +export default DisplayTableData; diff --git a/public/react/src/modules/paths/statics/StaticNumberAndTxt.js b/public/react/src/modules/paths/statics/StaticNumberAndTxt.js new file mode 100644 index 000000000..e061bdc80 --- /dev/null +++ b/public/react/src/modules/paths/statics/StaticNumberAndTxt.js @@ -0,0 +1,43 @@ +/* + * @Description: 数字及文字提示 + * @Author: tangjiang + * @Github: + * @Date: 2020-01-10 10:26:57 + * @LastEditors : tangjiang + * @LastEditTime : 2020-01-10 11:15:28 + */ +import './index.scss'; +import React from 'react'; +import { Tooltip } from 'antd'; +const numberal = require('numeral'); + +const StaticNumberAndTxt = ({ + count = 0, // 总数 + txt, // 文字描述 + type = 'tishi1', // 字体类型 + desc // 描述信息 +}) => { + + const formatNumber = (value, format = '0,0') => { + return numberal(value).format(format); + } + + const _classes = `iconfont icon-${type} icon`; + return ( +
+ {formatNumber(count)} + + {txt} + + + + +
+ ); +} + +export default StaticNumberAndTxt; diff --git a/public/react/src/modules/paths/statics/index.js b/public/react/src/modules/paths/statics/index.js new file mode 100644 index 000000000..d026d714a --- /dev/null +++ b/public/react/src/modules/paths/statics/index.js @@ -0,0 +1,147 @@ +/* + * @Description: 实践课程统计页面 + * @Author: tangjiang + * @Github: + * @Date: 2020-01-10 09:33:45 + * @LastEditors : tangjiang + * @LastEditTime : 2020-01-10 13:45:26 + */ +import './index.scss'; +import React from 'react'; +import StaticNumberAndTxt from './StaticNumberAndTxt'; +import { Table, Tabs } from 'antd'; +const { TabPane } = Tabs; +const App = () => { + + const columns = [ + { + title: '序号', + dataIndex: 'id' + }, + { + title: '使用单位', + dataIndex: 'id2' + }, + { + title: '使用课堂/个', + dataIndex: 'id3' + }, + { + title: '课堂实训/个', + dataIndex: 'id4' + }, + { + title: '选用实训/个', + dataIndex: 'id5' + }, + { + title: '选用实训/次', + dataIndex: 'id6' + } + ]; + + const datas = [ + { + key: '1', + id: 1, + id2: '', + id3: '', + id4: '', + id5: '', + id6: '' + }, + { + key: '1', + id: 1, + id2: '', + id3: '', + id4: '', + id5: '', + id6: '' + }, + { + key: '1', + id: 1, + id2: '', + id3: '', + id4: '', + id5: '', + id6: '' + }, + { + key: '1', + id: 1, + id2: '', + id3: '', + id4: '', + id5: '', + id6: '' + } + ]; + return ( +
+
+
+
+
+ 学习统计 + Android综合实训之物联网移动应用 +
+
+ + + + + + +
+
+
+ + + Content of Tab Pane 1 + + + Content of Tab Pane 2 + + + Content of Tab Pane 3 + + +
+ + + + + ); +} + +export default App; diff --git a/public/react/src/modules/paths/statics/index.scss b/public/react/src/modules/paths/statics/index.scss new file mode 100644 index 000000000..7f36468ba --- /dev/null +++ b/public/react/src/modules/paths/statics/index.scss @@ -0,0 +1,92 @@ +.static_wrap { + .static_section_header, + .static_section_table{ + background-color: #fff; + border-radius: 5px; + padding: 30px 20px 0; + margin-top: 20px; + } + + .static_section_header{ + .header_title{ + line-height: 1; + .title-p, + .title-sub{ + display: inline-block; + vertical-align: bottom; + color: #303133; + } + + .title-p{ + position: relative; + font-size: 20px; + height: 20px; + line-height: 1; + font-weight: bold; + + &::before{ + position: absolute; + content: ''; + border-left: 1px solid rgba(192,196,204,1); + right: -10px; + top: 2px; + bottom: 0px; + margin-left: 10px; + } + } + .title-sub{ + margin-left: 20px; + font-size: 16px; + max-width: 1000px; + overflow: hidden; + text-overflow:ellipsis; + white-space: nowrap; + vertical-align: bottom; + } + } + + .header-number{ + height: 158px; + } + .header-flex{ + display: flex; + justify-content: space-around; + align-items: center; + + .static-flex-item{ + display: flex; + flex-direction: column; + justify-content: center; + .item-count{ + font-size: 24px; + color: #4CACFF; + font-weight: bold; + } + .item-txt{ + font-size: 14px; + line-height: 1.5; + text-align: center; + color: #909399; + .icon{ + margin-left: 5px; + font-size: 16px !important; + } + } + } + } + } + .static_section_table{ + .ant-table-body th{ + background: rgba(241,248,255,1); + color:#303133; + text-align: center; + } + .ant-table-body tr:nth-child(even){ + background: rgba(241,248,255,.4); + } + } +} + +.tool-clazz{ + max-width: 200px !important; +} \ No newline at end of file From 05e69e8f7481d4c6a1493c5a79843d2b2d65b4bf Mon Sep 17 00:00:00 2001 From: tangjiang <465264938@qq.com> Date: Sat, 11 Jan 2020 13:35:16 +0800 Subject: [PATCH 002/204] commit --- public/react/package.json | 3 +- .../modules/paths/statics/DisplayTableData.js | 59 ++++++- .../react/src/modules/paths/statics/index.js | 148 +++++++++++------- .../src/modules/paths/statics/index.scss | 22 ++- .../src/modules/paths/statics/mockData.js | 84 ++++++++++ 5 files changed, 239 insertions(+), 77 deletions(-) create mode 100644 public/react/src/modules/paths/statics/mockData.js diff --git a/public/react/package.json b/public/react/package.json index 39067977d..771c6257f 100644 --- a/public/react/package.json +++ b/public/react/package.json @@ -7,6 +7,7 @@ "@monaco-editor/react": "^2.3.0", "@novnc/novnc": "^1.1.0", "antd": "^3.23.2", + "antd-table-infinity": "^1.1.3", "array-flatten": "^2.1.2", "autoprefixer": "7.1.6", "axios": "^0.18.0", @@ -71,7 +72,6 @@ "rc-tree": "^1.7.11", "rc-upload": "^2.5.1", "react": "^16.9.0", - "react-base-table": "^1.9.1", "react-beautiful-dnd": "^10.0.4", "react-codemirror": "^1.0.0", "react-codemirror2": "^6.0.0", @@ -177,6 +177,7 @@ "compression-webpack-plugin": "^1.1.12", "concat": "^1.0.3", "happypack": "^5.0.1", + "mockjs": "^1.1.0", "node-sass": "^4.12.0", "reqwest": "^2.0.5", "webpack-bundle-analyzer": "^3.0.3", diff --git a/public/react/src/modules/paths/statics/DisplayTableData.js b/public/react/src/modules/paths/statics/DisplayTableData.js index 59c4f092a..3e4bcb665 100644 --- a/public/react/src/modules/paths/statics/DisplayTableData.js +++ b/public/react/src/modules/paths/statics/DisplayTableData.js @@ -4,21 +4,64 @@ * @Github: * @Date: 2020-01-10 13:46:30 * @LastEditors : tangjiang - * @LastEditTime : 2020-01-10 13:48:54 + * @LastEditTime : 2020-01-11 11:20:50 */ -import React from 'react'; -// import { Table } from 'antd'; +import 'antd-table-infinity/dist/index.css'; +import 'antd-table-infinity/index.css'; +import './index.scss'; +import React, { useState, useEffect } from 'react'; +import { Spin } from 'antd'; +// import {SumTable as Table} from 'antd-table-infinity'; +import { SumTable as Table } from 'antd-table-infinity'; +import { columns, fetchData, sumData } from './mockData'; const DisplayTableData = ({ - columns, - datas + // columns = [], + // datas, + // fetchData }) => { + const [data, setData] = useState([]); + const [loading, setLoading] = useState(false); + + const handleFetchData = () => { + setLoading(true); + fetchData(data.length).then(newData => { + setLoading(false); + const _data = data.concat(newData); + setData(_data); + }) + } + useEffect(() => { + handleFetchData(); + }, []); + + const loadMoreContent = () => ( +
+ +
+ ); return (
); } diff --git a/public/react/src/modules/paths/statics/index.js b/public/react/src/modules/paths/statics/index.js index d026d714a..5076e0a0e 100644 --- a/public/react/src/modules/paths/statics/index.js +++ b/public/react/src/modules/paths/statics/index.js @@ -4,80 +4,104 @@ * @Github: * @Date: 2020-01-10 09:33:45 * @LastEditors : tangjiang - * @LastEditTime : 2020-01-10 13:45:26 + * @LastEditTime : 2020-01-11 11:18:38 */ import './index.scss'; -import React from 'react'; +import React, { useState } from 'react'; import StaticNumberAndTxt from './StaticNumberAndTxt'; +import DisplayTableData from './DisplayTableData'; import { Table, Tabs } from 'antd'; const { TabPane } = Tabs; const App = () => { + // const datas = [ + // { + // key: '1', + // id: 1, + // id2: '', + // id3: '', + // id4: '', + // id5: '', + // id6: '' + // }, + // { + // key: '2', + // id: 2, + // id2: '', + // id3: '', + // id4: '', + // id5: '', + // id6: '' + // }, + // { + // key: '3', + // id: 3, + // id2: '', + // id3: '', + // id4: '', + // id5: '', + // id6: '' + // }, + // { + // key: '4', + // id: 4, + // id2: '', + // id3: '', + // id4: '', + // id5: '', + // id6: '' + // } + // ]; + const [datas, setDatas] = useState([]); const columns = [ { title: '序号', - dataIndex: 'id' + id: 'id', + //align: 'center', + width: 100 }, { title: '使用单位', - dataIndex: 'id2' + id: 'id2', + //align: 'center', + flexGrow: 1 }, { title: '使用课堂/个', - dataIndex: 'id3' + id: 'id3', + //align: 'center', + flexGrow: 1, + sortable: true }, { title: '课堂实训/个', - dataIndex: 'id4' + id: 'id4', + //align: 'center', + flexGrow: 1, + sortable: true }, { title: '选用实训/个', - dataIndex: 'id5' + id: 'id5', + //align: 'center', + flexGrow: 1, + sortable: true }, { title: '选用实训/次', - dataIndex: 'id6' + id: 'id6', + //align: 'center', + flexGrow: 1, + sortable: true } ]; - const datas = [ - { - key: '1', - id: 1, - id2: '', - id3: '', - id4: '', - id5: '', - id6: '' - }, - { - key: '1', - id: 1, - id2: '', - id3: '', - id4: '', - id5: '', - id6: '' - }, - { - key: '1', - id: 1, - id2: '', - id3: '', - id4: '', - id5: '', - id6: '' - }, - { - key: '1', - id: 1, - id2: '', - id3: '', - id4: '', - id5: '', - id6: '' - } - ]; + + + const handleFetchData = () => { + + } + return (
@@ -121,21 +145,25 @@ const App = () => {
- - - Content of Tab Pane 1 - - - Content of Tab Pane 2 - - - Content of Tab Pane 3 - - -
+ + + + + Content of Tab Pane 2 + + + Content of Tab Pane 3 + + */} + diff --git a/public/react/src/modules/paths/statics/index.scss b/public/react/src/modules/paths/statics/index.scss index 7f36468ba..646aefdcf 100644 --- a/public/react/src/modules/paths/statics/index.scss +++ b/public/react/src/modules/paths/statics/index.scss @@ -7,6 +7,10 @@ margin-top: 20px; } + .static_section_table{ + margin-bottom: 140px; + } + .static_section_header{ .header_title{ line-height: 1; @@ -75,18 +79,20 @@ } } } - .static_section_table{ - .ant-table-body th{ - background: rgba(241,248,255,1); - color:#303133; - text-align: center; + .statc_table{ + .ant-table-header{ + overflow-x: hidden !important; + margin-bottom: 0px !important; + border-bottom: 2px solid #e8e8e8; + background: green; } - .ant-table-body tr:nth-child(even){ - background: rgba(241,248,255,.4); + .ant-table-footer .ant-table-content{ + border-top: 1px solid #e8e8e8; + box-sizing: border-box; } } } .tool-clazz{ max-width: 200px !important; -} \ No newline at end of file +} diff --git a/public/react/src/modules/paths/statics/mockData.js b/public/react/src/modules/paths/statics/mockData.js new file mode 100644 index 000000000..bf505ffb5 --- /dev/null +++ b/public/react/src/modules/paths/statics/mockData.js @@ -0,0 +1,84 @@ +/* + * @Description: 模拟数据 + * @Author: tangjiang + * @Github: + * @Date: 2020-01-11 10:55:33 + * @LastEditors : tangjiang + * @LastEditTime : 2020-01-11 11:58:08 + */ +import { random } from 'lodash'; + +const getGuid = () => + 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, c => { + /* eslint-disable */ + let r = (Math.random() * 16) | 0, + v = c == 'x' ? r : (r & 0x3) | 0x8; + return v.toString(16); + }); + +const fetchData = (startIndex = 0) => + new Promise(resolve => { + setTimeout(() => { + resolve( + startIndex >= 500 // 总共只有500条数据 + ? [] + : Array.from({ length: 50 }).map((_, i) => { + // 每次返回100条 + const index = startIndex + i; + return { + key: getGuid(), + index: `${index}`, + name: 'John Brown', + age: 32, + address: 'New York No. 1 Lake Park', + }; + }), + ); + }, random(0, 1.0) * 1000); + }); + +const columns = [ + { + title: '序号', + dataIndex: 'index', + render: text => text, + width: 50, + }, + { + title: '使用单位', + dataIndex: 'name', + // width: 100, + }, + { + title: '使用课堂/个', + // width: 200, + dataIndex: 'age', + }, + { + title: '课堂学生/个', + // width: 200, + dataIndex: 'address', + }, + { + title: '选用实训/个', + // width: 200, + dataIndex: 'address', + }, + { + title: '选用实训/个', + // width: 200, + dataIndex: 'address', + } +]; + +const sumData = [ + { + index: '合计', + key: ',4', + name: 'Disabled User', + age: 99, + address: 'Sidney No. 1 Lake Park', + }, +]; + +export { columns, fetchData, sumData }; From 0d9143c61182b86c5a43afea73108b5f043c5fba Mon Sep 17 00:00:00 2001 From: tangjiang <465264938@qq.com> Date: Sat, 11 Jan 2020 14:42:05 +0800 Subject: [PATCH 003/204] update static table --- public/react/src/AppConfig.js | 2 +- .../src/modules/paths/statics/DisplayTableData.js | 6 +++--- public/react/src/modules/paths/statics/mockData.js | 13 ++++++++----- 3 files changed, 12 insertions(+), 9 deletions(-) diff --git a/public/react/src/AppConfig.js b/public/react/src/AppConfig.js index 5f870b683..526b380d6 100644 --- a/public/react/src/AppConfig.js +++ b/public/react/src/AppConfig.js @@ -83,7 +83,7 @@ export function initAxiosInterceptors(props) { //proxy="http://47.96.87.25:48080" proxy="https://pre-newweb.educoder.net" proxy="https://test-newweb.educoder.net" - //proxy="https://test-jupyterweb.educoder.net" + // proxy="https://test-jupyterweb.educoder.net" //proxy="http://192.168.2.63:3001" // 在这里使用requestMap控制,避免用户通过双击等操作发出重复的请求; diff --git a/public/react/src/modules/paths/statics/DisplayTableData.js b/public/react/src/modules/paths/statics/DisplayTableData.js index 3e4bcb665..3d9f1aa82 100644 --- a/public/react/src/modules/paths/statics/DisplayTableData.js +++ b/public/react/src/modules/paths/statics/DisplayTableData.js @@ -4,7 +4,7 @@ * @Github: * @Date: 2020-01-10 13:46:30 * @LastEditors : tangjiang - * @LastEditTime : 2020-01-11 11:20:50 + * @LastEditTime : 2020-01-11 14:02:32 */ import 'antd-table-infinity/dist/index.css'; import 'antd-table-infinity/index.css'; @@ -60,8 +60,8 @@ const DisplayTableData = ({ sumData={sumData} scroll={{ y: 450 }} dataSource={data} - bordered - debug + // bordered + // debug /> ); } diff --git a/public/react/src/modules/paths/statics/mockData.js b/public/react/src/modules/paths/statics/mockData.js index bf505ffb5..def1e904b 100644 --- a/public/react/src/modules/paths/statics/mockData.js +++ b/public/react/src/modules/paths/statics/mockData.js @@ -4,7 +4,7 @@ * @Github: * @Date: 2020-01-11 10:55:33 * @LastEditors : tangjiang - * @LastEditTime : 2020-01-11 11:58:08 + * @LastEditTime : 2020-01-11 14:01:49 */ import { random } from 'lodash'; @@ -31,6 +31,8 @@ const fetchData = (startIndex = 0) => name: 'John Brown', age: 32, address: 'New York No. 1 Lake Park', + address2: 'address2', + address3: 'address3' }; }), ); @@ -42,7 +44,7 @@ const columns = [ title: '序号', dataIndex: 'index', render: text => text, - width: 50, + width: 80, }, { title: '使用单位', @@ -62,22 +64,23 @@ const columns = [ { title: '选用实训/个', // width: 200, - dataIndex: 'address', + dataIndex: 'address2', }, { title: '选用实训/个', // width: 200, - dataIndex: 'address', + dataIndex: 'address3', } ]; const sumData = [ { index: '合计', - key: ',4', name: 'Disabled User', age: 99, address: 'Sidney No. 1 Lake Park', + address2: 'address2', + addrexs3: 'address3' }, ]; From be54acf180ed62e0278cf425cffabc494049d735 Mon Sep 17 00:00:00 2001 From: tangjiang <465264938@qq.com> Date: Sat, 11 Jan 2020 16:45:33 +0800 Subject: [PATCH 004/204] update tpi style --- public/react/public/css/css_min_all.css | 2 +- public/react/public/css/taskstyle.css | 2 +- public/react/src/modules/page/Header.js | 7 ++-- public/react/src/modules/page/VNCContainer.js | 35 +++++++++++++++++-- public/react/src/modules/page/VNCDisplay.js | 3 +- public/react/src/modules/page/header.scss | 6 ++++ public/react/src/modules/page/tpiPage.css | 6 ++-- 7 files changed, 52 insertions(+), 9 deletions(-) create mode 100644 public/react/src/modules/page/header.scss diff --git a/public/react/public/css/css_min_all.css b/public/react/public/css/css_min_all.css index 431a4da8e..93b1c7f96 100755 --- a/public/react/public/css/css_min_all.css +++ b/public/react/public/css/css_min_all.css @@ -1269,7 +1269,7 @@ input.knowledge_frame{height:28px;line-height:28px;border:none;background:#f3f5f .-relative { position: relative;} .-bg-white { background-color: #eee;} .split-panel.-handle .split-panel--second { padding-left: 2px;} -.split-panel--second { overflow: hidden;} +/* .split-panel--second { overflow: hidden;} */ .task-answer-view { position: absolute; top: 0; right: 0; bottom: 0;left: 0; display: flex; flex-direction: column; border-top: 1px solid #515151;} .-vertical { flex-direction: column;box-flex-direction: column;-webkit-flex-direction: column;} diff --git a/public/react/public/css/taskstyle.css b/public/react/public/css/taskstyle.css index 29358d6e0..85960fa8b 100755 --- a/public/react/public/css/taskstyle.css +++ b/public/react/public/css/taskstyle.css @@ -145,7 +145,7 @@ input.knowledge_frame{height:28px;line-height:28px;border:none;background:#f3f5f .-relative { position: relative;} .-bg-white { background-color: #eee;} .split-panel.-handle .split-panel--second { padding-left: 2px;} -.split-panel--second { overflow: hidden;} +/* .split-panel--second { overflow: hidden;} */ .task-answer-view { position: absolute; top: 0; right: 0; bottom: 0;left: 0; display: flex; flex-direction: column; border-top: 1px solid #515151;} .-vertical { flex-direction: column;box-flex-direction: column;-webkit-flex-direction: column;} diff --git a/public/react/src/modules/page/Header.js b/public/react/src/modules/page/Header.js index 1c24b6a52..283ec9953 100644 --- a/public/react/src/modules/page/Header.js +++ b/public/react/src/modules/page/Header.js @@ -1,3 +1,4 @@ +import './header.scss'; import React, { Component } from 'react'; import Button from 'material-ui/Button'; @@ -120,9 +121,11 @@ class Header extends Component {
{shixun ? - + // className="mr20 mt8 exitBtn" + - {'退出闯关'} + {/* {'退出闯关'} */} + {'退出实训'} : ''}
diff --git a/public/react/src/modules/page/VNCContainer.js b/public/react/src/modules/page/VNCContainer.js index 55a991ae8..7bd393525 100644 --- a/public/react/src/modules/page/VNCContainer.js +++ b/public/react/src/modules/page/VNCContainer.js @@ -338,6 +338,33 @@ class VNCContainer extends Component { .float_button:hover .text { color: #4CACFF; } + .resetVNC1{ + top: -50px; + writing-mode: initial; + left: calc(100% - 230px); + background-image: none; + width: auto; + // background: #081516; + height: 30px; + padding: 0 6px; + border-radius: 4px; + z-index: 10; + font-size: 16px; + transition: color .3s; + } + .resetVNC1 .text { + top: 0px; + writing-mode: initial; + left: unset; + } + .resetVNC1 .text span { + vertical-align: middle; + margin-left: 2px; + } + .float_button:hover .text { + transition: color .3s; + color: #4CACFF; + } `}
网址克隆
@@ -354,11 +381,15 @@ class VNCContainer extends Component { > - - {/* */} + {/* {this.state.vnc_reseting ? : } 重置桌面系统 + */} + + {this.state.vnc_reseting ? + : } + 重置实训 {/* diff --git a/public/react/src/modules/page/VNCDisplay.js b/public/react/src/modules/page/VNCDisplay.js index b9ec77988..17dbff309 100644 --- a/public/react/src/modules/page/VNCDisplay.js +++ b/public/react/src/modules/page/VNCDisplay.js @@ -166,7 +166,8 @@ class VNCDisplay extends Component { `}
Loading
-
Send CtrlAltDel
+ {/*
Send CtrlAltDel
*/} +
diff --git a/public/react/src/modules/page/header.scss b/public/react/src/modules/page/header.scss new file mode 100644 index 000000000..b8320638f --- /dev/null +++ b/public/react/src/modules/page/header.scss @@ -0,0 +1,6 @@ +.headerRight .exit_btn{ + color: rgba(237,237,237,1); + &:hover{ + // color: #fff; + } +} \ No newline at end of file diff --git a/public/react/src/modules/page/tpiPage.css b/public/react/src/modules/page/tpiPage.css index 0c4faee83..015a66b98 100644 --- a/public/react/src/modules/page/tpiPage.css +++ b/public/react/src/modules/page/tpiPage.css @@ -120,8 +120,10 @@ button.buttonHoverColor:hover a { #myshixun_top { - display: flex; - height: 54px; + display: flex; + position: fixed; + height: 54px; + z-index: 1 !important; } .headerLeft { flex: 0 0 400px; From 1fe5acad9991091b487b9fb4524cc683d944c194 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sat, 11 Jan 2020 16:48:59 +0800 Subject: [PATCH 005/204] =?UTF-8?q?=E8=AF=95=E5=8D=B7=E9=A2=98=E7=9A=84?= =?UTF-8?q?=E9=AA=8C=E8=AF=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/courses_controller.rb | 2 +- .../exercise_answers_controller.rb | 144 ++++++++---------- 2 files changed, 66 insertions(+), 80 deletions(-) diff --git a/app/controllers/courses_controller.rb b/app/controllers/courses_controller.rb index 753a3d942..b19ad96e8 100644 --- a/app/controllers/courses_controller.rb +++ b/app/controllers/courses_controller.rb @@ -182,7 +182,7 @@ class CoursesController < ApplicationController CreateSubjectCourseStudentJob.perform_later(@course.id) if @course.subject && @course.subject.subject_appointments.count > 0 rescue => e uid_logger_error(e.message) - tip_exception("调用失败") + tip_exception(e.message) raise ActiveRecord::Rollback end end diff --git a/app/controllers/exercise_answers_controller.rb b/app/controllers/exercise_answers_controller.rb index d74e14fe1..dfbe68cb5 100644 --- a/app/controllers/exercise_answers_controller.rb +++ b/app/controllers/exercise_answers_controller.rb @@ -2,94 +2,80 @@ class ExerciseAnswersController < ApplicationController before_action :require_login, :check_auth before_action :get_exercise_question include ExercisesHelper - - # model validation error - rescue_from ActiveRecord::RecordInvalid do |ex| - render_error(ex.record.errors.full_messages.join(',')) - end - # form validation error - rescue_from ActiveModel::ValidationError do |ex| - render_error(ex.model.errors.full_messages.join(',')) - end + include ControllerRescueHandler def create #每一次答案的点击,请求一次,实训题不在这里回答 - begin - q_type = @exercise_question.question_type #试卷的类型 - choice_id = params[:exercise_choice_id].present? ? params[:exercise_choice_id] : "" - answer_text = params[:answer_text].present? ? params[:answer_text].strip : "" #为字符串 - if q_type < Exercise::SUBJECTIVE && (q_type != Exercise::MULTIPLE) && choice_id.blank? - normal_status(-1,"请选择序号") - else - ea = @exercise_question.exercise_answers.search_answer_users("user_id",current_user.id) #试卷的当前用户的答案 - if q_type == Exercise::SINGLE || q_type == Exercise::JUDGMENT #选择题(单选)/判断题 - if ea.exists? - ea.first.update!(exercise_choice_id: choice_id ) - else - answer_option = { - :user_id => current_user.id, - :exercise_question_id => @exercise_question.id, - :exercise_choice_id => choice_id, - :answer_text => "" - } - ex_a = ExerciseAnswer.new(answer_option) - ex_a.save! - end - elsif q_type == Exercise::MULTIPLE #多选题的 - choice_ids = params[:exercise_choice_id].present? ? params[:exercise_choice_id] : [] - - ea_ids = ea.pluck(:exercise_choice_id) - common_answer_ids = choice_ids & ea_ids #已经存在的试卷选项id - new_ids = (choice_ids - common_answer_ids).uniq # 新增的id - old_ids = (ea_ids - common_answer_ids).uniq #没有选择的,则删掉 - if new_ids.size > 0 - new_ids.each do |e| - answer_option = { - :user_id => current_user.id, - :exercise_question_id => @exercise_question.id, - :exercise_choice_id => e, - :answer_text => "" - } - ex_a = ExerciseAnswer.new(answer_option) - ex_a.save! - end - end - if old_ids.size > 0 - ea_answer = ea.search_answer_users("exercise_choice_id",old_ids) - ea_answer.destroy_all - end - elsif q_type == Exercise::COMPLETION #填空题 - answer_option = { - :user_id => current_user.id, - :exercise_question_id => @exercise_question.id, - :exercise_choice_id => choice_id, - :answer_text => answer_text - } - ea_answer = ea.search_answer_users("exercise_choice_id",choice_id) - if ea.present? && ea_answer.present? - ea_answer.update!(answer_option) - else - ex_new = ExerciseAnswer.new(answer_option) - ex_new.save! - end - elsif q_type == Exercise::SUBJECTIVE #简答题 + q_type = @exercise_question.question_type #试卷的类型 + choice_id = params[:exercise_choice_id].present? ? params[:exercise_choice_id] : "" + answer_text = params[:answer_text].present? ? params[:answer_text].strip : "" #为字符串 + if q_type < Exercise::SUBJECTIVE && (q_type != Exercise::MULTIPLE) && choice_id.blank? + normal_status(-1,"请选择序号") + else + ea = @exercise_question.exercise_answers.search_answer_users("user_id",current_user.id) #试卷的当前用户的答案 + if q_type == Exercise::SINGLE || q_type == Exercise::JUDGMENT #选择题(单选)/判断题 + if ea.exists? + ea.first.update!(exercise_choice_id: choice_id ) + else answer_option = { - :user_id => current_user.id, - :exercise_question_id => @exercise_question.id + :user_id => current_user.id, + :exercise_question_id => @exercise_question.id, + :exercise_choice_id => choice_id, + :answer_text => "" } - if ea.present? #已经回答了的, - ea.first.update!(answer_text: answer_text) - else - answer_option.merge!(answer_text:answer_text) + ex_a = ExerciseAnswer.new(answer_option) + ex_a.save! + end + elsif q_type == Exercise::MULTIPLE #多选题的 + choice_ids = params[:exercise_choice_id].present? ? params[:exercise_choice_id] : [] + + ea_ids = ea.pluck(:exercise_choice_id) + common_answer_ids = choice_ids & ea_ids #已经存在的试卷选项id + new_ids = (choice_ids - common_answer_ids).uniq # 新增的id + old_ids = (ea_ids - common_answer_ids).uniq #没有选择的,则删掉 + if new_ids.size > 0 + new_ids.each do |e| + answer_option = { + :user_id => current_user.id, + :exercise_question_id => @exercise_question.id, + :exercise_choice_id => e, + :answer_text => "" + } ex_a = ExerciseAnswer.new(answer_option) ex_a.save! end end - normal_status(0,"回答成功") + if old_ids.size > 0 + ea_answer = ea.search_answer_users("exercise_choice_id",old_ids) + ea_answer.destroy_all + end + elsif q_type == Exercise::COMPLETION #填空题 + answer_option = { + :user_id => current_user.id, + :exercise_question_id => @exercise_question.id, + :exercise_choice_id => choice_id, + :answer_text => answer_text + } + ea_answer = ea.search_answer_users("exercise_choice_id",choice_id) + if ea.present? && ea_answer.present? + ea_answer.update!(answer_option) + else + ex_new = ExerciseAnswer.new(answer_option) + ex_new.save! + end + elsif q_type == Exercise::SUBJECTIVE #简答题 + answer_option = { + :user_id => current_user.id, + :exercise_question_id => @exercise_question.id + } + if ea.present? #已经回答了的, + ea.first.update!(answer_text: answer_text) + else + answer_option.merge!(answer_text:answer_text) + ex_a = ExerciseAnswer.new(answer_option) + ex_a.save! + end end - rescue Exception => e - uid_logger_error(e.message) - tip_exception("页面调用失败!") - raise ActiveRecord::Rollback + normal_status(0,"回答成功") end end From 4098b420d133fe40378f487249d57da689f2b5ed Mon Sep 17 00:00:00 2001 From: tangjiang <465264938@qq.com> Date: Sat, 11 Jan 2020 16:51:10 +0800 Subject: [PATCH 006/204] update diff --- public/react/src/common/educoder.js | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/public/react/src/common/educoder.js b/public/react/src/common/educoder.js index b8c735e24..ded33c43a 100644 --- a/public/react/src/common/educoder.js +++ b/public/react/src/common/educoder.js @@ -3,13 +3,9 @@ // export { default as OrderStateUtil } from '../routes/Order/components/OrderStateUtil'; export { getImageUrl as getImageUrl, getRandomNumber as getRandomNumber,getUrl as getUrl, publicSearchs as publicSearchs,getRandomcode as getRandomcode,getUrlmys as getUrlmys, getUrl2 as getUrl2, setImagesUrl as setImagesUrl -<<<<<<< HEAD , getUploadActionUrl as getUploadActionUrl,getUploadActionUrltwo as getUploadActionUrltwo ,getUploadActionUrlthree as getUploadActionUrlthree, getUploadActionUrlOfAuth as getUploadActionUrlOfAuth , getTaskUrlById as getTaskUrlById, TEST_HOST ,htmlEncode as htmlEncode ,getupload_git_file as getupload_git_file} from './UrlTool'; -======= - , getUploadActionUrl as getUploadActionUrl,getUploadActionUrltwo as getUploadActionUrltwo ,getUploadActionUrlthree as getUploadActionUrlthree, getUploadActionUrlOfAuth as getUploadActionUrlOfAuth - , getTaskUrlById as getTaskUrlById, TEST_HOST ,htmlEncode as htmlEncode ,getupload_git_file as getupload_git_file} from './UrlTool'; ->>>>>>> dev_aliyun + export {setmiyah as setmiyah} from './Component'; export { default as queryString } from './UrlTool2'; From a5601a2b2d0460fcb73cf29b9646e09092213a6a Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sat, 11 Jan 2020 16:55:02 +0800 Subject: [PATCH 007/204] =?UTF-8?q?=E8=AF=95=E5=8D=B7=E9=A2=98=E7=9A=84?= =?UTF-8?q?=E9=AA=8C=E8=AF=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/exercise_answers_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/exercise_answers_controller.rb b/app/controllers/exercise_answers_controller.rb index dfbe68cb5..3556ab8d3 100644 --- a/app/controllers/exercise_answers_controller.rb +++ b/app/controllers/exercise_answers_controller.rb @@ -57,7 +57,7 @@ class ExerciseAnswersController < ApplicationController } ea_answer = ea.search_answer_users("exercise_choice_id",choice_id) if ea.present? && ea_answer.present? - ea_answer.update!(answer_option) + ea_answer.first.update!(answer_option) else ex_new = ExerciseAnswer.new(answer_option) ex_new.save! From e26ef0f133c46fb6f4c84f67401645fff697f461 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sat, 11 Jan 2020 16:59:38 +0800 Subject: [PATCH 008/204] =?UTF-8?q?=E8=AF=95=E5=8D=B7=E9=A2=98=E7=9A=84?= =?UTF-8?q?=E9=AA=8C=E8=AF=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/exercise_answers_controller.rb | 1 - 1 file changed, 1 deletion(-) diff --git a/app/controllers/exercise_answers_controller.rb b/app/controllers/exercise_answers_controller.rb index 3556ab8d3..158628475 100644 --- a/app/controllers/exercise_answers_controller.rb +++ b/app/controllers/exercise_answers_controller.rb @@ -2,7 +2,6 @@ class ExerciseAnswersController < ApplicationController before_action :require_login, :check_auth before_action :get_exercise_question include ExercisesHelper - include ControllerRescueHandler def create #每一次答案的点击,请求一次,实训题不在这里回答 q_type = @exercise_question.question_type #试卷的类型 From d5e2446016bf55c4c2cb9a0781b52f29124c1299 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sat, 11 Jan 2020 17:10:39 +0800 Subject: [PATCH 009/204] =?UTF-8?q?=E8=AF=95=E5=8D=B7=E7=9A=84=E9=AA=8C?= =?UTF-8?q?=E8=AF=81=E4=BF=A1=E6=81=AF?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/exercises_controller.rb | 3733 ++++++++++++++++------- 1 file changed, 2619 insertions(+), 1114 deletions(-) diff --git a/app/controllers/exercises_controller.rb b/app/controllers/exercises_controller.rb index ea4e38ab9..408f95945 100644 --- a/app/controllers/exercises_controller.rb +++ b/app/controllers/exercises_controller.rb @@ -1,26 +1,26 @@ class ExercisesController < ApplicationController before_action :require_login, :check_auth, except: [:index] - before_action :find_course,only: [:index,:new,:create,:my_exercises,:public_exercises,:set_public,:destroys, - :join_exercise_banks,:publish_modal,:publish,:end_modal,:end_exercise] #需要有课堂id参数的 - before_action :get_exercise,except: [:index,:new,:create,:my_exercises,:public_exercises,:set_public,:destroys, - :join_exercise_banks,:publish_modal,:publish,:end_modal,:end_exercise] + before_action :find_course, only: [:index, :new, :create, :my_exercises, :public_exercises, :set_public, :destroys, + :join_exercise_banks, :publish_modal, :publish, :end_modal, :end_exercise] #需要有课堂id参数的 + before_action :get_exercise, except: [:index, :new, :create, :my_exercises, :public_exercises, :set_public, :destroys, + :join_exercise_banks, :publish_modal, :publish, :end_modal, :end_exercise] before_action :user_course_identity - before_action :is_course_teacher,except: [:index,:start_answer,:exercise_setting,:commit_exercise,:exercise_lists,:review_exercise, - :exercise_result,:common_header,:cancel_exercise,:begin_commit] - before_action :get_left_banner_id,only:[:common_header,:start_answer,:review_exercise,:index,:new,:edit] - before_action :validates_exercise_params,only: [:create,:update] - before_action :get_exercise_question_counts,only: [:show,:edit,:start_answer,:review_exercise,:blank_exercise,:export_exercise] - before_action :validate_publish_time,only: [:commit_setting] #提交设置时,需判断时间是否符合 - before_action :check_course_public,only: [:set_public] - before_action :check_user_on_answer,only: [:show,:start_answer,:exercise_lists] #判断当前用户在试卷的权限/老师是否属于分班的权限 - before_action :only_student_in,only: [:start_answer] - before_action :check_user_id_start_answer,only: [:start_answer,:review_exercise] + before_action :is_course_teacher, except: [:index, :start_answer, :exercise_setting, :commit_exercise, :exercise_lists, :review_exercise, + :exercise_result, :common_header, :cancel_exercise, :begin_commit] + before_action :get_left_banner_id, only: [:common_header, :start_answer, :review_exercise, :index, :new, :edit] + before_action :validates_exercise_params, only: [:create, :update] + before_action :get_exercise_question_counts, only: [:show, :edit, :start_answer, :review_exercise, :blank_exercise, :export_exercise] + before_action :validate_publish_time, only: [:commit_setting] #提交设置时,需判断时间是否符合 + before_action :check_course_public, only: [:set_public] + before_action :check_user_on_answer, only: [:show, :start_answer, :exercise_lists] #判断当前用户在试卷的权限/老师是否属于分班的权限 + before_action :only_student_in, only: [:start_answer] + before_action :check_user_id_start_answer, only: [:start_answer, :review_exercise] # before_action :commit_user_exercise,only: [:start_answer,:exercise_lists,:review_exercise] #已有定时的任务 - before_action :check_exercise_time,only: [:commit_exercise] #提交试卷时,判断时间是否超过 - before_action :check_exercise_status,only: [:redo_modal,:redo_exercise] + before_action :check_exercise_time, only: [:commit_exercise] #提交试卷时,判断时间是否超过 + before_action :check_exercise_status, only: [:redo_modal, :redo_exercise] before_action :check_exercise_is_end, only: [:review_exercise] - before_action :check_exercise_public,only: [:exercise_result] #试卷是否为公开 - before_action :commit_shixun_present,only: [:commit_shixun] + before_action :check_exercise_public, only: [:exercise_result] #试卷是否为公开 + before_action :commit_shixun_present, only: [:commit_shixun] include ExportHelper include ExercisesHelper @@ -37,28 +37,28 @@ class ExercisesController < ApplicationController begin # 按发布时间或创建时间排序 @exercises_all = @course.exercises - member_show_exercises = @exercises_all.is_exercise_published #已发布的或已截止的试卷 + member_show_exercises = @exercises_all.is_exercise_published #已发布的或已截止的试卷 @current_user_ = current_user # 课堂的学生人数 @course_all_members = @course.students #当前课堂的全部学生 - @current_student = @course_all_members.course_find_by_ids("user_id",current_user.id) #当前用户是否为课堂的学生 + @current_student = @course_all_members.course_find_by_ids("user_id", current_user.id) #当前用户是否为课堂的学生 # exercises的不同用户群体的显示 - if @user_course_identity < Course::STUDENT # @is_teacher_or 1为老师/管理员/助教 + if @user_course_identity < Course::STUDENT # @is_teacher_or 1为老师/管理员/助教 @is_teacher_or = 1 - @exercises = @exercises_all #老师能看到全部的试卷,不管是已发布的/未发布的/已截止的/统一设置的/私有设置的(看到内容不同) - elsif @user_course_identity == Course::STUDENT # 2为课堂成员,能看到统一设置的和自己班级的 + @exercises = @exercises_all #老师能看到全部的试卷,不管是已发布的/未发布的/已截止的/统一设置的/私有设置的(看到内容不同) + elsif @user_course_identity == Course::STUDENT # 2为课堂成员,能看到统一设置的和自己班级的 @is_teacher_or = 2 - @member_group_id = @current_student.first.try(:course_group_id).to_i # 成员的分班id,默认为0 - if @member_group_id == 0 #表示是课堂的未分班成员,只能查看统一设置的试卷(已发布的/已截止的) + @member_group_id = @current_student.first.try(:course_group_id).to_i # 成员的分班id,默认为0 + if @member_group_id == 0 #表示是课堂的未分班成员,只能查看统一设置的试卷(已发布的/已截止的) @exercises = member_show_exercises.exists? ? member_show_exercises.unified_setting : [] - else #已分班级的成员,可以查看统一设置和单独设置(试卷是发布在该班级)试卷 + else #已分班级的成员,可以查看统一设置和单独设置(试卷是发布在该班级)试卷 # 已发布 当前用户班级分组的 试卷id publish_exercise_ids = @course.exercise_group_settings.exercise_group_published.where("course_group_id = #{@member_group_id}").pluck(:exercise_id) @exercises = member_show_exercises.unified_setting.or(member_show_exercises.where(id: publish_exercise_ids)) end - else #用户未登陆或不是该课堂成员,仅显示统一设置的(已发布的/已截止的),如有公开,则不显示锁,不公开,则显示锁 + else #用户未登陆或不是该课堂成员,仅显示统一设置的(已发布的/已截止的),如有公开,则不显示锁,不公开,则显示锁 @is_teacher_or = 0 @exercises = member_show_exercises.unified_setting end @@ -75,7 +75,7 @@ class ExercisesController < ApplicationController ex_setting_ids = @course.exercise_group_settings.where("course_group_id = #{@member_group_id}").exercise_group_not_published.pluck(:exercise_id) when 2 ex_setting_ids = @course.exercise_group_settings.where("course_group_id = #{@member_group_id}") - .where("publish_time is not null and publish_time <= ? and end_time > ?",Time.now,Time.now).pluck(:exercise_id) + .where("publish_time is not null and publish_time <= ? and end_time > ?", Time.now, Time.now).pluck(:exercise_id) when 3 ex_setting_ids = @course.exercise_group_settings.where("course_group_id = #{@member_group_id}").exercise_group_ended.pluck(:exercise_id) end @@ -90,11 +90,11 @@ class ExercisesController < ApplicationController @exercises = @exercises.exercise_search(search_type) end - @exercises_select_count = @exercises.size # 全部页面,需返回 - @exercises = @exercises.distinct.order( "IF(ISNULL(publish_time),0,1), publish_time DESC,created_at DESC") #出现错误 + @exercises_select_count = @exercises.size # 全部页面,需返回 + @exercises = @exercises.distinct.order("IF(ISNULL(publish_time),0,1), publish_time DESC,created_at DESC") #出现错误 # 分页 - @page = params[:page] || 1 + @page = params[:page] || 1 @limit = params[:limit] || 15 @exercises = @exercises.page(@page).per(@limit) @exercises = @exercises&.includes(:published_settings) @@ -102,10 +102,10 @@ class ExercisesController < ApplicationController @exercises = [] end - @course_all_members_count = @course_all_members.size #当前课堂的学生数 - @exercises_count = @exercises_all.size # 全部页面,需返回 + @course_all_members_count = @course_all_members.size #当前课堂的学生数 + @exercises_count = @exercises_all.size # 全部页面,需返回 @exercises_unpublish_counts = @exercises_all.exercise_by_status(1).size #未发布的试卷数 - @exercises_published_counts = @exercises_count - @exercises_unpublish_counts # 已发布的试卷数,包含已截止的 + @exercises_published_counts = @exercises_count - @exercises_unpublish_counts # 已发布的试卷数,包含已截止的 rescue Exception => e uid_logger_error(e.message) @@ -128,108 +128,77 @@ class ExercisesController < ApplicationController def create ActiveRecord::Base.transaction do - begin - ex_name = params[:exercise_name] - ex_desc = params[:exercise_description] - exercise_options = { - :exercise_name => ex_name, - :exercise_description => ex_desc, - :user_id => current_user.id, - :course_id => @course.id, - :time => -1, - :exercise_status => 1 - } - @exercise = Exercise.create!(exercise_options) - rescue Exception => e - uid_logger_error(e.message) - tip_exception("试卷创建失败!") - raise ActiveRecord::Rollback - end + ex_name = params[:exercise_name] + ex_desc = params[:exercise_description] + exercise_options = { + :exercise_name => ex_name, + :exercise_description => ex_desc, + :user_id => current_user.id, + :course_id => @course.id, + :time => -1, + :exercise_status => 1 + } + @exercise = Exercise.create!(exercise_options) end end #试卷的内容,及试题/答案的内容编辑 def edit ActiveRecord::Base.transaction do - begin - @exercise_questions = @exercise.exercise_questions.order("question_number ASC") - rescue Exception => e - uid_logger_error(e.message) - tip_exception("试卷创建失败!") - raise ActiveRecord::Rollback - end + @exercise_questions = @exercise.exercise_questions.order("question_number ASC") end end def update ActiveRecord::Base.transaction do - begin - ex_name = params[:exercise_name] - ex_desc = params[:exercise_description] - exercise_options = { - :exercise_name => ex_name, - :exercise_description => ex_desc, - } - @exercise.update!(exercise_options) - normal_status(0,"试卷更新成功!") - rescue Exception => e - uid_logger_error(e.message) - tip_exception("试卷创建失败!") - raise ActiveRecord::Rollback - end + ex_name = params[:exercise_name] + ex_desc = params[:exercise_description] + exercise_options = { + :exercise_name => ex_name, + :exercise_description => ex_desc, + } + @exercise.update!(exercise_options) + normal_status(0, "试卷更新成功!") end end def show ActiveRecord::Base.transaction do - begin - if @user_course_identity < Course::STUDENT - @is_teacher_or = 1 #为老师/助教/管理员 - else - @is_teacher_or = 0 #为学生 - end - @exercise_questions = @exercise.exercise_questions&.includes(:exercise_choices,:exercise_shixun_challenges,:exercise_standard_answers).order("question_number ASC") - rescue Exception => e - uid_logger_error(e.message) - tip_exception("试卷创建失败!") - raise ActiveRecord::Rollback + if @user_course_identity < Course::STUDENT + @is_teacher_or = 1 #为老师/助教/管理员 + else + @is_teacher_or = 0 #为学生 end + @exercise_questions = @exercise.exercise_questions&.includes(:exercise_choices, :exercise_shixun_challenges, :exercise_standard_answers).order("question_number ASC") end end #试卷的公用头部 def common_header ActiveRecord::Base.transaction do - begin - @user_left_time = nil - if @user_course_identity > Course::ASSISTANT_PROFESSOR - @is_teacher_or = 0 - @user_exercise_answer = @exercise.check_user_answer_status(current_user) - @user_commit_counts = 0 - @user_left_time = get_exercise_left_time(@exercise,current_user) - else - @is_teacher_or = 1 - @user_exercise_answer = 3 #教师页面 - @user_commit_counts = @exercise.exercise_users.where(commit_status:1).size #已提交的用户数 - end - @ex_status = @exercise.get_exercise_status(current_user) + @user_left_time = nil + if @user_course_identity > Course::ASSISTANT_PROFESSOR + @is_teacher_or = 0 + @user_exercise_answer = @exercise.check_user_answer_status(current_user) + @user_commit_counts = 0 + @user_left_time = get_exercise_left_time(@exercise, current_user) + else + @is_teacher_or = 1 + @user_exercise_answer = 3 #教师页面 + @user_commit_counts = @exercise.exercise_users.where(commit_status: 1).size #已提交的用户数 + end + @ex_status = @exercise.get_exercise_status(current_user) - exercise_id_array = [@exercise.id] - @exercise_publish_count = get_user_permission_course(exercise_id_array,Exercise::PUBLISHED).size #是否存在已发布的 - @exercise_unpublish_count = get_user_permission_course(exercise_id_array,Exercise::UNPUBLISHED).size #是否存在未发布的 + exercise_id_array = [@exercise.id] + @exercise_publish_count = get_user_permission_course(exercise_id_array, Exercise::PUBLISHED).size #是否存在已发布的 + @exercise_unpublish_count = get_user_permission_course(exercise_id_array, Exercise::UNPUBLISHED).size #是否存在未发布的 - if (@exercise_publish_count == 0) && (@exercise_unpublish_count == 0) #即表示没有分班 - if @ex_status == Exercise::UNPUBLISHED - @exercise_unpublish_count = 1 #试卷未发布,且课堂没有分班的时候 - elsif @ex_status == Exercise::PUBLISHED - @exercise_publish_count = 1 #试卷未发布,且课堂没有分班的时候 - end + if (@exercise_publish_count == 0) && (@exercise_unpublish_count == 0) #即表示没有分班 + if @ex_status == Exercise::UNPUBLISHED + @exercise_unpublish_count = 1 #试卷未发布,且课堂没有分班的时候 + elsif @ex_status == Exercise::PUBLISHED + @exercise_publish_count = 1 #试卷未发布,且课堂没有分班的时候 end - - rescue Exception => e - uid_logger_error(e.message) - tip_exception("没有权限") - raise ActiveRecord::Rollback end end end @@ -237,381 +206,338 @@ class ExercisesController < ApplicationController #实训题目的选用 def choose_shixun ActiveRecord::Base.transaction do - begin - search = params[:search] - if @user_course_identity > Course::ADMIN #当不为管理员的时候 - user_school_id = current_user.school_id #当前用户的学校id - if user_school_id.present? - none_shixun_ids = ShixunSchool.where("school_id != #{user_school_id}").pluck(:shixun_id) - @publish_shixuns = Shixun.where.not(id: none_shixun_ids).unhidden - end - else - @publish_shixuns = Shixun.unhidden - end - if search.present? - @publish_shixuns = @publish_shixuns.search_by_name(search) + search = params[:search] + if @user_course_identity > Course::ADMIN #当不为管理员的时候 + user_school_id = current_user.school_id #当前用户的学校id + if user_school_id.present? + none_shixun_ids = ShixunSchool.where("school_id != #{user_school_id}").pluck(:shixun_id) + @publish_shixuns = Shixun.where.not(id: none_shixun_ids).unhidden end + else + @publish_shixuns = Shixun.unhidden + end + if search.present? + @publish_shixuns = @publish_shixuns.search_by_name(search) + end - @shixuns = @publish_shixuns.joins(:challenges).where("challenges.st != 0").distinct - # 全部页面,需返回 - @shixuns_count = @shixuns.count + @shixuns = @publish_shixuns.joins(:challenges).where("challenges.st != 0").distinct + # 全部页面,需返回 + @shixuns_count = @shixuns.count - # 分页 - @page = params[:page] || 1 - @limit = params[:limit] || 8 + # 分页 + @page = params[:page] || 1 + @limit = params[:limit] || 8 - @shixuns = @shixuns.page(@page).per(@limit) - rescue Exception => e - uid_logger_error(e.message) - tip_exception("实训选择失败!") - end + @shixuns = @shixuns.page(@page).per(@limit) end end #确认实训的选择 def commit_shixun ActiveRecord::Base.transaction do - begin - @shixun_challenges = @shixun.challenges - @shixun_challenges_count = @shixun_challenges.size - rescue Exception => e - uid_logger_error(e.message) - tip_exception("页面调用失败!") - raise ActiveRecord::Rollback - end + @shixun_challenges = @shixun.challenges + @shixun_challenges_count = @shixun_challenges.size end end # 首页批量或单独删除 def destroys ActiveRecord::Base.transaction do - begin - check_ids = Exercise.where(id: params[:check_ids]) - check_ids.destroy_all - normal_status(0, "试卷已删除成功!") - rescue Exception => e - uid_logger_error(e.message) - tip_exception("试卷删除失败!") - raise ActiveRecord::Rollback - end + check_ids = Exercise.where(id: params[:check_ids]) + check_ids.destroy_all + normal_status(0, "试卷已删除成功!") end end # 设为公开 def set_public ActiveRecord::Base.transaction do - begin - check_ids = Exercise.where(id: params[:check_ids]) - check_ids.each do |exercise| - exercise.update!(is_public: true) - end - normal_status(0, "试卷已设为公开!") - rescue Exception => e - uid_logger_error(e.message) - tip_exception("试卷设为公开失败!") - raise ActiveRecord::Rollback + check_ids = Exercise.where(id: params[:check_ids]) + check_ids.each do |exercise| + exercise.update!(is_public: true) end + normal_status(0, "试卷已设为公开!") end end ## 加入题库 def join_exercise_banks ActiveRecord::Base.transaction do - begin - check_ids = Exercise.where(id: params[:check_ids]) - check_ids.each do |exercise| - current_ex_bank = current_user.exercise_banks.find_by_container(exercise.id,"Exercise")&.first - if current_ex_bank.present? #当前用户的选择试卷是否已加入习题库,存在则更新习题库和问题库,否则新建习题库和问题库 - ex_params = { - :name => exercise.exercise_name, - :description => exercise.exercise_description, - :course_list_id => exercise.course.try(:course_list_id) - } - current_ex_bank.update!(ex_params) - # question_bank = QuestionBank.ques_by_container(current_ex_bank.id,current_ex_bank.container_type).first #该习题库是否存在于问题库里 - # ques_params = { - # :name => current_ex_bank.name, - # :course_list_id => current_ex_bank.course_list_id - # } - # question_bank.update_attributes(ques_params) if question_bank.present? - current_ex_bank.exercise_bank_questions.destroy_all # 更新后,习题库的问题全部删除,后续重新再建 - else - ex_params = { - :name => exercise.exercise_name, - :description => exercise.exercise_description, - :user_id => current_user.id, - :is_public => 0, - :course_list_id => exercise.course.try(:course_list_id), - :container_id => exercise.id, - :container_type => "Exercise", - :quotes => 1 - } - current_ex_bank= ExerciseBank.new ex_params - current_ex_bank.save! #如果习题库保存成功,则会创建问题库question_bank - # if current_ex_bank.save - # ques_params = { - # :name => current_ex_bank.name, - # :container_id => current_ex_bank.id, - # :container_type => current_ex_bank.container_type, - # :quotes => current_ex_bank.quotes, - # :user_id => current_ex_bank.user_id, - # :is_public => current_ex_bank.is_public, - # :course_list_id => current_ex_bank.course_list_id - # } - # question_bank = QuestionBank.new ques_params - # question_bank.save - # end - exercise.update!(exercise_bank_id: current_ex_bank.id) - end - # 试卷的问题的输入 - exercise.exercise_questions.each do |q| - option = { - :question_title => q.question_title, - :question_type => q.question_type, - :question_number => q.question_number, - :question_score => q.question_score, + check_ids = Exercise.where(id: params[:check_ids]) + check_ids.each do |exercise| + current_ex_bank = current_user.exercise_banks.find_by_container(exercise.id, "Exercise")&.first + if current_ex_bank.present? #当前用户的选择试卷是否已加入习题库,存在则更新习题库和问题库,否则新建习题库和问题库 + ex_params = { + :name => exercise.exercise_name, + :description => exercise.exercise_description, + :course_list_id => exercise.course.try(:course_list_id) + } + current_ex_bank.update!(ex_params) + # question_bank = QuestionBank.ques_by_container(current_ex_bank.id,current_ex_bank.container_type).first #该习题库是否存在于问题库里 + # ques_params = { + # :name => current_ex_bank.name, + # :course_list_id => current_ex_bank.course_list_id + # } + # question_bank.update_attributes(ques_params) if question_bank.present? + current_ex_bank.exercise_bank_questions.destroy_all # 更新后,习题库的问题全部删除,后续重新再建 + else + ex_params = { + :name => exercise.exercise_name, + :description => exercise.exercise_description, + :user_id => current_user.id, + :is_public => 0, + :course_list_id => exercise.course.try(:course_list_id), + :container_id => exercise.id, + :container_type => "Exercise", + :quotes => 1 + } + current_ex_bank = ExerciseBank.new ex_params + current_ex_bank.save! #如果习题库保存成功,则会创建问题库question_bank + # if current_ex_bank.save + # ques_params = { + # :name => current_ex_bank.name, + # :container_id => current_ex_bank.id, + # :container_type => current_ex_bank.container_type, + # :quotes => current_ex_bank.quotes, + # :user_id => current_ex_bank.user_id, + # :is_public => current_ex_bank.is_public, + # :course_list_id => current_ex_bank.course_list_id + # } + # question_bank = QuestionBank.new ques_params + # question_bank.save + # end + exercise.update!(exercise_bank_id: current_ex_bank.id) + end + # 试卷的问题的输入 + exercise.exercise_questions.each do |q| + option = { + :question_title => q.question_title, + :question_type => q.question_type, + :question_number => q.question_number, + :question_score => q.question_score, + :shixun_id => q.shixun_id, + :shixun_name => q.shixun_name + } + exercise_bank_question = current_ex_bank.exercise_bank_questions.new option + exercise_bank_question.save! + ## 试卷选项的输入 + if q.question_type != Exercise::PRACTICAL #不为实训题时,试卷选项加入试题答案库 + ex_choices = q.exercise_choices + ex_standard = q.exercise_standard_answers + ex_choices.each do |c| + choice_option = { + :choice_position => c.choice_position, + :choice_text => c.choice_text + } + ex_bank_choice = exercise_bank_question.exercise_bank_choices.new choice_option + ex_bank_choice.save! + end + ex_standard.each do |s| + ex_stand = { + :exercise_bank_choice_id => s.exercise_choice_id, + :answer_text => s.answer_text + } + ex_stand_bank = exercise_bank_question.exercise_bank_standard_answers.new ex_stand + ex_stand_bank.save! + end + else #当为实训题时 + shixun_challenges = q.exercise_shixun_challenges + shixun_challenges.each do |c| + challenge_option = { + :position => c.position, + :challenge_id => c.challenge_id, :shixun_id => q.shixun_id, - :shixun_name => q.shixun_name - } - exercise_bank_question = current_ex_bank.exercise_bank_questions.new option - exercise_bank_question.save! - ## 试卷选项的输入 - if q.question_type != Exercise::PRACTICAL #不为实训题时,试卷选项加入试题答案库 - ex_choices = q.exercise_choices - ex_standard = q.exercise_standard_answers - ex_choices.each do |c| - choice_option = { - :choice_position => c.choice_position, - :choice_text =>c.choice_text - } - ex_bank_choice = exercise_bank_question.exercise_bank_choices.new choice_option - ex_bank_choice.save! - end - ex_standard.each do |s| - ex_stand = { - :exercise_bank_choice_id => s.exercise_choice_id, - :answer_text => s.answer_text - } - ex_stand_bank = exercise_bank_question.exercise_bank_standard_answers.new ex_stand - ex_stand_bank.save! - end - else #当为实训题时 - shixun_challenges = q.exercise_shixun_challenges - shixun_challenges.each do |c| - challenge_option = { - :position => c.position, - :challenge_id => c.challenge_id, - :shixun_id => q.shixun_id, - :question_score => c.question_score - } - shixun_challenge_bank = exercise_bank_question.exercise_bank_shixun_challenges.new challenge_option - shixun_challenge_bank.save! - end + :question_score => c.question_score + } + shixun_challenge_bank = exercise_bank_question.exercise_bank_shixun_challenges.new challenge_option + shixun_challenge_bank.save! end end - current_ex_bank.save! end - normal_status(0, "题库更新成功!") - rescue Exception => e - uid_logger_error(e.message) - tip_exception("题库更新失败!") - raise ActiveRecord::Rollback + current_ex_bank.save! end + normal_status(0, "题库更新成功!") end end #试卷的设置页面 def exercise_setting ActiveRecord::Base.transaction do - begin - @user_permission = 2 - @user_course_groups = @course.teacher_group(current_user.id) #当前老师的分班 - @being_setting_course_ids = @exercise.common_published_ids(current_user.id) #当前用户已发布的班级的id - @user_published_setting = @exercise.exercise_group_settings - .find_in_exercise_group("course_group_id",@being_setting_course_ids) #当前用户已发布班级的试卷设置 - exercise_ids = [@exercise.id] - @exercise_publish_count = get_user_permission_course(exercise_ids,Exercise::PUBLISHED).count #判断当前用户是否有试卷已发布的分班,用于显示立即截止/撤销发布 - @exercise_unpublish_count = get_user_permission_course(exercise_ids,Exercise::UNPUBLISHED).count #判断当前用户是否有试卷未发布的分班,用户显示立即发布 - @exercise_users_count = @exercise.exercise_users.commit_exercise_by_status(1).count #判断当前试卷是否有已提交的 - # ## 需添加发送消息的接口,稍后添加 - rescue Exception => e - uid_logger_error(e.message) - tip_exception("页面调用失败!") - raise ActiveRecord::Rollback - end + @user_permission = 2 + @user_course_groups = @course.teacher_group(current_user.id) #当前老师的分班 + @being_setting_course_ids = @exercise.common_published_ids(current_user.id) #当前用户已发布的班级的id + @user_published_setting = @exercise.exercise_group_settings + .find_in_exercise_group("course_group_id", @being_setting_course_ids) #当前用户已发布班级的试卷设置 + exercise_ids = [@exercise.id] + @exercise_publish_count = get_user_permission_course(exercise_ids, Exercise::PUBLISHED).count #判断当前用户是否有试卷已发布的分班,用于显示立即截止/撤销发布 + @exercise_unpublish_count = get_user_permission_course(exercise_ids, Exercise::UNPUBLISHED).count #判断当前用户是否有试卷未发布的分班,用户显示立即发布 + @exercise_users_count = @exercise.exercise_users.commit_exercise_by_status(1).count #判断当前试卷是否有已提交的 + # ## 需添加发送消息的接口,稍后添加 end end #试卷的提交设置 def commit_setting ActiveRecord::Base.transaction do - begin - error_count = 0 # 判断循环里是否有已发布/已截止的,且时间更改了的分班。 - # course_group_ids = @course.teacher_course_group_ids(current_user.id) #当前老师的班级id数组 - course_group_ids = @course.charge_group_ids(current_user) #当前老师的班级id数组 + error_count = 0 # 判断循环里是否有已发布/已截止的,且时间更改了的分班。 + # course_group_ids = @course.teacher_course_group_ids(current_user.id) #当前老师的班级id数组 + course_group_ids = @course.charge_group_ids(current_user) #当前老师的班级id数组 - exercise_status = @exercise.get_exercise_status(current_user) + exercise_status = @exercise.get_exercise_status(current_user) - if exercise_status == Exercise::UNPUBLISHED && course_group_ids.size > 0 # 试卷未发布,且老师的分班大于1 ,才可以修改统一设置,否则按试卷默认的来处理 - unified_setting = params[:unified_setting] + if exercise_status == Exercise::UNPUBLISHED && course_group_ids.size > 0 # 试卷未发布,且老师的分班大于1 ,才可以修改统一设置,否则按试卷默认的来处理 + unified_setting = params[:unified_setting] + else + unified_setting = @exercise.unified_setting + end + + show_statistic = params[:show_statistic] ? true : false + exercise_time = params[:time].blank? ? -1 : params[:time] + question_random = params[:question_random] ? true : false #问题是否随机,0为不随机,1为随机 + choice_random = params[:choice_random] ? true : false + score_open = params[:score_open] ? true : false #分数是否公开 + answer_open = params[:answer_open] ? true : false #答案是否公开 + + # 统一设置或者分班为0,则更新试卷,并删除试卷分组 + if unified_setting || (course_group_ids.size == 0) + tip_exception("发布时间不能为空") if params[:publish_time].blank? + tip_exception("截止时间不能为空") if params[:end_time].blank? + tip_exception("截止时间不能早于发布时间") if params[:publish_time].to_time > params[:end_time].to_time + tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && params[:end_time].to_time > @course.end_date.end_of_day + + params_publish_time = params[:publish_time].to_time + params_end_time = params[:end_time].to_time + + if (exercise_status != Exercise::UNPUBLISHED) && (@exercise.publish_time != params_publish_time) + normal_status(-1, "已发布/已截止,不允许修改发布时间") + elsif params_publish_time.present? && params_end_time.present? && params_end_time < params_publish_time + normal_status(-1, "截止时间不能小于发布时间") else - unified_setting = @exercise.unified_setting - end - - show_statistic = params[:show_statistic] ? true :false - exercise_time = params[:time].blank? ? -1 : params[:time] - question_random = params[:question_random] ? true :false #问题是否随机,0为不随机,1为随机 - choice_random = params[:choice_random] ? true :false - score_open = params[:score_open] ? true : false #分数是否公开 - answer_open = params[:answer_open] ? true : false #答案是否公开 - - # 统一设置或者分班为0,则更新试卷,并删除试卷分组 - if unified_setting || (course_group_ids.size == 0) - tip_exception("发布时间不能为空") if params[:publish_time].blank? - tip_exception("截止时间不能为空") if params[:end_time].blank? - tip_exception("截止时间不能早于发布时间") if params[:publish_time].to_time > params[:end_time].to_time - tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if - @course.end_date.present? && params[:end_time].to_time > @course.end_date.end_of_day - - params_publish_time = params[:publish_time].to_time - params_end_time = params[:end_time].to_time - - if (exercise_status != Exercise::UNPUBLISHED) && (@exercise.publish_time != params_publish_time) - normal_status(-1,"已发布/已截止,不允许修改发布时间") - elsif params_publish_time.present? && params_end_time.present? && params_end_time < params_publish_time - normal_status(-1,"截止时间不能小于发布时间") - else - #发布时间小于当前时间,则试卷显示为未发布,当截止时间大于当前时间,则显示为已截止 - exercise_status_n = set_exercise_status(params_publish_time,params_end_time) - exercise_params = { - :unified_setting => unified_setting, - :show_statistic => show_statistic, - :time => exercise_time, - :question_random => question_random, - :choice_random => choice_random, - :score_open => score_open, - :answer_open => answer_open, - :exercise_status => exercise_status_n, - :publish_time => params_publish_time, - :end_time => params_end_time - } - @exercise.update!(exercise_params) - @exercise.exercise_group_settings.destroy_all - normal_status(0, "试卷设置成功!") + #发布时间小于当前时间,则试卷显示为未发布,当截止时间大于当前时间,则显示为已截止 + exercise_status_n = set_exercise_status(params_publish_time, params_end_time) + exercise_params = { + :unified_setting => unified_setting, + :show_statistic => show_statistic, + :time => exercise_time, + :question_random => question_random, + :choice_random => choice_random, + :score_open => score_open, + :answer_open => answer_open, + :exercise_status => exercise_status_n, + :publish_time => params_publish_time, + :end_time => params_end_time + } + @exercise.update!(exercise_params) + @exercise.exercise_group_settings.destroy_all + normal_status(0, "试卷设置成功!") + end + else + params_times = params[:publish_time_groups] #分班返回的json数组{"publish_time_groups":[{"course_group_id":"1","publish_time":"xx","end_time":"xxx"}]} + exercise_groups = @exercise.exercise_group_settings.find_in_exercise_group("course_id", @course.id) #试卷的全部分班信息 + exercise_groups_ids = exercise_groups.pluck(:course_group_id) #问卷的全部分班id + total_common = params_times.map {|k| k[:course_group_id]}.sum.uniq #传入的所有分组的分班id + total_common_group = exercise_groups_ids & total_common #传入的分班与问卷已存在的分班的交集 + old_exercise_groups = exercise_groups_ids - total_common_group #后来传入的分班里,没有了的班级,即需要删除 + + params_times.each do |t| + tip_exception("发布时间不能为空") if t[:publish_time].blank? + tip_exception("截止时间不能为空") if t[:end_time].blank? + tip_exception("截止时间不能早于发布时间") if t[:publish_time].to_time > t[:end_time].to_time + tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && t[:end_time].to_time > @course.end_date.end_of_day + + course_id = t[:course_group_id] + exercise_publish_time = t[:publish_time].to_time + exercise_end_time = t[:end_time].to_time + + exercise_group = exercise_groups.find_in_exercise_group("course_group_id", course_id) #判断该分班是否存在 + if exercise_group.present? && (exercise_group.first.publish_time < Time.now) && (exercise_publish_time != exercise_group.first.publish_time) + error_count += 1 end - else - params_times = params[:publish_time_groups] #分班返回的json数组{"publish_time_groups":[{"course_group_id":"1","publish_time":"xx","end_time":"xxx"}]} - exercise_groups = @exercise.exercise_group_settings.find_in_exercise_group("course_id",@course.id) #试卷的全部分班信息 - exercise_groups_ids = exercise_groups.pluck(:course_group_id) #问卷的全部分班id - total_common = params_times.map{|k| k[:course_group_id]}.sum.uniq #传入的所有分组的分班id - total_common_group = exercise_groups_ids & total_common #传入的分班与问卷已存在的分班的交集 - old_exercise_groups = exercise_groups_ids - total_common_group #后来传入的分班里,没有了的班级,即需要删除 - - params_times.each do |t| - tip_exception("发布时间不能为空") if t[:publish_time].blank? - tip_exception("截止时间不能为空") if t[:end_time].blank? - tip_exception("截止时间不能早于发布时间") if t[:publish_time].to_time > t[:end_time].to_time - tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if - @course.end_date.present? && t[:end_time].to_time > @course.end_date.end_of_day - - course_id = t[:course_group_id] - exercise_publish_time = t[:publish_time].to_time - exercise_end_time = t[:end_time].to_time - - exercise_group = exercise_groups.find_in_exercise_group("course_group_id",course_id) #判断该分班是否存在 - if exercise_group.present? && (exercise_group.first.publish_time < Time.now) && (exercise_publish_time != exercise_group.first.publish_time) - error_count += 1 - end - if exercise_group.present? && (exercise_group.first.publish_time < Time.now && exercise_group.first.end_time > Time.now) && (exercise_end_time < Time.now) - error_count += 1 - end - if error_count == 0 - common_group = exercise_groups_ids & course_id #传入的班级与问卷已存在的班级的交集,即表示已有分班的 - new_group_ids = course_id - common_group #新传入的班级id - if common_group.count > 0 #判断试卷的分班设置是否存在,存在则更新,负责则新建 - exercise_group_sets = exercise_groups.find_in_exercise_group("course_group_id",common_group) - exercise_group_sets.each do |the_group_setting| + if exercise_group.present? && (exercise_group.first.publish_time < Time.now && exercise_group.first.end_time > Time.now) && (exercise_end_time < Time.now) + error_count += 1 + end + if error_count == 0 + common_group = exercise_groups_ids & course_id #传入的班级与问卷已存在的班级的交集,即表示已有分班的 + new_group_ids = course_id - common_group #新传入的班级id + if common_group.count > 0 #判断试卷的分班设置是否存在,存在则更新,负责则新建 + exercise_group_sets = exercise_groups.find_in_exercise_group("course_group_id", common_group) + exercise_group_sets.each do |the_group_setting| + ex_group_params = { + :publish_time => exercise_publish_time, + :end_time => exercise_end_time + } + + the_group_setting_status = set_exercise_status(the_group_setting.publish_time, the_group_setting.end_time) + if the_group_setting_status == 2 + ex_group_params = { + :publish_time => the_group_setting.publish_time, + :end_time => exercise_end_time < Time.now ? the_group_setting.end_time : exercise_end_time + } + elsif the_group_setting_status == 3 ex_group_params = { - :publish_time => exercise_publish_time, + :publish_time => the_group_setting.publish_time, :end_time => exercise_end_time } - - the_group_setting_status = set_exercise_status(the_group_setting.publish_time,the_group_setting.end_time) - if the_group_setting_status == 2 - ex_group_params = { - :publish_time => the_group_setting.publish_time, - :end_time => exercise_end_time < Time.now ? the_group_setting.end_time : exercise_end_time - } - elsif the_group_setting_status == 3 - ex_group_params = { - :publish_time => the_group_setting.publish_time, - :end_time => exercise_end_time - } - end - the_group_setting.update!(ex_group_params) end + the_group_setting.update!(ex_group_params) end - if new_group_ids.size > 0 - new_group_ids.each do |c| - exercise_group_params = { - :exercise_id => @exercise.id, - :course_group_id => c, - :course_id => @course.id, - :publish_time => exercise_publish_time, - :end_time => exercise_end_time - } - new_exercise_group = ExerciseGroupSetting.new(exercise_group_params) - new_exercise_group.save! - end + end + if new_group_ids.size > 0 + new_group_ids.each do |c| + exercise_group_params = { + :exercise_id => @exercise.id, + :course_group_id => c, + :course_id => @course.id, + :publish_time => exercise_publish_time, + :end_time => exercise_end_time + } + new_exercise_group = ExerciseGroupSetting.new(exercise_group_params) + new_exercise_group.save! end end end + end - if error_count > 0 - error_count == 0 - normal_status(-1,"试卷发布/截止时间不能小于当前时间") - else - # 未发布的分班设置才能删除 - if old_exercise_groups.size > 0 - old_all_ex_groups = exercise_groups.find_in_exercise_group("course_group_id",old_exercise_groups).exercise_group_not_published - old_all_ex_groups.destroy_all - end - #试卷更新为exercise_group_setting的发布时间最小,截止时间最大 - e_time_present = exercise_groups.end_time_no_null.map(&:end_time) - p_time_present = exercise_groups.publish_time_no_null.map(&:publish_time) - e_time = e_time_present.size > 0 ? e_time_present.max : nil - p_time = p_time_present.size > 0 ? p_time_present.min : nil + if error_count > 0 + error_count == 0 + normal_status(-1, "试卷发布/截止时间不能小于当前时间") + else + # 未发布的分班设置才能删除 + if old_exercise_groups.size > 0 + old_all_ex_groups = exercise_groups.find_in_exercise_group("course_group_id", old_exercise_groups).exercise_group_not_published + old_all_ex_groups.destroy_all + end + #试卷更新为exercise_group_setting的发布时间最小,截止时间最大 + e_time_present = exercise_groups.end_time_no_null.map(&:end_time) + p_time_present = exercise_groups.publish_time_no_null.map(&:publish_time) + e_time = e_time_present.size > 0 ? e_time_present.max : nil + p_time = p_time_present.size > 0 ? p_time_present.min : nil + exercise_status = 1 + if p_time.nil? #发布时间为空,则表示问卷未发布 exercise_status = 1 - if p_time.nil? #发布时间为空,则表示问卷未发布 - exercise_status = 1 - elsif p_time.present? && e_time.present? - exercise_status = set_exercise_status(p_time,e_time) - end - exercise_params = { - :unified_setting => unified_setting, - :show_statistic => show_statistic, - :time => exercise_time, - :question_random => question_random, - :choice_random => choice_random, - :score_open => score_open, - :answer_open => answer_open, - :exercise_status => exercise_status, - :publish_time => p_time, - :end_time => e_time - } - @exercise.update!(exercise_params) - if @exercise.exercise_status == Exercise::PUBLISHED - if @exercise.course_acts.size == 0 - @exercise.course_acts << CourseActivity.new(:user_id => @exercise.user_id,:course_id => @exercise.course_id) - end + elsif p_time.present? && e_time.present? + exercise_status = set_exercise_status(p_time, e_time) + end + exercise_params = { + :unified_setting => unified_setting, + :show_statistic => show_statistic, + :time => exercise_time, + :question_random => question_random, + :choice_random => choice_random, + :score_open => score_open, + :answer_open => answer_open, + :exercise_status => exercise_status, + :publish_time => p_time, + :end_time => e_time + } + @exercise.update!(exercise_params) + if @exercise.exercise_status == Exercise::PUBLISHED + if @exercise.course_acts.size == 0 + @exercise.course_acts << CourseActivity.new(:user_id => @exercise.user_id, :course_id => @exercise.course_id) end - normal_status(0, "试卷设置成功!") end + normal_status(0, "试卷设置成功!") end - rescue Exception => e - uid_logger_error(e.message) - tip_exception(e.message) - raise ActiveRecord::Rollback end end end @@ -641,7 +567,7 @@ class ExercisesController < ApplicationController exercise_user.update!(score: score, subjective_score: subjective_score, objective_score: objective_score) else exercise_user.update!(start_at: start_at_time, end_at: Time.now, status: 1, commit_status: 1, score: score, - subjective_score: subjective_score, objective_score: objective_score, commit_method: 5) + subjective_score: subjective_score, objective_score: objective_score, commit_method: 5) end ExerciseUserScore.create!(exercise_id: @exercise.id, exercise_user_id: exercise_user.id, @@ -653,26 +579,20 @@ class ExercisesController < ApplicationController #我的题库 def my_exercises ActiveRecord::Base.transaction do - begin - ## 我的试卷题库 - @current_user_exercises = current_user.exercise_banks.find_by_c_type("Exercise") - if @current_user_exercises.present? + ## 我的试卷题库 + @current_user_exercises = current_user.exercise_banks.find_by_c_type("Exercise") + if @current_user_exercises.present? - if params[:search].present? - search_type = params[:search].to_s.strip - @current_user_exercises = @current_user_exercises.exercise_bank_search(search_type) - end - page = params[:page] || 1 - limit = params[:limit] || 15 - @my_exercises_count = @current_user_exercises.size - @current_user_exercises = @current_user_exercises.page(page).per(limit) - else - @current_user_exercises = [] + if params[:search].present? + search_type = params[:search].to_s.strip + @current_user_exercises = @current_user_exercises.exercise_bank_search(search_type) end - rescue Exception => e - uid_logger_error(e.message) - tip_exception("页面调用失败!") - raise ActiveRecord::Rollback + page = params[:page] || 1 + limit = params[:limit] || 15 + @my_exercises_count = @current_user_exercises.size + @current_user_exercises = @current_user_exercises.page(page).per(limit) + else + @current_user_exercises = [] end end end @@ -680,32 +600,26 @@ class ExercisesController < ApplicationController # 公共题库 def public_exercises ActiveRecord::Base.transaction do - begin - if current_user.is_certification_teacher - @user_certification = 1 #用户已通过认证 - @public_exercises = ExerciseBank.find_by_c_type("Exercise").public_exercises - if @public_exercises.present? - if params[:search].present? - search_type = params[:search].to_s.strip - @public_exercises = @public_exercises.exercise_bank_search(search_type) - end - page = params[:page] || 1 - limit = params[:limit] || 15 - @public_exercises_count = @public_exercises.size - @public_exercises = @public_exercises.page(page).per(limit) - else - @public_exercises_count = 0 - @public_exercises = [] + if current_user.is_certification_teacher + @user_certification = 1 #用户已通过认证 + @public_exercises = ExerciseBank.find_by_c_type("Exercise").public_exercises + if @public_exercises.present? + if params[:search].present? + search_type = params[:search].to_s.strip + @public_exercises = @public_exercises.exercise_bank_search(search_type) end + page = params[:page] || 1 + limit = params[:limit] || 15 + @public_exercises_count = @public_exercises.size + @public_exercises = @public_exercises.page(page).per(limit) else - @user_certification = 0 #用户未通过认证 @public_exercises_count = 0 @public_exercises = [] end - rescue Exception => e - uid_logger_error(e.message) - tip_exception("题库调用失败!") - raise ActiveRecord::Rollback + else + @user_certification = 0 #用户未通过认证 + @public_exercises_count = 0 + @public_exercises = [] end end end @@ -714,17 +628,11 @@ class ExercisesController < ApplicationController def publish_modal ActiveRecord::Base.transaction do - begin - exercise_ids = params[:check_ids] - if exercise_ids.count > 0 - @course_groups = get_user_permission_course(exercise_ids,1) - else - @course_groups = [] - end - rescue Exception => e - uid_logger_error(e.message) - tip_exception("没有权限") - raise ActiveRecord::Rollback + exercise_ids = params[:check_ids] + if exercise_ids.count > 0 + @course_groups = get_user_permission_course(exercise_ids, 1) + else + @course_groups = [] end end end @@ -744,109 +652,95 @@ class ExercisesController < ApplicationController if params[:detail].blank? tip_exception("缺少截止时间参数") if params[:end_time].blank? tip_exception("截止时间不能早于当前时间") if params[:end_time] <= strf_time(Time.now) - tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if - @course.end_date.present? && params[:end_time] > strf_time(@course.end_date.end_of_day) + tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && params[:end_time] > strf_time(@course.end_date.end_of_day) else - group_end_times = params[:group_end_times].reject(&:blank?).map{|time| time.to_time} + group_end_times = params[:group_end_times].reject(&:blank?).map {|time| time.to_time} tip_exception("缺少截止时间参数") if group_end_times.blank? tip_exception("截止时间和分班参数的个数不一致") if group_end_times.length != group_ids.length group_end_times.each do |time| tip_exception("分班截止时间不能早于当前时间") if time <= Time.now - tip_exception("分班截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if - @course.end_date.present? && time > @course.end_date.end_of_day + tip_exception("分班截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && time > @course.end_date.end_of_day end end ActiveRecord::Base.transaction do - begin - check_ids = Exercise.where(id: params[:check_ids]) - ex_end_time = params[:end_time].blank? ? Time.at(((1.month.since.to_i)/3600.0).ceil * 3600) : params[:end_time].to_time - check_ids.each do |exercise| - if exercise.present? - if exercise.unified_setting - ex_status = exercise.exercise_status #则为试卷的状态 + check_ids = Exercise.where(id: params[:check_ids]) + ex_end_time = params[:end_time].blank? ? Time.at(((1.month.since.to_i) / 3600.0).ceil * 3600) : params[:end_time].to_time + check_ids.each do |exercise| + if exercise.present? + if exercise.unified_setting + ex_status = exercise.exercise_status #则为试卷的状态 + else + ex_status = @course.course_groups.where(id: params[:group_ids]).size != + exercise.exercise_group_settings.where(course_group_id: params[:group_ids]).exercise_group_published.size ? 1 : 0 + end + if ex_status == 1 #如果试卷存在已发布的,或者是已截止的,那么则直接跳过 + g_course = group_ids #表示是否传入分班参数,如果传入分班的参数,那么试卷的统一设置需修改 + tiding_group_ids = g_course + if g_course + user_course_groups = @course.course_groups.pluck(:id) + if g_course.map(&:to_i).sort == user_course_groups.sort && + ((params[:detail] && group_end_times.min == group_end_times.max) || params[:detail].blank?) # 如果是设置为全部班级,则试卷不用分组,且试卷设定为统一设置,否则则分组设置 + exercise.exercise_group_settings.destroy_all + ex_unified = true + e_time = params[:detail] ? group_end_times.max : ex_end_time + tiding_group_ids = [] + else + ex_unified = false + g_course.each_with_index do |i, index| + exercise_group_setting = exercise.exercise_group_settings.find_in_exercise_group("course_group_id", i).first #根据课堂分班的id,寻找试卷所在的班级 + group_end_time = params[:detail] ? group_end_times[index] : ex_end_time + if exercise_group_setting.present? #如果该试卷分组存在,则更新,否则新建 + exercise_group_setting.update!(publish_time: Time.now, end_time: group_end_time) + else + p_course_group = { + :exercise_id => exercise.id, + :course_group_id => i, + :course_id => exercise.course.id, + :publish_time => Time.now, + :end_time => group_end_time, + } + new_exercise_group = exercise.exercise_group_settings.new p_course_group + new_exercise_group.save! + end + end + # group_ids = params[:group_ids] + e_time = exercise.exercise_group_settings.end_time_no_null.map(&:end_time).max + end else - ex_status = @course.course_groups.where(id: params[:group_ids]).size != - exercise.exercise_group_settings.where(course_group_id: params[:group_ids]).exercise_group_published.size ? 1 : 0 + exercise.exercise_group_settings.destroy_all + ex_unified = true + e_time = ex_end_time end - if ex_status == 1 #如果试卷存在已发布的,或者是已截止的,那么则直接跳过 - g_course = group_ids #表示是否传入分班参数,如果传入分班的参数,那么试卷的统一设置需修改 - tiding_group_ids = g_course - if g_course - user_course_groups = @course.course_groups.pluck(:id) - if g_course.map(&:to_i).sort == user_course_groups.sort && - ((params[:detail] && group_end_times.min == group_end_times.max) || params[:detail].blank?) # 如果是设置为全部班级,则试卷不用分组,且试卷设定为统一设置,否则则分组设置 - exercise.exercise_group_settings.destroy_all - ex_unified = true - e_time = params[:detail] ? group_end_times.max : ex_end_time - tiding_group_ids = [] - else - ex_unified = false - g_course.each_with_index do |i, index| - exercise_group_setting = exercise.exercise_group_settings.find_in_exercise_group("course_group_id",i).first #根据课堂分班的id,寻找试卷所在的班级 - group_end_time = params[:detail] ? group_end_times[index] : ex_end_time - if exercise_group_setting.present? #如果该试卷分组存在,则更新,否则新建 - exercise_group_setting.update!(publish_time: Time.now, end_time: group_end_time) - else - p_course_group = { - :exercise_id => exercise.id, - :course_group_id => i, - :course_id => exercise.course.id, - :publish_time => Time.now, - :end_time => group_end_time, - } - new_exercise_group = exercise.exercise_group_settings.new p_course_group - new_exercise_group.save! - end - end - # group_ids = params[:group_ids] - e_time = exercise.exercise_group_settings.end_time_no_null.map(&:end_time).max - end - else - exercise.exercise_group_settings.destroy_all - ex_unified = true - e_time = ex_end_time - end - ex_status = set_exercise_status(Time.now,e_time) - exercise_params = { - :publish_time => Time.now, - :end_time => e_time, - :exercise_status => ex_status, - :unified_setting => ex_unified - } - exercise.update!(exercise_params) + ex_status = set_exercise_status(Time.now, e_time) + exercise_params = { + :publish_time => Time.now, + :end_time => e_time, + :exercise_status => ex_status, + :unified_setting => ex_unified + } + exercise.update!(exercise_params) - if exercise.course_acts.size == 0 - exercise.course_acts << CourseActivity.new(:user_id => exercise.user_id,:course_id => exercise.course_id) - end - ExercisePublishNotifyJob.perform_later(exercise.id, tiding_group_ids) + if exercise.course_acts.size == 0 + exercise.course_acts << CourseActivity.new(:user_id => exercise.user_id, :course_id => exercise.course_id) end + ExercisePublishNotifyJob.perform_later(exercise.id, tiding_group_ids) end end - normal_status(0, "试卷发布成功!") - rescue Exception => e - uid_logger_error(e.message) - tip_exception("试卷发布失败") - raise ActiveRecord::Rollback end + normal_status(0, "试卷发布成功!") end end #立即截止的弹窗内容 def end_modal ActiveRecord::Base.transaction do - begin - exercise_ids = params[:check_ids] - if exercise_ids.count > 0 - @course_groups = get_user_permission_course(exercise_ids,3) - else - @course_groups = [] - end - rescue Exception => e - uid_logger_error(e.message) - tip_exception("没有权限") - raise ActiveRecord::Rollback + exercise_ids = params[:check_ids] + if exercise_ids.count > 0 + @course_groups = get_user_permission_course(exercise_ids, 3) + else + @course_groups = [] end end end @@ -855,128 +749,116 @@ class ExercisesController < ApplicationController def end_exercise ActiveRecord::Base.transaction do - begin - check_ids = Exercise.where(id:params[:check_ids]) - course_students = @course.students #课堂的全部学生数 - check_ids.each do |exercise| - exercise_status= exercise.get_exercise_status(current_user) - if exercise_status == Exercise::PUBLISHED #跳过已截止的或未发布的 - g_course = params[:group_ids] - if g_course.present? - teacher_course_group_ids = @course.charge_group_ids(current_user) - all_course_group_ids = @course.course_groups.pluck(:id) - if exercise.unified_setting && g_course.map(&:to_i).sort == all_course_group_ids.sort #开始为统一设置 - exercise.exercise_group_settings.destroy_all - new_ex_status = set_exercise_status(exercise.publish_time,Time.now) - exercise.update!(:end_time => Time.now,:exercise_status => new_ex_status) - exercise_users = exercise.exercise_users - else - course_members_ids = course_students.course_find_by_ids("course_group_id",g_course).pluck(:user_id).uniq #该班级的全部学生 - exercise_users = exercise.exercise_users.exercise_commit_users(course_members_ids) #参与答题的学生数 - ex_group_setting = exercise.exercise_group_settings - old_exercise_groups = ex_group_setting.find_in_exercise_group("course_group_id",g_course) #试卷的分组设置 - left_course_groups = teacher_course_group_ids - g_course - left_exercise_groups = ex_group_setting.find_in_exercise_group("course_group_id",left_course_groups) - if left_exercise_groups.blank? && exercise.unified_setting - if left_course_groups.size > 0 #开始为统一设置,但是立即截止为分班。则创建没有立即截止的班级的exercise_group_setting - left_course_groups.each do |g| - ex_group_options = { - :exercise_id => exercise.id, - :course_group_id => g, - :course_id => @course.id, - :publish_time => exercise.publish_time, - :end_time => exercise.end_time - } - ExerciseGroupSetting.create!(ex_group_options) - end - end - end - if old_exercise_groups.present? - old_exercise_groups.update_all(:end_time => Time.now) - else - g_course.each do |g| + check_ids = Exercise.where(id: params[:check_ids]) + course_students = @course.students #课堂的全部学生数 + check_ids.each do |exercise| + exercise_status = exercise.get_exercise_status(current_user) + if exercise_status == Exercise::PUBLISHED #跳过已截止的或未发布的 + g_course = params[:group_ids] + if g_course.present? + teacher_course_group_ids = @course.charge_group_ids(current_user) + all_course_group_ids = @course.course_groups.pluck(:id) + if exercise.unified_setting && g_course.map(&:to_i).sort == all_course_group_ids.sort #开始为统一设置 + exercise.exercise_group_settings.destroy_all + new_ex_status = set_exercise_status(exercise.publish_time, Time.now) + exercise.update!(:end_time => Time.now, :exercise_status => new_ex_status) + exercise_users = exercise.exercise_users + else + course_members_ids = course_students.course_find_by_ids("course_group_id", g_course).pluck(:user_id).uniq #该班级的全部学生 + exercise_users = exercise.exercise_users.exercise_commit_users(course_members_ids) #参与答题的学生数 + ex_group_setting = exercise.exercise_group_settings + old_exercise_groups = ex_group_setting.find_in_exercise_group("course_group_id", g_course) #试卷的分组设置 + left_course_groups = teacher_course_group_ids - g_course + left_exercise_groups = ex_group_setting.find_in_exercise_group("course_group_id", left_course_groups) + if left_exercise_groups.blank? && exercise.unified_setting + if left_course_groups.size > 0 #开始为统一设置,但是立即截止为分班。则创建没有立即截止的班级的exercise_group_setting + left_course_groups.each do |g| ex_group_options = { - :exercise_id => exercise.id, - :course_group_id => g, - :course_id => @course.id, - :publish_time => exercise.publish_time, - :end_time => Time.now + :exercise_id => exercise.id, + :course_group_id => g, + :course_id => @course.id, + :publish_time => exercise.publish_time, + :end_time => exercise.end_time } ExerciseGroupSetting.create!(ex_group_options) end end - new_end_time = exercise.exercise_group_settings.end_time_no_null.map(&:end_time) # 试卷结束时间不为空的 - new_end_time_s = new_end_time.count > 0 ? new_end_time.max : Time.now - new_ex_status = set_exercise_status(exercise.publish_time,new_end_time_s) - exercise.update!(:end_time => new_end_time_s,:exercise_status => new_ex_status,:unified_setting => false) end - else - exercise_users = exercise.exercise_users - exercise.update!(:exercise_status => 3, :end_time => Time.now,:unified_setting => true) + if old_exercise_groups.present? + old_exercise_groups.update_all(:end_time => Time.now) + else + g_course.each do |g| + ex_group_options = { + :exercise_id => exercise.id, + :course_group_id => g, + :course_id => @course.id, + :publish_time => exercise.publish_time, + :end_time => Time.now + } + ExerciseGroupSetting.create!(ex_group_options) + end + end + new_end_time = exercise.exercise_group_settings.end_time_no_null.map(&:end_time) # 试卷结束时间不为空的 + new_end_time_s = new_end_time.count > 0 ? new_end_time.max : Time.now + new_ex_status = set_exercise_status(exercise.publish_time, new_end_time_s) + exercise.update!(:end_time => new_end_time_s, :exercise_status => new_ex_status, :unified_setting => false) end - - ex_user_ids = exercise_users.pluck(:id) - - EndExerciseCalculateJob.perform_later(ex_user_ids,exercise,Time.now.to_s) - # exercise_users.each do |user| - # if user.commit_status == 0 && user.start_at.present? - # objective_score = calculate_student_score(exercise,user.user)[:total_score] - # user_sub_score = user.subjective_score - # subjective_score = user_sub_score < 0.0 ? 0.0 : user_sub_score - # total_score = objective_score + subjective_score - # commit_option = { - # :status => 1, - # :commit_status => 1, - # :end_at => Time.now, - # :objective_score => objective_score, - # :score => total_score, - # :subjective_score => user_sub_score - # } - # user.update_attributes(commit_option) - # end - # end + else + exercise_users = exercise.exercise_users + exercise.update!(:exercise_status => 3, :end_time => Time.now, :unified_setting => true) end + + ex_user_ids = exercise_users.pluck(:id) + + EndExerciseCalculateJob.perform_later(ex_user_ids, exercise, Time.now.to_s) + # exercise_users.each do |user| + # if user.commit_status == 0 && user.start_at.present? + # objective_score = calculate_student_score(exercise,user.user)[:total_score] + # user_sub_score = user.subjective_score + # subjective_score = user_sub_score < 0.0 ? 0.0 : user_sub_score + # total_score = objective_score + subjective_score + # commit_option = { + # :status => 1, + # :commit_status => 1, + # :end_at => Time.now, + # :objective_score => objective_score, + # :score => total_score, + # :subjective_score => user_sub_score + # } + # user.update_attributes(commit_option) + # end + # end end - normal_status(0, "试卷截止成功!") - rescue Exception => e - uid_logger_error(e.message) - tip_exception("立即截止失败!") - raise ActiveRecord::Rollback end + normal_status(0, "试卷截止成功!") end end #学生撤销回答 def cancel_exercise ActiveRecord::Base.transaction do - begin - ex_question_ids = @exercise.exercise_questions.pluck(:id) - exercise_user = @exercise.exercise_users.exercise_commit_users(current_user.id).first - if exercise_user.present? - if exercise_user.commit_status == 1 && @exercise.get_exercise_status(current_user) == Exercise::PUBLISHED #用户已提交且试卷提交中 - if @exercise.time == -1 || ((Time.now.to_i - exercise_user.start_at.to_i) < @exercise.time.to_i * 60) - exercise_user.update!(:score => nil, :end_at => nil, :status => nil, :commit_status => 0, - :objective_score => 0.0, :subjective_score => -1.0) - exercise_user.user.exercise_shixun_answers.search_shixun_answers("exercise_question_id",ex_question_ids).destroy_all - exercise_answers = exercise_user.user.exercise_answers.search_answer_users("exercise_question_id",ex_question_ids) - exercise_answers.update_all(:score => -1.0) - all_answer_comment = ExerciseAnswerComment.search_answer_comments("exercise_question_id",ex_question_ids) - .search_answer_comments("exercise_answer_id",exercise_answers.pluck(:id)) - all_answer_comment.destroy_all - normal_status(0,"撤销回答成功") - else - normal_status(-1,"用户答题时间已到") - end + ex_question_ids = @exercise.exercise_questions.pluck(:id) + exercise_user = @exercise.exercise_users.exercise_commit_users(current_user.id).first + if exercise_user.present? + if exercise_user.commit_status == 1 && @exercise.get_exercise_status(current_user) == Exercise::PUBLISHED #用户已提交且试卷提交中 + if @exercise.time == -1 || ((Time.now.to_i - exercise_user.start_at.to_i) < @exercise.time.to_i * 60) + exercise_user.update!(:score => nil, :end_at => nil, :status => nil, :commit_status => 0, + :objective_score => 0.0, :subjective_score => -1.0) + exercise_user.user.exercise_shixun_answers.search_shixun_answers("exercise_question_id", ex_question_ids).destroy_all + exercise_answers = exercise_user.user.exercise_answers.search_answer_users("exercise_question_id", ex_question_ids) + exercise_answers.update_all(:score => -1.0) + all_answer_comment = ExerciseAnswerComment.search_answer_comments("exercise_question_id", ex_question_ids) + .search_answer_comments("exercise_answer_id", exercise_answers.pluck(:id)) + all_answer_comment.destroy_all + normal_status(0, "撤销回答成功") else - normal_status(-1,"用户未提交/试卷不是提交中") + normal_status(-1, "用户答题时间已到") end else - normal_status(-1,"当前用户未答题") + normal_status(-1, "用户未提交/试卷不是提交中") end - rescue Exception => e - uid_logger_error(e.message) - tip_exception("页面调用失败") - raise ActiveRecord::Rollback + else + normal_status(-1, "当前用户未答题") end end end @@ -984,307 +866,1614 @@ class ExercisesController < ApplicationController #打回重做modal def redo_modal ActiveRecord::Base.transaction do - begin - #搜索 - if params[:realname].present? - search_name = params[:realname] - #搜索用户的nickname,如果存在则返回,否则继续查询用户的真实姓名或学生号 - @exercise_users = @exercise_users.includes(:user).where("LOWER(concat(users.lastname, users.firstname)) like ?", - "%#{search_name}%") - end - if params[:student_id].present? - search_st_id = params[:student_id].to_i - @exercise_users = @exercise_users.includes(user: [:user_extension]) - .where('user_extensions.student_id like ?',"%#{search_st_id}%") - end - sort = params[:sort] ? params[:sort] : "asc" - @exercise_users = @exercise_users.order("score #{sort}") - @exercise_users_size = @exercise_users.size - # 分页 - page = params[:page] || 1 - limit = params[:limit] || 15 - @exercise_users = @exercise_users.page(page).per(limit) - rescue Exception => e - uid_logger_error(e.message) - tip_exception("没有权限") - raise ActiveRecord::Rollback + #搜索 + if params[:realname].present? + search_name = params[:realname] + #搜索用户的nickname,如果存在则返回,否则继续查询用户的真实姓名或学生号 + @exercise_users = @exercise_users.includes(:user).where("LOWER(concat(users.lastname, users.firstname)) like ?", + "%#{search_name}%") end + if params[:student_id].present? + search_st_id = params[:student_id].to_i + @exercise_users = @exercise_users.includes(user: [:user_extension]) + .where('user_extensions.student_id like ?', "%#{search_st_id}%") + end + sort = params[:sort] ? params[:sort] : "asc" + @exercise_users = @exercise_users.order("score #{sort}") + @exercise_users_size = @exercise_users.size + # 分页 + page = params[:page] || 1 + limit = params[:limit] || 15 + @exercise_users = @exercise_users.page(page).per(limit) end end #打回重做确认 def redo_exercise ActiveRecord::Base.transaction do - begin - user_ids = params[:user_ids] - if user_ids.present? - redo_option = { - :score => 0.0, - :start_at => nil, - :end_at => nil, - :status => nil, - :commit_status => 0, - :objective_score => 0.0, - :subjective_score => -1.0, - :commit_method => 0 - } - redo_exercise_users = @exercise_users.exercise_commit_users(user_ids) - redo_exercise_users.update_all(redo_option) - exercise_question_ids = @exercise.exercise_questions.pluck(:id).uniq - ExerciseAnswer.search_answer_users("user_id",user_ids) - .search_answer_users("exercise_question_id",exercise_question_ids).destroy_all - ExerciseShixunAnswer.search_shixun_answers("user_id",user_ids) - .search_shixun_answers("exercise_question_id",exercise_question_ids).destroy_all - - normal_status(0,"已成功打回重做!") - else - normal_status(-1,"请选择学生!") - end - rescue Exception => e - uid_logger_error(e.message) - tip_exception("没有权限") - raise ActiveRecord::Rollback + user_ids = params[:user_ids] + if user_ids.present? + redo_option = { + :score => 0.0, + :start_at => nil, + :end_at => nil, + :status => nil, + :commit_status => 0, + :objective_score => 0.0, + :subjective_score => -1.0, + :commit_method => 0 + } + redo_exercise_users = @exercise_users.exercise_commit_users(user_ids) + redo_exercise_users.update_all(redo_option) + exercise_question_ids = @exercise.exercise_questions.pluck(:id).uniq + ExerciseAnswer.search_answer_users("user_id", user_ids) + .search_answer_users("exercise_question_id", exercise_question_ids).destroy_all + ExerciseShixunAnswer.search_shixun_answers("user_id", user_ids) + .search_shixun_answers("exercise_question_id", exercise_question_ids).destroy_all + + normal_status(0, "已成功打回重做!") + else + normal_status(-1, "请选择学生!") end end end #学生开始答题页面 def start_answer - begin - ex_users_current = ExerciseUser.where(user_id:@exercise_current_user_id,exercise_id:@exercise.id) #不能用@exercise.exercise_users,因为exercise_users删除时,只是状态改变,未删除 - @exercise_user_current = ex_users_current&.first - if ex_users_current.exists? - if @exercise_user_current.start_at.blank? - @exercise_user_current.update!(start_at: Time.now) + ex_users_current = ExerciseUser.where(user_id: @exercise_current_user_id, exercise_id: @exercise.id) #不能用@exercise.exercise_users,因为exercise_users删除时,只是状态改变,未删除 + @exercise_user_current = ex_users_current&.first + if ex_users_current.exists? + if @exercise_user_current.start_at.blank? + @exercise_user_current.update!(start_at: Time.now) + end + else + if @user_course_identity > Course::ASSISTANT_PROFESSOR #当为老师的时候,不创建exercise_user表,理论上老师是不能进入答题的 + exercise_user_params = { + :user_id => @exercise_current_user_id, + :exercise_id => @exercise.id, + :start_at => Time.now + } + exercise_user_current = ExerciseUser.new(exercise_user_params) + exercise_user_current.save! + end + end + @t_user_exercise_status = @exercise.get_exercise_status(current_user) + + @user_left_time = nil + if @user_course_identity < Course::STUDENT || (@t_user_exercise_status == 3) || + (ex_users_current.exists? && @exercise_user_current.commit_status == 1) + @user_exercise_status = 1 #当前用户为老师/试卷已截止/试卷已提交不可编辑 + else + @user_left_time = get_exercise_left_time(@exercise, current_user) + @user_exercise_status = 0 #可编辑 + end + + @exercise_questions = @exercise.exercise_questions + + if @exercise.question_random + @exercise_questions = @exercise_questions.order("RAND()") + else + @exercise_questions = @exercise_questions.order("question_number ASC") + end + # 判断问题是否已回答还是未回答 + @exercise_questions = @exercise_questions.includes(:exercise_shixun_challenges, + :exercise_shixun_answers, + :exercise_answers, + :exercise_standard_answers) + + if @t_user_exercise_status == Exercise::DEADLINE + get_each_student_exercise(@exercise.id, @exercise_questions, @exercise_current_user_id) + end + get_user_answer_status(@exercise_questions, @exercise_current_user_id, @exercise, @t_user_exercise_status) + + end + + #提交试卷前的弹窗 + def begin_commit + ActiveRecord::Base.transaction do + if @user_course_identity > Course::ASSISTANT_PROFESSOR #为学生时 + @exercise_questions = @exercise.exercise_questions + @shixun_undo = 0 + @ques_undo = 0 + ex_answer_time = @exercise.time.to_i + if ex_answer_time > 0 #有剩余时间的时候 + user_left_time = get_exercise_left_time(@exercise, current_user) + @ex_end_time = Time.now + user_left_time.to_i.seconds + else + @ex_end_time = @exercise.get_exercise_end_time(current_user.id) end - else - if @user_course_identity > Course::ASSISTANT_PROFESSOR #当为老师的时候,不创建exercise_user表,理论上老师是不能进入答题的 - exercise_user_params = { - :user_id => @exercise_current_user_id, - :exercise_id => @exercise.id, - :start_at => Time.now - } - exercise_user_current = ExerciseUser.new(exercise_user_params) - exercise_user_current.save! + # @ex_end_time = @exercise.get_exercise_end_time(current_user.id) + # if ex_answer_time > 0 + # left_answer_time = Time.now + ex_answer_time.minutes #判断试卷的倒计时和截止时间哪个先到 + # if left_answer_time < @ex_end_time + # exercise_end_time = @exercise.exercise_users.exercise_commit_users(current_user.id) + # if exercise_end_time.present? + # ex_end_times = exercise_end_time.first.start_at.nil? ? Time.now : exercise_end_time.first.start_at + # @ex_end_time = ex_end_times + ex_answer_time.minutes + # end + # end + # end + @exercise_questions.each do |q| + if q.question_type == Exercise::PRACTICAL #当为实训题时 + user_myshixun = q.shixun.myshixuns.search_myshixun_user(current_user.id) + if user_myshixun.blank? || user_myshixun.first.status != Exercise::UNPUBLISHED #当前用户的实训是否做完 + @shixun_undo += 1 + end + else + ques_vote = q.exercise_answers.search_exercise_answer("user_id", current_user.id) + if ques_vote.blank? + @ques_undo += 1 + end + end end end - @t_user_exercise_status = @exercise.get_exercise_status(current_user) + end + end - @user_left_time = nil - if @user_course_identity < Course::STUDENT || (@t_user_exercise_status == 3) || - (ex_users_current.exists? && @exercise_user_current.commit_status == 1) - @user_exercise_status = 1 #当前用户为老师/试卷已截止/试卷已提交不可编辑 + # 学生提交试卷 + def commit_exercise + tip_exception(0, "试卷截止时间已到,系统已自动提交") if @answer_committed_user.commit_status == 1 + ActiveRecord::Base.transaction do + can_commit_exercise = false + user_left_time = nil + if @user_course_identity > Course::ASSISTANT_PROFESSOR #为学生时 + if params[:commit_method].to_i == 2 #自动提交时 + user_left_time = get_exercise_left_time(@exercise, current_user) + Rails.logger.info("######__________auto_commit_user_left_time_________################{user_left_time}") + if user_left_time.to_i <= 0 + can_commit_exercise = true + end + else + can_commit_exercise = true + end + if can_commit_exercise + objective_score = calculate_student_score(@exercise, current_user, Time.now)[:total_score] + subjective_score = @answer_committed_user.subjective_score + total_score_subjective_score = subjective_score < 0.0 ? 0.0 : subjective_score + total_score = objective_score + total_score_subjective_score + commit_option = { + :status => 1, + :commit_status => 1, + :end_at => Time.now, + :objective_score => objective_score, + :score => total_score, + :subjective_score => subjective_score, + :commit_method => @answer_committed_user&.commit_method.to_i > 0 ? @answer_committed_user&.commit_method.to_i : params[:commit_method].to_i + } + @answer_committed_user.update!(commit_option) + CommitExercsieNotifyJobJob.perform_later(@exercise.id, current_user.id) + normal_status(0, "试卷提交成功!") + else + normal_status(-2, "#{user_left_time.to_i}") + end else - @user_left_time = get_exercise_left_time(@exercise,current_user) - @user_exercise_status = 0 #可编辑 + normal_status(-1, "提交失败,当前用户不为课堂学生!") + end + end + end + + #教师评阅试卷 及学生查看试卷 + def review_exercise + ActiveRecord::Base.transaction do + # 1 老师权限,0 学生权限 + @is_teacher_or = (@user_course_identity < Course::STUDENT) ? 1 : 0 + @student_status = 2 + @exercise_questions = @exercise.exercise_questions.includes(:exercise_shixun_challenges, :exercise_standard_answers, :exercise_answers, :exercise_shixun_answers, :exercise_answer_comments).order("question_number ASC") + @question_status = [] + get_exercise_status = @exercise.get_exercise_status(current_user) #当前用户的试卷状态 + @ex_answer_status = @exercise.get_exercise_status(@ex_user&.user) #当前试卷用户的试卷状态 + if @ex_user.present? && @is_teacher_or == 0 + if get_exercise_status == Exercise::PUBLISHED #当前用户已提交,且试卷未截止 + if @ex_user.commit_status == 0 #学生未提交,且当前为学生 + @student_status = 0 + else + @student_status = 1 + get_user_answer_status(@exercise_questions, @exercise_current_user_id, @exercise, get_exercise_status) + end + end + end + if @student_status == 2 + get_each_student_exercise(@exercise.id, @exercise_questions, @exercise_current_user_id) + end + end + end + + #答题列表 + def exercise_lists + @current_user_id = current_user.id + exercise_ids = [@exercise.id] + @exercise_status = @exercise.get_exercise_status(current_user) + @course_all_members = @course.students + @c_group_counts = @course.course_groups_count + question_types = @exercise.exercise_questions.pluck(:question_type).uniq + @exercise_publish_count = get_user_permission_course(exercise_ids, Exercise::PUBLISHED).count #判断是否有已发布的分班 + @exercise_unpublish_count = get_user_permission_course(exercise_ids, Exercise::UNPUBLISHED).count #判断是否有未发布的分班 + + if (question_types.size > 1) && question_types.include?(Exercise::SUBJECTIVE) #是否包含主观题,或者是否大于1 + @subjective_type = 1 + else + @subjective_type = 0 + end + + #初始化值 + @exercise_users_list = [] #答题用户列表 + @exercise_course_groups = [] #当前用户有权限的班级 + @exercise_unanswers = 0 # 未答用户数 + @exercise_answers = 0 #已答用户数 + @exercise_users_count = 0 #全部用户数 + @teacher_review_count = 0 #已评数 + @teacher_unreview_count = 0 #未评数 + + #试卷的答题列表页的显示用户 + if @user_course_identity < Course::STUDENT #当前为老师,而且老师只能查看自己班级的/课堂的试卷 + @exercise_current_user_status = 0 + unless @exercise_status == Exercise::UNPUBLISHED + ex_common_ids = @exercise.common_published_ids(current_user.id) + @exercise_course_groups = @course.get_ex_published_course(ex_common_ids) + @exercise_users_list = @exercise.all_exercise_users(current_user.id) #当前老师所在班级的全部学生 + get_exercise_answers(@exercise_users_list, @exercise_status) + end + else #当前为学生或者有过答题的 + @ex_user_end_time = @exercise.get_exercise_end_time(current_user.id) #当前用户所看到的剩余时间 + @exercise_all_users = @exercise.get_stu_exercise_users + get_exercise_answers(@exercise_all_users, @exercise_status) # 未答和已答的 + exercise_current_user = @exercise_all_users.exercise_commit_users(current_user.id) + if exercise_current_user.exists? #表示为课堂学生或已回答的 + @exercise_current_user_status = 1 + if @exercise.score_open && @exercise_status == Exercise::DEADLINE #勾选了成绩公开且试卷已截止的 + all_user_ids = @exercise_all_users.pluck(:user_id) + all_user_ids.delete(current_user.id) #删除了当前用户的ID + @exercise_users_list = @exercise_all_users.exercise_commit_users(all_user_ids).distinct + @current_user_ex_answers = exercise_current_user #当前用户的回答 + else + @exercise_users_list = exercise_current_user + end + else #表示为未回答的,或未非课堂成员的 + @exercise_current_user_status = 2 #当前用户非课堂成员 + end + end + + if @exercise_unanswers < 0 + @exercise_unanswers = 0 + end + + #筛选/分类,排序 + order = params[:order] + order_type = params[:order_type] || "desc" + + if @exercise_users_list.present? && @exercise_users_list.size > 0 + @exercise_users_count = @exercise_users_list.size #当前显示的全部成员数量 + teacher_reviews = @exercise_users_list.exercise_review + teacher_unreviews = @exercise_users_list.exercise_unreview + @teacher_review_count = teacher_reviews.size #已评阅 + @teacher_unreview_count = teacher_unreviews.size #未评阅 + + #是否评阅 + if params[:review].present? + review_type = params[:review].first.to_i #已评,则数据为1,未评,则数据为0,前端传过来的为数组 + if review_type == 1 + @exercise_users_list = teacher_reviews + else + @exercise_users_list = teacher_unreviews + end + end + + #答题状态的选择 + if params[:commit_status].present? + choose_type = params[:commit_status] + @exercise_users_list = @exercise_users_list.commit_exercise_by_status(choose_type) + end + + #班级的选择 + if params[:exercise_group_id].present? + group_id = params[:exercise_group_id] + exercise_students = @course_all_members.course_find_by_ids("course_group_id", group_id) #试卷所分班的全部人数 + user_ids = exercise_students.pluck(:user_id).reject(&:blank?) + @exercise_users_list = @exercise_users_list.exercise_commit_users(user_ids) + end + + #搜索 + if params[:search].present? + @exercise_users_list = @exercise_users_list.joins(user: :user_extension).where("CONCAT(lastname, firstname) like ? OR student_id like ?", "%#{params[:search]}%", "%#{params[:search]}%") end - @exercise_questions = @exercise.exercise_questions + exercise_user_joins = @exercise_users_list.joins(user: :user_extension) - if @exercise.question_random - @exercise_questions = @exercise_questions.order("RAND()") + if order == "student_id" + @exercise_users_list = exercise_user_joins.order("user_extensions.student_id #{order_type}") + elsif order == "score" + @exercise_users_list = exercise_user_joins.order("#{order} #{order_type}") else - @exercise_questions = @exercise_questions.order("question_number ASC") + @exercise_users_list = exercise_user_joins.order("end_at #{order_type}, start_at #{order_type}") end - # 判断问题是否已回答还是未回答 - @exercise_questions = @exercise_questions.includes(:exercise_shixun_challenges, - :exercise_shixun_answers, - :exercise_answers, - :exercise_standard_answers) - if @t_user_exercise_status == Exercise::DEADLINE - get_each_student_exercise(@exercise.id,@exercise_questions,@exercise_current_user_id) + @export_ex_users = @exercise_users_list + + @exercise_users_size = @exercise_users_list.size + + # 分页 + @page = params[:page] || 1 + @limit = params[:limit] || 20 + @exercise_users_list = @exercise_users_list.page(@page).per(@limit) + else + @exercise_users_list = [] + @export_ex_users = @exercise_users_list + @exercise_users_size = 0 + end + + if params[:format] == "xlsx" + if @user_course_identity > Course::ASSISTANT_PROFESSOR + tip_exception(403, "无权限操作") + elsif @exercise_status == Exercise::UNPUBLISHED + normal_status(-1, "试卷未发布") + elsif (@exercise_users_size == 0) || (@export_ex_users&.exercise_user_committed.size == 0) + normal_status(-1, "暂无用户提交") + elsif params[:export].present? && params[:export] + normal_status(0, "正在下载中") + else + respond_to do |format| + format.xlsx { + set_export_cookies + get_export_users(@exercise, @course, @export_ex_users) + exercise_export_name_ = + "#{current_user.real_name}_#{@course.name}_#{@exercise.exercise_name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}" + render xlsx: "#{exercise_export_name_.strip}", template: "exercises/exercise_lists.xlsx.axlsx", locals: {table_columns: @table_columns, exercise_users: @user_columns} + } + end end - get_user_answer_status(@exercise_questions,@exercise_current_user_id,@exercise,@t_user_exercise_status) + end + end - rescue Exception => e - uid_logger_error(e.message) - tip_exception(e.message) - raise ActiveRecord::Rollback + #导出空白试卷 + def export_exercise + @request_url = request.base_url + @exercise_questions = @exercise.exercise_questions.includes(:exercise_choices).order("question_number ASC") + filename_ = "#{@exercise.user.real_name}_#{@course.name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}.pdf" + stylesheets = "#{Rails.root}/app/templates/exercise_export/exercise_export.css" + if params[:export].present? && params[:export] + normal_status(0, "正在下载中") + else + set_export_cookies + render pdf: 'exercise_export/blank_exercise', filename: filename_, stylesheets: stylesheets, disposition: 'inline', type: "pdf_attachment.content_type", stream: false end end - #提交试卷前的弹窗 - def begin_commit - ActiveRecord::Base.transaction do - begin - if @user_course_identity > Course::ASSISTANT_PROFESSOR #为学生时 - @exercise_questions = @exercise.exercise_questions - @shixun_undo = 0 - @ques_undo = 0 - ex_answer_time = @exercise.time.to_i - if ex_answer_time > 0 #有剩余时间的时候 - user_left_time = get_exercise_left_time(@exercise,current_user) - @ex_end_time = Time.now + user_left_time.to_i.seconds - else - @ex_end_time = @exercise.get_exercise_end_time(current_user.id) - end - # @ex_end_time = @exercise.get_exercise_end_time(current_user.id) - # if ex_answer_time > 0 - # left_answer_time = Time.now + ex_answer_time.minutes #判断试卷的倒计时和截止时间哪个先到 - # if left_answer_time < @ex_end_time - # exercise_end_time = @exercise.exercise_users.exercise_commit_users(current_user.id) - # if exercise_end_time.present? - # ex_end_times = exercise_end_time.first.start_at.nil? ? Time.now : exercise_end_time.first.start_at - # @ex_end_time = ex_end_times + ex_answer_time.minutes - # end - # end - # end - @exercise_questions.each do |q| - if q.question_type == Exercise::PRACTICAL #当为实训题时 - user_myshixun = q.shixun.myshixuns.search_myshixun_user(current_user.id) - if user_myshixun.blank? || user_myshixun.first.status != Exercise::UNPUBLISHED #当前用户的实训是否做完 - @shixun_undo += 1 + #空白试卷预览页面,仅供测试使用,无其他任何用途 + # def blank_exercise + # ActiveRecord::Base.transaction do + # begin + # @exercise_questions = @exercise.exercise_questions.order("question_number ASC") + # challenge_ids = @exercise_questions.joins(:exercise_shixun_challenges).pluck("exercise_shixun_challenges.challenge_id") + # get_each_student_exercise(@exercise.id,@exercise_questions,31798) + # @games = @exercise_user.user.games.ch_games(challenge_ids) + # respond_to do |format| + # format.html + # end + # rescue Exception => e + # uid_logger_error(e.message) + # tip_exception("没有权限") + # raise ActiveRecord::Rollback + # end + # end + # end + + #学生的统计结果 + def exercise_result + exercise_ids = [@exercise.id] + @exercise_publish_count = get_user_permission_course(exercise_ids, Exercise::PUBLISHED).size #判断是否有已发布的分班 + @exercise_unpublish_count = get_user_permission_course(exercise_ids, Exercise::UNPUBLISHED).size #判断是否有未发布的分班 + @course_all_members = @course.students #课堂的全部学生 + @exercise_all_users = @exercise.exercise_users + ex_common_ids = @exercise.common_published_ids(current_user.id) + @exercise_course_groups = @course.get_ex_published_course(ex_common_ids) + + #班级的选择 + if params[:exercise_group_id].present? + group_id = params[:exercise_group_id] + exercise_students = @course_all_members.course_find_by_ids("course_group_id", group_id) # 试卷所分班的全部人数 + user_ids = exercise_students.pluck(:user_id).reject(&:blank?) + @exercise_all_users = @exercise.exercise_users.exercise_commit_users(user_ids) + @course_all_members_count = @exercise_all_users.size + else + @exercise_users_list = @exercise.all_exercise_users(current_user.id) + @course_all_members_count = @exercise_users_list.size + end + @exercise_commit_users = @exercise_all_users.commit_exercise_by_status(1) #试卷的已提交用户 + @exercise_commit_user_ids = @exercise_commit_users.pluck(:user_id).uniq #已提交试卷的全部用户id + @exercise_commit_user_counts = @exercise_commit_users.size #试卷的已提交用户人数 + @exercise_status = @exercise.get_exercise_status(current_user) + + #提交率 + if @course_all_members_count == 0 + commit_percent = 0.00 + min_score = 0.0 + max_score = 0.0 + average_score = 0.0 + fail_counts = 0 + pass_counts = 0 + good_counts = 0 + best_counts = 0 + else + commit_percent = (@exercise_commit_user_counts / @course_all_members_count.to_f).round(3) + exercise_scores = @exercise_commit_users.pluck(:score).reject(&:blank?) + min_score = exercise_scores.min.present? ? exercise_scores.min : 0.0 + max_score = exercise_scores.max.present? ? exercise_scores.max : 0.0 + total_score = exercise_scores.sum.present? ? exercise_scores.sum : 0.0 + average_score = @exercise_commit_user_counts > 0 ? (total_score.round(1) / @exercise_commit_user_counts).round(1) : 0.0 + question_scores = @exercise.question_scores + fail_score = question_scores * 0.6.round(2) + pass_score = question_scores * 0.7.round(2) + good_score = question_scores * 0.9.round(2) + + fail_counts = exercise_scores.count {|a| a < fail_score} + pass_counts = exercise_scores.count {|a| a < pass_score && a >= fail_score} + good_counts = exercise_scores.count {|a| a < good_score && a >= pass_score} + best_counts = exercise_scores.count {|a| a >= good_score && a <= question_scores} + end + @counts_array = { + :commit_percent => commit_percent, + :min_score => min_score.to_s, + :max_score => max_score.to_s, + :average_score => average_score.to_s, + :fail_counts => fail_counts, + :pass_counts => pass_counts, + :good_counts => good_counts, + :best_counts => best_counts, + } + + @exercise_questions = @exercise.exercise_questions&.includes(:exercise_choices, :exercise_answers, :exercise_standard_answers, :exercise_shixun_challenges, :exercise_shixun_answers) + + percent_sort = "desc" + + if params[:sort].present? + percent_sort = params[:sort] + end + # @paging_type = "percent" + # # 按题型排序 + # if params[:sort].present? + # @paging_type = params[:sort].to_s + # end + + ques_result_all = exercise_commit_result(@exercise_questions, @exercise_commit_user_ids) + + #默认降序排列 + if percent_sort == "desc" + @question_result_hash = ques_result_all.sort_by {|s| s[:percent]}.reverse + else + @question_result_hash = ques_result_all.sort_by {|s| s[:percent]} + end + class ExercisesController < ApplicationController + before_action :require_login, :check_auth, except: [:index] + before_action :find_course, only: [:index, :new, :create, :my_exercises, :public_exercises, :set_public, :destroys, + :join_exercise_banks, :publish_modal, :publish, :end_modal, :end_exercise] #需要有课堂id参数的 + before_action :get_exercise, except: [:index, :new, :create, :my_exercises, :public_exercises, :set_public, :destroys, + :join_exercise_banks, :publish_modal, :publish, :end_modal, :end_exercise] + before_action :user_course_identity + before_action :is_course_teacher, except: [:index, :start_answer, :exercise_setting, :commit_exercise, :exercise_lists, :review_exercise, + :exercise_result, :common_header, :cancel_exercise, :begin_commit] + before_action :get_left_banner_id, only: [:common_header, :start_answer, :review_exercise, :index, :new, :edit] + before_action :validates_exercise_params, only: [:create, :update] + before_action :get_exercise_question_counts, only: [:show, :edit, :start_answer, :review_exercise, :blank_exercise, :export_exercise] + before_action :validate_publish_time, only: [:commit_setting] #提交设置时,需判断时间是否符合 + before_action :check_course_public, only: [:set_public] + before_action :check_user_on_answer, only: [:show, :start_answer, :exercise_lists] #判断当前用户在试卷的权限/老师是否属于分班的权限 + before_action :only_student_in, only: [:start_answer] + before_action :check_user_id_start_answer, only: [:start_answer, :review_exercise] + # before_action :commit_user_exercise,only: [:start_answer,:exercise_lists,:review_exercise] #已有定时的任务 + before_action :check_exercise_time, only: [:commit_exercise] #提交试卷时,判断时间是否超过 + before_action :check_exercise_status, only: [:redo_modal, :redo_exercise] + before_action :check_exercise_is_end, only: [:review_exercise] + before_action :check_exercise_public, only: [:exercise_result] #试卷是否为公开 + before_action :commit_shixun_present, only: [:commit_shixun] + include ExportHelper + include ExercisesHelper + + # model validation error + rescue_from ActiveRecord::RecordInvalid do |ex| + render_error(ex.record.errors.full_messages.join(',')) + end + # form validation error + rescue_from ActiveModel::ValidationError do |ex| + render_error(ex.model.errors.full_messages.join(',')) + end + + def index + begin + # 按发布时间或创建时间排序 + @exercises_all = @course.exercises + member_show_exercises = @exercises_all.is_exercise_published #已发布的或已截止的试卷 + @current_user_ = current_user + + # 课堂的学生人数 + @course_all_members = @course.students #当前课堂的全部学生 + @current_student = @course_all_members.course_find_by_ids("user_id", current_user.id) #当前用户是否为课堂的学生 + + # exercises的不同用户群体的显示 + if @user_course_identity < Course::STUDENT # @is_teacher_or 1为老师/管理员/助教 + @is_teacher_or = 1 + @exercises = @exercises_all #老师能看到全部的试卷,不管是已发布的/未发布的/已截止的/统一设置的/私有设置的(看到内容不同) + elsif @user_course_identity == Course::STUDENT # 2为课堂成员,能看到统一设置的和自己班级的 + @is_teacher_or = 2 + @member_group_id = @current_student.first.try(:course_group_id).to_i # 成员的分班id,默认为0 + if @member_group_id == 0 #表示是课堂的未分班成员,只能查看统一设置的试卷(已发布的/已截止的) + @exercises = member_show_exercises.exists? ? member_show_exercises.unified_setting : [] + else #已分班级的成员,可以查看统一设置和单独设置(试卷是发布在该班级)试卷 + # 已发布 当前用户班级分组的 试卷id + publish_exercise_ids = @course.exercise_group_settings.exercise_group_published.where("course_group_id = #{@member_group_id}").pluck(:exercise_id) + @exercises = member_show_exercises.unified_setting.or(member_show_exercises.where(id: publish_exercise_ids)) + end + else #用户未登陆或不是该课堂成员,仅显示统一设置的(已发布的/已截止的),如有公开,则不显示锁,不公开,则显示锁 + @is_teacher_or = 0 + @exercises = member_show_exercises.unified_setting + end + + if @exercises.size > 0 + if params[:type].present? + choose_type = params[:type].to_i + ex_setting_ids = [] + if @is_teacher_or != 2 + @exercises = @exercises.where("exercise_status = #{choose_type}") + else + case choose_type + when 1 + ex_setting_ids = @course.exercise_group_settings.where("course_group_id = #{@member_group_id}").exercise_group_not_published.pluck(:exercise_id) + when 2 + ex_setting_ids = @course.exercise_group_settings.where("course_group_id = #{@member_group_id}") + .where("publish_time is not null and publish_time <= ? and end_time > ?", Time.now, Time.now).pluck(:exercise_id) + when 3 + ex_setting_ids = @course.exercise_group_settings.where("course_group_id = #{@member_group_id}").exercise_group_ended.pluck(:exercise_id) + end + unified_setting_ids = @exercises.unified_setting.where("exercise_status = #{choose_type}").pluck(:id) + ex_ids = (ex_setting_ids + unified_setting_ids).uniq + @exercises = @exercises.where(id: ex_ids) end + end + + if params[:search].present? + search_type = params[:search].to_s.strip + @exercises = @exercises.exercise_search(search_type) + end + + @exercises_select_count = @exercises.size # 全部页面,需返回 + @exercises = @exercises.distinct.order("IF(ISNULL(publish_time),0,1), publish_time DESC,created_at DESC") #出现错误 + + # 分页 + @page = params[:page] || 1 + @limit = params[:limit] || 15 + @exercises = @exercises.page(@page).per(@limit) + @exercises = @exercises&.includes(:published_settings) + else + @exercises = [] + end + + @course_all_members_count = @course_all_members.size #当前课堂的学生数 + @exercises_count = @exercises_all.size # 全部页面,需返回 + @exercises_unpublish_counts = @exercises_all.exercise_by_status(1).size #未发布的试卷数 + @exercises_published_counts = @exercises_count - @exercises_unpublish_counts # 已发布的试卷数,包含已截止的 + + rescue Exception => e + uid_logger_error(e.message) + tip_exception(e.message) + raise ActiveRecord::Rollback + end + end + + def new + ActiveRecord::Base.transaction do + begin + @exercise = Exercise.new + rescue Exception => e + uid_logger_error(e.message) + tip_exception("试卷创建失败!") + raise ActiveRecord::Rollback + end + end + end + + def create + ActiveRecord::Base.transaction do + ex_name = params[:exercise_name] + ex_desc = params[:exercise_description] + exercise_options = { + :exercise_name => ex_name, + :exercise_description => ex_desc, + :user_id => current_user.id, + :course_id => @course.id, + :time => -1, + :exercise_status => 1 + } + @exercise = Exercise.create!(exercise_options) + end + end + + #试卷的内容,及试题/答案的内容编辑 + def edit + ActiveRecord::Base.transaction do + @exercise_questions = @exercise.exercise_questions.order("question_number ASC") + end + end + + def update + ActiveRecord::Base.transaction do + ex_name = params[:exercise_name] + ex_desc = params[:exercise_description] + exercise_options = { + :exercise_name => ex_name, + :exercise_description => ex_desc, + } + @exercise.update!(exercise_options) + normal_status(0, "试卷更新成功!") + end + end + + def show + ActiveRecord::Base.transaction do + if @user_course_identity < Course::STUDENT + @is_teacher_or = 1 #为老师/助教/管理员 + else + @is_teacher_or = 0 #为学生 + end + @exercise_questions = @exercise.exercise_questions&.includes(:exercise_choices, :exercise_shixun_challenges, :exercise_standard_answers).order("question_number ASC") + end + end + + #试卷的公用头部 + def common_header + ActiveRecord::Base.transaction do + @user_left_time = nil + if @user_course_identity > Course::ASSISTANT_PROFESSOR + @is_teacher_or = 0 + @user_exercise_answer = @exercise.check_user_answer_status(current_user) + @user_commit_counts = 0 + @user_left_time = get_exercise_left_time(@exercise, current_user) + else + @is_teacher_or = 1 + @user_exercise_answer = 3 #教师页面 + @user_commit_counts = @exercise.exercise_users.where(commit_status: 1).size #已提交的用户数 + end + @ex_status = @exercise.get_exercise_status(current_user) + + exercise_id_array = [@exercise.id] + @exercise_publish_count = get_user_permission_course(exercise_id_array, Exercise::PUBLISHED).size #是否存在已发布的 + @exercise_unpublish_count = get_user_permission_course(exercise_id_array, Exercise::UNPUBLISHED).size #是否存在未发布的 + + if (@exercise_publish_count == 0) && (@exercise_unpublish_count == 0) #即表示没有分班 + if @ex_status == Exercise::UNPUBLISHED + @exercise_unpublish_count = 1 #试卷未发布,且课堂没有分班的时候 + elsif @ex_status == Exercise::PUBLISHED + @exercise_publish_count = 1 #试卷未发布,且课堂没有分班的时候 + end + end + end + end + + #实训题目的选用 + def choose_shixun + ActiveRecord::Base.transaction do + search = params[:search] + if @user_course_identity > Course::ADMIN #当不为管理员的时候 + user_school_id = current_user.school_id #当前用户的学校id + if user_school_id.present? + none_shixun_ids = ShixunSchool.where("school_id != #{user_school_id}").pluck(:shixun_id) + @publish_shixuns = Shixun.where.not(id: none_shixun_ids).unhidden + end + else + @publish_shixuns = Shixun.unhidden + end + if search.present? + @publish_shixuns = @publish_shixuns.search_by_name(search) + end + + @shixuns = @publish_shixuns.joins(:challenges).where("challenges.st != 0").distinct + # 全部页面,需返回 + @shixuns_count = @shixuns.count + + # 分页 + @page = params[:page] || 1 + @limit = params[:limit] || 8 + + @shixuns = @shixuns.page(@page).per(@limit) + end + end + + #确认实训的选择 + def commit_shixun + ActiveRecord::Base.transaction do + @shixun_challenges = @shixun.challenges + @shixun_challenges_count = @shixun_challenges.size + end + end + + # 首页批量或单独删除 + def destroys + ActiveRecord::Base.transaction do + check_ids = Exercise.where(id: params[:check_ids]) + check_ids.destroy_all + normal_status(0, "试卷已删除成功!") + end + end + + # 设为公开 + def set_public + ActiveRecord::Base.transaction do + check_ids = Exercise.where(id: params[:check_ids]) + check_ids.each do |exercise| + exercise.update!(is_public: true) + end + normal_status(0, "试卷已设为公开!") + end + end + + ## 加入题库 + def join_exercise_banks + ActiveRecord::Base.transaction do + check_ids = Exercise.where(id: params[:check_ids]) + check_ids.each do |exercise| + current_ex_bank = current_user.exercise_banks.find_by_container(exercise.id, "Exercise")&.first + if current_ex_bank.present? #当前用户的选择试卷是否已加入习题库,存在则更新习题库和问题库,否则新建习题库和问题库 + ex_params = { + :name => exercise.exercise_name, + :description => exercise.exercise_description, + :course_list_id => exercise.course.try(:course_list_id) + } + current_ex_bank.update!(ex_params) + # question_bank = QuestionBank.ques_by_container(current_ex_bank.id,current_ex_bank.container_type).first #该习题库是否存在于问题库里 + # ques_params = { + # :name => current_ex_bank.name, + # :course_list_id => current_ex_bank.course_list_id + # } + # question_bank.update_attributes(ques_params) if question_bank.present? + current_ex_bank.exercise_bank_questions.destroy_all # 更新后,习题库的问题全部删除,后续重新再建 + else + ex_params = { + :name => exercise.exercise_name, + :description => exercise.exercise_description, + :user_id => current_user.id, + :is_public => 0, + :course_list_id => exercise.course.try(:course_list_id), + :container_id => exercise.id, + :container_type => "Exercise", + :quotes => 1 + } + current_ex_bank = ExerciseBank.new ex_params + current_ex_bank.save! #如果习题库保存成功,则会创建问题库question_bank + # if current_ex_bank.save + # ques_params = { + # :name => current_ex_bank.name, + # :container_id => current_ex_bank.id, + # :container_type => current_ex_bank.container_type, + # :quotes => current_ex_bank.quotes, + # :user_id => current_ex_bank.user_id, + # :is_public => current_ex_bank.is_public, + # :course_list_id => current_ex_bank.course_list_id + # } + # question_bank = QuestionBank.new ques_params + # question_bank.save + # end + exercise.update!(exercise_bank_id: current_ex_bank.id) + end + # 试卷的问题的输入 + exercise.exercise_questions.each do |q| + option = { + :question_title => q.question_title, + :question_type => q.question_type, + :question_number => q.question_number, + :question_score => q.question_score, + :shixun_id => q.shixun_id, + :shixun_name => q.shixun_name + } + exercise_bank_question = current_ex_bank.exercise_bank_questions.new option + exercise_bank_question.save! + ## 试卷选项的输入 + if q.question_type != Exercise::PRACTICAL #不为实训题时,试卷选项加入试题答案库 + ex_choices = q.exercise_choices + ex_standard = q.exercise_standard_answers + ex_choices.each do |c| + choice_option = { + :choice_position => c.choice_position, + :choice_text => c.choice_text + } + ex_bank_choice = exercise_bank_question.exercise_bank_choices.new choice_option + ex_bank_choice.save! + end + ex_standard.each do |s| + ex_stand = { + :exercise_bank_choice_id => s.exercise_choice_id, + :answer_text => s.answer_text + } + ex_stand_bank = exercise_bank_question.exercise_bank_standard_answers.new ex_stand + ex_stand_bank.save! + end + else #当为实训题时 + shixun_challenges = q.exercise_shixun_challenges + shixun_challenges.each do |c| + challenge_option = { + :position => c.position, + :challenge_id => c.challenge_id, + :shixun_id => q.shixun_id, + :question_score => c.question_score + } + shixun_challenge_bank = exercise_bank_question.exercise_bank_shixun_challenges.new challenge_option + shixun_challenge_bank.save! + end + end + end + current_ex_bank.save! + end + normal_status(0, "题库更新成功!") + end + end + + #试卷的设置页面 + def exercise_setting + ActiveRecord::Base.transaction do + @user_permission = 2 + @user_course_groups = @course.teacher_group(current_user.id) #当前老师的分班 + @being_setting_course_ids = @exercise.common_published_ids(current_user.id) #当前用户已发布的班级的id + @user_published_setting = @exercise.exercise_group_settings + .find_in_exercise_group("course_group_id", @being_setting_course_ids) #当前用户已发布班级的试卷设置 + exercise_ids = [@exercise.id] + @exercise_publish_count = get_user_permission_course(exercise_ids, Exercise::PUBLISHED).count #判断当前用户是否有试卷已发布的分班,用于显示立即截止/撤销发布 + @exercise_unpublish_count = get_user_permission_course(exercise_ids, Exercise::UNPUBLISHED).count #判断当前用户是否有试卷未发布的分班,用户显示立即发布 + @exercise_users_count = @exercise.exercise_users.commit_exercise_by_status(1).count #判断当前试卷是否有已提交的 + # ## 需添加发送消息的接口,稍后添加 + end + end + + #试卷的提交设置 + def commit_setting + ActiveRecord::Base.transaction do + error_count = 0 # 判断循环里是否有已发布/已截止的,且时间更改了的分班。 + # course_group_ids = @course.teacher_course_group_ids(current_user.id) #当前老师的班级id数组 + course_group_ids = @course.charge_group_ids(current_user) #当前老师的班级id数组 + + exercise_status = @exercise.get_exercise_status(current_user) + + if exercise_status == Exercise::UNPUBLISHED && course_group_ids.size > 0 # 试卷未发布,且老师的分班大于1 ,才可以修改统一设置,否则按试卷默认的来处理 + unified_setting = params[:unified_setting] + else + unified_setting = @exercise.unified_setting + end + + show_statistic = params[:show_statistic] ? true : false + exercise_time = params[:time].blank? ? -1 : params[:time] + question_random = params[:question_random] ? true : false #问题是否随机,0为不随机,1为随机 + choice_random = params[:choice_random] ? true : false + score_open = params[:score_open] ? true : false #分数是否公开 + answer_open = params[:answer_open] ? true : false #答案是否公开 + + # 统一设置或者分班为0,则更新试卷,并删除试卷分组 + if unified_setting || (course_group_ids.size == 0) + tip_exception("发布时间不能为空") if params[:publish_time].blank? + tip_exception("截止时间不能为空") if params[:end_time].blank? + tip_exception("截止时间不能早于发布时间") if params[:publish_time].to_time > params[:end_time].to_time + tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && params[:end_time].to_time > @course.end_date.end_of_day + + params_publish_time = params[:publish_time].to_time + params_end_time = params[:end_time].to_time + + if (exercise_status != Exercise::UNPUBLISHED) && (@exercise.publish_time != params_publish_time) + normal_status(-1, "已发布/已截止,不允许修改发布时间") + elsif params_publish_time.present? && params_end_time.present? && params_end_time < params_publish_time + normal_status(-1, "截止时间不能小于发布时间") + else + #发布时间小于当前时间,则试卷显示为未发布,当截止时间大于当前时间,则显示为已截止 + exercise_status_n = set_exercise_status(params_publish_time, params_end_time) + exercise_params = { + :unified_setting => unified_setting, + :show_statistic => show_statistic, + :time => exercise_time, + :question_random => question_random, + :choice_random => choice_random, + :score_open => score_open, + :answer_open => answer_open, + :exercise_status => exercise_status_n, + :publish_time => params_publish_time, + :end_time => params_end_time + } + @exercise.update!(exercise_params) + @exercise.exercise_group_settings.destroy_all + normal_status(0, "试卷设置成功!") + end + else + params_times = params[:publish_time_groups] #分班返回的json数组{"publish_time_groups":[{"course_group_id":"1","publish_time":"xx","end_time":"xxx"}]} + exercise_groups = @exercise.exercise_group_settings.find_in_exercise_group("course_id", @course.id) #试卷的全部分班信息 + exercise_groups_ids = exercise_groups.pluck(:course_group_id) #问卷的全部分班id + total_common = params_times.map {|k| k[:course_group_id]}.sum.uniq #传入的所有分组的分班id + total_common_group = exercise_groups_ids & total_common #传入的分班与问卷已存在的分班的交集 + old_exercise_groups = exercise_groups_ids - total_common_group #后来传入的分班里,没有了的班级,即需要删除 + + params_times.each do |t| + tip_exception("发布时间不能为空") if t[:publish_time].blank? + tip_exception("截止时间不能为空") if t[:end_time].blank? + tip_exception("截止时间不能早于发布时间") if t[:publish_time].to_time > t[:end_time].to_time + tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && t[:end_time].to_time > @course.end_date.end_of_day + + course_id = t[:course_group_id] + exercise_publish_time = t[:publish_time].to_time + exercise_end_time = t[:end_time].to_time + + exercise_group = exercise_groups.find_in_exercise_group("course_group_id", course_id) #判断该分班是否存在 + if exercise_group.present? && (exercise_group.first.publish_time < Time.now) && (exercise_publish_time != exercise_group.first.publish_time) + error_count += 1 + end + if exercise_group.present? && (exercise_group.first.publish_time < Time.now && exercise_group.first.end_time > Time.now) && (exercise_end_time < Time.now) + error_count += 1 + end + if error_count == 0 + common_group = exercise_groups_ids & course_id #传入的班级与问卷已存在的班级的交集,即表示已有分班的 + new_group_ids = course_id - common_group #新传入的班级id + if common_group.count > 0 #判断试卷的分班设置是否存在,存在则更新,负责则新建 + exercise_group_sets = exercise_groups.find_in_exercise_group("course_group_id", common_group) + exercise_group_sets.each do |the_group_setting| + ex_group_params = { + :publish_time => exercise_publish_time, + :end_time => exercise_end_time + } + + the_group_setting_status = set_exercise_status(the_group_setting.publish_time, the_group_setting.end_time) + if the_group_setting_status == 2 + ex_group_params = { + :publish_time => the_group_setting.publish_time, + :end_time => exercise_end_time < Time.now ? the_group_setting.end_time : exercise_end_time + } + elsif the_group_setting_status == 3 + ex_group_params = { + :publish_time => the_group_setting.publish_time, + :end_time => exercise_end_time + } + end + the_group_setting.update!(ex_group_params) + end + end + if new_group_ids.size > 0 + new_group_ids.each do |c| + exercise_group_params = { + :exercise_id => @exercise.id, + :course_group_id => c, + :course_id => @course.id, + :publish_time => exercise_publish_time, + :end_time => exercise_end_time + } + new_exercise_group = ExerciseGroupSetting.new(exercise_group_params) + new_exercise_group.save! + end + end + end + end + + if error_count > 0 + error_count == 0 + normal_status(-1, "试卷发布/截止时间不能小于当前时间") + else + # 未发布的分班设置才能删除 + if old_exercise_groups.size > 0 + old_all_ex_groups = exercise_groups.find_in_exercise_group("course_group_id", old_exercise_groups).exercise_group_not_published + old_all_ex_groups.destroy_all + end + #试卷更新为exercise_group_setting的发布时间最小,截止时间最大 + e_time_present = exercise_groups.end_time_no_null.map(&:end_time) + p_time_present = exercise_groups.publish_time_no_null.map(&:publish_time) + e_time = e_time_present.size > 0 ? e_time_present.max : nil + p_time = p_time_present.size > 0 ? p_time_present.min : nil + exercise_status = 1 + if p_time.nil? #发布时间为空,则表示问卷未发布 + exercise_status = 1 + elsif p_time.present? && e_time.present? + exercise_status = set_exercise_status(p_time, e_time) + end + exercise_params = { + :unified_setting => unified_setting, + :show_statistic => show_statistic, + :time => exercise_time, + :question_random => question_random, + :choice_random => choice_random, + :score_open => score_open, + :answer_open => answer_open, + :exercise_status => exercise_status, + :publish_time => p_time, + :end_time => e_time + } + @exercise.update!(exercise_params) + if @exercise.exercise_status == Exercise::PUBLISHED + if @exercise.course_acts.size == 0 + @exercise.course_acts << CourseActivity.new(:user_id => @exercise.user_id, :course_id => @exercise.course_id) + end + end + normal_status(0, "试卷设置成功!") + end + end + end + end + + # 对未提交的用户进行调分 + def adjust_score + exercise_user = @exercise.exercise_users.find_by!(user_id: params[:user_id]) + tip_exception("已提交的作品请去评阅页进行调分") if exercise_user.commit_status == 1 && exercise_user.commit_method != 5 + if @exercise.subjective_score > 0 + tip_exception("主观题成绩不能为空") if params[:subjective_score].blank? + tip_exception("主观题成绩不能小于零") if params[:subjective_score].to_f < 0 + tip_exception("主观题成绩不能大于总分值:#{@exercise.subjective_score}分") if params[:subjective_score].to_f.round(1) > @exercise.subjective_score.round(1) + end + + if @exercise.objective_score > 0 + tip_exception("客观题成绩不能为空") if params[:objective_score].blank? + tip_exception("客观题成绩不能小于零") if params[:objective_score].to_f < 0 + tip_exception("客观题成绩不能大于总分值:#{@exercise.objective_score}分") if params[:objective_score].to_f.round(1) > @exercise.objective_score.round(1) + end + + ActiveRecord::Base.transaction do + start_at_time = exercise_user.start_at || Time.now + subjective_score = @exercise.subjective_score > 0 ? params[:subjective_score].to_f.round(2) : 0 + objective_score = @exercise.objective_score > 0 ? params[:objective_score].to_f.round(2) : 0 + score = subjective_score + objective_score + if exercise_user.commit_status == 1 + exercise_user.update!(score: score, subjective_score: subjective_score, objective_score: objective_score) + else + exercise_user.update!(start_at: start_at_time, end_at: Time.now, status: 1, commit_status: 1, score: score, + subjective_score: subjective_score, objective_score: objective_score, commit_method: 5) + end + + ExerciseUserScore.create!(exercise_id: @exercise.id, exercise_user_id: exercise_user.id, + subjective_score: subjective_score, objective_score: objective_score) + normal_status("操作成功") + end + end + + #我的题库 + def my_exercises + ActiveRecord::Base.transaction do + ## 我的试卷题库 + @current_user_exercises = current_user.exercise_banks.find_by_c_type("Exercise") + if @current_user_exercises.present? + + if params[:search].present? + search_type = params[:search].to_s.strip + @current_user_exercises = @current_user_exercises.exercise_bank_search(search_type) + end + page = params[:page] || 1 + limit = params[:limit] || 15 + @my_exercises_count = @current_user_exercises.size + @current_user_exercises = @current_user_exercises.page(page).per(limit) + else + @current_user_exercises = [] + end + end + end + + # 公共题库 + def public_exercises + ActiveRecord::Base.transaction do + if current_user.is_certification_teacher + @user_certification = 1 #用户已通过认证 + @public_exercises = ExerciseBank.find_by_c_type("Exercise").public_exercises + if @public_exercises.present? + if params[:search].present? + search_type = params[:search].to_s.strip + @public_exercises = @public_exercises.exercise_bank_search(search_type) + end + page = params[:page] || 1 + limit = params[:limit] || 15 + @public_exercises_count = @public_exercises.size + @public_exercises = @public_exercises.page(page).per(limit) + else + @public_exercises_count = 0 + @public_exercises = [] + end + else + @user_certification = 0 #用户未通过认证 + @public_exercises_count = 0 + @public_exercises = [] + end + end + end + + #立即发布的弹窗内容 + def publish_modal + + ActiveRecord::Base.transaction do + exercise_ids = params[:check_ids] + if exercise_ids.count > 0 + @course_groups = get_user_permission_course(exercise_ids, 1) + else + @course_groups = [] + end + end + end + + # 详情页的立即发布弹框 + def publish_groups + @current_user = current_user + # 可立即发布的分班:当前用户管理的分班去除已发布的分班 + group_ids = @course.charge_group_ids(@current_user) - @exercise.exercise_group_settings.exercise_group_published.pluck(:course_group_id) + @course_groups = @course.course_groups.where(id: group_ids) + @group_settings = @exercise.exercise_group_settings.where(course_group_id: group_ids) + end + + #首页批量或单独 立即发布,应是跳出弹窗,设置开始时间和截止时间。 + def publish + group_ids = params[:group_ids]&.reject(&:blank?) + if params[:detail].blank? + tip_exception("缺少截止时间参数") if params[:end_time].blank? + tip_exception("截止时间不能早于当前时间") if params[:end_time] <= strf_time(Time.now) + tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && params[:end_time] > strf_time(@course.end_date.end_of_day) + else + group_end_times = params[:group_end_times].reject(&:blank?).map {|time| time.to_time} + tip_exception("缺少截止时间参数") if group_end_times.blank? + tip_exception("截止时间和分班参数的个数不一致") if group_end_times.length != group_ids.length + group_end_times.each do |time| + tip_exception("分班截止时间不能早于当前时间") if time <= Time.now + tip_exception("分班截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && time > @course.end_date.end_of_day + end + end + + ActiveRecord::Base.transaction do + check_ids = Exercise.where(id: params[:check_ids]) + ex_end_time = params[:end_time].blank? ? Time.at(((1.month.since.to_i) / 3600.0).ceil * 3600) : params[:end_time].to_time + check_ids.each do |exercise| + if exercise.present? + if exercise.unified_setting + ex_status = exercise.exercise_status #则为试卷的状态 + else + ex_status = @course.course_groups.where(id: params[:group_ids]).size != + exercise.exercise_group_settings.where(course_group_id: params[:group_ids]).exercise_group_published.size ? 1 : 0 + end + if ex_status == 1 #如果试卷存在已发布的,或者是已截止的,那么则直接跳过 + g_course = group_ids #表示是否传入分班参数,如果传入分班的参数,那么试卷的统一设置需修改 + tiding_group_ids = g_course + if g_course + user_course_groups = @course.course_groups.pluck(:id) + if g_course.map(&:to_i).sort == user_course_groups.sort && + ((params[:detail] && group_end_times.min == group_end_times.max) || params[:detail].blank?) # 如果是设置为全部班级,则试卷不用分组,且试卷设定为统一设置,否则则分组设置 + exercise.exercise_group_settings.destroy_all + ex_unified = true + e_time = params[:detail] ? group_end_times.max : ex_end_time + tiding_group_ids = [] + else + ex_unified = false + g_course.each_with_index do |i, index| + exercise_group_setting = exercise.exercise_group_settings.find_in_exercise_group("course_group_id", i).first #根据课堂分班的id,寻找试卷所在的班级 + group_end_time = params[:detail] ? group_end_times[index] : ex_end_time + if exercise_group_setting.present? #如果该试卷分组存在,则更新,否则新建 + exercise_group_setting.update!(publish_time: Time.now, end_time: group_end_time) + else + p_course_group = { + :exercise_id => exercise.id, + :course_group_id => i, + :course_id => exercise.course.id, + :publish_time => Time.now, + :end_time => group_end_time, + } + new_exercise_group = exercise.exercise_group_settings.new p_course_group + new_exercise_group.save! + end + end + # group_ids = params[:group_ids] + e_time = exercise.exercise_group_settings.end_time_no_null.map(&:end_time).max + end + else + exercise.exercise_group_settings.destroy_all + ex_unified = true + e_time = ex_end_time + end + + ex_status = set_exercise_status(Time.now, e_time) + exercise_params = { + :publish_time => Time.now, + :end_time => e_time, + :exercise_status => ex_status, + :unified_setting => ex_unified + } + exercise.update!(exercise_params) + + if exercise.course_acts.size == 0 + exercise.course_acts << CourseActivity.new(:user_id => exercise.user_id, :course_id => exercise.course_id) + end + ExercisePublishNotifyJob.perform_later(exercise.id, tiding_group_ids) + end + end + end + normal_status(0, "试卷发布成功!") + end + end + + #立即截止的弹窗内容 + def end_modal + ActiveRecord::Base.transaction do + exercise_ids = params[:check_ids] + if exercise_ids.count > 0 + @course_groups = get_user_permission_course(exercise_ids, 3) + else + @course_groups = [] + end + end + end + + # 首页批量或单独 立即截止,截止时间为当前时间 + def end_exercise + + ActiveRecord::Base.transaction do + check_ids = Exercise.where(id: params[:check_ids]) + course_students = @course.students #课堂的全部学生数 + check_ids.each do |exercise| + exercise_status = exercise.get_exercise_status(current_user) + if exercise_status == Exercise::PUBLISHED #跳过已截止的或未发布的 + g_course = params[:group_ids] + if g_course.present? + teacher_course_group_ids = @course.charge_group_ids(current_user) + all_course_group_ids = @course.course_groups.pluck(:id) + if exercise.unified_setting && g_course.map(&:to_i).sort == all_course_group_ids.sort #开始为统一设置 + exercise.exercise_group_settings.destroy_all + new_ex_status = set_exercise_status(exercise.publish_time, Time.now) + exercise.update!(:end_time => Time.now, :exercise_status => new_ex_status) + exercise_users = exercise.exercise_users + else + course_members_ids = course_students.course_find_by_ids("course_group_id", g_course).pluck(:user_id).uniq #该班级的全部学生 + exercise_users = exercise.exercise_users.exercise_commit_users(course_members_ids) #参与答题的学生数 + ex_group_setting = exercise.exercise_group_settings + old_exercise_groups = ex_group_setting.find_in_exercise_group("course_group_id", g_course) #试卷的分组设置 + left_course_groups = teacher_course_group_ids - g_course + left_exercise_groups = ex_group_setting.find_in_exercise_group("course_group_id", left_course_groups) + if left_exercise_groups.blank? && exercise.unified_setting + if left_course_groups.size > 0 #开始为统一设置,但是立即截止为分班。则创建没有立即截止的班级的exercise_group_setting + left_course_groups.each do |g| + ex_group_options = { + :exercise_id => exercise.id, + :course_group_id => g, + :course_id => @course.id, + :publish_time => exercise.publish_time, + :end_time => exercise.end_time + } + ExerciseGroupSetting.create!(ex_group_options) + end + end + end + if old_exercise_groups.present? + old_exercise_groups.update_all(:end_time => Time.now) + else + g_course.each do |g| + ex_group_options = { + :exercise_id => exercise.id, + :course_group_id => g, + :course_id => @course.id, + :publish_time => exercise.publish_time, + :end_time => Time.now + } + ExerciseGroupSetting.create!(ex_group_options) + end + end + new_end_time = exercise.exercise_group_settings.end_time_no_null.map(&:end_time) # 试卷结束时间不为空的 + new_end_time_s = new_end_time.count > 0 ? new_end_time.max : Time.now + new_ex_status = set_exercise_status(exercise.publish_time, new_end_time_s) + exercise.update!(:end_time => new_end_time_s, :exercise_status => new_ex_status, :unified_setting => false) + end + else + exercise_users = exercise.exercise_users + exercise.update!(:exercise_status => 3, :end_time => Time.now, :unified_setting => true) + end + + ex_user_ids = exercise_users.pluck(:id) + + EndExerciseCalculateJob.perform_later(ex_user_ids, exercise, Time.now.to_s) + # exercise_users.each do |user| + # if user.commit_status == 0 && user.start_at.present? + # objective_score = calculate_student_score(exercise,user.user)[:total_score] + # user_sub_score = user.subjective_score + # subjective_score = user_sub_score < 0.0 ? 0.0 : user_sub_score + # total_score = objective_score + subjective_score + # commit_option = { + # :status => 1, + # :commit_status => 1, + # :end_at => Time.now, + # :objective_score => objective_score, + # :score => total_score, + # :subjective_score => user_sub_score + # } + # user.update_attributes(commit_option) + # end + # end + end + end + normal_status(0, "试卷截止成功!") + end + end + + #学生撤销回答 + def cancel_exercise + ActiveRecord::Base.transaction do + ex_question_ids = @exercise.exercise_questions.pluck(:id) + exercise_user = @exercise.exercise_users.exercise_commit_users(current_user.id).first + if exercise_user.present? + if exercise_user.commit_status == 1 && @exercise.get_exercise_status(current_user) == Exercise::PUBLISHED #用户已提交且试卷提交中 + if @exercise.time == -1 || ((Time.now.to_i - exercise_user.start_at.to_i) < @exercise.time.to_i * 60) + exercise_user.update!(:score => nil, :end_at => nil, :status => nil, :commit_status => 0, + :objective_score => 0.0, :subjective_score => -1.0) + exercise_user.user.exercise_shixun_answers.search_shixun_answers("exercise_question_id", ex_question_ids).destroy_all + exercise_answers = exercise_user.user.exercise_answers.search_answer_users("exercise_question_id", ex_question_ids) + exercise_answers.update_all(:score => -1.0) + all_answer_comment = ExerciseAnswerComment.search_answer_comments("exercise_question_id", ex_question_ids) + .search_answer_comments("exercise_answer_id", exercise_answers.pluck(:id)) + all_answer_comment.destroy_all + normal_status(0, "撤销回答成功") + else + normal_status(-1, "用户答题时间已到") + end + else + normal_status(-1, "用户未提交/试卷不是提交中") + end + else + normal_status(-1, "当前用户未答题") + end + end + end + + #打回重做modal + def redo_modal + ActiveRecord::Base.transaction do + #搜索 + if params[:realname].present? + search_name = params[:realname] + #搜索用户的nickname,如果存在则返回,否则继续查询用户的真实姓名或学生号 + @exercise_users = @exercise_users.includes(:user).where("LOWER(concat(users.lastname, users.firstname)) like ?", + "%#{search_name}%") + end + if params[:student_id].present? + search_st_id = params[:student_id].to_i + @exercise_users = @exercise_users.includes(user: [:user_extension]) + .where('user_extensions.student_id like ?', "%#{search_st_id}%") + end + sort = params[:sort] ? params[:sort] : "asc" + @exercise_users = @exercise_users.order("score #{sort}") + @exercise_users_size = @exercise_users.size + # 分页 + page = params[:page] || 1 + limit = params[:limit] || 15 + @exercise_users = @exercise_users.page(page).per(limit) + end + end + + #打回重做确认 + def redo_exercise + ActiveRecord::Base.transaction do + user_ids = params[:user_ids] + if user_ids.present? + redo_option = { + :score => 0.0, + :start_at => nil, + :end_at => nil, + :status => nil, + :commit_status => 0, + :objective_score => 0.0, + :subjective_score => -1.0, + :commit_method => 0 + } + redo_exercise_users = @exercise_users.exercise_commit_users(user_ids) + redo_exercise_users.update_all(redo_option) + exercise_question_ids = @exercise.exercise_questions.pluck(:id).uniq + ExerciseAnswer.search_answer_users("user_id", user_ids) + .search_answer_users("exercise_question_id", exercise_question_ids).destroy_all + ExerciseShixunAnswer.search_shixun_answers("user_id", user_ids) + .search_shixun_answers("exercise_question_id", exercise_question_ids).destroy_all + + normal_status(0, "已成功打回重做!") + else + normal_status(-1, "请选择学生!") + end + end + end + + #学生开始答题页面 + def start_answer + ex_users_current = ExerciseUser.where(user_id: @exercise_current_user_id, exercise_id: @exercise.id) #不能用@exercise.exercise_users,因为exercise_users删除时,只是状态改变,未删除 + @exercise_user_current = ex_users_current&.first + if ex_users_current.exists? + if @exercise_user_current.start_at.blank? + @exercise_user_current.update!(start_at: Time.now) + end + else + if @user_course_identity > Course::ASSISTANT_PROFESSOR #当为老师的时候,不创建exercise_user表,理论上老师是不能进入答题的 + exercise_user_params = { + :user_id => @exercise_current_user_id, + :exercise_id => @exercise.id, + :start_at => Time.now + } + exercise_user_current = ExerciseUser.new(exercise_user_params) + exercise_user_current.save! + end + end + @t_user_exercise_status = @exercise.get_exercise_status(current_user) + + @user_left_time = nil + if @user_course_identity < Course::STUDENT || (@t_user_exercise_status == 3) || + (ex_users_current.exists? && @exercise_user_current.commit_status == 1) + @user_exercise_status = 1 #当前用户为老师/试卷已截止/试卷已提交不可编辑 + else + @user_left_time = get_exercise_left_time(@exercise, current_user) + @user_exercise_status = 0 #可编辑 + end + + @exercise_questions = @exercise.exercise_questions + + if @exercise.question_random + @exercise_questions = @exercise_questions.order("RAND()") + else + @exercise_questions = @exercise_questions.order("question_number ASC") + end + # 判断问题是否已回答还是未回答 + @exercise_questions = @exercise_questions.includes(:exercise_shixun_challenges, + :exercise_shixun_answers, + :exercise_answers, + :exercise_standard_answers) + + if @t_user_exercise_status == Exercise::DEADLINE + get_each_student_exercise(@exercise.id, @exercise_questions, @exercise_current_user_id) + end + get_user_answer_status(@exercise_questions, @exercise_current_user_id, @exercise, @t_user_exercise_status) + + end + + #提交试卷前的弹窗 + def begin_commit + ActiveRecord::Base.transaction do + if @user_course_identity > Course::ASSISTANT_PROFESSOR #为学生时 + @exercise_questions = @exercise.exercise_questions + @shixun_undo = 0 + @ques_undo = 0 + ex_answer_time = @exercise.time.to_i + if ex_answer_time > 0 #有剩余时间的时候 + user_left_time = get_exercise_left_time(@exercise, current_user) + @ex_end_time = Time.now + user_left_time.to_i.seconds else - ques_vote = q.exercise_answers.search_exercise_answer("user_id",current_user.id) - if ques_vote.blank? - @ques_undo += 1 + @ex_end_time = @exercise.get_exercise_end_time(current_user.id) + end + # @ex_end_time = @exercise.get_exercise_end_time(current_user.id) + # if ex_answer_time > 0 + # left_answer_time = Time.now + ex_answer_time.minutes #判断试卷的倒计时和截止时间哪个先到 + # if left_answer_time < @ex_end_time + # exercise_end_time = @exercise.exercise_users.exercise_commit_users(current_user.id) + # if exercise_end_time.present? + # ex_end_times = exercise_end_time.first.start_at.nil? ? Time.now : exercise_end_time.first.start_at + # @ex_end_time = ex_end_times + ex_answer_time.minutes + # end + # end + # end + @exercise_questions.each do |q| + if q.question_type == Exercise::PRACTICAL #当为实训题时 + user_myshixun = q.shixun.myshixuns.search_myshixun_user(current_user.id) + if user_myshixun.blank? || user_myshixun.first.status != Exercise::UNPUBLISHED #当前用户的实训是否做完 + @shixun_undo += 1 + end + else + ques_vote = q.exercise_answers.search_exercise_answer("user_id", current_user.id) + if ques_vote.blank? + @ques_undo += 1 + end end end end end - rescue Exception => e - uid_logger_error(e.message) - tip_exception("试卷提交失败!") - raise ActiveRecord::Rollback end - end - end - # 学生提交试卷 - def commit_exercise - tip_exception(0, "试卷截止时间已到,系统已自动提交") if @answer_committed_user.commit_status == 1 - ActiveRecord::Base.transaction do - begin - can_commit_exercise = false - user_left_time = nil - if @user_course_identity > Course::ASSISTANT_PROFESSOR #为学生时 - if params[:commit_method].to_i == 2 #自动提交时 - user_left_time = get_exercise_left_time(@exercise,current_user) - Rails.logger.info("######__________auto_commit_user_left_time_________################{user_left_time}") - if user_left_time.to_i <= 0 + # 学生提交试卷 + def commit_exercise + tip_exception(0, "试卷截止时间已到,系统已自动提交") if @answer_committed_user.commit_status == 1 + ActiveRecord::Base.transaction do + can_commit_exercise = false + user_left_time = nil + if @user_course_identity > Course::ASSISTANT_PROFESSOR #为学生时 + if params[:commit_method].to_i == 2 #自动提交时 + user_left_time = get_exercise_left_time(@exercise, current_user) + Rails.logger.info("######__________auto_commit_user_left_time_________################{user_left_time}") + if user_left_time.to_i <= 0 + can_commit_exercise = true + end + else can_commit_exercise = true end + if can_commit_exercise + objective_score = calculate_student_score(@exercise, current_user, Time.now)[:total_score] + subjective_score = @answer_committed_user.subjective_score + total_score_subjective_score = subjective_score < 0.0 ? 0.0 : subjective_score + total_score = objective_score + total_score_subjective_score + commit_option = { + :status => 1, + :commit_status => 1, + :end_at => Time.now, + :objective_score => objective_score, + :score => total_score, + :subjective_score => subjective_score, + :commit_method => @answer_committed_user&.commit_method.to_i > 0 ? @answer_committed_user&.commit_method.to_i : params[:commit_method].to_i + } + @answer_committed_user.update!(commit_option) + CommitExercsieNotifyJobJob.perform_later(@exercise.id, current_user.id) + normal_status(0, "试卷提交成功!") + else + normal_status(-2, "#{user_left_time.to_i}") + end else - can_commit_exercise = true - end - if can_commit_exercise - objective_score = calculate_student_score(@exercise,current_user,Time.now)[:total_score] - subjective_score = @answer_committed_user.subjective_score - total_score_subjective_score = subjective_score < 0.0 ? 0.0 : subjective_score - total_score = objective_score + total_score_subjective_score - commit_option = { - :status => 1, - :commit_status => 1, - :end_at => Time.now, - :objective_score => objective_score, - :score => total_score, - :subjective_score => subjective_score, - :commit_method => @answer_committed_user&.commit_method.to_i > 0 ? @answer_committed_user&.commit_method.to_i : params[:commit_method].to_i - } - @answer_committed_user.update!(commit_option) - CommitExercsieNotifyJobJob.perform_later(@exercise.id, current_user.id) - normal_status(0,"试卷提交成功!") - else - normal_status(-2,"#{user_left_time.to_i}") + normal_status(-1, "提交失败,当前用户不为课堂学生!") end - else - normal_status(-1,"提交失败,当前用户不为课堂学生!") end - rescue Exception => e - uid_logger_error(e.message) - tip_exception("试卷提交失败!") - raise ActiveRecord::Rollback end - end - end - #教师评阅试卷 及学生查看试卷 - def review_exercise - ActiveRecord::Base.transaction do - begin - # 1 老师权限,0 学生权限 - @is_teacher_or = (@user_course_identity < Course::STUDENT) ? 1 : 0 - @student_status = 2 - @exercise_questions = @exercise.exercise_questions.includes(:exercise_shixun_challenges,:exercise_standard_answers,:exercise_answers,:exercise_shixun_answers,:exercise_answer_comments).order("question_number ASC") - @question_status = [] - get_exercise_status = @exercise.get_exercise_status(current_user) #当前用户的试卷状态 - @ex_answer_status = @exercise.get_exercise_status(@ex_user&.user) #当前试卷用户的试卷状态 - if @ex_user.present? && @is_teacher_or == 0 - if get_exercise_status == Exercise::PUBLISHED #当前用户已提交,且试卷未截止 - if @ex_user.commit_status == 0 #学生未提交,且当前为学生 - @student_status = 0 - else - @student_status = 1 - get_user_answer_status(@exercise_questions,@exercise_current_user_id,@exercise,get_exercise_status) + #教师评阅试卷 及学生查看试卷 + def review_exercise + ActiveRecord::Base.transaction do + # 1 老师权限,0 学生权限 + @is_teacher_or = (@user_course_identity < Course::STUDENT) ? 1 : 0 + @student_status = 2 + @exercise_questions = @exercise.exercise_questions.includes(:exercise_shixun_challenges, :exercise_standard_answers, :exercise_answers, :exercise_shixun_answers, :exercise_answer_comments).order("question_number ASC") + @question_status = [] + get_exercise_status = @exercise.get_exercise_status(current_user) #当前用户的试卷状态 + @ex_answer_status = @exercise.get_exercise_status(@ex_user&.user) #当前试卷用户的试卷状态 + if @ex_user.present? && @is_teacher_or == 0 + if get_exercise_status == Exercise::PUBLISHED #当前用户已提交,且试卷未截止 + if @ex_user.commit_status == 0 #学生未提交,且当前为学生 + @student_status = 0 + else + @student_status = 1 + get_user_answer_status(@exercise_questions, @exercise_current_user_id, @exercise, get_exercise_status) + end end end + if @student_status == 2 + get_each_student_exercise(@exercise.id, @exercise_questions, @exercise_current_user_id) + end end - if @student_status == 2 - get_each_student_exercise(@exercise.id,@exercise_questions,@exercise_current_user_id) - end - rescue Exception => e - uid_logger_error(e.message) - tip_exception("没有权限") - raise ActiveRecord::Rollback end - end - end - #答题列表 - def exercise_lists - begin + #答题列表 + def exercise_lists @current_user_id = current_user.id exercise_ids = [@exercise.id] @exercise_status = @exercise.get_exercise_status(current_user) @course_all_members = @course.students @c_group_counts = @course.course_groups_count question_types = @exercise.exercise_questions.pluck(:question_type).uniq - @exercise_publish_count = get_user_permission_course(exercise_ids,Exercise::PUBLISHED).count #判断是否有已发布的分班 - @exercise_unpublish_count = get_user_permission_course(exercise_ids,Exercise::UNPUBLISHED).count #判断是否有未发布的分班 + @exercise_publish_count = get_user_permission_course(exercise_ids, Exercise::PUBLISHED).count #判断是否有已发布的分班 + @exercise_unpublish_count = get_user_permission_course(exercise_ids, Exercise::UNPUBLISHED).count #判断是否有未发布的分班 - if (question_types.size > 1) && question_types.include?(Exercise::SUBJECTIVE) #是否包含主观题,或者是否大于1 + if (question_types.size > 1) && question_types.include?(Exercise::SUBJECTIVE) #是否包含主观题,或者是否大于1 @subjective_type = 1 else @subjective_type = 0 end #初始化值 - @exercise_users_list = [] #答题用户列表 - @exercise_course_groups = [] #当前用户有权限的班级 - @exercise_unanswers = 0 # 未答用户数 - @exercise_answers = 0 #已答用户数 - @exercise_users_count = 0 #全部用户数 - @teacher_review_count = 0 #已评数 - @teacher_unreview_count = 0 #未评数 + @exercise_users_list = [] #答题用户列表 + @exercise_course_groups = [] #当前用户有权限的班级 + @exercise_unanswers = 0 # 未答用户数 + @exercise_answers = 0 #已答用户数 + @exercise_users_count = 0 #全部用户数 + @teacher_review_count = 0 #已评数 + @teacher_unreview_count = 0 #未评数 #试卷的答题列表页的显示用户 - if @user_course_identity < Course::STUDENT #当前为老师,而且老师只能查看自己班级的/课堂的试卷 + if @user_course_identity < Course::STUDENT #当前为老师,而且老师只能查看自己班级的/课堂的试卷 @exercise_current_user_status = 0 unless @exercise_status == Exercise::UNPUBLISHED ex_common_ids = @exercise.common_published_ids(current_user.id) @exercise_course_groups = @course.get_ex_published_course(ex_common_ids) - @exercise_users_list = @exercise.all_exercise_users(current_user.id) #当前老师所在班级的全部学生 + @exercise_users_list = @exercise.all_exercise_users(current_user.id) #当前老师所在班级的全部学生 get_exercise_answers(@exercise_users_list, @exercise_status) end - else #当前为学生或者有过答题的 - @ex_user_end_time = @exercise.get_exercise_end_time(current_user.id) #当前用户所看到的剩余时间 + else #当前为学生或者有过答题的 + @ex_user_end_time = @exercise.get_exercise_end_time(current_user.id) #当前用户所看到的剩余时间 @exercise_all_users = @exercise.get_stu_exercise_users - get_exercise_answers(@exercise_all_users, @exercise_status) # 未答和已答的 + get_exercise_answers(@exercise_all_users, @exercise_status) # 未答和已答的 exercise_current_user = @exercise_all_users.exercise_commit_users(current_user.id) - if exercise_current_user.exists? #表示为课堂学生或已回答的 + if exercise_current_user.exists? #表示为课堂学生或已回答的 @exercise_current_user_status = 1 - if @exercise.score_open && @exercise_status == Exercise::DEADLINE #勾选了成绩公开且试卷已截止的 + if @exercise.score_open && @exercise_status == Exercise::DEADLINE #勾选了成绩公开且试卷已截止的 all_user_ids = @exercise_all_users.pluck(:user_id) - all_user_ids.delete(current_user.id) #删除了当前用户的ID + all_user_ids.delete(current_user.id) #删除了当前用户的ID @exercise_users_list = @exercise_all_users.exercise_commit_users(all_user_ids).distinct - @current_user_ex_answers = exercise_current_user #当前用户的回答 + @current_user_ex_answers = exercise_current_user #当前用户的回答 else @exercise_users_list = exercise_current_user end - else #表示为未回答的,或未非课堂成员的 - @exercise_current_user_status = 2 #当前用户非课堂成员 + else #表示为未回答的,或未非课堂成员的 + @exercise_current_user_status = 2 #当前用户非课堂成员 end end @@ -1297,230 +2486,545 @@ class ExercisesController < ApplicationController order_type = params[:order_type] || "desc" if @exercise_users_list.present? && @exercise_users_list.size > 0 - @exercise_users_count = @exercise_users_list.size #当前显示的全部成员数量 + @exercise_users_count = @exercise_users_list.size #当前显示的全部成员数量 teacher_reviews = @exercise_users_list.exercise_review teacher_unreviews = @exercise_users_list.exercise_unreview - @teacher_review_count = teacher_reviews.size #已评阅 - @teacher_unreview_count = teacher_unreviews.size #未评阅 + @teacher_review_count = teacher_reviews.size #已评阅 + @teacher_unreview_count = teacher_unreviews.size #未评阅 #是否评阅 if params[:review].present? - review_type = params[:review].first.to_i #已评,则数据为1,未评,则数据为0,前端传过来的为数组 + review_type = params[:review].first.to_i #已评,则数据为1,未评,则数据为0,前端传过来的为数组 if review_type == 1 - @exercise_users_list = teacher_reviews + @exercise_users_list = teacher_reviews + else + @exercise_users_list = teacher_unreviews + end + end + + #答题状态的选择 + if params[:commit_status].present? + choose_type = params[:commit_status] + @exercise_users_list = @exercise_users_list.commit_exercise_by_status(choose_type) + end + + #班级的选择 + if params[:exercise_group_id].present? + group_id = params[:exercise_group_id] + exercise_students = @course_all_members.course_find_by_ids("course_group_id", group_id) #试卷所分班的全部人数 + user_ids = exercise_students.pluck(:user_id).reject(&:blank?) + @exercise_users_list = @exercise_users_list.exercise_commit_users(user_ids) + end + + #搜索 + if params[:search].present? + @exercise_users_list = @exercise_users_list.joins(user: :user_extension).where("CONCAT(lastname, firstname) like ? OR student_id like ?", "%#{params[:search]}%", "%#{params[:search]}%") + end + + exercise_user_joins = @exercise_users_list.joins(user: :user_extension) + + if order == "student_id" + @exercise_users_list = exercise_user_joins.order("user_extensions.student_id #{order_type}") + elsif order == "score" + @exercise_users_list = exercise_user_joins.order("#{order} #{order_type}") + else + @exercise_users_list = exercise_user_joins.order("end_at #{order_type}, start_at #{order_type}") + end + + @export_ex_users = @exercise_users_list + + @exercise_users_size = @exercise_users_list.size + + # 分页 + @page = params[:page] || 1 + @limit = params[:limit] || 20 + @exercise_users_list = @exercise_users_list.page(@page).per(@limit) + else + @exercise_users_list = [] + @export_ex_users = @exercise_users_list + @exercise_users_size = 0 + end + + if params[:format] == "xlsx" + if @user_course_identity > Course::ASSISTANT_PROFESSOR + tip_exception(403, "无权限操作") + elsif @exercise_status == Exercise::UNPUBLISHED + normal_status(-1, "试卷未发布") + elsif (@exercise_users_size == 0) || (@export_ex_users&.exercise_user_committed.size == 0) + normal_status(-1, "暂无用户提交") + elsif params[:export].present? && params[:export] + normal_status(0, "正在下载中") else - @exercise_users_list = teacher_unreviews + respond_to do |format| + format.xlsx { + set_export_cookies + get_export_users(@exercise, @course, @export_ex_users) + exercise_export_name_ = + "#{current_user.real_name}_#{@course.name}_#{@exercise.exercise_name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}" + render xlsx: "#{exercise_export_name_.strip}", template: "exercises/exercise_lists.xlsx.axlsx", locals: {table_columns: @table_columns, exercise_users: @user_columns} + } + end end end + end - #答题状态的选择 - if params[:commit_status].present? - choose_type = params[:commit_status] - @exercise_users_list = @exercise_users_list.commit_exercise_by_status(choose_type) + #导出空白试卷 + def export_exercise + @request_url = request.base_url + @exercise_questions = @exercise.exercise_questions.includes(:exercise_choices).order("question_number ASC") + filename_ = "#{@exercise.user.real_name}_#{@course.name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}.pdf" + stylesheets = "#{Rails.root}/app/templates/exercise_export/exercise_export.css" + if params[:export].present? && params[:export] + normal_status(0, "正在下载中") + else + set_export_cookies + render pdf: 'exercise_export/blank_exercise', filename: filename_, stylesheets: stylesheets, disposition: 'inline', type: "pdf_attachment.content_type", stream: false end + end + + #空白试卷预览页面,仅供测试使用,无其他任何用途 + # def blank_exercise + # ActiveRecord::Base.transaction do + # begin + # @exercise_questions = @exercise.exercise_questions.order("question_number ASC") + # challenge_ids = @exercise_questions.joins(:exercise_shixun_challenges).pluck("exercise_shixun_challenges.challenge_id") + # get_each_student_exercise(@exercise.id,@exercise_questions,31798) + # @games = @exercise_user.user.games.ch_games(challenge_ids) + # respond_to do |format| + # format.html + # end + # rescue Exception => e + # uid_logger_error(e.message) + # tip_exception("没有权限") + # raise ActiveRecord::Rollback + # end + # end + # end + + #学生的统计结果 + def exercise_result + exercise_ids = [@exercise.id] + @exercise_publish_count = get_user_permission_course(exercise_ids, Exercise::PUBLISHED).size #判断是否有已发布的分班 + @exercise_unpublish_count = get_user_permission_course(exercise_ids, Exercise::UNPUBLISHED).size #判断是否有未发布的分班 + @course_all_members = @course.students #课堂的全部学生 + @exercise_all_users = @exercise.exercise_users + ex_common_ids = @exercise.common_published_ids(current_user.id) + @exercise_course_groups = @course.get_ex_published_course(ex_common_ids) #班级的选择 if params[:exercise_group_id].present? group_id = params[:exercise_group_id] - exercise_students = @course_all_members.course_find_by_ids("course_group_id",group_id) #试卷所分班的全部人数 + exercise_students = @course_all_members.course_find_by_ids("course_group_id", group_id) # 试卷所分班的全部人数 user_ids = exercise_students.pluck(:user_id).reject(&:blank?) - @exercise_users_list = @exercise_users_list.exercise_commit_users(user_ids) + @exercise_all_users = @exercise.exercise_users.exercise_commit_users(user_ids) + @course_all_members_count = @exercise_all_users.size + else + @exercise_users_list = @exercise.all_exercise_users(current_user.id) + @course_all_members_count = @exercise_users_list.size end + @exercise_commit_users = @exercise_all_users.commit_exercise_by_status(1) #试卷的已提交用户 + @exercise_commit_user_ids = @exercise_commit_users.pluck(:user_id).uniq #已提交试卷的全部用户id + @exercise_commit_user_counts = @exercise_commit_users.size #试卷的已提交用户人数 + @exercise_status = @exercise.get_exercise_status(current_user) - #搜索 - if params[:search].present? - @exercise_users_list = @exercise_users_list.joins(user: :user_extension).where("CONCAT(lastname, firstname) like ? OR student_id like ?", "%#{params[:search]}%", "%#{params[:search]}%") + #提交率 + if @course_all_members_count == 0 + commit_percent = 0.00 + min_score = 0.0 + max_score = 0.0 + average_score = 0.0 + fail_counts = 0 + pass_counts = 0 + good_counts = 0 + best_counts = 0 + else + commit_percent = (@exercise_commit_user_counts / @course_all_members_count.to_f).round(3) + exercise_scores = @exercise_commit_users.pluck(:score).reject(&:blank?) + min_score = exercise_scores.min.present? ? exercise_scores.min : 0.0 + max_score = exercise_scores.max.present? ? exercise_scores.max : 0.0 + total_score = exercise_scores.sum.present? ? exercise_scores.sum : 0.0 + average_score = @exercise_commit_user_counts > 0 ? (total_score.round(1) / @exercise_commit_user_counts).round(1) : 0.0 + question_scores = @exercise.question_scores + fail_score = question_scores * 0.6.round(2) + pass_score = question_scores * 0.7.round(2) + good_score = question_scores * 0.9.round(2) + + fail_counts = exercise_scores.count {|a| a < fail_score} + pass_counts = exercise_scores.count {|a| a < pass_score && a >= fail_score} + good_counts = exercise_scores.count {|a| a < good_score && a >= pass_score} + best_counts = exercise_scores.count {|a| a >= good_score && a <= question_scores} + end + @counts_array = { + :commit_percent => commit_percent, + :min_score => min_score.to_s, + :max_score => max_score.to_s, + :average_score => average_score.to_s, + :fail_counts => fail_counts, + :pass_counts => pass_counts, + :good_counts => good_counts, + :best_counts => best_counts, + } + + @exercise_questions = @exercise.exercise_questions&.includes(:exercise_choices, :exercise_answers, :exercise_standard_answers, :exercise_shixun_challenges, :exercise_shixun_answers) + + percent_sort = "desc" + + if params[:sort].present? + percent_sort = params[:sort] end + # @paging_type = "percent" + # # 按题型排序 + # if params[:sort].present? + # @paging_type = params[:sort].to_s + # end - exercise_user_joins = @exercise_users_list.joins(user: :user_extension) + ques_result_all = exercise_commit_result(@exercise_questions, @exercise_commit_user_ids) - if order == "student_id" - @exercise_users_list = exercise_user_joins.order("user_extensions.student_id #{order_type}") - elsif order == "score" - @exercise_users_list = exercise_user_joins.order("#{order} #{order_type}") + #默认降序排列 + if percent_sort == "desc" + @question_result_hash = ques_result_all.sort_by {|s| s[:percent]}.reverse else - @exercise_users_list = exercise_user_joins.order("end_at #{order_type}, start_at #{order_type}") + @question_result_hash = ques_result_all.sort_by {|s| s[:percent]} end - @export_ex_users = @exercise_users_list + @exercise_questions_count = @exercise_questions.size + @page = params[:page] || 1 + @limit = params[:limit] || 10 + @question_result_hash = Kaminari.paginate_array(@question_result_hash).page(@page).per(@limit) + end - @exercise_users_size = @exercise_users_list.size + private - # 分页 - @page = params[:page] || 1 - @limit = params[:limit] || 20 - @exercise_users_list = @exercise_users_list.page(@page).per(@limit) - else - @exercise_users_list = [] - @export_ex_users = @exercise_users_list - @exercise_users_size = 0 + def exercise_params + params.require(:exercise).permit(:exercise_name, :exercise_description, :course_id, :exercise_status, :user_id, :time, + :publish_time, :end_time, :show_result, :question_random, :choice_random, :is_public, + :score_open, :answer_open, :exercise_bank_id, :unified_setting, :show_statistic) end - if params[:format] == "xlsx" - if @user_course_identity > Course::ASSISTANT_PROFESSOR - tip_exception(403,"无权限操作") - elsif @exercise_status == Exercise::UNPUBLISHED - normal_status(-1,"试卷未发布") - elsif (@exercise_users_size == 0) || ( @export_ex_users&.exercise_user_committed.size == 0) - normal_status(-1,"暂无用户提交") - elsif params[:export].present? && params[:export] - normal_status(0,"正在下载中") + def is_course_teacher + unless @user_course_identity < Course::STUDENT #为老师/助教/管理员 + normal_status(403, "...") + end + end + + #检查传入的参数内容是否符合 + def validates_exercise_params + normal_status(-1, "试卷标题不能为空!") if params[:exercise_name].blank? + normal_status(-1, "试卷标题不能超过60个字符") if (params[:exercise_name].length > 60) + normal_status(-1, "试卷须知不能超过100个字符") if (params[:exercise_description].present? && + params[:exercise_description].length > 100) + end + + #判断设置的时间是否合理 + def validate_publish_time + # 截止时间存在,且截止时间必须大于当前时间或发布时间 + unified_setting = params[:unified_setting] + publish_course = params[:publish_time_groups] + if @course.is_end + normal_status(-1, "课堂已结束不能再修改") + elsif unified_setting + ex_group_settings = @exercise.exercise_group_settings + if ex_group_settings.present? + p_time_present = ex_group_settings.publish_time_no_null.map(&:publish_time).min + if p_time_present && p_time_present < Time.now + normal_status(-1, "设置失败,存在已发布的分班") + end + elsif params[:publish_time].blank? + normal_status(-1, "发布时间不允许为空") + end + elsif unified_setting.present? && !unified_setting #非统一设置,分班不能为空 + if publish_course.present? + course_ids = publish_course.map {|a| a[:course_group_id]}.sum + publish_t = publish_course.map {|a| a[:publish_time]} + if course_ids.include?(nil) || course_ids.count == 0 + normal_status(-1, "请选择分班") + elsif publish_t.include?(nil) || publish_t.count == 0 + normal_status(-1, "发布时间不允许为空") + end + else + normal_status(-1, "请选择分班") + end + end + end + + def get_exercise + @exercise = Exercise.find_by(id: params[:id]) + if @exercise.blank? + normal_status(404, "试卷不存在") else - respond_to do |format| - format.xlsx{ - set_export_cookies - get_export_users(@exercise,@course,@export_ex_users) - exercise_export_name_ = - "#{current_user.real_name}_#{@course.name}_#{@exercise.exercise_name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}" - render xlsx: "#{exercise_export_name_.strip}",template: "exercises/exercise_lists.xlsx.axlsx",locals: {table_columns:@table_columns,exercise_users:@user_columns} - } + @course = @exercise.course + normal_status(404, "课堂不存在") if @course.blank? + end + end + + def get_exercise_question_counts #获取试卷的问题数及总分数 + exercise_questions = @exercise.exercise_questions + @exercise_ques_count = exercise_questions.size # 全部的题目数 + @exercise_ques_scores = exercise_questions.pluck(:question_score).sum + + #单选题的数量及分数 + exercise_single_ques = exercise_questions.find_by_custom("question_type", Exercise::SINGLE) + @exercise_single_ques_count = exercise_single_ques.size + @exercise_single_ques_scores = exercise_single_ques.pluck(:question_score).sum + + #多选题的数量及分数 + exercise_double_ques = exercise_questions.find_by_custom("question_type", Exercise::MULTIPLE) + @exercise_double_ques_count = exercise_double_ques.size + @exercise_double_ques_scores = exercise_double_ques.pluck(:question_score).sum + + # 判断题数量及分数 + exercise_ques_judge = exercise_questions.find_by_custom("question_type", Exercise::JUDGMENT) + @exercise_ques_judge_count = exercise_ques_judge.size + @exercise_ques_judge_scores = exercise_ques_judge.pluck(:question_score).sum + + #填空题数量及分数 + exercise_ques_null = exercise_questions.find_by_custom("question_type", Exercise::COMPLETION) + @exercise_ques_null_count = exercise_ques_null.size + @exercise_ques_null_scores = exercise_ques_null.pluck(:question_score).sum + + #简答题数量及分数 + exercise_ques_main = exercise_questions.find_by_custom("question_type", Exercise::SUBJECTIVE) + @exercise_ques_main_count = exercise_ques_main.size + @exercise_ques_main_scores = exercise_ques_main.pluck(:question_score).sum + + #实训题数量及分数 + exercise_ques_shixun = exercise_questions.find_by_custom("question_type", Exercise::PRACTICAL) + @exercise_ques_shixun_count = exercise_ques_shixun.size + @exercise_ques_shixun_scores = exercise_ques_shixun.pluck(:question_score).sum + + @exercise_questions = @exercise_questions&.includes(:exercise_choices, :exercise_shixun_challenges, :exercise_answers, :exercise_shixun_answers, :exercise_answer_comments, :exercise_standard_answers) + + end + + #获取用户有权限的分班 + def get_user_permission_course(exercise_ids, status) + exercise_status = status.to_i #传入的试卷发布状态 + unpublish_group = [] + course_groups = [] + user_groups_id = @course.charge_group_ids(current_user) + exercises_all = Exercise.includes(:exercise_group_settings).where(id: exercise_ids) + exercises_all.each do |exercise| + if exercise.present? + if exercise.unified_setting #统一设置只有两种情况,全部发布,全部截止 + exercise_user_status = exercise.get_exercise_status(current_user) #当前用户的能看到的试卷 + if (exercise_user_status == exercise_status) || exercise_status == Exercise::DEADLINE #未发布的情况 + unpublish_group = unpublish_group + user_groups_id + end + else + ex_all_group_settings = exercise.exercise_group_settings + ex_group_settings = ex_all_group_settings.exercise_group_published.pluck(:course_group_id).uniq #问卷设置的班级 + if exercise_status == Exercise::UNPUBLISHED + unpublish_group = user_groups_id - ex_group_settings + elsif exercise_status == Exercise::DEADLINE + ex_ended_groups = ex_all_group_settings.exercise_group_ended.pluck(:course_group_id).uniq + ex_and_user = user_groups_id & ex_group_settings #用户已设置的分班 + unpublish_group = unpublish_group + ex_and_user - ex_ended_groups #已发布的全部班级减去截止的全部班级 + else + ex_ended_groups = ex_all_group_settings.exercise_group_ended.pluck(:course_group_id).uniq + ex_and_user = user_groups_id & ex_group_settings #用户已设置的分班 + unpublish_group = unpublish_group + ex_and_user - ex_ended_groups + end + end end end + Rails.logger.info("#####____________unpublish_group_______#######{unpublish_group}") + unpublish_group = unpublish_group.uniq + if unpublish_group.count > 0 + course_groups = CourseGroup.by_group_ids(unpublish_group) + end + course_groups end - rescue Exception => e - uid_logger_error(e.message) - tip_exception(e.message) - raise ActiveRecord::Rollback - end - end - #导出空白试卷 - def export_exercise - @request_url = request.base_url - @exercise_questions = @exercise.exercise_questions.includes(:exercise_choices).order("question_number ASC") - filename_ = "#{@exercise.user.real_name}_#{@course.name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}.pdf" - stylesheets = "#{Rails.root}/app/templates/exercise_export/exercise_export.css" - if params[:export].present? && params[:export] - normal_status(0,"正在下载中") - else - set_export_cookies - render pdf: 'exercise_export/blank_exercise', filename: filename_, stylesheets: stylesheets, disposition: 'inline', type:"pdf_attachment.content_type",stream:false - end - end + def set_exercise_status(publish_time, end_time) + time_now_i = Time.now + if publish_time.present? && (publish_time <= time_now_i) && (end_time > time_now_i) + 2 + elsif publish_time.nil? || (publish_time.present? && publish_time > time_now_i) + 1 + elsif end_time.present? && (end_time <= time_now_i) + 3 + elsif end_time.present? && publish_time.present? && (end_time < publish_time) + normal_status(-1, "时间设置错误!") + else + 1 + end + end - #空白试卷预览页面,仅供测试使用,无其他任何用途 - # def blank_exercise - # ActiveRecord::Base.transaction do - # begin - # @exercise_questions = @exercise.exercise_questions.order("question_number ASC") - # challenge_ids = @exercise_questions.joins(:exercise_shixun_challenges).pluck("exercise_shixun_challenges.challenge_id") - # get_each_student_exercise(@exercise.id,@exercise_questions,31798) - # @games = @exercise_user.user.games.ch_games(challenge_ids) - # respond_to do |format| - # format.html - # end - # rescue Exception => e - # uid_logger_error(e.message) - # tip_exception("没有权限") - # raise ActiveRecord::Rollback - # end - # end - # end + def check_course_public + unless @course.is_public == 1 # 0为私有,1为公开 + normal_status(403, "...") + end + end - #学生的统计结果 - def exercise_result - begin - exercise_ids = [@exercise.id] - @exercise_publish_count = get_user_permission_course(exercise_ids,Exercise::PUBLISHED).size #判断是否有已发布的分班 - @exercise_unpublish_count = get_user_permission_course(exercise_ids,Exercise::UNPUBLISHED).size #判断是否有未发布的分班 - @course_all_members = @course.students #课堂的全部学生 - @exercise_all_users = @exercise.exercise_users - ex_common_ids = @exercise.common_published_ids(current_user.id) - @exercise_course_groups = @course.get_ex_published_course(ex_common_ids) + def check_user_id_start_answer #判断用户在开始答题时,是否有用户id传入,如果为老师,则id必需,否则为当前用户的id + user_login = params[:login] + if user_login.blank? && @user_course_identity < Course::STUDENT #id不存在,且当前为老师/管理员等 + normal_status(-1, "请输入学生登陆名!") + else + if @user_course_identity < Course::STUDENT || @exercise.score_open + @ex_answerer = user_login.blank? ? current_user : User.find_by(login: user_login) + else + @ex_answerer = current_user + end - #班级的选择 - if params[:exercise_group_id].present? - group_id = params[:exercise_group_id] - exercise_students = @course_all_members.course_find_by_ids("course_group_id",group_id) # 试卷所分班的全部人数 - user_ids = exercise_students.pluck(:user_id).reject(&:blank?) - @exercise_all_users = @exercise.exercise_users.exercise_commit_users(user_ids) - @course_all_members_count = @exercise_all_users.size - else - @exercise_users_list = @exercise.all_exercise_users(current_user.id) - @course_all_members_count = @exercise_users_list.size - end - @exercise_commit_users = @exercise_all_users.commit_exercise_by_status(1) #试卷的已提交用户 - @exercise_commit_user_ids = @exercise_commit_users.pluck(:user_id).uniq #已提交试卷的全部用户id - @exercise_commit_user_counts = @exercise_commit_users.size #试卷的已提交用户人数 - @exercise_status = @exercise.get_exercise_status(current_user) - - #提交率 - if @course_all_members_count == 0 - commit_percent = 0.00 - min_score = 0.0 - max_score = 0.0 - average_score = 0.0 - fail_counts = 0 - pass_counts = 0 - good_counts = 0 - best_counts = 0 - else - commit_percent = (@exercise_commit_user_counts / @course_all_members_count.to_f).round(3) - exercise_scores = @exercise_commit_users.pluck(:score).reject(&:blank?) - min_score = exercise_scores.min.present? ? exercise_scores.min : 0.0 - max_score = exercise_scores.max.present? ? exercise_scores.max : 0.0 - total_score = exercise_scores.sum.present? ? exercise_scores.sum : 0.0 - average_score = @exercise_commit_user_counts > 0 ? (total_score.round(1) / @exercise_commit_user_counts).round(1) : 0.0 - question_scores = @exercise.question_scores - fail_score = question_scores * 0.6.round(2) - pass_score = question_scores * 0.7.round(2) - good_score = question_scores * 0.9.round(2) - - fail_counts = exercise_scores.count{|a| a < fail_score} - pass_counts = exercise_scores.count{|a| a < pass_score && a >= fail_score} - good_counts = exercise_scores.count{|a| a < good_score && a >= pass_score} - best_counts = exercise_scores.count{|a| a >= good_score && a <= question_scores} - end - @counts_array = { - :commit_percent => commit_percent, - :min_score => min_score.to_s, - :max_score => max_score.to_s, - :average_score => average_score.to_s, - :fail_counts => fail_counts, - :pass_counts => pass_counts, - :good_counts => good_counts, - :best_counts => best_counts, - } + if @ex_answerer.blank? + normal_status(404, "答题用户不存在") + elsif @user_course_identity > Course::STUDENT && !@exercise.is_public + normal_status(403, "非公开试卷") + else + # @exercise_current_user_id = @ex_answerer.id || current_user.id + @exercise_current_user_id = @ex_answerer.id + end + end + end - @exercise_questions = @exercise.exercise_questions&.includes(:exercise_choices,:exercise_answers,:exercise_standard_answers,:exercise_shixun_challenges,:exercise_shixun_answers) + ## 判断开始答题页面的用户权限 + def check_user_on_answer + if @user_course_identity == Course::STUDENT && @exercise.get_exercise_status(current_user) == Exercise::UNPUBLISHED #试卷未发布,且当前用户不为老师/管理员 + normal_status(-1, "未发布试卷!") + elsif @user_course_identity > Course::STUDENT && (!@exercise.is_public || (@exercise.is_public && !@exercise.unified_setting)) ##不为课堂成员,且试卷不为公开的,或试卷公开,但不是统一设置的 + normal_status(-1, "试卷暂未公开!") + end + end - percent_sort = "desc" + def check_exercise_time + @answer_committed_user = @exercise.exercise_users.exercise_commit_users(current_user.id)&.first + if @answer_committed_user.blank? + normal_status(404, "答题用户不存在") + end + end - if params[:sort].present? - percent_sort = params[:sort] + #打回重做时的初步判断 + def check_exercise_status + @exercise_users = @exercise.all_exercise_users(current_user.id).commit_exercise_by_status(1) #当前教师所在分班的全部已提交的学生数 + if @exercise.get_exercise_status(current_user) != Exercise::PUBLISHED + normal_status(-1, "非提交中的试卷不允许打回重做!") + elsif @exercise_users.count < 1 + normal_status(-1, "暂无人提交试卷!") + end end - # @paging_type = "percent" - # # 按题型排序 - # if params[:sort].present? - # @paging_type = params[:sort].to_s - # end - ques_result_all = exercise_commit_result(@exercise_questions,@exercise_commit_user_ids) - #默认降序排列 - if percent_sort == "desc" - @question_result_hash = ques_result_all.sort_by{|s| s[:percent]}.reverse - else - @question_result_hash = ques_result_all.sort_by{|s| s[:percent]} + #查看试题页面,当为学生时,除非试卷已截止,或已提交才可以查看 + def check_exercise_is_end + ex_status = @exercise.get_exercise_status(current_user) + @ex_user = @exercise.exercise_users.find_by(user_id: @exercise_current_user_id) #该试卷的回答者 + if @user_course_identity > Course::ASSISTANT_PROFESSOR + if ex_status == Exercise::UNPUBLISHED + normal_status(-1, "试卷未发布") + elsif @ex_user.present? && @ex_user.commit_status == 0 + normal_status(-1, "试卷未提交") + elsif params[:user_id].present? && current_user.id != params[:user_id] + normal_status(-1, "不能查看他人的试卷") + end + end + end + + #查看试卷是否选择为公开统计 + def check_exercise_public + if @user_course_identity > Course::ASSISTANT_PROFESSOR #当前为学生,试卷公开统计,且已截止,且已提交 + ex_user = @exercise.exercise_users.exercise_commit_users(current_user.id).first + unless @exercise.get_exercise_status(current_user) == Exercise::DEADLINE && ex_user.present? && ex_user.commit_status == 1 && + @exercise.show_statistic + normal_status(-1, "学生暂不能查看") + end + end + end + + def get_left_banner_id + left_banner_content = @course.course_modules.search_by_module_type("exercise") + if left_banner_content.present? + @left_banner_id = left_banner_content.first.id + @left_banner_name = left_banner_content.first.module_name + else + normal_status(404, "左侧导航不存在") + end + end + + def get_user_answer_status(exercise_questions, user_id, exercise, exercise_user_status) + @question_status = [] + @exercise_all_questions = [] + ex_question_random = exercise.question_random + question_answered = 0 + exercise_questions.each_with_index do |q, index| + if ex_question_random && exercise_user_status != Exercise::DEADLINE + ques_number = index + 1 + else + ques_number = q.question_number + end + ques_status = 0 + if q.question_type != Exercise::PRACTICAL + ques_vote = q.exercise_answers.select {|answer| answer.user_id == user_id} + + if ques_vote.present? + #其他题目,需回答的有内容,才会为已答,否则如内容为空,视为未答 + vote_answer_id = ques_vote.pluck(:exercise_choice_id).reject(&:blank?) + vote_text_count = ques_vote.pluck(:answer_text).reject(&:blank?).size + if q.question_type <= Exercise::JUDGMENT #选择题和判断题的时候,需要有选项,才算回答 + if vote_answer_id.size > 0 + ques_status = 1 + question_answered += 1 + end + else + if vote_text_count > 0 #主观题,必选有内容,才算回答 + ques_status = 1 + question_answered += 1 + end + end + end + else + if Myshixun.exists?(user_id: user_id, shixun_id: q.shixun_id) + ques_status = 1 + question_answered += 1 + end + end + question_status = { + :ques_id => q.id, + :ques_number => ques_number, #仅问题的显示位置变化,但是问题的question_number 不会变化,与之相关的choice/standard_answer/answer不会变化 + :ques_status => ques_status, + } + question_options = { + :question => q, + :ques_number => ques_number, + } + @question_status = @question_status.push(question_status).sort_by {|k| k[:ques_number]} + @exercise_all_questions = @exercise_all_questions.push(question_options).sort_by {|k| k[:ques_number]} + end + end + + #下一步也有check_on_users再进行判断 + def only_student_in + if @user_course_identity < Course::STUDENT + normal_status(-1, "老师身份不允许进入") + end + end + + #判断实训是否已选择 + def commit_shixun_present + question_shixun_ids = @exercise.exercise_questions.pluck(:shixun_id).reject(&:blank?) + shixun_id = params[:shixun_id] + @shixun = Shixun.find_by(id: shixun_id) + if shixun_id.present? && question_shixun_ids.include?(shixun_id) + normal_status(-1, "该实训已选择!") + elsif @shixun.blank? + normal_status(-1, "该实训不存在!") + end end - @exercise_questions_count = @exercise_questions.size - @page = params[:page] || 1 - @limit = params[:limit] || 10 - @question_result_hash = Kaminari.paginate_array(@question_result_hash).page(@page).per(@limit) - rescue Exception => e - uid_logger_error(e.message) - tip_exception("没有权限") - raise ActiveRecord::Rollback end + + @exercise_questions_count = @exercise_questions.size + @page = params[:page] || 1 + @limit = params[:limit] || 10 + @question_result_hash = Kaminari.paginate_array(@question_result_hash).page(@page).per(@limit) end private def exercise_params params.require(:exercise).permit(:exercise_name, :exercise_description, :course_id, :exercise_status, :user_id, :time, - :publish_time, :end_time, :show_result, :question_random, :choice_random, :is_public, - :score_open, :answer_open, :exercise_bank_id, :unified_setting, :show_statistic) + :publish_time, :end_time, :show_result, :question_random, :choice_random, :is_public, + :score_open, :answer_open, :exercise_bank_id, :unified_setting, :show_statistic) end def is_course_teacher @@ -1534,7 +3038,7 @@ class ExercisesController < ApplicationController normal_status(-1, "试卷标题不能为空!") if params[:exercise_name].blank? normal_status(-1, "试卷标题不能超过60个字符") if (params[:exercise_name].length > 60) normal_status(-1, "试卷须知不能超过100个字符") if (params[:exercise_description].present? && - params[:exercise_description].length > 100) + params[:exercise_description].length > 100) end #判断设置的时间是否合理 @@ -1543,39 +3047,39 @@ class ExercisesController < ApplicationController unified_setting = params[:unified_setting] publish_course = params[:publish_time_groups] if @course.is_end - normal_status(-1,"课堂已结束不能再修改") + normal_status(-1, "课堂已结束不能再修改") elsif unified_setting ex_group_settings = @exercise.exercise_group_settings if ex_group_settings.present? p_time_present = ex_group_settings.publish_time_no_null.map(&:publish_time).min if p_time_present && p_time_present < Time.now - normal_status(-1,"设置失败,存在已发布的分班") + normal_status(-1, "设置失败,存在已发布的分班") end elsif params[:publish_time].blank? - normal_status(-1,"发布时间不允许为空") + normal_status(-1, "发布时间不允许为空") end - elsif unified_setting.present? && !unified_setting #非统一设置,分班不能为空 + elsif unified_setting.present? && !unified_setting #非统一设置,分班不能为空 if publish_course.present? - course_ids = publish_course.map{|a| a[:course_group_id]}.sum - publish_t = publish_course.map{|a| a[:publish_time]} + course_ids = publish_course.map {|a| a[:course_group_id]}.sum + publish_t = publish_course.map {|a| a[:publish_time]} if course_ids.include?(nil) || course_ids.count == 0 - normal_status(-1,"请选择分班") + normal_status(-1, "请选择分班") elsif publish_t.include?(nil) || publish_t.count == 0 - normal_status(-1,"发布时间不允许为空") + normal_status(-1, "发布时间不允许为空") end else - normal_status(-1,"请选择分班") + normal_status(-1, "请选择分班") end end end def get_exercise - @exercise = Exercise.find_by(id:params[:id]) + @exercise = Exercise.find_by(id: params[:id]) if @exercise.blank? - normal_status(404,"试卷不存在") + normal_status(404, "试卷不存在") else @course = @exercise.course - normal_status(404,"课堂不存在") if @course.blank? + normal_status(404, "课堂不存在") if @course.blank? end end @@ -1585,65 +3089,65 @@ class ExercisesController < ApplicationController @exercise_ques_scores = exercise_questions.pluck(:question_score).sum #单选题的数量及分数 - exercise_single_ques = exercise_questions.find_by_custom("question_type",Exercise::SINGLE) + exercise_single_ques = exercise_questions.find_by_custom("question_type", Exercise::SINGLE) @exercise_single_ques_count = exercise_single_ques.size @exercise_single_ques_scores = exercise_single_ques.pluck(:question_score).sum #多选题的数量及分数 - exercise_double_ques = exercise_questions.find_by_custom("question_type",Exercise::MULTIPLE) + exercise_double_ques = exercise_questions.find_by_custom("question_type", Exercise::MULTIPLE) @exercise_double_ques_count = exercise_double_ques.size @exercise_double_ques_scores = exercise_double_ques.pluck(:question_score).sum # 判断题数量及分数 - exercise_ques_judge = exercise_questions.find_by_custom("question_type",Exercise::JUDGMENT) + exercise_ques_judge = exercise_questions.find_by_custom("question_type", Exercise::JUDGMENT) @exercise_ques_judge_count = exercise_ques_judge.size @exercise_ques_judge_scores = exercise_ques_judge.pluck(:question_score).sum #填空题数量及分数 - exercise_ques_null = exercise_questions.find_by_custom("question_type",Exercise::COMPLETION) + exercise_ques_null = exercise_questions.find_by_custom("question_type", Exercise::COMPLETION) @exercise_ques_null_count = exercise_ques_null.size @exercise_ques_null_scores = exercise_ques_null.pluck(:question_score).sum #简答题数量及分数 - exercise_ques_main = exercise_questions.find_by_custom("question_type",Exercise::SUBJECTIVE) + exercise_ques_main = exercise_questions.find_by_custom("question_type", Exercise::SUBJECTIVE) @exercise_ques_main_count = exercise_ques_main.size @exercise_ques_main_scores = exercise_ques_main.pluck(:question_score).sum #实训题数量及分数 - exercise_ques_shixun = exercise_questions.find_by_custom("question_type",Exercise::PRACTICAL) + exercise_ques_shixun = exercise_questions.find_by_custom("question_type", Exercise::PRACTICAL) @exercise_ques_shixun_count = exercise_ques_shixun.size @exercise_ques_shixun_scores = exercise_ques_shixun.pluck(:question_score).sum - @exercise_questions = @exercise_questions&.includes(:exercise_choices,:exercise_shixun_challenges,:exercise_answers,:exercise_shixun_answers,:exercise_answer_comments,:exercise_standard_answers) + @exercise_questions = @exercise_questions&.includes(:exercise_choices, :exercise_shixun_challenges, :exercise_answers, :exercise_shixun_answers, :exercise_answer_comments, :exercise_standard_answers) end #获取用户有权限的分班 - def get_user_permission_course(exercise_ids,status) + def get_user_permission_course(exercise_ids, status) exercise_status = status.to_i #传入的试卷发布状态 unpublish_group = [] course_groups = [] user_groups_id = @course.charge_group_ids(current_user) - exercises_all = Exercise.includes(:exercise_group_settings).where(id:exercise_ids) + exercises_all = Exercise.includes(:exercise_group_settings).where(id: exercise_ids) exercises_all.each do |exercise| if exercise.present? - if exercise.unified_setting #统一设置只有两种情况,全部发布,全部截止 - exercise_user_status = exercise.get_exercise_status(current_user) #当前用户的能看到的试卷 + if exercise.unified_setting #统一设置只有两种情况,全部发布,全部截止 + exercise_user_status = exercise.get_exercise_status(current_user) #当前用户的能看到的试卷 if (exercise_user_status == exercise_status) || exercise_status == Exercise::DEADLINE #未发布的情况 unpublish_group = unpublish_group + user_groups_id end else ex_all_group_settings = exercise.exercise_group_settings - ex_group_settings = ex_all_group_settings.exercise_group_published.pluck(:course_group_id).uniq #问卷设置的班级 + ex_group_settings = ex_all_group_settings.exercise_group_published.pluck(:course_group_id).uniq #问卷设置的班级 if exercise_status == Exercise::UNPUBLISHED - unpublish_group = user_groups_id - ex_group_settings + unpublish_group = user_groups_id - ex_group_settings elsif exercise_status == Exercise::DEADLINE ex_ended_groups = ex_all_group_settings.exercise_group_ended.pluck(:course_group_id).uniq - ex_and_user = user_groups_id & ex_group_settings #用户已设置的分班 - unpublish_group = unpublish_group + ex_and_user - ex_ended_groups #已发布的全部班级减去截止的全部班级 + ex_and_user = user_groups_id & ex_group_settings #用户已设置的分班 + unpublish_group = unpublish_group + ex_and_user - ex_ended_groups #已发布的全部班级减去截止的全部班级 else ex_ended_groups = ex_all_group_settings.exercise_group_ended.pluck(:course_group_id).uniq - ex_and_user = user_groups_id & ex_group_settings #用户已设置的分班 + ex_and_user = user_groups_id & ex_group_settings #用户已设置的分班 unpublish_group = unpublish_group + ex_and_user - ex_ended_groups end end @@ -1657,7 +3161,7 @@ class ExercisesController < ApplicationController course_groups end - def set_exercise_status(publish_time,end_time) + def set_exercise_status(publish_time, end_time) time_now_i = Time.now if publish_time.present? && (publish_time <= time_now_i) && (end_time > time_now_i) 2 @@ -1666,22 +3170,22 @@ class ExercisesController < ApplicationController elsif end_time.present? && (end_time <= time_now_i) 3 elsif end_time.present? && publish_time.present? && (end_time < publish_time) - normal_status(-1,"时间设置错误!") + normal_status(-1, "时间设置错误!") else 1 end end def check_course_public - unless @course.is_public == 1 # 0为私有,1为公开 - normal_status(403,"...") + unless @course.is_public == 1 # 0为私有,1为公开 + normal_status(403, "...") end end def check_user_id_start_answer #判断用户在开始答题时,是否有用户id传入,如果为老师,则id必需,否则为当前用户的id user_login = params[:login] - if user_login.blank? && @user_course_identity < Course::STUDENT #id不存在,且当前为老师/管理员等 - normal_status(-1,"请输入学生登陆名!") + if user_login.blank? && @user_course_identity < Course::STUDENT #id不存在,且当前为老师/管理员等 + normal_status(-1, "请输入学生登陆名!") else if @user_course_identity < Course::STUDENT || @exercise.score_open @ex_answerer = user_login.blank? ? current_user : User.find_by(login: user_login) @@ -1690,9 +3194,9 @@ class ExercisesController < ApplicationController end if @ex_answerer.blank? - normal_status(404,"答题用户不存在") + normal_status(404, "答题用户不存在") elsif @user_course_identity > Course::STUDENT && !@exercise.is_public - normal_status(403,"非公开试卷") + normal_status(403, "非公开试卷") else # @exercise_current_user_id = @ex_answerer.id || current_user.id @exercise_current_user_id = @ex_answerer.id @@ -1702,9 +3206,9 @@ class ExercisesController < ApplicationController ## 判断开始答题页面的用户权限 def check_user_on_answer - if @user_course_identity == Course::STUDENT && @exercise.get_exercise_status(current_user) == Exercise::UNPUBLISHED #试卷未发布,且当前用户不为老师/管理员 + if @user_course_identity == Course::STUDENT && @exercise.get_exercise_status(current_user) == Exercise::UNPUBLISHED #试卷未发布,且当前用户不为老师/管理员 normal_status(-1, "未发布试卷!") - elsif @user_course_identity > Course::STUDENT && (!@exercise.is_public || (@exercise.is_public && !@exercise.unified_setting)) ##不为课堂成员,且试卷不为公开的,或试卷公开,但不是统一设置的 + elsif @user_course_identity > Course::STUDENT && (!@exercise.is_public || (@exercise.is_public && !@exercise.unified_setting)) ##不为课堂成员,且试卷不为公开的,或试卷公开,但不是统一设置的 normal_status(-1, "试卷暂未公开!") end end @@ -1712,7 +3216,7 @@ class ExercisesController < ApplicationController def check_exercise_time @answer_committed_user = @exercise.exercise_users.exercise_commit_users(current_user.id)&.first if @answer_committed_user.blank? - normal_status(404,"答题用户不存在") + normal_status(404, "答题用户不存在") end end @@ -1720,9 +3224,9 @@ class ExercisesController < ApplicationController def check_exercise_status @exercise_users = @exercise.all_exercise_users(current_user.id).commit_exercise_by_status(1) #当前教师所在分班的全部已提交的学生数 if @exercise.get_exercise_status(current_user) != Exercise::PUBLISHED - normal_status(-1,"非提交中的试卷不允许打回重做!") + normal_status(-1, "非提交中的试卷不允许打回重做!") elsif @exercise_users.count < 1 - normal_status(-1,"暂无人提交试卷!") + normal_status(-1, "暂无人提交试卷!") end end @@ -1730,25 +3234,25 @@ class ExercisesController < ApplicationController #查看试题页面,当为学生时,除非试卷已截止,或已提交才可以查看 def check_exercise_is_end ex_status = @exercise.get_exercise_status(current_user) - @ex_user = @exercise.exercise_users.find_by(user_id:@exercise_current_user_id) #该试卷的回答者 + @ex_user = @exercise.exercise_users.find_by(user_id: @exercise_current_user_id) #该试卷的回答者 if @user_course_identity > Course::ASSISTANT_PROFESSOR if ex_status == Exercise::UNPUBLISHED - normal_status(-1,"试卷未发布") + normal_status(-1, "试卷未发布") elsif @ex_user.present? && @ex_user.commit_status == 0 - normal_status(-1,"试卷未提交") + normal_status(-1, "试卷未提交") elsif params[:user_id].present? && current_user.id != params[:user_id] - normal_status(-1,"不能查看他人的试卷") + normal_status(-1, "不能查看他人的试卷") end end end #查看试卷是否选择为公开统计 def check_exercise_public - if @user_course_identity > Course::ASSISTANT_PROFESSOR #当前为学生,试卷公开统计,且已截止,且已提交 + if @user_course_identity > Course::ASSISTANT_PROFESSOR #当前为学生,试卷公开统计,且已截止,且已提交 ex_user = @exercise.exercise_users.exercise_commit_users(current_user.id).first unless @exercise.get_exercise_status(current_user) == Exercise::DEADLINE && ex_user.present? && ex_user.commit_status == 1 && - @exercise.show_statistic - normal_status(-1,"学生暂不能查看") + @exercise.show_statistic + normal_status(-1, "学生暂不能查看") end end end @@ -1759,16 +3263,16 @@ class ExercisesController < ApplicationController @left_banner_id = left_banner_content.first.id @left_banner_name = left_banner_content.first.module_name else - normal_status(404,"左侧导航不存在") + normal_status(404, "左侧导航不存在") end end - def get_user_answer_status(exercise_questions,user_id,exercise,exercise_user_status) + def get_user_answer_status(exercise_questions, user_id, exercise, exercise_user_status) @question_status = [] @exercise_all_questions = [] ex_question_random = exercise.question_random question_answered = 0 - exercise_questions.each_with_index do |q,index| + exercise_questions.each_with_index do |q, index| if ex_question_random && exercise_user_status != Exercise::DEADLINE ques_number = index + 1 else @@ -1776,19 +3280,19 @@ class ExercisesController < ApplicationController end ques_status = 0 if q.question_type != Exercise::PRACTICAL - ques_vote = q.exercise_answers.select{|answer| answer.user_id == user_id} + ques_vote = q.exercise_answers.select {|answer| answer.user_id == user_id} if ques_vote.present? #其他题目,需回答的有内容,才会为已答,否则如内容为空,视为未答 vote_answer_id = ques_vote.pluck(:exercise_choice_id).reject(&:blank?) vote_text_count = ques_vote.pluck(:answer_text).reject(&:blank?).size - if q.question_type <= Exercise::JUDGMENT #选择题和判断题的时候,需要有选项,才算回答 + if q.question_type <= Exercise::JUDGMENT #选择题和判断题的时候,需要有选项,才算回答 if vote_answer_id.size > 0 ques_status = 1 question_answered += 1 end else - if vote_text_count > 0 #主观题,必选有内容,才算回答 + if vote_text_count > 0 #主观题,必选有内容,才算回答 ques_status = 1 question_answered += 1 end @@ -1801,22 +3305,23 @@ class ExercisesController < ApplicationController end end question_status = { - :ques_id => q.id, - :ques_number => ques_number, #仅问题的显示位置变化,但是问题的question_number 不会变化,与之相关的choice/standard_answer/answer不会变化 - :ques_status => ques_status, + :ques_id => q.id, + :ques_number => ques_number, #仅问题的显示位置变化,但是问题的question_number 不会变化,与之相关的choice/standard_answer/answer不会变化 + :ques_status => ques_status, } question_options = { - :question => q, - :ques_number => ques_number, + :question => q, + :ques_number => ques_number, } @question_status = @question_status.push(question_status).sort_by {|k| k[:ques_number]} @exercise_all_questions = @exercise_all_questions.push(question_options).sort_by {|k| k[:ques_number]} end end + #下一步也有check_on_users再进行判断 def only_student_in if @user_course_identity < Course::STUDENT - normal_status(-1,"老师身份不允许进入") + normal_status(-1, "老师身份不允许进入") end end @@ -1826,9 +3331,9 @@ class ExercisesController < ApplicationController shixun_id = params[:shixun_id] @shixun = Shixun.find_by(id: shixun_id) if shixun_id.present? && question_shixun_ids.include?(shixun_id) - normal_status(-1,"该实训已选择!") + normal_status(-1, "该实训已选择!") elsif @shixun.blank? - normal_status(-1,"该实训不存在!") + normal_status(-1, "该实训不存在!") end end From ba2249767258fb254e32e1cbb2dd69a266d577a6 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Sat, 11 Jan 2020 17:25:53 +0800 Subject: [PATCH 010/204] 1 --- app/controllers/subjects_controller.rb | 2 +- app/helpers/subjects_helper.rb | 4 ++-- app/views/subjects/show.json.jbuilder | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/app/controllers/subjects_controller.rb b/app/controllers/subjects_controller.rb index 1ceece56f..d58c4a9c3 100644 --- a/app/controllers/subjects_controller.rb +++ b/app/controllers/subjects_controller.rb @@ -92,7 +92,7 @@ class SubjectsController < ApplicationController @is_creator = current_user.creator_of_subject?(@subject) @is_manager = @user.manager_of_subject?(@subject) # 合作团队 - @shixuns = @subject.shixuns.published.pluck(:id) + # @shixuns = @subject.shixuns.published.pluck(:id) @courses = @subject.courses if @subject.excellent @members = @subject.subject_members.includes(:user) diff --git a/app/helpers/subjects_helper.rb b/app/helpers/subjects_helper.rb index 75ae9f041..72154b0a8 100644 --- a/app/helpers/subjects_helper.rb +++ b/app/helpers/subjects_helper.rb @@ -1,10 +1,10 @@ module SubjectsHelper # 实训路径的发布状态 - def publish_status subject, is_manager, user, shixuns + def publish_status subject, is_manager, user status = -1 if is_manager - status = 0 if subject.status == 0 && shixuns.count > 0 + status = 0 if subject.status == 0 status = 1 if subject.status == 1 status = 2 if subject.status == 2 && user.admin? end diff --git a/app/views/subjects/show.json.jbuilder b/app/views/subjects/show.json.jbuilder index 870d33d40..49ad55517 100644 --- a/app/views/subjects/show.json.jbuilder +++ b/app/views/subjects/show.json.jbuilder @@ -6,7 +6,7 @@ json.subject_score @subject.all_score json.member_count @subject.member_count json.allow_delete (@subject.status != 2 && @is_creator) || @user.admin? -json.publish_status publish_status(@subject, @is_manager, @user, @shixuns) +json.publish_status publish_status(@subject, @is_manager, @user) json.allow_statistics @is_manager json.allow_send @user.logged? json.allow_visit @subject.status > 1 || @is_manager From 5058b7973611f847afb17c46c0e38d7cba8b5a40 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sat, 11 Jan 2020 17:26:22 +0800 Subject: [PATCH 011/204] =?UTF-8?q?=E8=AF=84=E9=98=85=E5=92=8C=E5=9B=9E?= =?UTF-8?q?=E5=A4=8D=E7=9A=84=E5=AD=97=E7=AC=A6=E9=99=90=E5=88=B6=E6=94=B9?= =?UTF-8?q?=E4=B8=BA2000?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/memos_controller.rb | 2 +- app/controllers/messages_controller.rb | 2 +- app/models/discuss.rb | 2 +- app/models/graduation_work_score.rb | 2 +- app/models/hack_set.rb | 4 ++-- app/models/journals_for_message.rb | 2 +- app/models/student_works_score.rb | 2 +- 7 files changed, 8 insertions(+), 8 deletions(-) diff --git a/app/controllers/memos_controller.rb b/app/controllers/memos_controller.rb index a4d72371c..b80bfed32 100644 --- a/app/controllers/memos_controller.rb +++ b/app/controllers/memos_controller.rb @@ -144,7 +144,7 @@ class MemosController < ApplicationController def reply tip_exception("parent_id不能为空") if params[:parent_id].blank? tip_exception("content不能为空") if params[:content].blank? - tip_exception("内容不能超过1000字符") if params[:content].length > 1000 + tip_exception("内容不能超过2000字符") if params[:content].length > 2000 ActiveRecord::Base.transaction do begin diff --git a/app/controllers/messages_controller.rb b/app/controllers/messages_controller.rb index 7b096f1ec..2b9d9d69f 100644 --- a/app/controllers/messages_controller.rb +++ b/app/controllers/messages_controller.rb @@ -63,7 +63,7 @@ class MessagesController < ApplicationController def reply return normal_status(2, "回复内容不能为空") if params[:content].blank? - return normal_status(2, "回复内容不能超过1000字符") if params[:content].length > 1000 + return normal_status(2, "回复内容不能超过2000字符") if params[:content].length > 2000 @reply = Message.create!(board: @message.board, root_id: @message.root_id || @message.id, author: current_user, parent: @message, message_detail_attributes: { diff --git a/app/models/discuss.rb b/app/models/discuss.rb index b563a6295..a4c833b55 100644 --- a/app/models/discuss.rb +++ b/app/models/discuss.rb @@ -13,7 +13,7 @@ class Discuss < ApplicationRecord belongs_to :challenge, optional: true validate :validate_sensitive_string - validates :content, length: { maximum: 1000, too_long: "不能超过1000个字符" } + validates :content, length: { maximum: 2000, too_long: "不能超过2000个字符" } after_create :send_tiding diff --git a/app/models/graduation_work_score.rb b/app/models/graduation_work_score.rb index 5c2627c88..78c2727fc 100644 --- a/app/models/graduation_work_score.rb +++ b/app/models/graduation_work_score.rb @@ -5,5 +5,5 @@ class GraduationWorkScore < ApplicationRecord belongs_to :graduation_task has_many :attachments, as: :container, dependent: :destroy - validates :comment, length: { maximum: 1000, too_long: "不能超过1000个字符" } + validates :comment, length: { maximum: 2000, too_long: "不能超过2000个字符" } end diff --git a/app/models/hack_set.rb b/app/models/hack_set.rb index e2ca60549..2c21c3c22 100644 --- a/app/models/hack_set.rb +++ b/app/models/hack_set.rb @@ -1,6 +1,6 @@ class HackSet < ApplicationRecord - validates_length_of :input, maximum: 1000, message: "不能超过5000个字符" - validates_length_of :output, maximum: 1000, message: "不能超过5000个字符" + validates_length_of :input, maximum: 1000, message: "不能超过1000个字符" + validates_length_of :output, maximum: 1000, message: "不能超过1000个字符" validates :input, presence: { message: "测试集输入不能为空" } validates :output, presence: { message: "测试集输出不能为空" } validates_uniqueness_of :input, scope: [:hack_id, :input], message: "多个测试集的输入不能相同" diff --git a/app/models/journals_for_message.rb b/app/models/journals_for_message.rb index 190fa4351..3d0189c91 100644 --- a/app/models/journals_for_message.rb +++ b/app/models/journals_for_message.rb @@ -26,7 +26,7 @@ class JournalsForMessage < ApplicationRecord # "is_comprehensive_evaluation", # 1 教师评论、2 匿评、3 留言 # "hidden", 隐藏、 - validates :notes, length: { maximum: 1000, too_long: "不能超过1000个字符" } + validates :notes, length: { maximum: 2000, too_long: "不能超过2000个字符" } after_create :send_tiding diff --git a/app/models/student_works_score.rb b/app/models/student_works_score.rb index dec4512a8..a193d4e77 100644 --- a/app/models/student_works_score.rb +++ b/app/models/student_works_score.rb @@ -7,7 +7,7 @@ class StudentWorksScore < ApplicationRecord has_many :tidings, as: :container, dependent: :destroy has_many :attachments, as: :container, dependent: :destroy - validates :comment, length: { maximum: 1000, too_long: "不能超过1000个字符" } + validates :comment, length: { maximum: 2000, too_long: "不能超过2000个字符" } scope :shixun_comment, lambda { where(is_ultimate: 0) } From 12746914e1b853d9bae67c34e6f8949d00a50475 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sat, 11 Jan 2020 17:31:15 +0800 Subject: [PATCH 012/204] =?UTF-8?q?=E8=AF=95=E5=8D=B7=E7=9A=84=E9=AA=8C?= =?UTF-8?q?=E8=AF=81=E4=BF=A1=E6=81=AF?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/exercises_controller.rb | 1670 ----------------------- 1 file changed, 1670 deletions(-) diff --git a/app/controllers/exercises_controller.rb b/app/controllers/exercises_controller.rb index 408f95945..5b555cf4c 100644 --- a/app/controllers/exercises_controller.rb +++ b/app/controllers/exercises_controller.rb @@ -1342,1676 +1342,6 @@ class ExercisesController < ApplicationController else @question_result_hash = ques_result_all.sort_by {|s| s[:percent]} end - class ExercisesController < ApplicationController - before_action :require_login, :check_auth, except: [:index] - before_action :find_course, only: [:index, :new, :create, :my_exercises, :public_exercises, :set_public, :destroys, - :join_exercise_banks, :publish_modal, :publish, :end_modal, :end_exercise] #需要有课堂id参数的 - before_action :get_exercise, except: [:index, :new, :create, :my_exercises, :public_exercises, :set_public, :destroys, - :join_exercise_banks, :publish_modal, :publish, :end_modal, :end_exercise] - before_action :user_course_identity - before_action :is_course_teacher, except: [:index, :start_answer, :exercise_setting, :commit_exercise, :exercise_lists, :review_exercise, - :exercise_result, :common_header, :cancel_exercise, :begin_commit] - before_action :get_left_banner_id, only: [:common_header, :start_answer, :review_exercise, :index, :new, :edit] - before_action :validates_exercise_params, only: [:create, :update] - before_action :get_exercise_question_counts, only: [:show, :edit, :start_answer, :review_exercise, :blank_exercise, :export_exercise] - before_action :validate_publish_time, only: [:commit_setting] #提交设置时,需判断时间是否符合 - before_action :check_course_public, only: [:set_public] - before_action :check_user_on_answer, only: [:show, :start_answer, :exercise_lists] #判断当前用户在试卷的权限/老师是否属于分班的权限 - before_action :only_student_in, only: [:start_answer] - before_action :check_user_id_start_answer, only: [:start_answer, :review_exercise] - # before_action :commit_user_exercise,only: [:start_answer,:exercise_lists,:review_exercise] #已有定时的任务 - before_action :check_exercise_time, only: [:commit_exercise] #提交试卷时,判断时间是否超过 - before_action :check_exercise_status, only: [:redo_modal, :redo_exercise] - before_action :check_exercise_is_end, only: [:review_exercise] - before_action :check_exercise_public, only: [:exercise_result] #试卷是否为公开 - before_action :commit_shixun_present, only: [:commit_shixun] - include ExportHelper - include ExercisesHelper - - # model validation error - rescue_from ActiveRecord::RecordInvalid do |ex| - render_error(ex.record.errors.full_messages.join(',')) - end - # form validation error - rescue_from ActiveModel::ValidationError do |ex| - render_error(ex.model.errors.full_messages.join(',')) - end - - def index - begin - # 按发布时间或创建时间排序 - @exercises_all = @course.exercises - member_show_exercises = @exercises_all.is_exercise_published #已发布的或已截止的试卷 - @current_user_ = current_user - - # 课堂的学生人数 - @course_all_members = @course.students #当前课堂的全部学生 - @current_student = @course_all_members.course_find_by_ids("user_id", current_user.id) #当前用户是否为课堂的学生 - - # exercises的不同用户群体的显示 - if @user_course_identity < Course::STUDENT # @is_teacher_or 1为老师/管理员/助教 - @is_teacher_or = 1 - @exercises = @exercises_all #老师能看到全部的试卷,不管是已发布的/未发布的/已截止的/统一设置的/私有设置的(看到内容不同) - elsif @user_course_identity == Course::STUDENT # 2为课堂成员,能看到统一设置的和自己班级的 - @is_teacher_or = 2 - @member_group_id = @current_student.first.try(:course_group_id).to_i # 成员的分班id,默认为0 - if @member_group_id == 0 #表示是课堂的未分班成员,只能查看统一设置的试卷(已发布的/已截止的) - @exercises = member_show_exercises.exists? ? member_show_exercises.unified_setting : [] - else #已分班级的成员,可以查看统一设置和单独设置(试卷是发布在该班级)试卷 - # 已发布 当前用户班级分组的 试卷id - publish_exercise_ids = @course.exercise_group_settings.exercise_group_published.where("course_group_id = #{@member_group_id}").pluck(:exercise_id) - @exercises = member_show_exercises.unified_setting.or(member_show_exercises.where(id: publish_exercise_ids)) - end - else #用户未登陆或不是该课堂成员,仅显示统一设置的(已发布的/已截止的),如有公开,则不显示锁,不公开,则显示锁 - @is_teacher_or = 0 - @exercises = member_show_exercises.unified_setting - end - - if @exercises.size > 0 - if params[:type].present? - choose_type = params[:type].to_i - ex_setting_ids = [] - if @is_teacher_or != 2 - @exercises = @exercises.where("exercise_status = #{choose_type}") - else - case choose_type - when 1 - ex_setting_ids = @course.exercise_group_settings.where("course_group_id = #{@member_group_id}").exercise_group_not_published.pluck(:exercise_id) - when 2 - ex_setting_ids = @course.exercise_group_settings.where("course_group_id = #{@member_group_id}") - .where("publish_time is not null and publish_time <= ? and end_time > ?", Time.now, Time.now).pluck(:exercise_id) - when 3 - ex_setting_ids = @course.exercise_group_settings.where("course_group_id = #{@member_group_id}").exercise_group_ended.pluck(:exercise_id) - end - unified_setting_ids = @exercises.unified_setting.where("exercise_status = #{choose_type}").pluck(:id) - ex_ids = (ex_setting_ids + unified_setting_ids).uniq - @exercises = @exercises.where(id: ex_ids) - end - end - - if params[:search].present? - search_type = params[:search].to_s.strip - @exercises = @exercises.exercise_search(search_type) - end - - @exercises_select_count = @exercises.size # 全部页面,需返回 - @exercises = @exercises.distinct.order("IF(ISNULL(publish_time),0,1), publish_time DESC,created_at DESC") #出现错误 - - # 分页 - @page = params[:page] || 1 - @limit = params[:limit] || 15 - @exercises = @exercises.page(@page).per(@limit) - @exercises = @exercises&.includes(:published_settings) - else - @exercises = [] - end - - @course_all_members_count = @course_all_members.size #当前课堂的学生数 - @exercises_count = @exercises_all.size # 全部页面,需返回 - @exercises_unpublish_counts = @exercises_all.exercise_by_status(1).size #未发布的试卷数 - @exercises_published_counts = @exercises_count - @exercises_unpublish_counts # 已发布的试卷数,包含已截止的 - - rescue Exception => e - uid_logger_error(e.message) - tip_exception(e.message) - raise ActiveRecord::Rollback - end - end - - def new - ActiveRecord::Base.transaction do - begin - @exercise = Exercise.new - rescue Exception => e - uid_logger_error(e.message) - tip_exception("试卷创建失败!") - raise ActiveRecord::Rollback - end - end - end - - def create - ActiveRecord::Base.transaction do - ex_name = params[:exercise_name] - ex_desc = params[:exercise_description] - exercise_options = { - :exercise_name => ex_name, - :exercise_description => ex_desc, - :user_id => current_user.id, - :course_id => @course.id, - :time => -1, - :exercise_status => 1 - } - @exercise = Exercise.create!(exercise_options) - end - end - - #试卷的内容,及试题/答案的内容编辑 - def edit - ActiveRecord::Base.transaction do - @exercise_questions = @exercise.exercise_questions.order("question_number ASC") - end - end - - def update - ActiveRecord::Base.transaction do - ex_name = params[:exercise_name] - ex_desc = params[:exercise_description] - exercise_options = { - :exercise_name => ex_name, - :exercise_description => ex_desc, - } - @exercise.update!(exercise_options) - normal_status(0, "试卷更新成功!") - end - end - - def show - ActiveRecord::Base.transaction do - if @user_course_identity < Course::STUDENT - @is_teacher_or = 1 #为老师/助教/管理员 - else - @is_teacher_or = 0 #为学生 - end - @exercise_questions = @exercise.exercise_questions&.includes(:exercise_choices, :exercise_shixun_challenges, :exercise_standard_answers).order("question_number ASC") - end - end - - #试卷的公用头部 - def common_header - ActiveRecord::Base.transaction do - @user_left_time = nil - if @user_course_identity > Course::ASSISTANT_PROFESSOR - @is_teacher_or = 0 - @user_exercise_answer = @exercise.check_user_answer_status(current_user) - @user_commit_counts = 0 - @user_left_time = get_exercise_left_time(@exercise, current_user) - else - @is_teacher_or = 1 - @user_exercise_answer = 3 #教师页面 - @user_commit_counts = @exercise.exercise_users.where(commit_status: 1).size #已提交的用户数 - end - @ex_status = @exercise.get_exercise_status(current_user) - - exercise_id_array = [@exercise.id] - @exercise_publish_count = get_user_permission_course(exercise_id_array, Exercise::PUBLISHED).size #是否存在已发布的 - @exercise_unpublish_count = get_user_permission_course(exercise_id_array, Exercise::UNPUBLISHED).size #是否存在未发布的 - - if (@exercise_publish_count == 0) && (@exercise_unpublish_count == 0) #即表示没有分班 - if @ex_status == Exercise::UNPUBLISHED - @exercise_unpublish_count = 1 #试卷未发布,且课堂没有分班的时候 - elsif @ex_status == Exercise::PUBLISHED - @exercise_publish_count = 1 #试卷未发布,且课堂没有分班的时候 - end - end - end - end - - #实训题目的选用 - def choose_shixun - ActiveRecord::Base.transaction do - search = params[:search] - if @user_course_identity > Course::ADMIN #当不为管理员的时候 - user_school_id = current_user.school_id #当前用户的学校id - if user_school_id.present? - none_shixun_ids = ShixunSchool.where("school_id != #{user_school_id}").pluck(:shixun_id) - @publish_shixuns = Shixun.where.not(id: none_shixun_ids).unhidden - end - else - @publish_shixuns = Shixun.unhidden - end - if search.present? - @publish_shixuns = @publish_shixuns.search_by_name(search) - end - - @shixuns = @publish_shixuns.joins(:challenges).where("challenges.st != 0").distinct - # 全部页面,需返回 - @shixuns_count = @shixuns.count - - # 分页 - @page = params[:page] || 1 - @limit = params[:limit] || 8 - - @shixuns = @shixuns.page(@page).per(@limit) - end - end - - #确认实训的选择 - def commit_shixun - ActiveRecord::Base.transaction do - @shixun_challenges = @shixun.challenges - @shixun_challenges_count = @shixun_challenges.size - end - end - - # 首页批量或单独删除 - def destroys - ActiveRecord::Base.transaction do - check_ids = Exercise.where(id: params[:check_ids]) - check_ids.destroy_all - normal_status(0, "试卷已删除成功!") - end - end - - # 设为公开 - def set_public - ActiveRecord::Base.transaction do - check_ids = Exercise.where(id: params[:check_ids]) - check_ids.each do |exercise| - exercise.update!(is_public: true) - end - normal_status(0, "试卷已设为公开!") - end - end - - ## 加入题库 - def join_exercise_banks - ActiveRecord::Base.transaction do - check_ids = Exercise.where(id: params[:check_ids]) - check_ids.each do |exercise| - current_ex_bank = current_user.exercise_banks.find_by_container(exercise.id, "Exercise")&.first - if current_ex_bank.present? #当前用户的选择试卷是否已加入习题库,存在则更新习题库和问题库,否则新建习题库和问题库 - ex_params = { - :name => exercise.exercise_name, - :description => exercise.exercise_description, - :course_list_id => exercise.course.try(:course_list_id) - } - current_ex_bank.update!(ex_params) - # question_bank = QuestionBank.ques_by_container(current_ex_bank.id,current_ex_bank.container_type).first #该习题库是否存在于问题库里 - # ques_params = { - # :name => current_ex_bank.name, - # :course_list_id => current_ex_bank.course_list_id - # } - # question_bank.update_attributes(ques_params) if question_bank.present? - current_ex_bank.exercise_bank_questions.destroy_all # 更新后,习题库的问题全部删除,后续重新再建 - else - ex_params = { - :name => exercise.exercise_name, - :description => exercise.exercise_description, - :user_id => current_user.id, - :is_public => 0, - :course_list_id => exercise.course.try(:course_list_id), - :container_id => exercise.id, - :container_type => "Exercise", - :quotes => 1 - } - current_ex_bank = ExerciseBank.new ex_params - current_ex_bank.save! #如果习题库保存成功,则会创建问题库question_bank - # if current_ex_bank.save - # ques_params = { - # :name => current_ex_bank.name, - # :container_id => current_ex_bank.id, - # :container_type => current_ex_bank.container_type, - # :quotes => current_ex_bank.quotes, - # :user_id => current_ex_bank.user_id, - # :is_public => current_ex_bank.is_public, - # :course_list_id => current_ex_bank.course_list_id - # } - # question_bank = QuestionBank.new ques_params - # question_bank.save - # end - exercise.update!(exercise_bank_id: current_ex_bank.id) - end - # 试卷的问题的输入 - exercise.exercise_questions.each do |q| - option = { - :question_title => q.question_title, - :question_type => q.question_type, - :question_number => q.question_number, - :question_score => q.question_score, - :shixun_id => q.shixun_id, - :shixun_name => q.shixun_name - } - exercise_bank_question = current_ex_bank.exercise_bank_questions.new option - exercise_bank_question.save! - ## 试卷选项的输入 - if q.question_type != Exercise::PRACTICAL #不为实训题时,试卷选项加入试题答案库 - ex_choices = q.exercise_choices - ex_standard = q.exercise_standard_answers - ex_choices.each do |c| - choice_option = { - :choice_position => c.choice_position, - :choice_text => c.choice_text - } - ex_bank_choice = exercise_bank_question.exercise_bank_choices.new choice_option - ex_bank_choice.save! - end - ex_standard.each do |s| - ex_stand = { - :exercise_bank_choice_id => s.exercise_choice_id, - :answer_text => s.answer_text - } - ex_stand_bank = exercise_bank_question.exercise_bank_standard_answers.new ex_stand - ex_stand_bank.save! - end - else #当为实训题时 - shixun_challenges = q.exercise_shixun_challenges - shixun_challenges.each do |c| - challenge_option = { - :position => c.position, - :challenge_id => c.challenge_id, - :shixun_id => q.shixun_id, - :question_score => c.question_score - } - shixun_challenge_bank = exercise_bank_question.exercise_bank_shixun_challenges.new challenge_option - shixun_challenge_bank.save! - end - end - end - current_ex_bank.save! - end - normal_status(0, "题库更新成功!") - end - end - - #试卷的设置页面 - def exercise_setting - ActiveRecord::Base.transaction do - @user_permission = 2 - @user_course_groups = @course.teacher_group(current_user.id) #当前老师的分班 - @being_setting_course_ids = @exercise.common_published_ids(current_user.id) #当前用户已发布的班级的id - @user_published_setting = @exercise.exercise_group_settings - .find_in_exercise_group("course_group_id", @being_setting_course_ids) #当前用户已发布班级的试卷设置 - exercise_ids = [@exercise.id] - @exercise_publish_count = get_user_permission_course(exercise_ids, Exercise::PUBLISHED).count #判断当前用户是否有试卷已发布的分班,用于显示立即截止/撤销发布 - @exercise_unpublish_count = get_user_permission_course(exercise_ids, Exercise::UNPUBLISHED).count #判断当前用户是否有试卷未发布的分班,用户显示立即发布 - @exercise_users_count = @exercise.exercise_users.commit_exercise_by_status(1).count #判断当前试卷是否有已提交的 - # ## 需添加发送消息的接口,稍后添加 - end - end - - #试卷的提交设置 - def commit_setting - ActiveRecord::Base.transaction do - error_count = 0 # 判断循环里是否有已发布/已截止的,且时间更改了的分班。 - # course_group_ids = @course.teacher_course_group_ids(current_user.id) #当前老师的班级id数组 - course_group_ids = @course.charge_group_ids(current_user) #当前老师的班级id数组 - - exercise_status = @exercise.get_exercise_status(current_user) - - if exercise_status == Exercise::UNPUBLISHED && course_group_ids.size > 0 # 试卷未发布,且老师的分班大于1 ,才可以修改统一设置,否则按试卷默认的来处理 - unified_setting = params[:unified_setting] - else - unified_setting = @exercise.unified_setting - end - - show_statistic = params[:show_statistic] ? true : false - exercise_time = params[:time].blank? ? -1 : params[:time] - question_random = params[:question_random] ? true : false #问题是否随机,0为不随机,1为随机 - choice_random = params[:choice_random] ? true : false - score_open = params[:score_open] ? true : false #分数是否公开 - answer_open = params[:answer_open] ? true : false #答案是否公开 - - # 统一设置或者分班为0,则更新试卷,并删除试卷分组 - if unified_setting || (course_group_ids.size == 0) - tip_exception("发布时间不能为空") if params[:publish_time].blank? - tip_exception("截止时间不能为空") if params[:end_time].blank? - tip_exception("截止时间不能早于发布时间") if params[:publish_time].to_time > params[:end_time].to_time - tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && params[:end_time].to_time > @course.end_date.end_of_day - - params_publish_time = params[:publish_time].to_time - params_end_time = params[:end_time].to_time - - if (exercise_status != Exercise::UNPUBLISHED) && (@exercise.publish_time != params_publish_time) - normal_status(-1, "已发布/已截止,不允许修改发布时间") - elsif params_publish_time.present? && params_end_time.present? && params_end_time < params_publish_time - normal_status(-1, "截止时间不能小于发布时间") - else - #发布时间小于当前时间,则试卷显示为未发布,当截止时间大于当前时间,则显示为已截止 - exercise_status_n = set_exercise_status(params_publish_time, params_end_time) - exercise_params = { - :unified_setting => unified_setting, - :show_statistic => show_statistic, - :time => exercise_time, - :question_random => question_random, - :choice_random => choice_random, - :score_open => score_open, - :answer_open => answer_open, - :exercise_status => exercise_status_n, - :publish_time => params_publish_time, - :end_time => params_end_time - } - @exercise.update!(exercise_params) - @exercise.exercise_group_settings.destroy_all - normal_status(0, "试卷设置成功!") - end - else - params_times = params[:publish_time_groups] #分班返回的json数组{"publish_time_groups":[{"course_group_id":"1","publish_time":"xx","end_time":"xxx"}]} - exercise_groups = @exercise.exercise_group_settings.find_in_exercise_group("course_id", @course.id) #试卷的全部分班信息 - exercise_groups_ids = exercise_groups.pluck(:course_group_id) #问卷的全部分班id - total_common = params_times.map {|k| k[:course_group_id]}.sum.uniq #传入的所有分组的分班id - total_common_group = exercise_groups_ids & total_common #传入的分班与问卷已存在的分班的交集 - old_exercise_groups = exercise_groups_ids - total_common_group #后来传入的分班里,没有了的班级,即需要删除 - - params_times.each do |t| - tip_exception("发布时间不能为空") if t[:publish_time].blank? - tip_exception("截止时间不能为空") if t[:end_time].blank? - tip_exception("截止时间不能早于发布时间") if t[:publish_time].to_time > t[:end_time].to_time - tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && t[:end_time].to_time > @course.end_date.end_of_day - - course_id = t[:course_group_id] - exercise_publish_time = t[:publish_time].to_time - exercise_end_time = t[:end_time].to_time - - exercise_group = exercise_groups.find_in_exercise_group("course_group_id", course_id) #判断该分班是否存在 - if exercise_group.present? && (exercise_group.first.publish_time < Time.now) && (exercise_publish_time != exercise_group.first.publish_time) - error_count += 1 - end - if exercise_group.present? && (exercise_group.first.publish_time < Time.now && exercise_group.first.end_time > Time.now) && (exercise_end_time < Time.now) - error_count += 1 - end - if error_count == 0 - common_group = exercise_groups_ids & course_id #传入的班级与问卷已存在的班级的交集,即表示已有分班的 - new_group_ids = course_id - common_group #新传入的班级id - if common_group.count > 0 #判断试卷的分班设置是否存在,存在则更新,负责则新建 - exercise_group_sets = exercise_groups.find_in_exercise_group("course_group_id", common_group) - exercise_group_sets.each do |the_group_setting| - ex_group_params = { - :publish_time => exercise_publish_time, - :end_time => exercise_end_time - } - - the_group_setting_status = set_exercise_status(the_group_setting.publish_time, the_group_setting.end_time) - if the_group_setting_status == 2 - ex_group_params = { - :publish_time => the_group_setting.publish_time, - :end_time => exercise_end_time < Time.now ? the_group_setting.end_time : exercise_end_time - } - elsif the_group_setting_status == 3 - ex_group_params = { - :publish_time => the_group_setting.publish_time, - :end_time => exercise_end_time - } - end - the_group_setting.update!(ex_group_params) - end - end - if new_group_ids.size > 0 - new_group_ids.each do |c| - exercise_group_params = { - :exercise_id => @exercise.id, - :course_group_id => c, - :course_id => @course.id, - :publish_time => exercise_publish_time, - :end_time => exercise_end_time - } - new_exercise_group = ExerciseGroupSetting.new(exercise_group_params) - new_exercise_group.save! - end - end - end - end - - if error_count > 0 - error_count == 0 - normal_status(-1, "试卷发布/截止时间不能小于当前时间") - else - # 未发布的分班设置才能删除 - if old_exercise_groups.size > 0 - old_all_ex_groups = exercise_groups.find_in_exercise_group("course_group_id", old_exercise_groups).exercise_group_not_published - old_all_ex_groups.destroy_all - end - #试卷更新为exercise_group_setting的发布时间最小,截止时间最大 - e_time_present = exercise_groups.end_time_no_null.map(&:end_time) - p_time_present = exercise_groups.publish_time_no_null.map(&:publish_time) - e_time = e_time_present.size > 0 ? e_time_present.max : nil - p_time = p_time_present.size > 0 ? p_time_present.min : nil - exercise_status = 1 - if p_time.nil? #发布时间为空,则表示问卷未发布 - exercise_status = 1 - elsif p_time.present? && e_time.present? - exercise_status = set_exercise_status(p_time, e_time) - end - exercise_params = { - :unified_setting => unified_setting, - :show_statistic => show_statistic, - :time => exercise_time, - :question_random => question_random, - :choice_random => choice_random, - :score_open => score_open, - :answer_open => answer_open, - :exercise_status => exercise_status, - :publish_time => p_time, - :end_time => e_time - } - @exercise.update!(exercise_params) - if @exercise.exercise_status == Exercise::PUBLISHED - if @exercise.course_acts.size == 0 - @exercise.course_acts << CourseActivity.new(:user_id => @exercise.user_id, :course_id => @exercise.course_id) - end - end - normal_status(0, "试卷设置成功!") - end - end - end - end - - # 对未提交的用户进行调分 - def adjust_score - exercise_user = @exercise.exercise_users.find_by!(user_id: params[:user_id]) - tip_exception("已提交的作品请去评阅页进行调分") if exercise_user.commit_status == 1 && exercise_user.commit_method != 5 - if @exercise.subjective_score > 0 - tip_exception("主观题成绩不能为空") if params[:subjective_score].blank? - tip_exception("主观题成绩不能小于零") if params[:subjective_score].to_f < 0 - tip_exception("主观题成绩不能大于总分值:#{@exercise.subjective_score}分") if params[:subjective_score].to_f.round(1) > @exercise.subjective_score.round(1) - end - - if @exercise.objective_score > 0 - tip_exception("客观题成绩不能为空") if params[:objective_score].blank? - tip_exception("客观题成绩不能小于零") if params[:objective_score].to_f < 0 - tip_exception("客观题成绩不能大于总分值:#{@exercise.objective_score}分") if params[:objective_score].to_f.round(1) > @exercise.objective_score.round(1) - end - - ActiveRecord::Base.transaction do - start_at_time = exercise_user.start_at || Time.now - subjective_score = @exercise.subjective_score > 0 ? params[:subjective_score].to_f.round(2) : 0 - objective_score = @exercise.objective_score > 0 ? params[:objective_score].to_f.round(2) : 0 - score = subjective_score + objective_score - if exercise_user.commit_status == 1 - exercise_user.update!(score: score, subjective_score: subjective_score, objective_score: objective_score) - else - exercise_user.update!(start_at: start_at_time, end_at: Time.now, status: 1, commit_status: 1, score: score, - subjective_score: subjective_score, objective_score: objective_score, commit_method: 5) - end - - ExerciseUserScore.create!(exercise_id: @exercise.id, exercise_user_id: exercise_user.id, - subjective_score: subjective_score, objective_score: objective_score) - normal_status("操作成功") - end - end - - #我的题库 - def my_exercises - ActiveRecord::Base.transaction do - ## 我的试卷题库 - @current_user_exercises = current_user.exercise_banks.find_by_c_type("Exercise") - if @current_user_exercises.present? - - if params[:search].present? - search_type = params[:search].to_s.strip - @current_user_exercises = @current_user_exercises.exercise_bank_search(search_type) - end - page = params[:page] || 1 - limit = params[:limit] || 15 - @my_exercises_count = @current_user_exercises.size - @current_user_exercises = @current_user_exercises.page(page).per(limit) - else - @current_user_exercises = [] - end - end - end - - # 公共题库 - def public_exercises - ActiveRecord::Base.transaction do - if current_user.is_certification_teacher - @user_certification = 1 #用户已通过认证 - @public_exercises = ExerciseBank.find_by_c_type("Exercise").public_exercises - if @public_exercises.present? - if params[:search].present? - search_type = params[:search].to_s.strip - @public_exercises = @public_exercises.exercise_bank_search(search_type) - end - page = params[:page] || 1 - limit = params[:limit] || 15 - @public_exercises_count = @public_exercises.size - @public_exercises = @public_exercises.page(page).per(limit) - else - @public_exercises_count = 0 - @public_exercises = [] - end - else - @user_certification = 0 #用户未通过认证 - @public_exercises_count = 0 - @public_exercises = [] - end - end - end - - #立即发布的弹窗内容 - def publish_modal - - ActiveRecord::Base.transaction do - exercise_ids = params[:check_ids] - if exercise_ids.count > 0 - @course_groups = get_user_permission_course(exercise_ids, 1) - else - @course_groups = [] - end - end - end - - # 详情页的立即发布弹框 - def publish_groups - @current_user = current_user - # 可立即发布的分班:当前用户管理的分班去除已发布的分班 - group_ids = @course.charge_group_ids(@current_user) - @exercise.exercise_group_settings.exercise_group_published.pluck(:course_group_id) - @course_groups = @course.course_groups.where(id: group_ids) - @group_settings = @exercise.exercise_group_settings.where(course_group_id: group_ids) - end - - #首页批量或单独 立即发布,应是跳出弹窗,设置开始时间和截止时间。 - def publish - group_ids = params[:group_ids]&.reject(&:blank?) - if params[:detail].blank? - tip_exception("缺少截止时间参数") if params[:end_time].blank? - tip_exception("截止时间不能早于当前时间") if params[:end_time] <= strf_time(Time.now) - tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && params[:end_time] > strf_time(@course.end_date.end_of_day) - else - group_end_times = params[:group_end_times].reject(&:blank?).map {|time| time.to_time} - tip_exception("缺少截止时间参数") if group_end_times.blank? - tip_exception("截止时间和分班参数的个数不一致") if group_end_times.length != group_ids.length - group_end_times.each do |time| - tip_exception("分班截止时间不能早于当前时间") if time <= Time.now - tip_exception("分班截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && time > @course.end_date.end_of_day - end - end - - ActiveRecord::Base.transaction do - check_ids = Exercise.where(id: params[:check_ids]) - ex_end_time = params[:end_time].blank? ? Time.at(((1.month.since.to_i) / 3600.0).ceil * 3600) : params[:end_time].to_time - check_ids.each do |exercise| - if exercise.present? - if exercise.unified_setting - ex_status = exercise.exercise_status #则为试卷的状态 - else - ex_status = @course.course_groups.where(id: params[:group_ids]).size != - exercise.exercise_group_settings.where(course_group_id: params[:group_ids]).exercise_group_published.size ? 1 : 0 - end - if ex_status == 1 #如果试卷存在已发布的,或者是已截止的,那么则直接跳过 - g_course = group_ids #表示是否传入分班参数,如果传入分班的参数,那么试卷的统一设置需修改 - tiding_group_ids = g_course - if g_course - user_course_groups = @course.course_groups.pluck(:id) - if g_course.map(&:to_i).sort == user_course_groups.sort && - ((params[:detail] && group_end_times.min == group_end_times.max) || params[:detail].blank?) # 如果是设置为全部班级,则试卷不用分组,且试卷设定为统一设置,否则则分组设置 - exercise.exercise_group_settings.destroy_all - ex_unified = true - e_time = params[:detail] ? group_end_times.max : ex_end_time - tiding_group_ids = [] - else - ex_unified = false - g_course.each_with_index do |i, index| - exercise_group_setting = exercise.exercise_group_settings.find_in_exercise_group("course_group_id", i).first #根据课堂分班的id,寻找试卷所在的班级 - group_end_time = params[:detail] ? group_end_times[index] : ex_end_time - if exercise_group_setting.present? #如果该试卷分组存在,则更新,否则新建 - exercise_group_setting.update!(publish_time: Time.now, end_time: group_end_time) - else - p_course_group = { - :exercise_id => exercise.id, - :course_group_id => i, - :course_id => exercise.course.id, - :publish_time => Time.now, - :end_time => group_end_time, - } - new_exercise_group = exercise.exercise_group_settings.new p_course_group - new_exercise_group.save! - end - end - # group_ids = params[:group_ids] - e_time = exercise.exercise_group_settings.end_time_no_null.map(&:end_time).max - end - else - exercise.exercise_group_settings.destroy_all - ex_unified = true - e_time = ex_end_time - end - - ex_status = set_exercise_status(Time.now, e_time) - exercise_params = { - :publish_time => Time.now, - :end_time => e_time, - :exercise_status => ex_status, - :unified_setting => ex_unified - } - exercise.update!(exercise_params) - - if exercise.course_acts.size == 0 - exercise.course_acts << CourseActivity.new(:user_id => exercise.user_id, :course_id => exercise.course_id) - end - ExercisePublishNotifyJob.perform_later(exercise.id, tiding_group_ids) - end - end - end - normal_status(0, "试卷发布成功!") - end - end - - #立即截止的弹窗内容 - def end_modal - ActiveRecord::Base.transaction do - exercise_ids = params[:check_ids] - if exercise_ids.count > 0 - @course_groups = get_user_permission_course(exercise_ids, 3) - else - @course_groups = [] - end - end - end - - # 首页批量或单独 立即截止,截止时间为当前时间 - def end_exercise - - ActiveRecord::Base.transaction do - check_ids = Exercise.where(id: params[:check_ids]) - course_students = @course.students #课堂的全部学生数 - check_ids.each do |exercise| - exercise_status = exercise.get_exercise_status(current_user) - if exercise_status == Exercise::PUBLISHED #跳过已截止的或未发布的 - g_course = params[:group_ids] - if g_course.present? - teacher_course_group_ids = @course.charge_group_ids(current_user) - all_course_group_ids = @course.course_groups.pluck(:id) - if exercise.unified_setting && g_course.map(&:to_i).sort == all_course_group_ids.sort #开始为统一设置 - exercise.exercise_group_settings.destroy_all - new_ex_status = set_exercise_status(exercise.publish_time, Time.now) - exercise.update!(:end_time => Time.now, :exercise_status => new_ex_status) - exercise_users = exercise.exercise_users - else - course_members_ids = course_students.course_find_by_ids("course_group_id", g_course).pluck(:user_id).uniq #该班级的全部学生 - exercise_users = exercise.exercise_users.exercise_commit_users(course_members_ids) #参与答题的学生数 - ex_group_setting = exercise.exercise_group_settings - old_exercise_groups = ex_group_setting.find_in_exercise_group("course_group_id", g_course) #试卷的分组设置 - left_course_groups = teacher_course_group_ids - g_course - left_exercise_groups = ex_group_setting.find_in_exercise_group("course_group_id", left_course_groups) - if left_exercise_groups.blank? && exercise.unified_setting - if left_course_groups.size > 0 #开始为统一设置,但是立即截止为分班。则创建没有立即截止的班级的exercise_group_setting - left_course_groups.each do |g| - ex_group_options = { - :exercise_id => exercise.id, - :course_group_id => g, - :course_id => @course.id, - :publish_time => exercise.publish_time, - :end_time => exercise.end_time - } - ExerciseGroupSetting.create!(ex_group_options) - end - end - end - if old_exercise_groups.present? - old_exercise_groups.update_all(:end_time => Time.now) - else - g_course.each do |g| - ex_group_options = { - :exercise_id => exercise.id, - :course_group_id => g, - :course_id => @course.id, - :publish_time => exercise.publish_time, - :end_time => Time.now - } - ExerciseGroupSetting.create!(ex_group_options) - end - end - new_end_time = exercise.exercise_group_settings.end_time_no_null.map(&:end_time) # 试卷结束时间不为空的 - new_end_time_s = new_end_time.count > 0 ? new_end_time.max : Time.now - new_ex_status = set_exercise_status(exercise.publish_time, new_end_time_s) - exercise.update!(:end_time => new_end_time_s, :exercise_status => new_ex_status, :unified_setting => false) - end - else - exercise_users = exercise.exercise_users - exercise.update!(:exercise_status => 3, :end_time => Time.now, :unified_setting => true) - end - - ex_user_ids = exercise_users.pluck(:id) - - EndExerciseCalculateJob.perform_later(ex_user_ids, exercise, Time.now.to_s) - # exercise_users.each do |user| - # if user.commit_status == 0 && user.start_at.present? - # objective_score = calculate_student_score(exercise,user.user)[:total_score] - # user_sub_score = user.subjective_score - # subjective_score = user_sub_score < 0.0 ? 0.0 : user_sub_score - # total_score = objective_score + subjective_score - # commit_option = { - # :status => 1, - # :commit_status => 1, - # :end_at => Time.now, - # :objective_score => objective_score, - # :score => total_score, - # :subjective_score => user_sub_score - # } - # user.update_attributes(commit_option) - # end - # end - end - end - normal_status(0, "试卷截止成功!") - end - end - - #学生撤销回答 - def cancel_exercise - ActiveRecord::Base.transaction do - ex_question_ids = @exercise.exercise_questions.pluck(:id) - exercise_user = @exercise.exercise_users.exercise_commit_users(current_user.id).first - if exercise_user.present? - if exercise_user.commit_status == 1 && @exercise.get_exercise_status(current_user) == Exercise::PUBLISHED #用户已提交且试卷提交中 - if @exercise.time == -1 || ((Time.now.to_i - exercise_user.start_at.to_i) < @exercise.time.to_i * 60) - exercise_user.update!(:score => nil, :end_at => nil, :status => nil, :commit_status => 0, - :objective_score => 0.0, :subjective_score => -1.0) - exercise_user.user.exercise_shixun_answers.search_shixun_answers("exercise_question_id", ex_question_ids).destroy_all - exercise_answers = exercise_user.user.exercise_answers.search_answer_users("exercise_question_id", ex_question_ids) - exercise_answers.update_all(:score => -1.0) - all_answer_comment = ExerciseAnswerComment.search_answer_comments("exercise_question_id", ex_question_ids) - .search_answer_comments("exercise_answer_id", exercise_answers.pluck(:id)) - all_answer_comment.destroy_all - normal_status(0, "撤销回答成功") - else - normal_status(-1, "用户答题时间已到") - end - else - normal_status(-1, "用户未提交/试卷不是提交中") - end - else - normal_status(-1, "当前用户未答题") - end - end - end - - #打回重做modal - def redo_modal - ActiveRecord::Base.transaction do - #搜索 - if params[:realname].present? - search_name = params[:realname] - #搜索用户的nickname,如果存在则返回,否则继续查询用户的真实姓名或学生号 - @exercise_users = @exercise_users.includes(:user).where("LOWER(concat(users.lastname, users.firstname)) like ?", - "%#{search_name}%") - end - if params[:student_id].present? - search_st_id = params[:student_id].to_i - @exercise_users = @exercise_users.includes(user: [:user_extension]) - .where('user_extensions.student_id like ?', "%#{search_st_id}%") - end - sort = params[:sort] ? params[:sort] : "asc" - @exercise_users = @exercise_users.order("score #{sort}") - @exercise_users_size = @exercise_users.size - # 分页 - page = params[:page] || 1 - limit = params[:limit] || 15 - @exercise_users = @exercise_users.page(page).per(limit) - end - end - - #打回重做确认 - def redo_exercise - ActiveRecord::Base.transaction do - user_ids = params[:user_ids] - if user_ids.present? - redo_option = { - :score => 0.0, - :start_at => nil, - :end_at => nil, - :status => nil, - :commit_status => 0, - :objective_score => 0.0, - :subjective_score => -1.0, - :commit_method => 0 - } - redo_exercise_users = @exercise_users.exercise_commit_users(user_ids) - redo_exercise_users.update_all(redo_option) - exercise_question_ids = @exercise.exercise_questions.pluck(:id).uniq - ExerciseAnswer.search_answer_users("user_id", user_ids) - .search_answer_users("exercise_question_id", exercise_question_ids).destroy_all - ExerciseShixunAnswer.search_shixun_answers("user_id", user_ids) - .search_shixun_answers("exercise_question_id", exercise_question_ids).destroy_all - - normal_status(0, "已成功打回重做!") - else - normal_status(-1, "请选择学生!") - end - end - end - - #学生开始答题页面 - def start_answer - ex_users_current = ExerciseUser.where(user_id: @exercise_current_user_id, exercise_id: @exercise.id) #不能用@exercise.exercise_users,因为exercise_users删除时,只是状态改变,未删除 - @exercise_user_current = ex_users_current&.first - if ex_users_current.exists? - if @exercise_user_current.start_at.blank? - @exercise_user_current.update!(start_at: Time.now) - end - else - if @user_course_identity > Course::ASSISTANT_PROFESSOR #当为老师的时候,不创建exercise_user表,理论上老师是不能进入答题的 - exercise_user_params = { - :user_id => @exercise_current_user_id, - :exercise_id => @exercise.id, - :start_at => Time.now - } - exercise_user_current = ExerciseUser.new(exercise_user_params) - exercise_user_current.save! - end - end - @t_user_exercise_status = @exercise.get_exercise_status(current_user) - - @user_left_time = nil - if @user_course_identity < Course::STUDENT || (@t_user_exercise_status == 3) || - (ex_users_current.exists? && @exercise_user_current.commit_status == 1) - @user_exercise_status = 1 #当前用户为老师/试卷已截止/试卷已提交不可编辑 - else - @user_left_time = get_exercise_left_time(@exercise, current_user) - @user_exercise_status = 0 #可编辑 - end - - @exercise_questions = @exercise.exercise_questions - - if @exercise.question_random - @exercise_questions = @exercise_questions.order("RAND()") - else - @exercise_questions = @exercise_questions.order("question_number ASC") - end - # 判断问题是否已回答还是未回答 - @exercise_questions = @exercise_questions.includes(:exercise_shixun_challenges, - :exercise_shixun_answers, - :exercise_answers, - :exercise_standard_answers) - - if @t_user_exercise_status == Exercise::DEADLINE - get_each_student_exercise(@exercise.id, @exercise_questions, @exercise_current_user_id) - end - get_user_answer_status(@exercise_questions, @exercise_current_user_id, @exercise, @t_user_exercise_status) - - end - - #提交试卷前的弹窗 - def begin_commit - ActiveRecord::Base.transaction do - if @user_course_identity > Course::ASSISTANT_PROFESSOR #为学生时 - @exercise_questions = @exercise.exercise_questions - @shixun_undo = 0 - @ques_undo = 0 - ex_answer_time = @exercise.time.to_i - if ex_answer_time > 0 #有剩余时间的时候 - user_left_time = get_exercise_left_time(@exercise, current_user) - @ex_end_time = Time.now + user_left_time.to_i.seconds - else - @ex_end_time = @exercise.get_exercise_end_time(current_user.id) - end - # @ex_end_time = @exercise.get_exercise_end_time(current_user.id) - # if ex_answer_time > 0 - # left_answer_time = Time.now + ex_answer_time.minutes #判断试卷的倒计时和截止时间哪个先到 - # if left_answer_time < @ex_end_time - # exercise_end_time = @exercise.exercise_users.exercise_commit_users(current_user.id) - # if exercise_end_time.present? - # ex_end_times = exercise_end_time.first.start_at.nil? ? Time.now : exercise_end_time.first.start_at - # @ex_end_time = ex_end_times + ex_answer_time.minutes - # end - # end - # end - @exercise_questions.each do |q| - if q.question_type == Exercise::PRACTICAL #当为实训题时 - user_myshixun = q.shixun.myshixuns.search_myshixun_user(current_user.id) - if user_myshixun.blank? || user_myshixun.first.status != Exercise::UNPUBLISHED #当前用户的实训是否做完 - @shixun_undo += 1 - end - else - ques_vote = q.exercise_answers.search_exercise_answer("user_id", current_user.id) - if ques_vote.blank? - @ques_undo += 1 - end - end - end - end - end - end - - # 学生提交试卷 - def commit_exercise - tip_exception(0, "试卷截止时间已到,系统已自动提交") if @answer_committed_user.commit_status == 1 - ActiveRecord::Base.transaction do - can_commit_exercise = false - user_left_time = nil - if @user_course_identity > Course::ASSISTANT_PROFESSOR #为学生时 - if params[:commit_method].to_i == 2 #自动提交时 - user_left_time = get_exercise_left_time(@exercise, current_user) - Rails.logger.info("######__________auto_commit_user_left_time_________################{user_left_time}") - if user_left_time.to_i <= 0 - can_commit_exercise = true - end - else - can_commit_exercise = true - end - if can_commit_exercise - objective_score = calculate_student_score(@exercise, current_user, Time.now)[:total_score] - subjective_score = @answer_committed_user.subjective_score - total_score_subjective_score = subjective_score < 0.0 ? 0.0 : subjective_score - total_score = objective_score + total_score_subjective_score - commit_option = { - :status => 1, - :commit_status => 1, - :end_at => Time.now, - :objective_score => objective_score, - :score => total_score, - :subjective_score => subjective_score, - :commit_method => @answer_committed_user&.commit_method.to_i > 0 ? @answer_committed_user&.commit_method.to_i : params[:commit_method].to_i - } - @answer_committed_user.update!(commit_option) - CommitExercsieNotifyJobJob.perform_later(@exercise.id, current_user.id) - normal_status(0, "试卷提交成功!") - else - normal_status(-2, "#{user_left_time.to_i}") - end - else - normal_status(-1, "提交失败,当前用户不为课堂学生!") - end - end - end - - #教师评阅试卷 及学生查看试卷 - def review_exercise - ActiveRecord::Base.transaction do - # 1 老师权限,0 学生权限 - @is_teacher_or = (@user_course_identity < Course::STUDENT) ? 1 : 0 - @student_status = 2 - @exercise_questions = @exercise.exercise_questions.includes(:exercise_shixun_challenges, :exercise_standard_answers, :exercise_answers, :exercise_shixun_answers, :exercise_answer_comments).order("question_number ASC") - @question_status = [] - get_exercise_status = @exercise.get_exercise_status(current_user) #当前用户的试卷状态 - @ex_answer_status = @exercise.get_exercise_status(@ex_user&.user) #当前试卷用户的试卷状态 - if @ex_user.present? && @is_teacher_or == 0 - if get_exercise_status == Exercise::PUBLISHED #当前用户已提交,且试卷未截止 - if @ex_user.commit_status == 0 #学生未提交,且当前为学生 - @student_status = 0 - else - @student_status = 1 - get_user_answer_status(@exercise_questions, @exercise_current_user_id, @exercise, get_exercise_status) - end - end - end - if @student_status == 2 - get_each_student_exercise(@exercise.id, @exercise_questions, @exercise_current_user_id) - end - end - end - - #答题列表 - def exercise_lists - @current_user_id = current_user.id - exercise_ids = [@exercise.id] - @exercise_status = @exercise.get_exercise_status(current_user) - @course_all_members = @course.students - @c_group_counts = @course.course_groups_count - question_types = @exercise.exercise_questions.pluck(:question_type).uniq - @exercise_publish_count = get_user_permission_course(exercise_ids, Exercise::PUBLISHED).count #判断是否有已发布的分班 - @exercise_unpublish_count = get_user_permission_course(exercise_ids, Exercise::UNPUBLISHED).count #判断是否有未发布的分班 - - if (question_types.size > 1) && question_types.include?(Exercise::SUBJECTIVE) #是否包含主观题,或者是否大于1 - @subjective_type = 1 - else - @subjective_type = 0 - end - - #初始化值 - @exercise_users_list = [] #答题用户列表 - @exercise_course_groups = [] #当前用户有权限的班级 - @exercise_unanswers = 0 # 未答用户数 - @exercise_answers = 0 #已答用户数 - @exercise_users_count = 0 #全部用户数 - @teacher_review_count = 0 #已评数 - @teacher_unreview_count = 0 #未评数 - - #试卷的答题列表页的显示用户 - if @user_course_identity < Course::STUDENT #当前为老师,而且老师只能查看自己班级的/课堂的试卷 - @exercise_current_user_status = 0 - unless @exercise_status == Exercise::UNPUBLISHED - ex_common_ids = @exercise.common_published_ids(current_user.id) - @exercise_course_groups = @course.get_ex_published_course(ex_common_ids) - @exercise_users_list = @exercise.all_exercise_users(current_user.id) #当前老师所在班级的全部学生 - get_exercise_answers(@exercise_users_list, @exercise_status) - end - else #当前为学生或者有过答题的 - @ex_user_end_time = @exercise.get_exercise_end_time(current_user.id) #当前用户所看到的剩余时间 - @exercise_all_users = @exercise.get_stu_exercise_users - get_exercise_answers(@exercise_all_users, @exercise_status) # 未答和已答的 - exercise_current_user = @exercise_all_users.exercise_commit_users(current_user.id) - if exercise_current_user.exists? #表示为课堂学生或已回答的 - @exercise_current_user_status = 1 - if @exercise.score_open && @exercise_status == Exercise::DEADLINE #勾选了成绩公开且试卷已截止的 - all_user_ids = @exercise_all_users.pluck(:user_id) - all_user_ids.delete(current_user.id) #删除了当前用户的ID - @exercise_users_list = @exercise_all_users.exercise_commit_users(all_user_ids).distinct - @current_user_ex_answers = exercise_current_user #当前用户的回答 - else - @exercise_users_list = exercise_current_user - end - else #表示为未回答的,或未非课堂成员的 - @exercise_current_user_status = 2 #当前用户非课堂成员 - end - end - - if @exercise_unanswers < 0 - @exercise_unanswers = 0 - end - - #筛选/分类,排序 - order = params[:order] - order_type = params[:order_type] || "desc" - - if @exercise_users_list.present? && @exercise_users_list.size > 0 - @exercise_users_count = @exercise_users_list.size #当前显示的全部成员数量 - teacher_reviews = @exercise_users_list.exercise_review - teacher_unreviews = @exercise_users_list.exercise_unreview - @teacher_review_count = teacher_reviews.size #已评阅 - @teacher_unreview_count = teacher_unreviews.size #未评阅 - - #是否评阅 - if params[:review].present? - review_type = params[:review].first.to_i #已评,则数据为1,未评,则数据为0,前端传过来的为数组 - if review_type == 1 - @exercise_users_list = teacher_reviews - else - @exercise_users_list = teacher_unreviews - end - end - - #答题状态的选择 - if params[:commit_status].present? - choose_type = params[:commit_status] - @exercise_users_list = @exercise_users_list.commit_exercise_by_status(choose_type) - end - - #班级的选择 - if params[:exercise_group_id].present? - group_id = params[:exercise_group_id] - exercise_students = @course_all_members.course_find_by_ids("course_group_id", group_id) #试卷所分班的全部人数 - user_ids = exercise_students.pluck(:user_id).reject(&:blank?) - @exercise_users_list = @exercise_users_list.exercise_commit_users(user_ids) - end - - #搜索 - if params[:search].present? - @exercise_users_list = @exercise_users_list.joins(user: :user_extension).where("CONCAT(lastname, firstname) like ? OR student_id like ?", "%#{params[:search]}%", "%#{params[:search]}%") - end - - exercise_user_joins = @exercise_users_list.joins(user: :user_extension) - - if order == "student_id" - @exercise_users_list = exercise_user_joins.order("user_extensions.student_id #{order_type}") - elsif order == "score" - @exercise_users_list = exercise_user_joins.order("#{order} #{order_type}") - else - @exercise_users_list = exercise_user_joins.order("end_at #{order_type}, start_at #{order_type}") - end - - @export_ex_users = @exercise_users_list - - @exercise_users_size = @exercise_users_list.size - - # 分页 - @page = params[:page] || 1 - @limit = params[:limit] || 20 - @exercise_users_list = @exercise_users_list.page(@page).per(@limit) - else - @exercise_users_list = [] - @export_ex_users = @exercise_users_list - @exercise_users_size = 0 - end - - if params[:format] == "xlsx" - if @user_course_identity > Course::ASSISTANT_PROFESSOR - tip_exception(403, "无权限操作") - elsif @exercise_status == Exercise::UNPUBLISHED - normal_status(-1, "试卷未发布") - elsif (@exercise_users_size == 0) || (@export_ex_users&.exercise_user_committed.size == 0) - normal_status(-1, "暂无用户提交") - elsif params[:export].present? && params[:export] - normal_status(0, "正在下载中") - else - respond_to do |format| - format.xlsx { - set_export_cookies - get_export_users(@exercise, @course, @export_ex_users) - exercise_export_name_ = - "#{current_user.real_name}_#{@course.name}_#{@exercise.exercise_name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}" - render xlsx: "#{exercise_export_name_.strip}", template: "exercises/exercise_lists.xlsx.axlsx", locals: {table_columns: @table_columns, exercise_users: @user_columns} - } - end - end - end - end - - #导出空白试卷 - def export_exercise - @request_url = request.base_url - @exercise_questions = @exercise.exercise_questions.includes(:exercise_choices).order("question_number ASC") - filename_ = "#{@exercise.user.real_name}_#{@course.name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}.pdf" - stylesheets = "#{Rails.root}/app/templates/exercise_export/exercise_export.css" - if params[:export].present? && params[:export] - normal_status(0, "正在下载中") - else - set_export_cookies - render pdf: 'exercise_export/blank_exercise', filename: filename_, stylesheets: stylesheets, disposition: 'inline', type: "pdf_attachment.content_type", stream: false - end - end - - #空白试卷预览页面,仅供测试使用,无其他任何用途 - # def blank_exercise - # ActiveRecord::Base.transaction do - # begin - # @exercise_questions = @exercise.exercise_questions.order("question_number ASC") - # challenge_ids = @exercise_questions.joins(:exercise_shixun_challenges).pluck("exercise_shixun_challenges.challenge_id") - # get_each_student_exercise(@exercise.id,@exercise_questions,31798) - # @games = @exercise_user.user.games.ch_games(challenge_ids) - # respond_to do |format| - # format.html - # end - # rescue Exception => e - # uid_logger_error(e.message) - # tip_exception("没有权限") - # raise ActiveRecord::Rollback - # end - # end - # end - - #学生的统计结果 - def exercise_result - exercise_ids = [@exercise.id] - @exercise_publish_count = get_user_permission_course(exercise_ids, Exercise::PUBLISHED).size #判断是否有已发布的分班 - @exercise_unpublish_count = get_user_permission_course(exercise_ids, Exercise::UNPUBLISHED).size #判断是否有未发布的分班 - @course_all_members = @course.students #课堂的全部学生 - @exercise_all_users = @exercise.exercise_users - ex_common_ids = @exercise.common_published_ids(current_user.id) - @exercise_course_groups = @course.get_ex_published_course(ex_common_ids) - - #班级的选择 - if params[:exercise_group_id].present? - group_id = params[:exercise_group_id] - exercise_students = @course_all_members.course_find_by_ids("course_group_id", group_id) # 试卷所分班的全部人数 - user_ids = exercise_students.pluck(:user_id).reject(&:blank?) - @exercise_all_users = @exercise.exercise_users.exercise_commit_users(user_ids) - @course_all_members_count = @exercise_all_users.size - else - @exercise_users_list = @exercise.all_exercise_users(current_user.id) - @course_all_members_count = @exercise_users_list.size - end - @exercise_commit_users = @exercise_all_users.commit_exercise_by_status(1) #试卷的已提交用户 - @exercise_commit_user_ids = @exercise_commit_users.pluck(:user_id).uniq #已提交试卷的全部用户id - @exercise_commit_user_counts = @exercise_commit_users.size #试卷的已提交用户人数 - @exercise_status = @exercise.get_exercise_status(current_user) - - #提交率 - if @course_all_members_count == 0 - commit_percent = 0.00 - min_score = 0.0 - max_score = 0.0 - average_score = 0.0 - fail_counts = 0 - pass_counts = 0 - good_counts = 0 - best_counts = 0 - else - commit_percent = (@exercise_commit_user_counts / @course_all_members_count.to_f).round(3) - exercise_scores = @exercise_commit_users.pluck(:score).reject(&:blank?) - min_score = exercise_scores.min.present? ? exercise_scores.min : 0.0 - max_score = exercise_scores.max.present? ? exercise_scores.max : 0.0 - total_score = exercise_scores.sum.present? ? exercise_scores.sum : 0.0 - average_score = @exercise_commit_user_counts > 0 ? (total_score.round(1) / @exercise_commit_user_counts).round(1) : 0.0 - question_scores = @exercise.question_scores - fail_score = question_scores * 0.6.round(2) - pass_score = question_scores * 0.7.round(2) - good_score = question_scores * 0.9.round(2) - - fail_counts = exercise_scores.count {|a| a < fail_score} - pass_counts = exercise_scores.count {|a| a < pass_score && a >= fail_score} - good_counts = exercise_scores.count {|a| a < good_score && a >= pass_score} - best_counts = exercise_scores.count {|a| a >= good_score && a <= question_scores} - end - @counts_array = { - :commit_percent => commit_percent, - :min_score => min_score.to_s, - :max_score => max_score.to_s, - :average_score => average_score.to_s, - :fail_counts => fail_counts, - :pass_counts => pass_counts, - :good_counts => good_counts, - :best_counts => best_counts, - } - - @exercise_questions = @exercise.exercise_questions&.includes(:exercise_choices, :exercise_answers, :exercise_standard_answers, :exercise_shixun_challenges, :exercise_shixun_answers) - - percent_sort = "desc" - - if params[:sort].present? - percent_sort = params[:sort] - end - # @paging_type = "percent" - # # 按题型排序 - # if params[:sort].present? - # @paging_type = params[:sort].to_s - # end - - ques_result_all = exercise_commit_result(@exercise_questions, @exercise_commit_user_ids) - - #默认降序排列 - if percent_sort == "desc" - @question_result_hash = ques_result_all.sort_by {|s| s[:percent]}.reverse - else - @question_result_hash = ques_result_all.sort_by {|s| s[:percent]} - end - - @exercise_questions_count = @exercise_questions.size - @page = params[:page] || 1 - @limit = params[:limit] || 10 - @question_result_hash = Kaminari.paginate_array(@question_result_hash).page(@page).per(@limit) - end - - private - - def exercise_params - params.require(:exercise).permit(:exercise_name, :exercise_description, :course_id, :exercise_status, :user_id, :time, - :publish_time, :end_time, :show_result, :question_random, :choice_random, :is_public, - :score_open, :answer_open, :exercise_bank_id, :unified_setting, :show_statistic) - end - - def is_course_teacher - unless @user_course_identity < Course::STUDENT #为老师/助教/管理员 - normal_status(403, "...") - end - end - - #检查传入的参数内容是否符合 - def validates_exercise_params - normal_status(-1, "试卷标题不能为空!") if params[:exercise_name].blank? - normal_status(-1, "试卷标题不能超过60个字符") if (params[:exercise_name].length > 60) - normal_status(-1, "试卷须知不能超过100个字符") if (params[:exercise_description].present? && - params[:exercise_description].length > 100) - end - - #判断设置的时间是否合理 - def validate_publish_time - # 截止时间存在,且截止时间必须大于当前时间或发布时间 - unified_setting = params[:unified_setting] - publish_course = params[:publish_time_groups] - if @course.is_end - normal_status(-1, "课堂已结束不能再修改") - elsif unified_setting - ex_group_settings = @exercise.exercise_group_settings - if ex_group_settings.present? - p_time_present = ex_group_settings.publish_time_no_null.map(&:publish_time).min - if p_time_present && p_time_present < Time.now - normal_status(-1, "设置失败,存在已发布的分班") - end - elsif params[:publish_time].blank? - normal_status(-1, "发布时间不允许为空") - end - elsif unified_setting.present? && !unified_setting #非统一设置,分班不能为空 - if publish_course.present? - course_ids = publish_course.map {|a| a[:course_group_id]}.sum - publish_t = publish_course.map {|a| a[:publish_time]} - if course_ids.include?(nil) || course_ids.count == 0 - normal_status(-1, "请选择分班") - elsif publish_t.include?(nil) || publish_t.count == 0 - normal_status(-1, "发布时间不允许为空") - end - else - normal_status(-1, "请选择分班") - end - end - end - - def get_exercise - @exercise = Exercise.find_by(id: params[:id]) - if @exercise.blank? - normal_status(404, "试卷不存在") - else - @course = @exercise.course - normal_status(404, "课堂不存在") if @course.blank? - end - end - - def get_exercise_question_counts #获取试卷的问题数及总分数 - exercise_questions = @exercise.exercise_questions - @exercise_ques_count = exercise_questions.size # 全部的题目数 - @exercise_ques_scores = exercise_questions.pluck(:question_score).sum - - #单选题的数量及分数 - exercise_single_ques = exercise_questions.find_by_custom("question_type", Exercise::SINGLE) - @exercise_single_ques_count = exercise_single_ques.size - @exercise_single_ques_scores = exercise_single_ques.pluck(:question_score).sum - - #多选题的数量及分数 - exercise_double_ques = exercise_questions.find_by_custom("question_type", Exercise::MULTIPLE) - @exercise_double_ques_count = exercise_double_ques.size - @exercise_double_ques_scores = exercise_double_ques.pluck(:question_score).sum - - # 判断题数量及分数 - exercise_ques_judge = exercise_questions.find_by_custom("question_type", Exercise::JUDGMENT) - @exercise_ques_judge_count = exercise_ques_judge.size - @exercise_ques_judge_scores = exercise_ques_judge.pluck(:question_score).sum - - #填空题数量及分数 - exercise_ques_null = exercise_questions.find_by_custom("question_type", Exercise::COMPLETION) - @exercise_ques_null_count = exercise_ques_null.size - @exercise_ques_null_scores = exercise_ques_null.pluck(:question_score).sum - - #简答题数量及分数 - exercise_ques_main = exercise_questions.find_by_custom("question_type", Exercise::SUBJECTIVE) - @exercise_ques_main_count = exercise_ques_main.size - @exercise_ques_main_scores = exercise_ques_main.pluck(:question_score).sum - - #实训题数量及分数 - exercise_ques_shixun = exercise_questions.find_by_custom("question_type", Exercise::PRACTICAL) - @exercise_ques_shixun_count = exercise_ques_shixun.size - @exercise_ques_shixun_scores = exercise_ques_shixun.pluck(:question_score).sum - - @exercise_questions = @exercise_questions&.includes(:exercise_choices, :exercise_shixun_challenges, :exercise_answers, :exercise_shixun_answers, :exercise_answer_comments, :exercise_standard_answers) - - end - - #获取用户有权限的分班 - def get_user_permission_course(exercise_ids, status) - exercise_status = status.to_i #传入的试卷发布状态 - unpublish_group = [] - course_groups = [] - user_groups_id = @course.charge_group_ids(current_user) - exercises_all = Exercise.includes(:exercise_group_settings).where(id: exercise_ids) - exercises_all.each do |exercise| - if exercise.present? - if exercise.unified_setting #统一设置只有两种情况,全部发布,全部截止 - exercise_user_status = exercise.get_exercise_status(current_user) #当前用户的能看到的试卷 - if (exercise_user_status == exercise_status) || exercise_status == Exercise::DEADLINE #未发布的情况 - unpublish_group = unpublish_group + user_groups_id - end - else - ex_all_group_settings = exercise.exercise_group_settings - ex_group_settings = ex_all_group_settings.exercise_group_published.pluck(:course_group_id).uniq #问卷设置的班级 - if exercise_status == Exercise::UNPUBLISHED - unpublish_group = user_groups_id - ex_group_settings - elsif exercise_status == Exercise::DEADLINE - ex_ended_groups = ex_all_group_settings.exercise_group_ended.pluck(:course_group_id).uniq - ex_and_user = user_groups_id & ex_group_settings #用户已设置的分班 - unpublish_group = unpublish_group + ex_and_user - ex_ended_groups #已发布的全部班级减去截止的全部班级 - else - ex_ended_groups = ex_all_group_settings.exercise_group_ended.pluck(:course_group_id).uniq - ex_and_user = user_groups_id & ex_group_settings #用户已设置的分班 - unpublish_group = unpublish_group + ex_and_user - ex_ended_groups - end - end - end - end - Rails.logger.info("#####____________unpublish_group_______#######{unpublish_group}") - unpublish_group = unpublish_group.uniq - if unpublish_group.count > 0 - course_groups = CourseGroup.by_group_ids(unpublish_group) - end - course_groups - end - - def set_exercise_status(publish_time, end_time) - time_now_i = Time.now - if publish_time.present? && (publish_time <= time_now_i) && (end_time > time_now_i) - 2 - elsif publish_time.nil? || (publish_time.present? && publish_time > time_now_i) - 1 - elsif end_time.present? && (end_time <= time_now_i) - 3 - elsif end_time.present? && publish_time.present? && (end_time < publish_time) - normal_status(-1, "时间设置错误!") - else - 1 - end - end - - def check_course_public - unless @course.is_public == 1 # 0为私有,1为公开 - normal_status(403, "...") - end - end - - def check_user_id_start_answer #判断用户在开始答题时,是否有用户id传入,如果为老师,则id必需,否则为当前用户的id - user_login = params[:login] - if user_login.blank? && @user_course_identity < Course::STUDENT #id不存在,且当前为老师/管理员等 - normal_status(-1, "请输入学生登陆名!") - else - if @user_course_identity < Course::STUDENT || @exercise.score_open - @ex_answerer = user_login.blank? ? current_user : User.find_by(login: user_login) - else - @ex_answerer = current_user - end - - if @ex_answerer.blank? - normal_status(404, "答题用户不存在") - elsif @user_course_identity > Course::STUDENT && !@exercise.is_public - normal_status(403, "非公开试卷") - else - # @exercise_current_user_id = @ex_answerer.id || current_user.id - @exercise_current_user_id = @ex_answerer.id - end - end - end - - ## 判断开始答题页面的用户权限 - def check_user_on_answer - if @user_course_identity == Course::STUDENT && @exercise.get_exercise_status(current_user) == Exercise::UNPUBLISHED #试卷未发布,且当前用户不为老师/管理员 - normal_status(-1, "未发布试卷!") - elsif @user_course_identity > Course::STUDENT && (!@exercise.is_public || (@exercise.is_public && !@exercise.unified_setting)) ##不为课堂成员,且试卷不为公开的,或试卷公开,但不是统一设置的 - normal_status(-1, "试卷暂未公开!") - end - end - - def check_exercise_time - @answer_committed_user = @exercise.exercise_users.exercise_commit_users(current_user.id)&.first - if @answer_committed_user.blank? - normal_status(404, "答题用户不存在") - end - end - - #打回重做时的初步判断 - def check_exercise_status - @exercise_users = @exercise.all_exercise_users(current_user.id).commit_exercise_by_status(1) #当前教师所在分班的全部已提交的学生数 - if @exercise.get_exercise_status(current_user) != Exercise::PUBLISHED - normal_status(-1, "非提交中的试卷不允许打回重做!") - elsif @exercise_users.count < 1 - normal_status(-1, "暂无人提交试卷!") - end - end - - - #查看试题页面,当为学生时,除非试卷已截止,或已提交才可以查看 - def check_exercise_is_end - ex_status = @exercise.get_exercise_status(current_user) - @ex_user = @exercise.exercise_users.find_by(user_id: @exercise_current_user_id) #该试卷的回答者 - if @user_course_identity > Course::ASSISTANT_PROFESSOR - if ex_status == Exercise::UNPUBLISHED - normal_status(-1, "试卷未发布") - elsif @ex_user.present? && @ex_user.commit_status == 0 - normal_status(-1, "试卷未提交") - elsif params[:user_id].present? && current_user.id != params[:user_id] - normal_status(-1, "不能查看他人的试卷") - end - end - end - - #查看试卷是否选择为公开统计 - def check_exercise_public - if @user_course_identity > Course::ASSISTANT_PROFESSOR #当前为学生,试卷公开统计,且已截止,且已提交 - ex_user = @exercise.exercise_users.exercise_commit_users(current_user.id).first - unless @exercise.get_exercise_status(current_user) == Exercise::DEADLINE && ex_user.present? && ex_user.commit_status == 1 && - @exercise.show_statistic - normal_status(-1, "学生暂不能查看") - end - end - end - - def get_left_banner_id - left_banner_content = @course.course_modules.search_by_module_type("exercise") - if left_banner_content.present? - @left_banner_id = left_banner_content.first.id - @left_banner_name = left_banner_content.first.module_name - else - normal_status(404, "左侧导航不存在") - end - end - - def get_user_answer_status(exercise_questions, user_id, exercise, exercise_user_status) - @question_status = [] - @exercise_all_questions = [] - ex_question_random = exercise.question_random - question_answered = 0 - exercise_questions.each_with_index do |q, index| - if ex_question_random && exercise_user_status != Exercise::DEADLINE - ques_number = index + 1 - else - ques_number = q.question_number - end - ques_status = 0 - if q.question_type != Exercise::PRACTICAL - ques_vote = q.exercise_answers.select {|answer| answer.user_id == user_id} - - if ques_vote.present? - #其他题目,需回答的有内容,才会为已答,否则如内容为空,视为未答 - vote_answer_id = ques_vote.pluck(:exercise_choice_id).reject(&:blank?) - vote_text_count = ques_vote.pluck(:answer_text).reject(&:blank?).size - if q.question_type <= Exercise::JUDGMENT #选择题和判断题的时候,需要有选项,才算回答 - if vote_answer_id.size > 0 - ques_status = 1 - question_answered += 1 - end - else - if vote_text_count > 0 #主观题,必选有内容,才算回答 - ques_status = 1 - question_answered += 1 - end - end - end - else - if Myshixun.exists?(user_id: user_id, shixun_id: q.shixun_id) - ques_status = 1 - question_answered += 1 - end - end - question_status = { - :ques_id => q.id, - :ques_number => ques_number, #仅问题的显示位置变化,但是问题的question_number 不会变化,与之相关的choice/standard_answer/answer不会变化 - :ques_status => ques_status, - } - question_options = { - :question => q, - :ques_number => ques_number, - } - @question_status = @question_status.push(question_status).sort_by {|k| k[:ques_number]} - @exercise_all_questions = @exercise_all_questions.push(question_options).sort_by {|k| k[:ques_number]} - end - end - - #下一步也有check_on_users再进行判断 - def only_student_in - if @user_course_identity < Course::STUDENT - normal_status(-1, "老师身份不允许进入") - end - end - - #判断实训是否已选择 - def commit_shixun_present - question_shixun_ids = @exercise.exercise_questions.pluck(:shixun_id).reject(&:blank?) - shixun_id = params[:shixun_id] - @shixun = Shixun.find_by(id: shixun_id) - if shixun_id.present? && question_shixun_ids.include?(shixun_id) - normal_status(-1, "该实训已选择!") - elsif @shixun.blank? - normal_status(-1, "该实训不存在!") - end - end - - end @exercise_questions_count = @exercise_questions.size @page = params[:page] || 1 From e581771ec14286db7fbf3469cf761e27feafad4a Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sat, 11 Jan 2020 17:33:04 +0800 Subject: [PATCH 013/204] =?UTF-8?q?=E8=AF=95=E5=8D=B7=E7=9A=84=E9=AA=8C?= =?UTF-8?q?=E8=AF=81=E4=BF=A1=E6=81=AF?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/models/message_detail.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/models/message_detail.rb b/app/models/message_detail.rb index 9f5269bc5..d589ada3e 100644 --- a/app/models/message_detail.rb +++ b/app/models/message_detail.rb @@ -1,5 +1,5 @@ class MessageDetail < ApplicationRecord belongs_to :message, :touch => true - validates :content, length: { maximum: 5000, too_long: "内容不能超过5000个字符" } + validates :content, length: { maximum: 10000, too_long: "内容不能超过10000个字符" } end From 7ecac799d550d10bf5073187efad636e821a4006 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sat, 11 Jan 2020 17:50:47 +0800 Subject: [PATCH 014/204] =?UTF-8?q?=E7=BF=BB=E8=BD=AC=E8=AF=BE=E5=A0=82?= =?UTF-8?q?=EF=BC=9A=E5=85=AC=E5=BC=80=E8=AF=BE=EF=BC=8C=E5=AF=B9=E4=BA=8E?= =?UTF-8?q?=E9=9D=9E=E8=AF=BE=E5=A0=82=E6=88=90=E5=91=98=E4=B8=8D=E5=85=81?= =?UTF-8?q?=E8=AE=B8=E6=9F=A5=E7=9C=8B=E6=95=99=E5=B8=88=E5=88=97=E8=A1=A8?= =?UTF-8?q?=E3=80=81=E5=AD=A6=E7=94=9F=E5=88=97=E8=A1=A8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/courses_controller.rb | 3 +++ 1 file changed, 3 insertions(+) diff --git a/app/controllers/courses_controller.rb b/app/controllers/courses_controller.rb index 753a3d942..0a6e95470 100644 --- a/app/controllers/courses_controller.rb +++ b/app/controllers/courses_controller.rb @@ -394,6 +394,7 @@ class CoursesController < ApplicationController # 教师列表以及教师搜索 def teachers + tip_exception(403, "无权限访问") if @course.excellent && @user_course_identity > Course::ASSISTANT_PROFESSOR @search_str = params[:search].present? ? params[:search].strip : "" if @course.try(:id) != 1309 || current_user.admin_or_business? || current_user.try(:id) == 15582 @@ -850,6 +851,8 @@ class CoursesController < ApplicationController # 学生列表(包括各个子分班的学生列表)及搜索 def students + tip_exception(403, "无权限访问") if @course.excellent && @user_course_identity > Course::ASSISTANT_PROFESSOR + search = params[:search].present? ? params[:search].strip : nil order = params[:order].present? ? params[:order].to_i : 1 sort = params[:sort].present? ? params[:sort] : "asc" From be4a2102fcf720e62c83d228c03b4c916bbc9a25 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=A8=E6=A0=91=E6=98=8E?= <775174143@qq.com> Date: Sat, 11 Jan 2020 19:19:23 +0800 Subject: [PATCH 015/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/react/src/AppConfig.js | 2 +- .../tasks/GraduationTasksappraiseMainEditor.js | 18 ++++++++++++++---- .../Challenges/Challengesjupyter.js | 14 ++++++++------ 3 files changed, 23 insertions(+), 11 deletions(-) diff --git a/public/react/src/AppConfig.js b/public/react/src/AppConfig.js index 12e0043d5..02d554806 100644 --- a/public/react/src/AppConfig.js +++ b/public/react/src/AppConfig.js @@ -42,7 +42,7 @@ if (isDev) { // 老师 //debugType="teacher"; // 学生 -//debugType="student"; +debugType="student"; function railsgettimes(proxy) { diff --git a/public/react/src/modules/courses/graduation/tasks/GraduationTasksappraiseMainEditor.js b/public/react/src/modules/courses/graduation/tasks/GraduationTasksappraiseMainEditor.js index ec6979c19..376a45eb8 100644 --- a/public/react/src/modules/courses/graduation/tasks/GraduationTasksappraiseMainEditor.js +++ b/public/react/src/modules/courses/graduation/tasks/GraduationTasksappraiseMainEditor.js @@ -20,7 +20,8 @@ class GraduationTasksappraiseMainEditor extends Component{ score: undefined, same_score: false, errorMessage: '', - numberErrorMessage: '' + numberErrorMessage: '', + errorMessagetype:false } } onSubmit = () => { @@ -37,7 +38,10 @@ class GraduationTasksappraiseMainEditor extends Component{ return; } if (!score && this.props.isAdmin()===false) { - this.setState( {errorMessage : '分数不能同时为空' }) + this.setState( { + errorMessage : '分数不能同时为空', + errorMessagetype:true + }) // this.props.showNotification('请先输入评阅说明') return; } @@ -142,6 +146,12 @@ class GraduationTasksappraiseMainEditor extends Component{ }); } onScoreChange = (val) => { + if(val){ + this.setState( { + errorMessage: '', + errorMessagetype:false + }) + } if (val > 100 ) { this.props.showNotification('不能大于100') this.setState({ score: 100 }) @@ -163,7 +173,7 @@ class GraduationTasksappraiseMainEditor extends Component{ this.setState({ same_score: e.target.checked }) //!this.state.same_score } render(){ - let { total_count, comments, pageCount, fileList, score, same_score, errorMessage, numberErrorMessage } = this.state + let { total_count, comments, errorMessagetype, fileList, score, same_score, errorMessage, numberErrorMessage } = this.state const { current_user, memo, showSameScore, placeholder } = this.props const isAdmin = this.props.isAdmin() const commentUploadProp = { @@ -215,7 +225,7 @@ class GraduationTasksappraiseMainEditor extends Component{ `} {this.props.title && {this.props.title}} + watch={false} height={160} className={errorMessage&&errorMessagetype!=true ? 'editorInputError' : ''} imageExpand={true}> { showSameScore == true &&
整组同评 (选中,则本次评阅对象指小组全部成员,否则仅评阅此成员1人 ) diff --git a/public/react/src/modules/tpm/shixunchild/Challenges/Challengesjupyter.js b/public/react/src/modules/tpm/shixunchild/Challenges/Challengesjupyter.js index 61782d69f..9e50e44d5 100644 --- a/public/react/src/modules/tpm/shixunchild/Challenges/Challengesjupyter.js +++ b/public/react/src/modules/tpm/shixunchild/Challenges/Challengesjupyter.js @@ -87,7 +87,7 @@ class Challengesjupyter extends Component { // // } this.setState({ - opentitletype:true, + opentitletype:false, isopentitletype:"greater", boxoffsetHeigh:boxoffsetHeigh }) @@ -646,11 +646,13 @@ class Challengesjupyter extends Component { } {/*this.state.enlarge===false?"":*/} - {this.state.isopentitletype==="Less"?"":this.state.opentitletype===true?this.opentitle()} className={"pointer Breadcrumbfont color-grey-9 "}> - 阅读全文 - :this.opentitle()} className={"pointer Breadcrumbfont color-grey-9 "}> - 收起全文 - } + {/*{this.state.isopentitletype==="Less"?"":this.state.opentitletype===true?this.opentitle()} className={"pointer Breadcrumbfont color-grey-9 "}>*/} + {/* 阅读全文 */} + {/*:this.opentitle()} className={"pointer Breadcrumbfont color-grey-9 "}>*/} + {/* 收起全文 */} + {/*}*/} + +

From c9bc9fbe1e5299b8ae2625b49e2a7efa283931b4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=A8=E6=A0=91=E6=98=8E?= <775174143@qq.com> Date: Sat, 11 Jan 2020 19:19:45 +0800 Subject: [PATCH 016/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../graduation/tasks/GraduationTasksappraiseMainEditor.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/public/react/src/modules/courses/graduation/tasks/GraduationTasksappraiseMainEditor.js b/public/react/src/modules/courses/graduation/tasks/GraduationTasksappraiseMainEditor.js index 376a45eb8..1415414e4 100644 --- a/public/react/src/modules/courses/graduation/tasks/GraduationTasksappraiseMainEditor.js +++ b/public/react/src/modules/courses/graduation/tasks/GraduationTasksappraiseMainEditor.js @@ -39,7 +39,7 @@ class GraduationTasksappraiseMainEditor extends Component{ } if (!score && this.props.isAdmin()===false) { this.setState( { - errorMessage : '分数不能同时为空', + errorMessage : '分数不能为空', errorMessagetype:true }) // this.props.showNotification('请先输入评阅说明') From 2ec0ffc1dbd95d6f9678414276d264be6ab93009 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sat, 11 Jan 2020 19:34:40 +0800 Subject: [PATCH 017/204] =?UTF-8?q?=E5=B8=96=E5=AD=90=E6=8A=9B=E5=BC=82?= =?UTF-8?q?=E5=B8=B8?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/messages_controller.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/controllers/messages_controller.rb b/app/controllers/messages_controller.rb index 2b9d9d69f..0e28ccb4f 100644 --- a/app/controllers/messages_controller.rb +++ b/app/controllers/messages_controller.rb @@ -62,8 +62,8 @@ class MessagesController < ApplicationController end def reply - return normal_status(2, "回复内容不能为空") if params[:content].blank? - return normal_status(2, "回复内容不能超过2000字符") if params[:content].length > 2000 + return normal_status(-1, "回复内容不能为空") if params[:content].blank? + return normal_status(-1, "回复内容不能超过2000字符") if params[:content].length > 2000 @reply = Message.create!(board: @message.board, root_id: @message.root_id || @message.id, author: current_user, parent: @message, message_detail_attributes: { From 0b76c5d64892577e421f36f300369c04cecc51e4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=A8=E6=A0=91=E6=98=8E?= <775174143@qq.com> Date: Sat, 11 Jan 2020 19:34:49 +0800 Subject: [PATCH 018/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/react/src/modules/forums/MemoDetail.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/public/react/src/modules/forums/MemoDetail.js b/public/react/src/modules/forums/MemoDetail.js index 9f3885906..792b24aa9 100644 --- a/public/react/src/modules/forums/MemoDetail.js +++ b/public/react/src/modules/forums/MemoDetail.js @@ -845,7 +845,7 @@ class MemoDetail extends Component {
:
-
写评论1
+
写评论
}
From 079b5bb967bcf8a6e5795983a1554a30ebb8a07c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=A8=E6=A0=91=E6=98=8E?= <775174143@qq.com> Date: Sat, 11 Jan 2020 19:39:14 +0800 Subject: [PATCH 019/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/react/src/modules/tpm/NewHeader.js | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/public/react/src/modules/tpm/NewHeader.js b/public/react/src/modules/tpm/NewHeader.js index 572389b8a..5ca8e986b 100644 --- a/public/react/src/modules/tpm/NewHeader.js +++ b/public/react/src/modules/tpm/NewHeader.js @@ -1047,17 +1047,17 @@ submittojoinclass=(value)=>{ ` } -
  • - -
    -
    - 题库 -
    -
    -
    -
  • + {/*
  • */} + {/* */} + {/*
    */} + {/*
    */} + {/* 题库*/} + {/*
    */} + {/*
    */} + {/*
    */} + {/*
  • */}
  • Date: Sat, 11 Jan 2020 20:18:52 +0800 Subject: [PATCH 020/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/react/src/AppConfig.js | 2 +- public/react/src/context/TPIContextProvider.js | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/public/react/src/AppConfig.js b/public/react/src/AppConfig.js index 02d554806..12e0043d5 100644 --- a/public/react/src/AppConfig.js +++ b/public/react/src/AppConfig.js @@ -42,7 +42,7 @@ if (isDev) { // 老师 //debugType="teacher"; // 学生 -debugType="student"; +//debugType="student"; function railsgettimes(proxy) { diff --git a/public/react/src/context/TPIContextProvider.js b/public/react/src/context/TPIContextProvider.js index ed7eb2210..bb1e0bef4 100644 --- a/public/react/src/context/TPIContextProvider.js +++ b/public/react/src/context/TPIContextProvider.js @@ -32,7 +32,7 @@ import _ from 'lodash' import TPIContext from './TPIContext' import { EDU_ADMIN, EDU_SHIXUN_MANAGER, EDU_SHIXUN_MEMBER, EDU_CERTIFICATION_TEACHER - , EDU_GAME_MANAGER, EDU_TEACHER, EDU_NORMAL, EDU_BUSINESS, CNotificationHOC } from 'educoder' + , EDU_GAME_MANAGER, EDU_TEACHER, EDU_NORMAL, EDU_BUSINESS, CNotificationHOC ,getRandomNumber} from 'educoder' import { MuiThemeProvider, createMuiTheme, withStyles } from 'material-ui/styles'; import MUIDialogStyleUtil from '../modules/page/component/MUIDialogStyleUtil' @@ -176,7 +176,7 @@ class TPIContextProvider extends Component { testPath = 'http://test-newweb.educoder.net' } // var url = `${testPath}/api/v1/games/${ game.identifier }/cost_time` - var url = `${testPath}/api/tasks/${ game.identifier }/cost_time` + var url = `${testPath}/api/tasks/${ game.identifier }/cost_time${getRandomNumber()}` window.$.ajax({ type: 'get', url: url, From 06bae0facf6ef87cabb1232deccd26c8d545b730 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Sat, 11 Jan 2020 20:31:16 +0800 Subject: [PATCH 021/204] =?UTF-8?q?=E6=97=B6=E9=97=B4=E8=AF=BE=E7=A8=8B?= =?UTF-8?q?=E7=BB=9F=E8=AE=A1?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/subjects_controller.rb | 1 + app/views/subjects/statistics_info.json.jbuilder | 6 ++++++ 2 files changed, 7 insertions(+) create mode 100644 app/views/subjects/statistics_info.json.jbuilder diff --git a/app/controllers/subjects_controller.rb b/app/controllers/subjects_controller.rb index d58c4a9c3..47863a3a0 100644 --- a/app/controllers/subjects_controller.rb +++ b/app/controllers/subjects_controller.rb @@ -13,6 +13,7 @@ class SubjectsController < ApplicationController include ApplicationHelper include SubjectsHelper include GitCommon + include CustomSortable def index @tech_system = current_laboratory.subject_repertoires diff --git a/app/views/subjects/statistics_info.json.jbuilder b/app/views/subjects/statistics_info.json.jbuilder new file mode 100644 index 000000000..b31e41b31 --- /dev/null +++ b/app/views/subjects/statistics_info.json.jbuilder @@ -0,0 +1,6 @@ +json.status 0 +json.message "success" +json.data do + json.subject_info @subject.subject_record + json.other_info @data +end \ No newline at end of file From 72cea0893900ceceddc6703c1c2dfbe2eb61bddf Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=A8=E6=A0=91=E6=98=8E?= <775174143@qq.com> Date: Sat, 11 Jan 2020 20:33:44 +0800 Subject: [PATCH 022/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../react/src/modules/courses/coursesDetail/CoursesLeftNav.js | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/public/react/src/modules/courses/coursesDetail/CoursesLeftNav.js b/public/react/src/modules/courses/coursesDetail/CoursesLeftNav.js index c37b45c84..ba8fe27b0 100644 --- a/public/react/src/modules/courses/coursesDetail/CoursesLeftNav.js +++ b/public/react/src/modules/courses/coursesDetail/CoursesLeftNav.js @@ -549,6 +549,10 @@ class Coursesleftnav extends Component{ window.location.href=`/courses/${coursesId}/boards/${result.data.category_id}`; } + if(positiontype!="course_groups"){ + this.updasaveNavmoda() + } + if(positiontype==="course_groups"){ window.location.href=`/courses/${coursesId}/course_groups/${result.data.group_id}`; } From 6f610eebd26e9c93ffef348d9e6ea864ccbbe95d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=A8=E6=A0=91=E6=98=8E?= <775174143@qq.com> Date: Sat, 11 Jan 2020 20:50:34 +0800 Subject: [PATCH 023/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../modules/page/layers/TaskResultLayer.js | 55 +++++++++++-------- 1 file changed, 32 insertions(+), 23 deletions(-) diff --git a/public/react/src/modules/page/layers/TaskResultLayer.js b/public/react/src/modules/page/layers/TaskResultLayer.js index 9e096b7b3..f4ccea8f7 100644 --- a/public/react/src/modules/page/layers/TaskResultLayer.js +++ b/public/react/src/modules/page/layers/TaskResultLayer.js @@ -14,6 +14,7 @@ import passpartImg from '../../../images/tpi/passpart.png' import empiricgreenImg from '../../../images/tpi/empiricgreen.png' import { trigger } from 'educoder'; +import SecondTab from "../../paths/SchoolStatistics/SecondTab"; class TaskResultLayer extends Component { @@ -29,7 +30,7 @@ class TaskResultLayer extends Component { } componentWillReceiveProps(newProps, newContext) { - if (newProps.currentGamePassed && (!this.props.currentGamePassed + if (newProps.currentGamePassed && (!this.props.currentGamePassed || (newProps.currentGamePassed !== this.props.currentGamePassed ))) { // this.fakeRanking = this._fakeRanking() const $ = window.$; @@ -51,10 +52,10 @@ class TaskResultLayer extends Component { } } } - + onStarChange(challenge, index, value) { this.props.onStarChange(challenge, index, value); - + this.setState({ stared: value ? true : false, }) @@ -87,11 +88,11 @@ class TaskResultLayer extends Component { // this.context.router.push('/sample'); if (goNext === true) { if (next_game) { // https://www.trustie.net/issues/18573 - this.goNext = true; + this.goNext = true; } // 隐藏掉效果查看页面 window.$('#picture_display').hide() - } + } this.props.onGamePassed(); this.setState({ stared: false @@ -110,9 +111,9 @@ class TaskResultLayer extends Component { // return; // } // const { showLanguagePictrue } = this.props.challenge; - // if ( prevProps.challenge.showLanguagePictrue != showLanguagePictrue && + // if ( prevProps.challenge.showLanguagePictrue != showLanguagePictrue && // showLanguagePictrue == true ) { - + // } // } initEffectDisplayServerTimer = () => { @@ -128,7 +129,7 @@ class TaskResultLayer extends Component { this.setState({ timeRemain }) }, 1000) }) - + } componentWillUnmount() { this.intervalHandler && clearInterval(this.intervalHandler); @@ -162,7 +163,7 @@ class TaskResultLayer extends Component { // const fakeRanking = this.fakeRanking; return (
    - {currentGamePassed ? + {currentGamePassed ?
    @@ -174,52 +175,60 @@ class TaskResultLayer extends Component {

    {currentPassedGameGainExperience >= 0 ? `+${currentPassedGameGainExperience}` : '+0'} -

    +

    - +
    - { !game.star ? + { !game.star ?

    您的评价决定老师的江湖地位~

    this.onStarChange(this.props.game, this.props.challenge.position, value)} - /> + />
    : ''} -

    +

    {/*下一关*/} this.onFinish(true)}>{ next_game ? '下一关' : '完成'} - { challenge.showLanguagePictrue && + { challenge.showLanguagePictrue && this.onFinish()}> { `查看效果` } {/* ${ moment(this.state.timeRemain * 1000).format('mm:ss') } */} - + } - {/* - - (this.state.timeRemain ? + {/* + + (this.state.timeRemain ? - - + + : {}} style={{ backgroundColor: 'gray'}}> { `查看效果` } - + ) */} - {/* + {/* 注意:效果查看服务只会保留5分钟 效果查看服务已被终止运行,需要重新评测后才能查看 */} From 21c6e3ba7bcc6edb83b1257cc51c291588150c11 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sun, 12 Jan 2020 10:58:24 +0800 Subject: [PATCH 024/204] =?UTF-8?q?=E8=AF=95=E5=8D=B7=E7=9A=84=E6=B5=8B?= =?UTF-8?q?=E8=AF=95=E9=9B=86=E5=BE=97=E5=88=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/helpers/exercises_helper.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/helpers/exercises_helper.rb b/app/helpers/exercises_helper.rb index cf9aec815..4b18ccba2 100644 --- a/app/helpers/exercises_helper.rb +++ b/app/helpers/exercises_helper.rb @@ -530,7 +530,7 @@ module ExercisesHelper exercise_cha_score = 0.0 answer_status = 0 # if game.status == 2 && game.final_score >= 0 - if game.final_score > 0 && game.end_time && game.end_time < exercise_end_time + if game.final_score > 0 && (game.end_time.nil? && game.end_time < exercise_end_time) exercise_cha_score = game.real_score(exercise_cha.question_score) # exercise_cha_score = exercise_cha.question_score #每一关卡的得分 answer_status = 1 From 5a6c58a0f61aad60dcaf0434e22b50f1bbc6c7cc Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sun, 12 Jan 2020 10:59:10 +0800 Subject: [PATCH 025/204] =?UTF-8?q?=E8=AF=95=E5=8D=B7=E6=8C=89=E6=B5=8B?= =?UTF-8?q?=E8=AF=95=E9=9B=86=E7=BB=99=E5=88=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/helpers/exercises_helper.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/helpers/exercises_helper.rb b/app/helpers/exercises_helper.rb index 4b18ccba2..eaeb458a3 100644 --- a/app/helpers/exercises_helper.rb +++ b/app/helpers/exercises_helper.rb @@ -530,7 +530,7 @@ module ExercisesHelper exercise_cha_score = 0.0 answer_status = 0 # if game.status == 2 && game.final_score >= 0 - if game.final_score > 0 && (game.end_time.nil? && game.end_time < exercise_end_time) + if game.final_score > 0 && (game.end_time.nil? || game.end_time < exercise_end_time) exercise_cha_score = game.real_score(exercise_cha.question_score) # exercise_cha_score = exercise_cha.question_score #每一关卡的得分 answer_status = 1 From ee3444394572d84ad834a67b2a1f6eb1fbc92d81 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sun, 12 Jan 2020 11:14:37 +0800 Subject: [PATCH 026/204] =?UTF-8?q?=E8=AF=95=E5=8D=B7=E6=95=B0=E6=8D=AE?= =?UTF-8?q?=E8=BF=81=E7=A7=BB?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ...00112030419_migrate_3176_exercise_score.rb | 50 +++++++++++++++++++ 1 file changed, 50 insertions(+) create mode 100644 db/migrate/20200112030419_migrate_3176_exercise_score.rb diff --git a/db/migrate/20200112030419_migrate_3176_exercise_score.rb b/db/migrate/20200112030419_migrate_3176_exercise_score.rb new file mode 100644 index 000000000..449a87578 --- /dev/null +++ b/db/migrate/20200112030419_migrate_3176_exercise_score.rb @@ -0,0 +1,50 @@ +class Migrate3176ExerciseScore < ActiveRecord::Migration[5.2] + + def calculate_student_score(exercise,user) + score5 = 0.0 #实训题 + exercise_end_time = exercise.end_time + exercise_questions = exercise.exercise_questions.includes(:exercise_standard_answers,:exercise_shixun_challenges) + exercise_questions.each do |q| + if q.question_type == 5 + q.exercise_shixun_challenges.each do |exercise_cha| + game = Game.user_games(user.id,exercise_cha.challenge_id)&.first #当前用户的关卡 + if game.present? + exercise_cha_score = 0.0 + answer_status = 0 + # if game.status == 2 && game.final_score >= 0 + if game.final_score > 0 && (game.end_time.nil? || game.end_time < exercise_end_time) + exercise_cha_score = game.real_score(exercise_cha.question_score) + # exercise_cha_score = exercise_cha.question_score #每一关卡的得分 + answer_status = 1 + end + ex_shixun_answer_content = exercise_cha.exercise_shixun_answers.find_by(user_id:user.id,exercise_question_id:q.id) + if ex_shixun_answer_content.present? && !ex_shixun_answer_content.score >0 #把关卡的答案存入试卷的实训里 + ex_shixun_answer_content.update_attributes!(score:exercise_cha_score.round(1),status:answer_status) + end + score5 += exercise_cha_score + else + score5 += 0.0 + end + end + end + end + score5 + end + + def change + exercise = Exercise.find_by(id: 3176) + if exercise + exercise_users = exercise.exercise_users.where("start_at is not null") + exercise_users.each do |exercise_user| + calculate_score = calculate_student_score(exercise, exercise_user.user) + subjective_score = exercise_user.subjective_score + total_score_subjective_score = subjective_score < 0.0 ? 0.0 : subjective_score + total_score = calculate_score + total_score_subjective_score + if exercise_user.end_at.present? + exercise_user.update_attributes!(score:total_score,objective_score:calculate_score) + end + puts exercise_user.id + end + end + end +end From b4d6c003821d6ba05a80194ce67ce1ebe124db83 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sun, 12 Jan 2020 11:21:18 +0800 Subject: [PATCH 027/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- db/migrate/20200111024736_add_index_for_subject_records.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/db/migrate/20200111024736_add_index_for_subject_records.rb b/db/migrate/20200111024736_add_index_for_subject_records.rb index c27c9b9ae..e196c407f 100644 --- a/db/migrate/20200111024736_add_index_for_subject_records.rb +++ b/db/migrate/20200111024736_add_index_for_subject_records.rb @@ -1,6 +1,6 @@ class AddIndexForSubjectRecords < ActiveRecord::Migration[5.2] def change - remove_index :subject_records, :subject_id + # remove_index :subject_records, :subject_id add_index :subject_records, :subject_id, unique: true end end From f4a95fa206514fb5c950c39db69ac3dbdaaf7df9 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sun, 12 Jan 2020 11:50:16 +0800 Subject: [PATCH 028/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- db/migrate/20200112030419_migrate_3176_exercise_score.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/db/migrate/20200112030419_migrate_3176_exercise_score.rb b/db/migrate/20200112030419_migrate_3176_exercise_score.rb index 449a87578..e96931f79 100644 --- a/db/migrate/20200112030419_migrate_3176_exercise_score.rb +++ b/db/migrate/20200112030419_migrate_3176_exercise_score.rb @@ -18,7 +18,7 @@ class Migrate3176ExerciseScore < ActiveRecord::Migration[5.2] answer_status = 1 end ex_shixun_answer_content = exercise_cha.exercise_shixun_answers.find_by(user_id:user.id,exercise_question_id:q.id) - if ex_shixun_answer_content.present? && !ex_shixun_answer_content.score >0 #把关卡的答案存入试卷的实训里 + if ex_shixun_answer_content.present? && !(ex_shixun_answer_content.score >0) #把关卡的答案存入试卷的实训里 ex_shixun_answer_content.update_attributes!(score:exercise_cha_score.round(1),status:answer_status) end score5 += exercise_cha_score From ab089c2cc5ef9a943c13e5c88814faf829765bf3 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Sun, 12 Jan 2020 11:53:27 +0800 Subject: [PATCH 029/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ...00112035304_migrate_3517_exercise_score.rb | 49 +++++++++++++++++++ 1 file changed, 49 insertions(+) create mode 100644 db/migrate/20200112035304_migrate_3517_exercise_score.rb diff --git a/db/migrate/20200112035304_migrate_3517_exercise_score.rb b/db/migrate/20200112035304_migrate_3517_exercise_score.rb new file mode 100644 index 000000000..821b2bbd8 --- /dev/null +++ b/db/migrate/20200112035304_migrate_3517_exercise_score.rb @@ -0,0 +1,49 @@ +class Migrate3517ExerciseScore < ActiveRecord::Migration[5.2] + def calculate_student_score(exercise,user) + score5 = 0.0 #实训题 + exercise_end_time = exercise.end_time + exercise_questions = exercise.exercise_questions.includes(:exercise_standard_answers,:exercise_shixun_challenges) + exercise_questions.each do |q| + if q.question_type == 5 + q.exercise_shixun_challenges.each do |exercise_cha| + game = Game.user_games(user.id,exercise_cha.challenge_id)&.first #当前用户的关卡 + if game.present? + exercise_cha_score = 0.0 + answer_status = 0 + # if game.status == 2 && game.final_score >= 0 + if game.final_score > 0 && (game.end_time.nil? || game.end_time < exercise_end_time) + exercise_cha_score = game.real_score(exercise_cha.question_score) + # exercise_cha_score = exercise_cha.question_score #每一关卡的得分 + answer_status = 1 + end + ex_shixun_answer_content = exercise_cha.exercise_shixun_answers.find_by(user_id:user.id,exercise_question_id:q.id) + if ex_shixun_answer_content.present? && !(ex_shixun_answer_content.score >0) #把关卡的答案存入试卷的实训里 + ex_shixun_answer_content.update_attributes!(score:exercise_cha_score.round(1),status:answer_status) + end + score5 += exercise_cha_score + else + score5 += 0.0 + end + end + end + end + score5 + end + + def change + exercise = Exercise.find_by(id: 3517) + if exercise + exercise_users = exercise.exercise_users.where("start_at is not null") + exercise_users.each do |exercise_user| + calculate_score = calculate_student_score(exercise, exercise_user.user) + subjective_score = exercise_user.subjective_score + total_score_subjective_score = subjective_score < 0.0 ? 0.0 : subjective_score + total_score = calculate_score + total_score_subjective_score + if exercise_user.end_at.present? + exercise_user.update_attributes!(score:total_score,objective_score:calculate_score) + end + puts exercise_user.id + end + end + end +end From 185a64dce29145a5eba64b78c86bc19ca52ef86f Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Mon, 13 Jan 2020 10:02:45 +0800 Subject: [PATCH 030/204] =?UTF-8?q?=E4=BA=A4=E6=B5=81=E9=97=AE=E7=AD=94?= =?UTF-8?q?=EF=BC=9A=E5=8F=91=E9=80=81=E8=AF=84=E8=AE=BA=EF=BC=8C=E9=9C=80?= =?UTF-8?q?=E8=A6=81=E5=9C=A8=E7=8E=B0=E6=9C=89=E6=B5=81=E7=A8=8B=E7=9A=84?= =?UTF-8?q?=E5=9F=BA=E7=A1=80=E4=B8=8A=E5=A2=9E=E5=8A=A0=E2=80=9C=E5=AE=8C?= =?UTF-8?q?=E5=96=84=E8=B5=84=E6=96=99=E2=80=9D=E7=9A=84check=E5=92=8C?= =?UTF-8?q?=E5=BC=95=E5=AF=BC?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/memos_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/memos_controller.rb b/app/controllers/memos_controller.rb index b80bfed32..c0ea8d601 100644 --- a/app/controllers/memos_controller.rb +++ b/app/controllers/memos_controller.rb @@ -1,6 +1,6 @@ class MemosController < ApplicationController before_action :require_login, except: [:show, :index] - before_action :check_account, only: [:new, :create] + before_action :check_account, only: [:new, :create, :reply] before_action :set_memo, only: [:show, :edit, :update, :destroy, :sticky_or_cancel, :hidden, :more_reply] before_action :validate_memo_params, only: [:create, :update] before_action :owner_or_admin, only: [:edit, :update, :destroy] From b6cdd2ed1aaf3311d38da10393f21589d4ddd5cc Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Mon, 13 Jan 2020 10:08:25 +0800 Subject: [PATCH 031/204] =?UTF-8?q?=E6=B5=8B=E8=AF=95=E7=89=88=E8=B7=B3?= =?UTF-8?q?=E8=BF=87=E9=AA=8C=E8=AF=81?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/application_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb index fdb41c114..e0639de3f 100644 --- a/app/controllers/application_controller.rb +++ b/app/controllers/application_controller.rb @@ -23,7 +23,7 @@ class ApplicationController < ActionController::Base # 所有请求必须合法签名 def check_sign - if !Rails.env.development? + if !Rails.env.development? && EduSetting.get("host_name") != "https://test-newweb.educoder.net" Rails.logger.info("66666 #{params}") # suffix = request.url.split(".").last.split("?").first # suffix_arr = ["xls", "xlsx", "pdf", "zip"] # excel文件先注释 From 457c629b9ea59034bc663789b5bbfbc245deb6f8 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Mon, 13 Jan 2020 10:30:03 +0800 Subject: [PATCH 032/204] =?UTF-8?q?=E8=B0=83=E8=AF=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/application_controller.rb | 2 ++ 1 file changed, 2 insertions(+) diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb index e0639de3f..ed839eccf 100644 --- a/app/controllers/application_controller.rb +++ b/app/controllers/application_controller.rb @@ -23,6 +23,8 @@ class ApplicationController < ActionController::Base # 所有请求必须合法签名 def check_sign + Rails.logger.info("#####################request: #{request.headers}") + Rails.logger.info("#####################type: #{request.type}") if !Rails.env.development? && EduSetting.get("host_name") != "https://test-newweb.educoder.net" Rails.logger.info("66666 #{params}") # suffix = request.url.split(".").last.split("?").first From ec8e92c5f616bdb7ae8f5e8bd0a8349e28f5b8ff Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Mon, 13 Jan 2020 10:31:09 +0800 Subject: [PATCH 033/204] =?UTF-8?q?=E8=B0=83=E8=AF=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/application_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb index ed839eccf..9faa14593 100644 --- a/app/controllers/application_controller.rb +++ b/app/controllers/application_controller.rb @@ -24,7 +24,7 @@ class ApplicationController < ActionController::Base # 所有请求必须合法签名 def check_sign Rails.logger.info("#####################request: #{request.headers}") - Rails.logger.info("#####################type: #{request.type}") + #Rails.logger.info("#####################type: #{request.type}") if !Rails.env.development? && EduSetting.get("host_name") != "https://test-newweb.educoder.net" Rails.logger.info("66666 #{params}") # suffix = request.url.split(".").last.split("?").first From b2ad28591b418980713992e0c5480dacd982e69d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=A8=E6=A0=91=E6=98=8E?= <775174143@qq.com> Date: Mon, 13 Jan 2020 10:40:09 +0800 Subject: [PATCH 034/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../modules/courses/graduation/tasks/GraduationTaskDetail.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/public/react/src/modules/courses/graduation/tasks/GraduationTaskDetail.js b/public/react/src/modules/courses/graduation/tasks/GraduationTaskDetail.js index 44bcf5777..3330f9389 100644 --- a/public/react/src/modules/courses/graduation/tasks/GraduationTaskDetail.js +++ b/public/react/src/modules/courses/graduation/tasks/GraduationTaskDetail.js @@ -523,7 +523,7 @@ class GraduationTaskDetail extends Component{ 导出

  • :""} {questionslist.work_status===undefined||questionslist.work_status===null||questionslist.work_status.length===0?"":questionslist.work_status.map((item,key)=>{ From b4f6f5be639b4adf08c38d4e3b60cd67f90f31ec Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Mon, 13 Jan 2020 10:59:20 +0800 Subject: [PATCH 035/204] =?UTF-8?q?=E6=AF=95=E8=AE=BE=E4=BD=9C=E5=93=81?= =?UTF-8?q?=E9=99=84=E4=BB=B6=E5=AF=BC=E5=87=BA?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/helpers/export_helper.rb | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/app/helpers/export_helper.rb b/app/helpers/export_helper.rb index 8b61ca2b6..a5268a789 100644 --- a/app/helpers/export_helper.rb +++ b/app/helpers/export_helper.rb @@ -851,7 +851,8 @@ module ExportHelper def make_zip_name(work, file_name="") Rails.logger.info("######################file_name: #{file_name}") # name = file_name === "" ? "" : (file_name[0, file_name.rindex('.')]+"_") - "#{work&.homework_common.course&.user_group_name(work.user_id)}_#{work&.user&.student_id}_#{work&.user&.real_name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}" + course = work&.homework_common.course || work&.graduation_task.course + "#{course&.user_group_name(work.user_id)}_#{work&.user&.student_id}_#{work&.user&.real_name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}" end def zipping(zip_name_refer, files_paths, output_path, is_attachment=false, not_exist_file=[]) From 39fa3c8096d94a6493557d02a56c137fb3317c40 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Mon, 13 Jan 2020 11:04:03 +0800 Subject: [PATCH 036/204] =?UTF-8?q?=E6=AF=95=E8=AE=BE=E4=BD=9C=E5=93=81?= =?UTF-8?q?=E9=99=84=E4=BB=B6=E5=AF=BC=E5=87=BA?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/helpers/export_helper.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/helpers/export_helper.rb b/app/helpers/export_helper.rb index a5268a789..b7a4d4def 100644 --- a/app/helpers/export_helper.rb +++ b/app/helpers/export_helper.rb @@ -851,7 +851,7 @@ module ExportHelper def make_zip_name(work, file_name="") Rails.logger.info("######################file_name: #{file_name}") # name = file_name === "" ? "" : (file_name[0, file_name.rindex('.')]+"_") - course = work&.homework_common.course || work&.graduation_task.course + course = work&.homework_common&.course || work&.graduation_task&.course "#{course&.user_group_name(work.user_id)}_#{work&.user&.student_id}_#{work&.user&.real_name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}" end From 1c7db6bef9f2b87ca5f321d98d0af153eb9351a0 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Mon, 13 Jan 2020 11:06:56 +0800 Subject: [PATCH 037/204] =?UTF-8?q?=E6=AF=95=E8=AE=BE=E4=BD=9C=E5=93=81?= =?UTF-8?q?=E9=99=84=E4=BB=B6=E5=AF=BC=E5=87=BA?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/helpers/export_helper.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/helpers/export_helper.rb b/app/helpers/export_helper.rb index b7a4d4def..64ad114bd 100644 --- a/app/helpers/export_helper.rb +++ b/app/helpers/export_helper.rb @@ -851,7 +851,7 @@ module ExportHelper def make_zip_name(work, file_name="") Rails.logger.info("######################file_name: #{file_name}") # name = file_name === "" ? "" : (file_name[0, file_name.rindex('.')]+"_") - course = work&.homework_common&.course || work&.graduation_task&.course + course = work.is_a?(StudentWork) ? work&.homework_common&.course : work&.graduation_task&.course "#{course&.user_group_name(work.user_id)}_#{work&.user&.student_id}_#{work&.user&.real_name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}" end From 573cf053445c8756cdc8107648693463c541806c Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Mon, 13 Jan 2020 11:14:30 +0800 Subject: [PATCH 038/204] =?UTF-8?q?=E9=99=84=E4=BB=B6=E7=9A=84=E5=AF=BC?= =?UTF-8?q?=E5=87=BA?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/helpers/export_helper.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/helpers/export_helper.rb b/app/helpers/export_helper.rb index a5268a789..64ad114bd 100644 --- a/app/helpers/export_helper.rb +++ b/app/helpers/export_helper.rb @@ -851,7 +851,7 @@ module ExportHelper def make_zip_name(work, file_name="") Rails.logger.info("######################file_name: #{file_name}") # name = file_name === "" ? "" : (file_name[0, file_name.rindex('.')]+"_") - course = work&.homework_common.course || work&.graduation_task.course + course = work.is_a?(StudentWork) ? work&.homework_common&.course : work&.graduation_task&.course "#{course&.user_group_name(work.user_id)}_#{work&.user&.student_id}_#{work&.user&.real_name}_#{Time.now.strftime('%Y%m%d_%H%M%S')}" end From 1ecf433fc5cc084eef5b1babc563ade9bd251d7a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=A8=E6=A0=91=E6=98=8E?= <775174143@qq.com> Date: Mon, 13 Jan 2020 11:48:49 +0800 Subject: [PATCH 039/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/images/educoder/xcx/weixinhome.png | Bin 0 -> 54273 bytes 1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 public/images/educoder/xcx/weixinhome.png diff --git a/public/images/educoder/xcx/weixinhome.png b/public/images/educoder/xcx/weixinhome.png new file mode 100644 index 0000000000000000000000000000000000000000..0ba56d1b6a64d80ecbada157231fabb19fbfb96d GIT binary patch literal 54273 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 E0eq`7f&c&j literal 0 HcmV?d00001 From 1fa2fe4ad3b6ffc0d2adee088eb2e4980f118ae1 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Mon, 13 Jan 2020 14:37:53 +0800 Subject: [PATCH 040/204] =?UTF-8?q?=E8=B0=83=E6=95=B4=E6=9B=B4=E6=96=B0?= =?UTF-8?q?=E7=94=A8=E6=88=B7=E8=BA=AB=E4=BB=BD=E7=9A=84api?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/users/interests_controller.rb | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/app/controllers/users/interests_controller.rb b/app/controllers/users/interests_controller.rb index 93f2345f1..06470f553 100644 --- a/app/controllers/users/interests_controller.rb +++ b/app/controllers/users/interests_controller.rb @@ -9,18 +9,18 @@ class Users::InterestsController < Users::BaseController extension = current_user.user_extension || current_user.build_user_extension return render_error('请选择职业') unless %w(teacher student professional).include?(identity) - interest_ids = Array.wrap(params[:interest_ids]).map(&:to_i) - return render_error('请选择兴趣') if interest_ids.blank? + # interest_ids = Array.wrap(params[:interest_ids]).map(&:to_i) + # return render_error('请选择兴趣') if interest_ids.blank? ActiveRecord::Base.transaction do extension.update_column(:identity, identity) # 兴趣 - UserInterest.bulk_insert(:user_id, :repertoire_id) do |worker| - (Repertoire.pluck(:id) & interest_ids).each do |repertoire_id| - worker.add(user_id: current_user.id, repertoire_id: repertoire_id) - end - end + # UserInterest.bulk_insert(:user_id, :repertoire_id) do |worker| + # (Repertoire.pluck(:id) & interest_ids).each do |repertoire_id| + # worker.add(user_id: current_user.id, repertoire_id: repertoire_id) + # end + # end end render_ok From 2e6222bca279fbfc70dd83d25d6607a18d1b70f2 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Mon, 13 Jan 2020 15:23:36 +0800 Subject: [PATCH 041/204] =?UTF-8?q?=E9=A2=98=E5=BA=93?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/hacks_controller.rb | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/app/controllers/hacks_controller.rb b/app/controllers/hacks_controller.rb index 0e98e771b..6eb454feb 100644 --- a/app/controllers/hacks_controller.rb +++ b/app/controllers/hacks_controller.rb @@ -232,7 +232,11 @@ class HacksController < ApplicationController hacks = Hack.select(select_sql).mine(current_user.id) else # 全部包括已经发布的,和我的未发布的 - hacks = Hack.select(select_sql).published.opening.or(Hack.select(select_sql).unpublish.mine(current_user.id)) + if current_user.admin_or_business? + hacks = Hack.select(select_sql) + else + hacks = Hack.select(select_sql).published.opening.or(Hack.select(select_sql).unpublish.mine(current_user.id)) + end end # 搜索 if params[:search] From 6ebb02775dfbe64f8cc6bd0a1efa952d724b50e5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=A8=E6=A0=91=E6=98=8E?= <775174143@qq.com> Date: Mon, 13 Jan 2020 17:00:45 +0800 Subject: [PATCH 042/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/images/educoder/xcx/Professional.png | Bin 0 -> 23683 bytes public/images/educoder/xcx/Student.png | Bin 0 -> 20682 bytes public/images/educoder/xcx/Teacher.png | Bin 0 -> 36789 bytes 3 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 public/images/educoder/xcx/Professional.png create mode 100644 public/images/educoder/xcx/Student.png create mode 100644 public/images/educoder/xcx/Teacher.png diff --git a/public/images/educoder/xcx/Professional.png b/public/images/educoder/xcx/Professional.png new file mode 100644 index 0000000000000000000000000000000000000000..8273d9e795355254f0383f743cf8a66ea5e65647 GIT binary patch literal 23683 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�i& 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 Date: Mon, 13 Jan 2020 17:07:06 +0800 Subject: [PATCH 043/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/views/weapps/shared/_user.json.jbuilder | 1 + 1 file changed, 1 insertion(+) diff --git a/app/views/weapps/shared/_user.json.jbuilder b/app/views/weapps/shared/_user.json.jbuilder index be67384cc..53212ec15 100644 --- a/app/views/weapps/shared/_user.json.jbuilder +++ b/app/views/weapps/shared/_user.json.jbuilder @@ -7,6 +7,7 @@ json.admin user.admin? json.business user.business? json.is_teacher user.user_extension&.teacher? json.user_identity user.identity +json.identity user.user_extension&.identity json.tidding_count 0 json.user_phone_binded user.phone.present? json.phone user.phone From 0f822648408d4b4aaca4672be3874af05ebc36d2 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Mon, 13 Jan 2020 17:18:23 +0800 Subject: [PATCH 044/204] =?UTF-8?q?=E5=BE=AE=E4=BF=A1=E5=8F=91=E9=80=81?= =?UTF-8?q?=E9=AA=8C=E8=AF=81=E7=A0=81=E5=8A=A0=E5=AF=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../weapps/verification_codes_controller.rb | 22 +++++++++++++------ 1 file changed, 15 insertions(+), 7 deletions(-) diff --git a/app/controllers/weapps/verification_codes_controller.rb b/app/controllers/weapps/verification_codes_controller.rb index 7590c49f7..1876014db 100644 --- a/app/controllers/weapps/verification_codes_controller.rb +++ b/app/controllers/weapps/verification_codes_controller.rb @@ -19,11 +19,10 @@ class Weapps::VerificationCodesController < Weapps::BaseController return render_error('请输入正确的邮箱或手机号') end - code = %W(0 1 2 3 4 5 6 7 8 9) - verification_code = code.sample(6).join send_type = login =~ /^1\d{10}$/ ? 1 : 8 - # 记录验证码 - check_verification_code(verification_code, send_type, login) + + # 发送验证码 + send_code(send_type, login) render_ok end @@ -40,12 +39,21 @@ class Weapps::VerificationCodesController < Weapps::BaseController return render_error('请输入正确的邮箱或手机号') end + send_type = login =~ /^1\d{10}$/ ? 2 : 3 + + # 发送验证码 + send_code(send_type, login) + + render_ok + end + + def send_code send_type, login code = %W(0 1 2 3 4 5 6 7 8 9) verification_code = code.sample(6).join - send_type = login =~ /^1\d{10}$/ ? 2 : 3 # 记录验证码 - check_verification_code(verification_code, send_type, login) + sign = Digest::MD5.hexdigest("#{OPENKEY}#{login}") + tip_exception(501, "请求不合理") if sign != params[:smscode] - render_ok + check_verification_code(verification_code, send_type, login) end end \ No newline at end of file From 870f195f48db12fe139fe96ee4ce6a3f1a597e11 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Mon, 13 Jan 2020 17:41:00 +0800 Subject: [PATCH 045/204] =?UTF-8?q?=E5=88=A0=E9=99=A4=E5=A4=9A=E4=BD=99?= =?UTF-8?q?=E7=9A=84=E6=B3=A8=E9=87=8A?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/application_controller.rb | 2 -- app/services/git_service.rb | 2 +- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb index 9faa14593..e0639de3f 100644 --- a/app/controllers/application_controller.rb +++ b/app/controllers/application_controller.rb @@ -23,8 +23,6 @@ class ApplicationController < ActionController::Base # 所有请求必须合法签名 def check_sign - Rails.logger.info("#####################request: #{request.headers}") - #Rails.logger.info("#####################type: #{request.type}") if !Rails.env.development? && EduSetting.get("host_name") != "https://test-newweb.educoder.net" Rails.logger.info("66666 #{params}") # suffix = request.url.split(".").last.split("?").first diff --git a/app/services/git_service.rb b/app/services/git_service.rb index eedac2595..2bfc7423c 100644 --- a/app/services/git_service.rb +++ b/app/services/git_service.rb @@ -64,7 +64,7 @@ class GitService end def parse_return(body) - logger.info("--uri_exec: .....res is #{body}") + #logger.info("--uri_exec: .....res is #{body}") content = JSON.parse(body) if content["code"] != 0 From 49fb413662b27cb2eb985698e2a88828a0e87e3a Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Mon, 13 Jan 2020 17:42:27 +0800 Subject: [PATCH 046/204] =?UTF-8?q?=E5=B0=8F=E7=A8=8B=E5=BA=8F=E7=9A=84?= =?UTF-8?q?=E6=84=8F=E8=A7=81=E5=8F=8D=E9=A6=88?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/helps_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/helps_controller.rb b/app/controllers/helps_controller.rb index 8d58663f6..12cc8b9b3 100644 --- a/app/controllers/helps_controller.rb +++ b/app/controllers/helps_controller.rb @@ -29,7 +29,7 @@ class HelpsController < ApplicationController content = "

    [#{params[:question_kind]}]

    #{params[:description]}" if params[:attachment_ids] params[:attachment_ids].each do |attachment_id| - content += "![](/api/attachments/#{attachment_id})↵" + content += "![](/api/attachments/#{attachment_id})\n" end end else From 57235bd5198565965586fec50165a72f832f7b37 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Mon, 13 Jan 2020 17:47:21 +0800 Subject: [PATCH 047/204] =?UTF-8?q?=E5=B0=8F=E7=A8=8B=E5=BA=8F=E7=9A=84?= =?UTF-8?q?=E6=84=8F=E8=A7=81=E5=8F=8D=E9=A6=88?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/helps_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/helps_controller.rb b/app/controllers/helps_controller.rb index 12cc8b9b3..145ac1bec 100644 --- a/app/controllers/helps_controller.rb +++ b/app/controllers/helps_controller.rb @@ -26,7 +26,7 @@ class HelpsController < ApplicationController def feedback if params[:url].blank? - content = "

    [#{params[:question_kind]}]

    #{params[:description]}" + content = "

    [#{params[:question_kind]}]

    #{params[:description]}

    " if params[:attachment_ids] params[:attachment_ids].each do |attachment_id| content += "![](/api/attachments/#{attachment_id})\n" From d1ec190180ce69fc41a3fc73d09f2fde32ca5171 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Mon, 13 Jan 2020 18:02:37 +0800 Subject: [PATCH 048/204] =?UTF-8?q?=E5=B0=8F=E7=A8=8B=E5=BA=8F=E7=9A=84?= =?UTF-8?q?=E6=84=8F=E8=A7=81=E5=8F=8D=E9=A6=88?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/helps_controller.rb | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/app/controllers/helps_controller.rb b/app/controllers/helps_controller.rb index 145ac1bec..10a073684 100644 --- a/app/controllers/helps_controller.rb +++ b/app/controllers/helps_controller.rb @@ -26,14 +26,14 @@ class HelpsController < ApplicationController def feedback if params[:url].blank? - content = "

    [#{params[:question_kind]}]

    #{params[:description]}

    " + content = "[#{params[:question_kind]}]
    #{params[:description]}
    " if params[:attachment_ids] params[:attachment_ids].each do |attachment_id| - content += "![](/api/attachments/#{attachment_id})\n" + content += "![](/api/attachments/#{attachment_id})
    " end end else - content = "

    [#{params[:question_kind]}]

    问题页面网址:#{params[:url]}

    #{params[:description]}" + content = "[#{params[:question_kind]}]
    问题页面网址:#{params[:url]}
    #{params[:description]}" end ActiveRecord::Base.transaction do From 1e93f7b6fcfaa276055944b0f08ebe3f83603ad4 Mon Sep 17 00:00:00 2001 From: "sylor_huang@126.com" Date: Mon, 13 Jan 2020 18:18:23 +0800 Subject: [PATCH 049/204] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E5=A1=AB=E7=A9=BA?= =?UTF-8?q?=E9=A2=98=E7=9A=84=E6=A0=87=E5=87=86=E7=AD=94=E6=A1=88?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/helpers/exercises_helper.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/helpers/exercises_helper.rb b/app/helpers/exercises_helper.rb index eaeb458a3..f8fba93f5 100644 --- a/app/helpers/exercises_helper.rb +++ b/app/helpers/exercises_helper.rb @@ -188,7 +188,7 @@ module ExercisesHelper if ex_ordered all_user_answers = effictive_users.pluck(:answer_text) null_stand_choice.each_with_index do |s,index| - s_choice_text = null_stand_text[index] + s_choice_text = null_stand_text[index].to_s.strip.downcase user_count = 0 # user_count = user_count + effictive_users.where("exercise_choice_id = ? and answer_text = ?",s,s_choice_text).pluck(:user_id).uniq.size user_count = user_count + effictive_users.select{|answer| answer.exercise_choice_id == s && answer.answer_text == s_choice_text}.size From b1aa24c5068de92fdfb7458ebbc910c7adce26ac Mon Sep 17 00:00:00 2001 From: "sylor_huang@126.com" Date: Mon, 13 Jan 2020 18:27:53 +0800 Subject: [PATCH 050/204] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E5=A1=AB=E7=A9=BA?= =?UTF-8?q?=E9=A2=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/helpers/exercises_helper.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/helpers/exercises_helper.rb b/app/helpers/exercises_helper.rb index f8fba93f5..513f980d8 100644 --- a/app/helpers/exercises_helper.rb +++ b/app/helpers/exercises_helper.rb @@ -188,7 +188,7 @@ module ExercisesHelper if ex_ordered all_user_answers = effictive_users.pluck(:answer_text) null_stand_choice.each_with_index do |s,index| - s_choice_text = null_stand_text[index].to_s.strip.downcase + s_choice_text = null_stand_text[index].to_s.strip user_count = 0 # user_count = user_count + effictive_users.where("exercise_choice_id = ? and answer_text = ?",s,s_choice_text).pluck(:user_id).uniq.size user_count = user_count + effictive_users.select{|answer| answer.exercise_choice_id == s && answer.answer_text == s_choice_text}.size From 0a21fcdd873e20723ea0eb3b5e4080f301b13ae1 Mon Sep 17 00:00:00 2001 From: tangjiang <465264938@qq.com> Date: Tue, 14 Jan 2020 08:44:23 +0800 Subject: [PATCH 051/204] update static style --- .../modules/paths/statics/DisplayTableData.js | 4 +- .../react/src/modules/paths/statics/index.js | 30 +++++++----- .../src/modules/paths/statics/index.scss | 47 +++++++++++++++++-- .../src/modules/paths/statics/mockData.js | 42 +++++++++++------ 4 files changed, 88 insertions(+), 35 deletions(-) diff --git a/public/react/src/modules/paths/statics/DisplayTableData.js b/public/react/src/modules/paths/statics/DisplayTableData.js index 3d9f1aa82..15f892535 100644 --- a/public/react/src/modules/paths/statics/DisplayTableData.js +++ b/public/react/src/modules/paths/statics/DisplayTableData.js @@ -4,7 +4,7 @@ * @Github: * @Date: 2020-01-10 13:46:30 * @LastEditors : tangjiang - * @LastEditTime : 2020-01-11 14:02:32 + * @LastEditTime : 2020-01-11 17:35:03 */ import 'antd-table-infinity/dist/index.css'; import 'antd-table-infinity/index.css'; @@ -58,7 +58,7 @@ const DisplayTableData = ({ loadingIndicator={loadMoreContent} columns={columns} sumData={sumData} - scroll={{ y: 450 }} + scroll={{ y: 500 }} dataSource={data} // bordered // debug diff --git a/public/react/src/modules/paths/statics/index.js b/public/react/src/modules/paths/statics/index.js index 5076e0a0e..1b13500f0 100644 --- a/public/react/src/modules/paths/statics/index.js +++ b/public/react/src/modules/paths/statics/index.js @@ -4,7 +4,7 @@ * @Github: * @Date: 2020-01-10 09:33:45 * @LastEditors : tangjiang - * @LastEditTime : 2020-01-11 11:18:38 + * @LastEditTime : 2020-01-11 17:06:56 */ import './index.scss'; import React, { useState } from 'react'; @@ -145,26 +145,30 @@ const App = () => {
    - {/* - + + - - Content of Tab Pane 2 + + - - Content of Tab Pane 3 + + - */} - + +
    diff --git a/public/react/src/modules/paths/statics/index.scss b/public/react/src/modules/paths/statics/index.scss index 646aefdcf..945fa2740 100644 --- a/public/react/src/modules/paths/statics/index.scss +++ b/public/react/src/modules/paths/statics/index.scss @@ -9,6 +9,7 @@ .static_section_table{ margin-bottom: 140px; + padding-top: 5px; } .static_section_header{ @@ -71,6 +72,7 @@ line-height: 1.5; text-align: center; color: #909399; + margin-top: 20px; .icon{ margin-left: 5px; font-size: 16px !important; @@ -83,12 +85,47 @@ .ant-table-header{ overflow-x: hidden !important; margin-bottom: 0px !important; - border-bottom: 2px solid #e8e8e8; - background: green; + // border-bottom: 2px solid rgba(241,248,255,1); + // background: green; } - .ant-table-footer .ant-table-content{ - border-top: 1px solid #e8e8e8; - box-sizing: border-box; + // .ant-table-footer .ant-table-content{ + // border-top: 1px solid #e8e8e8; + // box-sizing: border-box; + // } + + .overflow_hidden{ + max-width: 300px; + overflow: hidden; + text-overflow:ellipsis; + white-space: nowrap; + } + table th, + table td{ + line-height: 1; + padding: 15px 0 + } + table th{ + background: rgba(241,248,255,1); + } + + table tr:nth-child(2n) td{ + background: rgba(241,248,255,.4); + } + + // .ant-table-thead>tr>th .ant-table-column-sorters:before{ + // background: rgba(241,248,255,1); + // } + .ant-table-thead>tr>th .ant-table-column-sorters:before { + position: absolute; + content: ""; + top: 0; + left: 0; + right: 0; + bottom: 0; + background: rgba(241,248,255,1); + -webkit-transition: all .3s; + -o-transition: all .3s; + transition: all .3s; } } } diff --git a/public/react/src/modules/paths/statics/mockData.js b/public/react/src/modules/paths/statics/mockData.js index def1e904b..54d34a3ff 100644 --- a/public/react/src/modules/paths/statics/mockData.js +++ b/public/react/src/modules/paths/statics/mockData.js @@ -4,7 +4,7 @@ * @Github: * @Date: 2020-01-11 10:55:33 * @LastEditors : tangjiang - * @LastEditTime : 2020-01-11 14:01:49 + * @LastEditTime : 2020-01-11 17:48:02 */ import { random } from 'lodash'; @@ -28,11 +28,11 @@ const fetchData = (startIndex = 0) => return { key: getGuid(), index: `${index}`, - name: 'John Brown', - age: 32, - address: 'New York No. 1 Lake Park', + name: '湖南长沙中南大学湖南长沙中南大学湖南长沙中南大学湖南长沙中南大学湖南长沙中南大学', + age: i+1, + address: 'New York No. ', address2: 'address2', - address3: 'address3' + bbb: 'address3' }; }), ); @@ -43,45 +43,57 @@ const columns = [ { title: '序号', dataIndex: 'index', - render: text => text, + render: text => text + 1, width: 80, + align: 'center' }, { title: '使用单位', dataIndex: 'name', - // width: 100, + width: 300, + className: 'overflow_hidden', + align: 'center' }, { title: '使用课堂/个', - // width: 200, + width: 200, dataIndex: 'age', + align: 'center', + sorter: (a, b) => a.age - b.age }, { title: '课堂学生/个', - // width: 200, + width: 200, dataIndex: 'address', + align: 'center', + sorter: (a, b) => a.age - b.age }, { title: '选用实训/个', - // width: 200, + width: 200, dataIndex: 'address2', + align: 'center', + sorter: (a, b) => a.age - b.age }, { title: '选用实训/个', - // width: 200, - dataIndex: 'address3', + width: 200, + dataIndex: 'bbb', + align: 'center', + sorter: (a, b) => a.bbb - b.bbb } ]; const sumData = [ { index: '合计', + key: 6, name: 'Disabled User', age: 99, - address: 'Sidney No. 1 Lake Park', + address: 'Sidney No.', address2: 'address2', - addrexs3: 'address3' - }, + bbb: 'address3', + } ]; export { columns, fetchData, sumData }; From 5e1d9acd80e30c4ad6d049859f379e3a827dc5a0 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 10:49:49 +0800 Subject: [PATCH 052/204] 1 --- .../chinese_dictionary.txt | 1 - config/harmonious_dictionary/harmonious.hash | Bin 46347 -> 46320 bytes 2 files changed, 1 deletion(-) diff --git a/config/harmonious_dictionary/chinese_dictionary.txt b/config/harmonious_dictionary/chinese_dictionary.txt index ce247eb45..c65450d70 100644 --- a/config/harmonious_dictionary/chinese_dictionary.txt +++ b/config/harmonious_dictionary/chinese_dictionary.txt @@ -613,7 +613,6 @@ a级情片 大史纪 戴相龙 弹劾 -登辉 邓笑贫 迪里夏提 地下教会 diff --git a/config/harmonious_dictionary/harmonious.hash b/config/harmonious_dictionary/harmonious.hash index 456a8254b258a810b2e661f5130946a71a39a915..7dfcdc80b75aa38a14a1ef1e29a791c268dbe4ca 100644 GIT binary patch delta 21 ccmeBv#q{AN6DtcxHIw;9R=3X0X`M^80b2G54*&oF delta 25 hcmezHlBxR@6DtcxHIv0gR=3W{516Dkdv`9?1^|B(355Uv From 42c4a4f953ee8cb53301239616c5c8d7b55c57f2 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Tue, 14 Jan 2020 11:09:53 +0800 Subject: [PATCH 053/204] =?UTF-8?q?=E9=80=89=E7=94=A8=E5=AE=9E=E8=AE=AD?= =?UTF-8?q?=E7=9A=84=E6=9D=83=E9=99=90?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/services/shixun_search_service.rb | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/app/services/shixun_search_service.rb b/app/services/shixun_search_service.rb index 32488a7c3..710910100 100644 --- a/app/services/shixun_search_service.rb +++ b/app/services/shixun_search_service.rb @@ -23,9 +23,10 @@ class ShixunSearchService < ApplicationService if User.current.admin? || User.current.business? || !User.current.school_id @shixuns = @shixuns.where(hidden: 0) else - none_shixun_ids = ShixunSchool.where("school_id != #{User.current.school_id}").pluck(:shixun_id) + shixun_ids = ShixunSchool.where(school_id: User.current.school_id).pluck(:shixun_id) + shixun_ids = shixun_ids.reject(&:blank?).length == 0 ? -1 : shixun_ids.join(",") - @shixuns = @shixuns.where.not(id: none_shixun_ids).where(hidden: 0, status: 2, public: 2).or(@shixuns.where(id: User.current.shixuns)) + @shixuns = @shixuns.where("use_scope = 1 or id in (#{shixun_ids})").unhidden.published.or(@shixuns.where(id: User.current.shixuns)) end end From 271dbe1cbd6e2812807a9da7b2c81a37ea20f483 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 11:39:08 +0800 Subject: [PATCH 054/204] 1 --- app/controllers/subjects_controller.rb | 21 +++++-------------- .../subjects/statistics_info.json.jbuilder | 2 ++ 2 files changed, 7 insertions(+), 16 deletions(-) diff --git a/app/controllers/subjects_controller.rb b/app/controllers/subjects_controller.rb index 47863a3a0..cdd449858 100644 --- a/app/controllers/subjects_controller.rb +++ b/app/controllers/subjects_controller.rb @@ -458,22 +458,6 @@ class SubjectsController < ApplicationController end def statistics_info - # data = Subjects::DataStatisticService.new(@subject) - # Rails.logger.info("study_count: #{data.study_count}") - # Rails.logger.info("course_study_count: #{ data.course_study_count}") - # Rails.logger.info("passed_count: #{data.passed_count}") - # Rails.logger.info("course_used_count: #{data.course_used_count}") - # Rails.logger.info("school_used_count: #{data.school_used_count}") - - # data_1 = Subjects::CourseUsedInfoService.call(@subject) - # Rails.logger.info("study_count: #{data_1}") - - # data_2 = Subjects::ShixunUsedInfoService.call(@subject) - # Rails.logger.info("study_count: #{data_2}") - - # data_3 = Subjects::UserUsedInfoService.call(@subject) - # Rails.logger.info("study_count: #{data_3}") - @data = if params[:type] == "shixun_info" @subject.subject_shixun_infos @@ -481,7 +465,12 @@ class SubjectsController < ApplicationController @subject.subject_user_infos else @subject.subject_course_records + select_sql = "count(*) total, sum(course_count) course_count, sum(student_count) student_count, " + + "sum(choice_shixun_num) choice_shixun_num, sum(choice_shixun_frequency) choice_shixun_frequency" + @total = @subject.subject_course_records.select("select_sql") end + + @data_count = @data.count @data = paginate custom_sort(@data, params[:sort_by], params[:sort_direction]) end diff --git a/app/views/subjects/statistics_info.json.jbuilder b/app/views/subjects/statistics_info.json.jbuilder index b31e41b31..0881651a9 100644 --- a/app/views/subjects/statistics_info.json.jbuilder +++ b/app/views/subjects/statistics_info.json.jbuilder @@ -3,4 +3,6 @@ json.message "success" json.data do json.subject_info @subject.subject_record json.other_info @data + json.total_count @data_count + json.total @total end \ No newline at end of file From e2fa4112b85078db7d1842a6a4189713aef9ed7e Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 11:39:51 +0800 Subject: [PATCH 055/204] 1 --- app/controllers/subjects_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/subjects_controller.rb b/app/controllers/subjects_controller.rb index cdd449858..cf1330125 100644 --- a/app/controllers/subjects_controller.rb +++ b/app/controllers/subjects_controller.rb @@ -467,7 +467,7 @@ class SubjectsController < ApplicationController @subject.subject_course_records select_sql = "count(*) total, sum(course_count) course_count, sum(student_count) student_count, " + "sum(choice_shixun_num) choice_shixun_num, sum(choice_shixun_frequency) choice_shixun_frequency" - @total = @subject.subject_course_records.select("select_sql") + @total = @subject.subject_course_records.select("select_sql").first end @data_count = @data.count From a7ea21e552020405b12c8b7ab6a5d16b00a1d504 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 11:40:43 +0800 Subject: [PATCH 056/204] 1 --- app/controllers/subjects_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/subjects_controller.rb b/app/controllers/subjects_controller.rb index cf1330125..676af6036 100644 --- a/app/controllers/subjects_controller.rb +++ b/app/controllers/subjects_controller.rb @@ -467,7 +467,7 @@ class SubjectsController < ApplicationController @subject.subject_course_records select_sql = "count(*) total, sum(course_count) course_count, sum(student_count) student_count, " + "sum(choice_shixun_num) choice_shixun_num, sum(choice_shixun_frequency) choice_shixun_frequency" - @total = @subject.subject_course_records.select("select_sql").first + @total = @subject.subject_course_records.select("#{select_sql}").first end @data_count = @data.count From 39ccb537294f55729fa3afc0e4d10c899d5d1624 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 11:43:07 +0800 Subject: [PATCH 057/204] 1 --- app/controllers/subjects_controller.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/controllers/subjects_controller.rb b/app/controllers/subjects_controller.rb index 676af6036..47c4d6a60 100644 --- a/app/controllers/subjects_controller.rb +++ b/app/controllers/subjects_controller.rb @@ -464,10 +464,10 @@ class SubjectsController < ApplicationController elsif params[:type] == "user_info" @subject.subject_user_infos else - @subject.subject_course_records - select_sql = "count(*) total, sum(course_count) course_count, sum(student_count) student_count, " + + select_sql = "count(subject_course_records.*) total, sum(course_count) course_count, sum(student_count) student_count, " + "sum(choice_shixun_num) choice_shixun_num, sum(choice_shixun_frequency) choice_shixun_frequency" @total = @subject.subject_course_records.select("#{select_sql}").first + @subject.subject_course_records end @data_count = @data.count From 6e528448a6dff21fea21eed77b5d029368b95261 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 11:45:17 +0800 Subject: [PATCH 058/204] 1 --- app/controllers/subjects_controller.rb | 3 --- app/views/subjects/statistics_info.json.jbuilder | 2 +- 2 files changed, 1 insertion(+), 4 deletions(-) diff --git a/app/controllers/subjects_controller.rb b/app/controllers/subjects_controller.rb index 47c4d6a60..248371e63 100644 --- a/app/controllers/subjects_controller.rb +++ b/app/controllers/subjects_controller.rb @@ -464,9 +464,6 @@ class SubjectsController < ApplicationController elsif params[:type] == "user_info" @subject.subject_user_infos else - select_sql = "count(subject_course_records.*) total, sum(course_count) course_count, sum(student_count) student_count, " + - "sum(choice_shixun_num) choice_shixun_num, sum(choice_shixun_frequency) choice_shixun_frequency" - @total = @subject.subject_course_records.select("#{select_sql}").first @subject.subject_course_records end diff --git a/app/views/subjects/statistics_info.json.jbuilder b/app/views/subjects/statistics_info.json.jbuilder index 0881651a9..daa3a6b60 100644 --- a/app/views/subjects/statistics_info.json.jbuilder +++ b/app/views/subjects/statistics_info.json.jbuilder @@ -4,5 +4,5 @@ json.data do json.subject_info @subject.subject_record json.other_info @data json.total_count @data_count - json.total @total + # json.total @total end \ No newline at end of file From fff12c44ad607d92f979f6371ad7e36598368209 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 11:48:42 +0800 Subject: [PATCH 059/204] 1 --- app/controllers/subjects_controller.rb | 3 +++ app/views/subjects/statistics_info.json.jbuilder | 2 +- 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/app/controllers/subjects_controller.rb b/app/controllers/subjects_controller.rb index 248371e63..8e78706ed 100644 --- a/app/controllers/subjects_controller.rb +++ b/app/controllers/subjects_controller.rb @@ -464,6 +464,9 @@ class SubjectsController < ApplicationController elsif params[:type] == "user_info" @subject.subject_user_infos else + select_sql = "count(subject_course_records.id) total, sum(course_count) course_count, sum(student_count) student_count, " + + "sum(choice_shixun_num) choice_shixun_num, sum(choice_shixun_frequency) choice_shixun_frequency" + @total = @subject.subject_course_records.select("#{select_sql}").first @subject.subject_course_records end diff --git a/app/views/subjects/statistics_info.json.jbuilder b/app/views/subjects/statistics_info.json.jbuilder index daa3a6b60..0881651a9 100644 --- a/app/views/subjects/statistics_info.json.jbuilder +++ b/app/views/subjects/statistics_info.json.jbuilder @@ -4,5 +4,5 @@ json.data do json.subject_info @subject.subject_record json.other_info @data json.total_count @data_count - # json.total @total + json.total @total end \ No newline at end of file From 9b30ab55becb6983e9bf3ac179601c87e7d17e07 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 11:52:22 +0800 Subject: [PATCH 060/204] 1 --- app/controllers/subjects_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/subjects_controller.rb b/app/controllers/subjects_controller.rb index 8e78706ed..3b1a6fc8b 100644 --- a/app/controllers/subjects_controller.rb +++ b/app/controllers/subjects_controller.rb @@ -466,7 +466,7 @@ class SubjectsController < ApplicationController else select_sql = "count(subject_course_records.id) total, sum(course_count) course_count, sum(student_count) student_count, " + "sum(choice_shixun_num) choice_shixun_num, sum(choice_shixun_frequency) choice_shixun_frequency" - @total = @subject.subject_course_records.select("#{select_sql}").first + @total = @subject.subject_course_records.select("#{select_sql}").first.except("id") @subject.subject_course_records end From ae032c8f675d4bf25ed06146a8f762d233f2e30b Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 11:53:01 +0800 Subject: [PATCH 061/204] 1 --- app/controllers/subjects_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/subjects_controller.rb b/app/controllers/subjects_controller.rb index 3b1a6fc8b..8e78706ed 100644 --- a/app/controllers/subjects_controller.rb +++ b/app/controllers/subjects_controller.rb @@ -466,7 +466,7 @@ class SubjectsController < ApplicationController else select_sql = "count(subject_course_records.id) total, sum(course_count) course_count, sum(student_count) student_count, " + "sum(choice_shixun_num) choice_shixun_num, sum(choice_shixun_frequency) choice_shixun_frequency" - @total = @subject.subject_course_records.select("#{select_sql}").first.except("id") + @total = @subject.subject_course_records.select("#{select_sql}").first @subject.subject_course_records end From 42174b1df60d4d6d7bbad49dcf3ca6adadc36b5c Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 11:53:16 +0800 Subject: [PATCH 062/204] 1 --- app/controllers/subjects_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/subjects_controller.rb b/app/controllers/subjects_controller.rb index 8e78706ed..ce7fc575c 100644 --- a/app/controllers/subjects_controller.rb +++ b/app/controllers/subjects_controller.rb @@ -464,7 +464,7 @@ class SubjectsController < ApplicationController elsif params[:type] == "user_info" @subject.subject_user_infos else - select_sql = "count(subject_course_records.id) total, sum(course_count) course_count, sum(student_count) student_count, " + + select_sql = "id, count(subject_course_records.id) total, sum(course_count) course_count, sum(student_count) student_count, " + "sum(choice_shixun_num) choice_shixun_num, sum(choice_shixun_frequency) choice_shixun_frequency" @total = @subject.subject_course_records.select("#{select_sql}").first @subject.subject_course_records From dc3a6026c715534f16099994a22046c87dbb5897 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Tue, 14 Jan 2020 13:55:42 +0800 Subject: [PATCH 063/204] =?UTF-8?q?=E5=AD=A6=E6=A0=A1=E7=9A=84=E8=AF=BE?= =?UTF-8?q?=E5=A0=82=E7=BB=9F=E8=AE=A1bug?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/colleges_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/colleges_controller.rb b/app/controllers/colleges_controller.rb index 707255866..8e18ae2ad 100644 --- a/app/controllers/colleges_controller.rb +++ b/app/controllers/colleges_controller.rb @@ -105,7 +105,7 @@ class CollegesController < ApplicationController @courses = paginate courses course_ids = @courses.map(&:id) - @student_count = StudentsForCourse.where(course_id: course_ids).group(:course_id).count + @student_count = CourseMember.where(course_id: course_ids, role: 4).group(:course_id).count @shixun_work_count = HomeworkCommon.where(homework_type: 4, course_id: course_ids).group(:course_id).count @attachment_count = Attachment.where(container_id: course_ids, container_type: 'Course').group(:container_id).count @message_count = Message.joins(:board).where(boards: { parent_id: 0, course_id: course_ids }).group('boards.course_id').count From 14f94b4eb981e94f640575b7717997b37496993b Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Tue, 14 Jan 2020 13:57:11 +0800 Subject: [PATCH 064/204] =?UTF-8?q?=E5=AD=A6=E6=A0=A1=E7=9A=84=E8=AF=BE?= =?UTF-8?q?=E5=A0=82=E7=BB=9F=E8=AE=A1bug?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/colleges_controller.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/controllers/colleges_controller.rb b/app/controllers/colleges_controller.rb index 8e18ae2ad..ee7b9c014 100644 --- a/app/controllers/colleges_controller.rb +++ b/app/controllers/colleges_controller.rb @@ -53,7 +53,7 @@ class CollegesController < ApplicationController homeworks = HomeworkCommon.where(:homework_type => 4, :course_id => course_ids.map(&:id)) un_shixun_work_count = homeworks.where("publish_time > '#{Time.now}' or publish_time is null").count shixun_work_count = homeworks.size - un_shixun_work_count - student_count = StudentsForCourse.where(:course_id => course_ids.map(&:id)).count + student_count = CourseMember.where(course_id: course_ids.map(&:id), role: 4).count myshixun_ids = StudentWork.select("myshixun_id").where("homework_common_id in (#{homeworks.map(&:id).join(',').strip == "" ? -1 : homeworks.map(&:id).join(',')}) and myshixun_id is not null") complete_myshixun = Myshixun.select("id").where(:status => 1, :id => myshixun_ids.map(&:myshixun_id)).size all_myshixun = Myshixun.select("id").where(:id => myshixun_ids.map(&:myshixun_id)).size From 5a107ad34e0b2b7f8f4a0b55c3b211e261e0f4d1 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Tue, 14 Jan 2020 14:14:57 +0800 Subject: [PATCH 065/204] =?UTF-8?q?=E8=BF=98=E5=8E=9F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/services/shixun_search_service.rb | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/app/services/shixun_search_service.rb b/app/services/shixun_search_service.rb index 710910100..32488a7c3 100644 --- a/app/services/shixun_search_service.rb +++ b/app/services/shixun_search_service.rb @@ -23,10 +23,9 @@ class ShixunSearchService < ApplicationService if User.current.admin? || User.current.business? || !User.current.school_id @shixuns = @shixuns.where(hidden: 0) else - shixun_ids = ShixunSchool.where(school_id: User.current.school_id).pluck(:shixun_id) - shixun_ids = shixun_ids.reject(&:blank?).length == 0 ? -1 : shixun_ids.join(",") + none_shixun_ids = ShixunSchool.where("school_id != #{User.current.school_id}").pluck(:shixun_id) - @shixuns = @shixuns.where("use_scope = 1 or id in (#{shixun_ids})").unhidden.published.or(@shixuns.where(id: User.current.shixuns)) + @shixuns = @shixuns.where.not(id: none_shixun_ids).where(hidden: 0, status: 2, public: 2).or(@shixuns.where(id: User.current.shixuns)) end end From ed84abf94def11844bb62b9b952fb8a515fe428e Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Tue, 14 Jan 2020 15:01:44 +0800 Subject: [PATCH 066/204] =?UTF-8?q?=E5=88=86=E7=8F=AD=E6=95=B0=E6=8D=AE?= =?UTF-8?q?=E7=9A=84=E8=BF=81=E7=A7=BB?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ...00114062353_migrate_coures_member_group.rb | 25 +++++++++++++++++++ 1 file changed, 25 insertions(+) create mode 100644 db/migrate/20200114062353_migrate_coures_member_group.rb diff --git a/db/migrate/20200114062353_migrate_coures_member_group.rb b/db/migrate/20200114062353_migrate_coures_member_group.rb new file mode 100644 index 000000000..4255bbe9b --- /dev/null +++ b/db/migrate/20200114062353_migrate_coures_member_group.rb @@ -0,0 +1,25 @@ +class MigrateCouresMemberGroup < ActiveRecord::Migration[5.2] + def change + course_ids = [377, 657, 715, 777, 973, 1093, 1131, 1180, 1309, 1920, 2037, 2346, 2354, 2493, 2752, 2920, 3000, + 3141, 3240, 3350, 3351, 3353, 3387, 3533, 3796] + + courses = Course.where(id: course_ids) + + courses.each do |course| + group_ids = course.course_groups.pluck(:id) + [0] + course.course_members.where.not(course_group_id: group_ids).each do |member| + if CourseGroup.where(course_id: course.id, name: member.course_group_name).exists? + new_group = CourseGroup.where(course_id: course.id, name: member.course_group_name).first + else + position = CourseGroup.where(course_id: course.id).order("position desc").first&.position.to_i + 1 + new_group = course.course_groups.create!(name: member.course_group_name, position: position) + course.exercise_group_settings.where(course_group_id: member.course_group_id).update_all(course_group_id: new_group.id) + course.attachment_group_settings.where(course_group_id: member.course_group_id).update_all(course_group_id: new_group.id) + HomeworkGroupReview.where(homework_common_id: course.homework_commons.pluck(:id)).where(course_group_id: member.course_group_id).update_all(course_group_id: new_group.id) + course.homework_group_settings.where(course_group_id: member.course_group_id).update_all(course_group_id: new_group.id) + end + member.update!(course_group_id: new_group.id) + end + end + end +end From 52ab6eb9e7bd01dc8419fc75a40e88d38abe6b52 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Tue, 14 Jan 2020 15:22:41 +0800 Subject: [PATCH 067/204] =?UTF-8?q?=E5=88=86=E7=8F=AD=E7=9A=84position?= =?UTF-8?q?=E8=BF=81=E7=A7=BB?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../20200114062353_migrate_coures_member_group.rb | 4 ++-- ...0114071420_migrate_course_group_member_count.rb | 4 ++++ .../20200114071917_migrate_coure_group_position.rb | 14 ++++++++++++++ 3 files changed, 20 insertions(+), 2 deletions(-) create mode 100644 db/migrate/20200114071420_migrate_course_group_member_count.rb create mode 100644 db/migrate/20200114071917_migrate_coure_group_position.rb diff --git a/db/migrate/20200114062353_migrate_coures_member_group.rb b/db/migrate/20200114062353_migrate_coures_member_group.rb index 4255bbe9b..b9992cb50 100644 --- a/db/migrate/20200114062353_migrate_coures_member_group.rb +++ b/db/migrate/20200114062353_migrate_coures_member_group.rb @@ -11,8 +11,8 @@ class MigrateCouresMemberGroup < ActiveRecord::Migration[5.2] if CourseGroup.where(course_id: course.id, name: member.course_group_name).exists? new_group = CourseGroup.where(course_id: course.id, name: member.course_group_name).first else - position = CourseGroup.where(course_id: course.id).order("position desc").first&.position.to_i + 1 - new_group = course.course_groups.create!(name: member.course_group_name, position: position) + # position = CourseGroup.where(course_id: course.id).order("position desc").first&.position.to_i + 1 + new_group = course.course_groups.create!(name: member.course_group_name) course.exercise_group_settings.where(course_group_id: member.course_group_id).update_all(course_group_id: new_group.id) course.attachment_group_settings.where(course_group_id: member.course_group_id).update_all(course_group_id: new_group.id) HomeworkGroupReview.where(homework_common_id: course.homework_commons.pluck(:id)).where(course_group_id: member.course_group_id).update_all(course_group_id: new_group.id) diff --git a/db/migrate/20200114071420_migrate_course_group_member_count.rb b/db/migrate/20200114071420_migrate_course_group_member_count.rb new file mode 100644 index 000000000..aad9dcc9c --- /dev/null +++ b/db/migrate/20200114071420_migrate_course_group_member_count.rb @@ -0,0 +1,4 @@ +class MigrateCourseGroupMemberCount < ActiveRecord::Migration[5.2] + def change + end +end diff --git a/db/migrate/20200114071917_migrate_coure_group_position.rb b/db/migrate/20200114071917_migrate_coure_group_position.rb new file mode 100644 index 000000000..0061eaad3 --- /dev/null +++ b/db/migrate/20200114071917_migrate_coure_group_position.rb @@ -0,0 +1,14 @@ +class MigrateCoureGroupPosition < ActiveRecord::Migration[5.2] + def change + course_ids = [377, 657, 715, 777, 973, 1093, 1131, 1180, 1309, 1920, 2037, 2346, 2354, 2493, 2752, 2920, 3000, + 3141, 3240, 3350, 3351, 3353, 3387, 3533, 3796] + + courses = Course.where(id: course_ids) + + courses.each do |course| + CourseGroup.where(coures_id: course.id).reorder("position ASC, CONVERT(course_groups.name USING gbk) COLLATE gbk_chinese_ci ASC").each_with_index do |group, index| + group.update!(position: index+1) + end + end + end +end From 34c5c550fa5e537b2f24306cb0627d3d11628a83 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Tue, 14 Jan 2020 15:23:33 +0800 Subject: [PATCH 068/204] =?UTF-8?q?=E5=88=86=E7=8F=AD=E7=9A=84position?= =?UTF-8?q?=E8=BF=81=E7=A7=BB?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- db/migrate/20200114071917_migrate_coure_group_position.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/db/migrate/20200114071917_migrate_coure_group_position.rb b/db/migrate/20200114071917_migrate_coure_group_position.rb index 0061eaad3..fc04e1bcb 100644 --- a/db/migrate/20200114071917_migrate_coure_group_position.rb +++ b/db/migrate/20200114071917_migrate_coure_group_position.rb @@ -6,7 +6,7 @@ class MigrateCoureGroupPosition < ActiveRecord::Migration[5.2] courses = Course.where(id: course_ids) courses.each do |course| - CourseGroup.where(coures_id: course.id).reorder("position ASC, CONVERT(course_groups.name USING gbk) COLLATE gbk_chinese_ci ASC").each_with_index do |group, index| + CourseGroup.where(course_id: course.id).reorder("position ASC, CONVERT(course_groups.name USING gbk) COLLATE gbk_chinese_ci ASC").each_with_index do |group, index| group.update!(position: index+1) end end From 72a48f6e6c22d576a67b3f18329eca397014c292 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Tue, 14 Jan 2020 15:25:30 +0800 Subject: [PATCH 069/204] =?UTF-8?q?=E5=AE=9E=E8=AE=AD=E7=9A=84=E6=90=9C?= =?UTF-8?q?=E7=B4=A2?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/services/shixun_search_service.rb | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/app/services/shixun_search_service.rb b/app/services/shixun_search_service.rb index 32488a7c3..710910100 100644 --- a/app/services/shixun_search_service.rb +++ b/app/services/shixun_search_service.rb @@ -23,9 +23,10 @@ class ShixunSearchService < ApplicationService if User.current.admin? || User.current.business? || !User.current.school_id @shixuns = @shixuns.where(hidden: 0) else - none_shixun_ids = ShixunSchool.where("school_id != #{User.current.school_id}").pluck(:shixun_id) + shixun_ids = ShixunSchool.where(school_id: User.current.school_id).pluck(:shixun_id) + shixun_ids = shixun_ids.reject(&:blank?).length == 0 ? -1 : shixun_ids.join(",") - @shixuns = @shixuns.where.not(id: none_shixun_ids).where(hidden: 0, status: 2, public: 2).or(@shixuns.where(id: User.current.shixuns)) + @shixuns = @shixuns.where("use_scope = 1 or id in (#{shixun_ids})").unhidden.published.or(@shixuns.where(id: User.current.shixuns)) end end From 91a83784e097d35744e840d1a2cc6499cdbcd5db Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Tue, 14 Jan 2020 15:27:04 +0800 Subject: [PATCH 070/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../20200114071420_migrate_course_group_member_count.rb | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/db/migrate/20200114071420_migrate_course_group_member_count.rb b/db/migrate/20200114071420_migrate_course_group_member_count.rb index aad9dcc9c..5273290f2 100644 --- a/db/migrate/20200114071420_migrate_course_group_member_count.rb +++ b/db/migrate/20200114071420_migrate_course_group_member_count.rb @@ -1,4 +1,8 @@ class MigrateCourseGroupMemberCount < ActiveRecord::Migration[5.2] def change + CourseGroup.reset_column_information + CourseGroup.find_each do |group| + CourseGroup.reset_counters(group.id, :course_members_count) + end end end From a4964802a3cf7a69602fe5b67d3af557ab179ebe Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Tue, 14 Jan 2020 15:46:17 +0800 Subject: [PATCH 071/204] =?UTF-8?q?=E8=AF=BE=E5=A0=82=E4=BB=BB=E5=8A=A1?= =?UTF-8?q?=E7=9A=84=E6=97=B6=E9=97=B4=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/application_controller.rb | 2 +- app/controllers/exercises_controller.rb | 2 +- app/controllers/graduation_tasks_controller.rb | 8 ++++---- app/controllers/polls_controller.rb | 2 +- app/services/update_homework_publish_setting_service.rb | 8 ++++---- .../20200114071420_migrate_course_group_member_count.rb | 8 -------- 6 files changed, 11 insertions(+), 19 deletions(-) delete mode 100644 db/migrate/20200114071420_migrate_course_group_member_count.rb diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb index e0639de3f..fdb41c114 100644 --- a/app/controllers/application_controller.rb +++ b/app/controllers/application_controller.rb @@ -23,7 +23,7 @@ class ApplicationController < ActionController::Base # 所有请求必须合法签名 def check_sign - if !Rails.env.development? && EduSetting.get("host_name") != "https://test-newweb.educoder.net" + if !Rails.env.development? Rails.logger.info("66666 #{params}") # suffix = request.url.split(".").last.split("?").first # suffix_arr = ["xls", "xlsx", "pdf", "zip"] # excel文件先注释 diff --git a/app/controllers/exercises_controller.rb b/app/controllers/exercises_controller.rb index 5b555cf4c..44bfcf03f 100644 --- a/app/controllers/exercises_controller.rb +++ b/app/controllers/exercises_controller.rb @@ -402,7 +402,7 @@ class ExercisesController < ApplicationController if unified_setting || (course_group_ids.size == 0) tip_exception("发布时间不能为空") if params[:publish_time].blank? tip_exception("截止时间不能为空") if params[:end_time].blank? - tip_exception("截止时间不能早于发布时间") if params[:publish_time].to_time > params[:end_time].to_time + tip_exception("截止时间必须晚于发布时间") if params[:publish_time].to_time >= params[:end_time].to_time tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && params[:end_time].to_time > @course.end_date.end_of_day params_publish_time = params[:publish_time].to_time diff --git a/app/controllers/graduation_tasks_controller.rb b/app/controllers/graduation_tasks_controller.rb index cac763344..6196aa5f5 100644 --- a/app/controllers/graduation_tasks_controller.rb +++ b/app/controllers/graduation_tasks_controller.rb @@ -384,11 +384,11 @@ class GraduationTasksController < ApplicationController if @task.status == 0 tip_exception("发布时间不能为空") if params[:publish_time].blank? tip_exception("截止时间不能为空") if params[:end_time].blank? - tip_exception("发布时间不能早于当前时间") if params[:publish_time] <= Time.now.strftime("%Y-%m-%d %H:%M:%S") - tip_exception("截止时间不能早于当前时间") if params[:end_time] <= Time.now.strftime("%Y-%m-%d %H:%M:%S") - tip_exception("截止时间不能早于发布时间") if params[:publish_time] > params[:end_time] + tip_exception("发布时间不能早于当前时间") if params[:publish_time].to_time <= Time.now + tip_exception("截止时间不能早于当前时间") if params[:end_time].to_time <= Time.now + tip_exception("截止时间必须晚于发布时间") if params[:publish_time].to_time >= params[:end_time].to_time tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if - @course.end_date.present? && params[:end_time] > strf_time(@course.end_date.end_of_day) + @course.end_date.present? && params[:end_time].to_time > @course.end_date.end_of_day @task.publish_time = params[:publish_time] @task.end_time = params[:end_time] diff --git a/app/controllers/polls_controller.rb b/app/controllers/polls_controller.rb index c9c9cc567..d320379be 100644 --- a/app/controllers/polls_controller.rb +++ b/app/controllers/polls_controller.rb @@ -724,7 +724,7 @@ class PollsController < ApplicationController if unified_setting || (course_group_ids.size == 0) tip_exception("发布时间不能为空") if params[:publish_time].blank? tip_exception("截止时间不能为空") if params[:end_time].blank? - tip_exception("截止时间不能早于发布时间") if params[:publish_time].to_time > params[:end_time].to_time + tip_exception("截止时间必须晚于发布时间") if params[:publish_time].to_time >= params[:end_time].to_time tip_exception("截止时间不能晚于课堂结束时间(#{@course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if @course.end_date.present? && params[:end_time].to_time > @course.end_date.end_of_day diff --git a/app/services/update_homework_publish_setting_service.rb b/app/services/update_homework_publish_setting_service.rb index 69a68b613..61902cd80 100644 --- a/app/services/update_homework_publish_setting_service.rb +++ b/app/services/update_homework_publish_setting_service.rb @@ -15,11 +15,11 @@ class UpdateHomeworkPublishSettingService < ApplicationService if params[:unified_setting] || course.course_groups_count == 0 tip_exception("发布时间不能为空") if params[:publish_time].blank? tip_exception("截止时间不能为空") if params[:end_time].blank? - tip_exception("发布时间不能早于当前时间") if params[:publish_time] <= Time.now.strftime("%Y-%m-%d %H:%M:%S") - tip_exception("截止时间不能早于当前时间") if params[:end_time] <= Time.now.strftime("%Y-%m-%d %H:%M:%S") - tip_exception("截止时间不能早于发布时间") if params[:publish_time] > params[:end_time] + tip_exception("发布时间不能早于当前时间") if params[:publish_time].to_time <= Time.now + tip_exception("截止时间不能早于当前时间") if params[:end_time].to_time <= Time.now + tip_exception("截止时间必须晚于发布时间") if params[:publish_time].to_time >= params[:end_time].to_time tip_exception("截止时间不能晚于课堂结束时间(#{course.end_date.end_of_day.strftime("%Y-%m-%d %H:%M")})") if - course.end_date.present? && params[:end_time] > course.end_date.end_of_day + course.end_date.present? && params[:end_time].to_time > course.end_date.end_of_day homework.unified_setting = 1 homework.homework_group_settings.destroy_all diff --git a/db/migrate/20200114071420_migrate_course_group_member_count.rb b/db/migrate/20200114071420_migrate_course_group_member_count.rb deleted file mode 100644 index 5273290f2..000000000 --- a/db/migrate/20200114071420_migrate_course_group_member_count.rb +++ /dev/null @@ -1,8 +0,0 @@ -class MigrateCourseGroupMemberCount < ActiveRecord::Migration[5.2] - def change - CourseGroup.reset_column_information - CourseGroup.find_each do |group| - CourseGroup.reset_counters(group.id, :course_members_count) - end - end -end From 7dfb5076c718483caa9c34c089e6b12f233f7c11 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Tue, 14 Jan 2020 15:56:38 +0800 Subject: [PATCH 072/204] =?UTF-8?q?=E5=AE=9E=E8=AE=AD=E7=9A=84=E6=90=9C?= =?UTF-8?q?=E7=B4=A2?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/services/shixun_search_service.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/services/shixun_search_service.rb b/app/services/shixun_search_service.rb index 710910100..8a99092cf 100644 --- a/app/services/shixun_search_service.rb +++ b/app/services/shixun_search_service.rb @@ -26,7 +26,7 @@ class ShixunSearchService < ApplicationService shixun_ids = ShixunSchool.where(school_id: User.current.school_id).pluck(:shixun_id) shixun_ids = shixun_ids.reject(&:blank?).length == 0 ? -1 : shixun_ids.join(",") - @shixuns = @shixuns.where("use_scope = 1 or id in (#{shixun_ids})").unhidden.published.or(@shixuns.where(id: User.current.shixuns)) + @shixuns = @shixuns.where("use_scope = 0 or id in (#{shixun_ids})").unhidden.published.or(@shixuns.where(id: User.current.shixuns)) end end From a07ffdb67093ab117ab9de740e046b96a0f44ea7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=A8=E6=A0=91=E6=98=8E?= <775174143@qq.com> Date: Tue, 14 Jan 2020 16:04:54 +0800 Subject: [PATCH 073/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/images/educoder/xcx/myinfobanner.png | Bin 214824 -> 67408 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/public/images/educoder/xcx/myinfobanner.png b/public/images/educoder/xcx/myinfobanner.png index 10046e3613147cc7a2d4bdbb5ee41930cd70136d..ed1b10b30edb5661f7268b7d1eb36fb81a49f448 100644 GIT binary patch literal 67408 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 literal 214824 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≪YlTiZ2 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
    rSsm%=yYX$QTE=G?++t`fcpPd zEe$w!tWeHG%q($+OVx7{nV=zd5LuJ$znw3f=EK7BO{RD=E>i`0XKR*)SL`2#>IC#5 zh~60uqPGYbNjIhjYkLXuS0XeL(=dq_d|S#zi9<=Xu!^EK#QG1{`u`)hmp#p!>$KlB zP3t^%l6$gP`29?_j`@=qsUiBefGrZEM%hQShI(Tr#lrLX2!GLToeYY5!tF1AXfBdNb(~24v@uIhER|T%_jt%(lxcv;^aiLACm?L?nJbvX^*MPF=qhGp* zNU_n1cHifClhDp8o4toNOZCqh7Rr$TUZ z|30jq?=O=&A^bKg_AymF&zM`LI7|5Ly3}RhM!BL&FI^)fuLGA?s|}$? zz{unJH|^0?zL!;`Sx8ub{l+e;_=*q&;D4+#+Yi@5pW|CaH0f>h=(PbObI+rzO2@~-j9LaX%A(Hd%u5q+ zhX8FEk^$5T`#j=N_75=?NyYye;(s+ZDWK%D8rta=rYvtn5ZEflzReB1&KU-YaN|<^ z(>kdIxV9RckgN&Ig*Gx-jlv`TZ_fFzxs&exUZ14?o*OC~5+?GywWtdT>)5GG!0M%{ z`Ta}JJmU>VEZI_gBKGtd{W;9v|IAqBIR0dl@shfaray|3>E{HcKLx}l#cAMM?5pOh zyQlw8gvc2v=P=K$21%CCqs@|KsNt(dXh)_Kf9p9^3!0( zXDNgGpVSYDu7LuDe)8|ooQUc_T+ From ef970827701697324e0a0e8710253f027094bd10 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E6=9D=A8=E6=A0=91=E6=98=8E?= <775174143@qq.com> Date: Tue, 14 Jan 2020 16:29:19 +0800 Subject: [PATCH 074/204] =?UTF-8?q?=E8=B0=83=E6=95=B4?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/images/educoder/xcx/SMIDCard.png | Bin 7361 -> 7733 bytes public/images/educoder/xcx/ZYIDCard.png | Bin 5539 -> 6001 bytes 2 files changed, 0 insertions(+), 0 deletions(-) diff --git a/public/images/educoder/xcx/SMIDCard.png b/public/images/educoder/xcx/SMIDCard.png index cea96596d10130744accaa84dcfab8b0ed87a1dc..7f265c3c44a1d0b055d81b777a1d3946ae5de794 100644 GIT binary patch literal 7733 zcmds65x!LY3XJ}6lp{$5oSb? z?(XyOp7(eDg7f8^FSDLC>#lvTz3;fLrzS?)G?eU=007YF>S&q)00aeo{~#v?e^=-a z^#OqESXWc+MxgylCPg6g@ObChgR1yPC}<_it1txSQ&^p7H-G(``b4_Y*isvty7G~l z5h(}HQoC*QV&bNlo{OKxhkP%KVittS!xH{fdY!L&UhyGwAyWorS17J@wKTZ>?d?6u zo>L2pPupsp+oO#b=nWbOq3*a-aMyLUxU(0_VBU?dEv{eS1oGf>0<6uyt~^2mL^o4^+Jr#sQU z>!mzz@zq>4C!=1o4i3# z;dKjtb}i)5V&57YL@6yaWf=zt-8F0AsefM*7`r1SgL~fmM_yS7GzB_A;vZ<)J+y|y z1QOO_l)=#BuusTS$Iw6I(&Ydjr5SmLs<$gKQ=4SFQGTrm&}Skd z2N2ijiaGb8g@w-7M1OMtWnAE**lv?b0r0aNln9o*y`2KrL9u~~mlBtw!Q5Qh7^YhmV)3)-~)^n!^PLXL-?xAsEW&noJ3R9H&yqqr?0F(3sdC8DeI@O1S&D zDutjL$~BOq8=GWD>3CwOn8!yB|#7ww}2TD#n4F@Y_%1pHpEap#X(_60PV_ZH)!?EnlSdG7UQfM zW0G2x*!?O#_#-av3w`7IC}9$|yC_%oxNMgk-X7G=#@Gj{jt=|U@wdhC#~p*|~Cw03q#Dsu^ip% z?}`F~$*bqCLl4q64-rHFWx!8?@HAHz51==q6=}yztqpjUP z#F9O-Jz8GH$6N3gDQufEO{(0;xSLjuoD0;-mdmSq&q)9mNTGAf;7lod`TetiLCLb> zcUAVdmTRy)pqAX#)SBF^CHW)#$9CZ9+_T%4xg+x^KZ;;?(+VDQO~p&cYK z$G(v|&@JTXxAFoCy$a8X2q?bM(tB7rv`fJ8?Z92M4nEQnlML~T4Cp2MrMNuJjMu!Q z%2cAI5cQQ`(q~)2{=zb^?#i%C4GX=I`e-Dp&^)CImQ*~QJ;_avXI$p*n>XjWuuMEU zd0o^dKKBD|+!B*t3VXv+gEpECAgF!b^Gi0%Vb+i&46 z?pHMz&RhYf5RvJ$qcRJ5n5`wdJG55|y1@{a)?3dMPQqezrL4M}*y+wM74Pv&K+*o~ zii61ItMBnlLCP!}3F+Zno?j0pk8TE?S|y;wV$V8!*DRxN3S)aA2B&<6HQZ)l2+irR zxeUDdJtu8@O4?t(FIo%LU1J|4+f;Scu2g@-3z)Y!AT81WmeEHaa*L>VIJZBiB+D@( z$0kv2zkV1#L>#w;(FM-`If4C-YR`=yzIgBcvTUXVEyPO|H;it5$;tReuJ|cgUtuu+ zcA*gdtl6!USnKH{ID7druC*Z;7V@0~Pvx+@_9=A=PooVfq#Isxs2oY^13n{KNkuqf zel(~KJ4Ccyfcu&WY*-w@@U7}M#)uq_gmD>XOOyQ<%#cBb{f~T$K zoBdkMq-L$Mr&+g%zpj5%Qhc9$($ASw7@5f0l*Ox?n^sFN`qRlePGe|Radt4v-@3ZZ zVHPSXb>)$P#|1ZwJ4c`9B&p13g6k7IjP)li2|68Mzp7$|a`cpD`|6V=5BLN;c1cU) zmZN)jC!CA>HQfaTGUVW-&48o6wZCftLxSdQrnf`C>=x&yp z2lmk{>T!9_Vlu&%&-X@HEMc8Wh%n(9=CI!lKJcQ(xsHV_4@Ue~lz61Dp1Z+~;mg{C z3&h5cStYxAW!apuT_fpuX#(W*P|;u*ec;*jN1V6+~Ah=XH}}35r0UAK5D>u`4|)bP%ys z7!*RL^GKY;gs^qJM-UKmK0IV0j#%7$dp}RNVDKaX%a*&X7BA@e-s;3+OQJE5zj$~v zU1g7c%`)=Uh6%8v>`-k0HH14C2tCO?^I)zB@@DFO?1Uq{F7j4g=ddYZL+ACowJ8zZ zIw5W}dr$UFfdke!xUD8iTth!y*V!V_%9!|g3mfSb{JME=WrQFi&7h`Y7%S~>Jxe_( zRk@r3XAtC_gJ(AYqFz#QycA!y3Kp&gX!sY|R*Z?imo_X4Q1xY5pM1!`nb;#;2sA38 ze5Gs1b;>5E|1uoJUz6(krh2VAh?FM`X1ihLJCWfL5E7K!I{wZMEO!2{T-pQ&NubhU z6u;KBWC=#K8C?ta%(%XE`H$M*zu(I(?9NoAtUvP=QO0~>AsJ-ruU3cNN9-4{D@2%9 z8zghu`>u82OFrD6ESq^-E?yGW9g=RDKf7bu;k}3vnrtd!q|7O9S98+=_780E$HuvW z&d+~MZ$U(!&Fj31BD8sDnlp^IsJ@BygBPSc=dRwf1+#M{25zf`qKxYgx|q%?+P=3h zOJpJw|GZpAA}k%P0-MLDGY#1L)zTtF<}eY@O<#5Lwdo1&)w+v9mZ zw3{E(WXCC9!wniH%hPw)O-2msKjcCXjDth2hWzPHv03|^bXg;hmXPS^F8*2PdiwC^ zo`%I^Z$m5fBqTo39dlS&vQNG(=O6-6z7&_!Uu|OurpvFkTiw@@Pisy(c(IFG6lVLguu-l60p^bmT z9=mDa>&%4Le7X_LFb~Bk*Wj~ND_JBM?#{iaG&7&}j3+AXT}OxHTMQVp7&u?le8v{N zezHJK+*jk;6F!QIXrzq0tf#4Y{nw1!CgCXkvGJkjp@4k)%Gb7h_ulLQfOd_iyfe5w z7g(G%UJ^s)G;-JPaow}Y=*?od`!ugz|XLb|&I7^2371Di1g zurqGU4HYL2#)oxOntxvDy9l9{PZy<2e@C5e`29gz`jbhcC#OQ1yu4&?Jxe#!^K6i! zUoXWat&XbeZM=Eqb2GmA!o)a#r`?x;LcgSvDf|1Pn2C*z$(rkMjPAB`Lvp}VKqb(% z^Rix0O=b<;%A6s)#mZ8*qwpoLs{Hw9*4$s$CSXK9bc%S~u=B_S zzJ{a2cB<%lQDrQz*vT*=M+>*+wBgG!b=b$*D-kPWQzI8MeDFabp2IiMtNNJ}3(J%U zo2z}R=>k7eRu_By`P=FY0mJVd{qBsP<(OJEq0^)Hj%L}Bac=lHIy14Msbk7|R}$WG zd{?bGnN4}Q8DmA&?tvFEq^God?oJT9<5+_)98hjjk_clPO)~LJsR+ z_uk!hd=88}G4Pn;@an$lCV(TyH5V|q1DDKrCF(+XFdLUp9Xb{XBrg`ssB02vXBDS1 z`#NuFNh!bmXXEm6J-QN6@#!!;bv~dw=GUvWm$3%-z4>c>Ak-Pc&vqY~PP`LeUhXu8 zJL`|UvxmS#l^B^Iud3u`oaK^k^B?)o`qttm6~p<}g)x8hiX#p3UaI05@R9!gyK!rq zs;?gC$QOnEoUyQC(G;fhn=7vHf&99OXkY!ir8)f8**lzXuqmU2{wJp5u|9ATB7*4} zDw7QMm475bN8)w0_K*9Z#SVVY0je^_wz8r)iF0$UZM!7#oI6DlCeGYkR>$=)afEfl zQ2wmqvb^0viy0)5Bz9mA<5?$x)2RvhvQ4?~~4a)UMFdEk6n-M(n z4D&CrH!g6S&bL_;qm=PM&(TW+*wsRfRx&-m6f4gMS7l~{B-D{SxGYIF(pefDaY&&`}klyUw+cJ4(#Ij*qqc zIUsr4u^+w^-CJweVXRrk3|^5T;!%s>Dmh?vuP;gzW0g4S`V& zd?-@aPqiXcLW-*TOBO$Tva|C9cozLN;7U-w zZzb2|!JnRptL+r3R~6oSCLDh(9EeFS4tCAlDZ21>;YNZtw({Aesd}w>t7s;q zOo~Fx@X(h5>bby26oJ^be$*38eoQZt!Fl_1E1{GGao{Z$h4~gg=2GYUS485YHVxoB zF+uViw{!8)kkMI)E5!IU4JW$*SEo_a%1)^VX?>Zj^HN&=HR51F3*6ZS^V--R=Y62P z42AD9R0pR#{Fa>w;rzk4pEt%(Yn9|S6QK~H1Owp~t8Eg@l6XjbjUvZZrU*2JXK37_ z|JXhaxI{LXhCS$d=D?!nJkZqJII=p#nmO)N`Xe>T26xZ0dabjs6L>)PVfR?rd{aE_ zRX5^wMA~vp>HThaMZNF~E(_X$vxKM6wP7PPIskU!(~?bE^`5idInCmky=6isH(fSK zsIA8^k4JeI8{UnUq%6=nrEuic>*oVxloR7A%Xx0y@VKXgMp1n{wa4+~l21D=n-gvO zRGAUVUO95b!Fx-)AqnY`n_NbrBg4*r&-P`PZ1PqM3;-A2P?`}gqqVWUo~3g7>^jo= zInR@20gEr!ickVnLYswCACm}H&f$KPm<@%K-b6~YVarqLZrOz4fkf^OHMFlI(2$mC zQTsesfYsKghfunuGBz#3OW<3(cJXv+rP1s?@GN0MLSt?{O=x5Mtrmgvl^q2oN&=%nm{VXHx%>m-&JU#vo?>s z{_0bWj+3u~Sr>KrUZ@&C3u2<@+>gpW*Z~4%TWH^-$ob?f^9}TNrz#|TBgTfG$fYXi zqV3LT|Mn{Lmy3{XqdW6r6dlH>A~DtD?EUh&BvTNCg4td%l}1qJ*q>If-iKakfi$l_ z?j(EDb+X1o`71n9_)nj!7&iFedt)bs&c?SS8zmKT!&Qd}LCmLb=`YNIoybDJ2>Q4x zU&2Uz`A83ww<34_rc8?fk=jH$;?|x5Zi^MdbDveG-8AvWphGrgFMGy%sh&58E`RRo zH+zZSDThoHn|c1|inWBVFA4xx|5&+!Gen;8M3#t&`Pu>B9S-aabWw#r0s2nzSk?e4 zn3DmJm;}J@WP`vn2M9dNZ~uS#7wZH?ddQk`%bK#un({!|)lpV^^LN3s;{BlztHQP} zG0cHADP<+Kb3RAy#LG_X3e;)>eOtRmDAWTS4+VMugHsMlJgTM0xtl&_?fJGos=ZS? z3nUWcasNV+)XM62{xdpg8NxmpK|y6M#;-j<6bn2Kfw6}tQK83VO{+y-{M3rdJm(sw z1>zEDUx3IW{&!l=zpXrMgC^bb6-Y0j9)XA=p2&SS25Ksftt4(7aF?xIV^?DrfbbxY z-zA9i?a^kCUnVT-7A>)FKfVDe2?ae~RYs)g{I3fpY3D47Ra-`ts&+QZxe9|qeE={{ zJ4+$Xh@W1>n78t9oD(pD8mOV$hjY4z)hC7^f|T^wq;J&WNI;89koW)^l!h05V*e2A z4nK!XzO!7BKj$=bqOcxm91+;d1jv8dhA^Ywls;5&P!qNJhHhy|4swBluh$qG`Usq~ z;{}Pj5D*kok1NOPMrG9{02I#okU!14l)aoNm3lBo;^e*qaIIiZMBYD@HI(e;22erA zpyL9CHF3!I5?CDP0IhM<0iKw z+$#FVzy3xj=Bg`$$-lL(f0*QkI2MWyaUpMVx5z>BfF9p#<`~n;h!WC{+sG|JRDeKQ>kJQ)VHdGqPCMxSIRpEFcBPSBV>fQ|e-<(TtFIl-?U z0p1x-0TjfST8;+1BK0o;l0i?z8&&W~G2jw&Eh;?#jdKJ->tJ-jVL?AVu}R6gDr^3c^e9 zjQMtcAcl%GRKDpbn&l&2Cxhlg$Uo^}g)nlwK<75#;Zi;+Zrf4kZ);fy4Ggf=sBKN7 z*t0&2GKGko({lj`@+UGAW4F`CPc-&9@oK9+u~YwWd7kiE*L=r3zDY8UJ}LwB8_$BV zi|6m7J{pBgO-k@OF4YC{hvm{EpqR|(p?MNuLIrcOuusV*O2^O0W}x)U U`k$iwK{^=Fy>6sgrjCyMFUTa+82|tP literal 7361 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 diff --git a/public/images/educoder/xcx/ZYIDCard.png b/public/images/educoder/xcx/ZYIDCard.png index 7f2085fce564fdcc67cd6392fd7e8063321db867..6edb41dcde205363994ca58405a96dbde83eecd7 100644 GIT binary patch literal 6001 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 Date: Tue, 14 Jan 2020 16:52:03 +0800 Subject: [PATCH 075/204] 1 --- db/migrate/20200114040211_add_wechar_support_for_shixuns.rb | 5 +++++ lib/tasks/statistic_subject_info.rake | 2 +- 2 files changed, 6 insertions(+), 1 deletion(-) create mode 100644 db/migrate/20200114040211_add_wechar_support_for_shixuns.rb diff --git a/db/migrate/20200114040211_add_wechar_support_for_shixuns.rb b/db/migrate/20200114040211_add_wechar_support_for_shixuns.rb new file mode 100644 index 000000000..9d82add97 --- /dev/null +++ b/db/migrate/20200114040211_add_wechar_support_for_shixuns.rb @@ -0,0 +1,5 @@ +class AddWecharSupportForShixuns < ActiveRecord::Migration[5.2] + def change + add_column :shixuns, :is_wechat_support, :boolean, :default => false + end +end diff --git a/lib/tasks/statistic_subject_info.rake b/lib/tasks/statistic_subject_info.rake index 0385e3b5a..d9591c065 100644 --- a/lib/tasks/statistic_subject_info.rake +++ b/lib/tasks/statistic_subject_info.rake @@ -117,7 +117,7 @@ namespace :subjects do task user_info_statistic: :environment do puts("---------------------user_info_statistic_begin") Rails.logger.info("---------------------user_info_statistic_begin") - subjects = Subject.where(status: 2) + subjects = Subject.where(status: 2, id: 211) str = "" buffer_size = 0 column_value = "user_id, subject_id, username, passed_myshixun_count, passed_games_count, " + From 841968d7412b02b7935497a5da9cd6b985b80700 Mon Sep 17 00:00:00 2001 From: tangjiang <465264938@qq.com> Date: Tue, 14 Jan 2020 17:04:57 +0800 Subject: [PATCH 076/204] finish static pages --- public/react/package.json | 2 - .../modules/paths/statics/DisplayTableData.js | 109 +++--- .../react/src/modules/paths/statics/index.js | 326 +++++++++++++----- .../src/modules/paths/statics/index.scss | 95 +++-- .../src/modules/paths/statics/mockData.js | 10 +- public/react/src/redux/actions/actionTypes.js | 6 +- public/react/src/redux/actions/index.js | 12 +- public/react/src/redux/actions/static.js | 41 +++ public/react/src/redux/reducers/index.js | 4 +- .../react/src/redux/reducers/staticReducer.js | 69 ++++ public/react/src/services/staticService.js | 14 + 11 files changed, 509 insertions(+), 179 deletions(-) create mode 100644 public/react/src/redux/actions/static.js create mode 100644 public/react/src/redux/reducers/staticReducer.js create mode 100644 public/react/src/services/staticService.js diff --git a/public/react/package.json b/public/react/package.json index 771c6257f..bf0b5cce0 100644 --- a/public/react/package.json +++ b/public/react/package.json @@ -7,7 +7,6 @@ "@monaco-editor/react": "^2.3.0", "@novnc/novnc": "^1.1.0", "antd": "^3.23.2", - "antd-table-infinity": "^1.1.3", "array-flatten": "^2.1.2", "autoprefixer": "7.1.6", "axios": "^0.18.0", @@ -79,7 +78,6 @@ "react-dev-utils": "^5.0.0", "react-dom": "^16.9.0", "react-hot-loader": "^4.0.0", - "react-infinite-scroller": "^1.2.4", "react-loadable": "^5.3.1", "react-monaco-editor": "^0.25.1", "react-player": "^1.11.1", diff --git a/public/react/src/modules/paths/statics/DisplayTableData.js b/public/react/src/modules/paths/statics/DisplayTableData.js index 15f892535..f59dd719d 100644 --- a/public/react/src/modules/paths/statics/DisplayTableData.js +++ b/public/react/src/modules/paths/statics/DisplayTableData.js @@ -1,69 +1,80 @@ /* - * @Description: 展示表格数据 + * @Description: * @Author: tangjiang * @Github: - * @Date: 2020-01-10 13:46:30 + * @Date: 2020-01-14 13:39:12 * @LastEditors : tangjiang - * @LastEditTime : 2020-01-11 17:35:03 + * @LastEditTime : 2020-01-14 16:30:05 */ -import 'antd-table-infinity/dist/index.css'; -import 'antd-table-infinity/index.css'; import './index.scss'; -import React, { useState, useEffect } from 'react'; -import { Spin } from 'antd'; -// import {SumTable as Table} from 'antd-table-infinity'; -import { SumTable as Table } from 'antd-table-infinity'; -import { columns, fetchData, sumData } from './mockData'; +import React, { useRef, useState, useEffect } from 'react'; +import { Table } from 'antd'; +import ReactDom from 'react-dom'; -const DisplayTableData = ({ - // columns = [], - // datas, - // fetchData -}) => { - - const [data, setData] = useState([]); +const DisplayTableData = (props) => { + const {columns, datas, fetchData, total} = props; + let tableEl = useRef(null); const [loading, setLoading] = useState(false); - const handleFetchData = () => { - setLoading(true); - fetchData(data.length).then(newData => { - setLoading(false); - const _data = data.concat(newData); - setData(_data); - }) + const renderFooter = (obj = {}) => { + const {course_count, student_count, choice_shixun_num, choice_shixun_frequency, total} = obj; + if (!obj) return '' + else { + return ( +
      +
    • 总计
    • +
    • {total || '-'}
    • +
    • {course_count || '-'}
    • +
    • {student_count || '-'}
    • +
    • {choice_shixun_num || '-'}
    • +
    • {choice_shixun_frequency || '-'}
    • +
    + ) + } } + useEffect(() => { - handleFetchData(); + const table = ReactDom.findDOMNode(tableEl); + // console.log(table); + const tableBody = table.querySelector('.ant-table-body'); + let _scrollTop = 0;//保存上次滚动距离 + let isRun = false;//是否执行查询 + tableBody.addEventListener('scroll', () => { + if(tableBody.scrollTop === 0 ){ + _scrollTop = 0; + } + // 上一次滚动高度与当前滚动高度不同则是纵向滚动 + if (_scrollTop !== tableBody.scrollTop) { + //是否滑动到距离底部40px的位置 + const scorll = _scrollTop >= tableBody.scrollHeight-tableBody.clientHeight-40; + //isRun为true时 代表已经执行查询 + if(isRun && scorll){ + return; + } + //_scrollTop < tableBody.scrollTop 判断是否向下滑动 + isRun = _scrollTop < tableBody.scrollTop && scorll; + //保存当前滚动位置 + _scrollTop = tableBody.scrollTop; + if (isRun) { + fetchData && fetchData(); + } + } + }) }, []); - const loadMoreContent = () => ( -
    - -
    - ); return (

    a~@HaLuV}Y6p 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 z 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

    record.id} columns={columns} - sumData={sumData} - scroll={{ y: 500 }} - dataSource={data} - // bordered - // debug + dataSource={datas} + pagination={false} + loading={loading} + scroll={{y: 500}} + ref={(ref)=>tableEl=ref} + footer={total ? () => renderFooter(total) : ''} /> ); } -export default DisplayTableData; +export default DisplayTableData; \ No newline at end of file diff --git a/public/react/src/modules/paths/statics/index.js b/public/react/src/modules/paths/statics/index.js index 1b13500f0..37cc44df3 100644 --- a/public/react/src/modules/paths/statics/index.js +++ b/public/react/src/modules/paths/statics/index.js @@ -4,102 +4,240 @@ * @Github: * @Date: 2020-01-10 09:33:45 * @LastEditors : tangjiang - * @LastEditTime : 2020-01-11 17:06:56 + * @LastEditTime : 2020-01-14 17:01:32 */ import './index.scss'; -import React, { useState } from 'react'; +import React, { useEffect } from 'react'; import StaticNumberAndTxt from './StaticNumberAndTxt'; import DisplayTableData from './DisplayTableData'; -import { Table, Tabs } from 'antd'; +import { Tabs, Tooltip } from 'antd'; +import { connect } from 'react-redux'; +import moment from 'moment'; +import actions from '../../../redux/actions'; const { TabPane } = Tabs; -const App = () => { +const App = (props) => { - // const datas = [ - // { - // key: '1', - // id: 1, - // id2: '', - // id3: '', - // id4: '', - // id5: '', - // id6: '' - // }, - // { - // key: '2', - // id: 2, - // id2: '', - // id3: '', - // id4: '', - // id5: '', - // id6: '' - // }, - // { - // key: '3', - // id: 3, - // id2: '', - // id3: '', - // id4: '', - // id5: '', - // id6: '' - // }, - // { - // key: '4', - // id: 4, - // id2: '', - // id3: '', - // id4: '', - // id5: '', - // id6: '' - // } - // ]; - const [datas, setDatas] = useState([]); + const { + subject_info, + other_info, + total, + staticList, + changeParams, + initTotal + } = props; + // const [datas, setDatas] = useState([]); + // const [sortedInfo, setSortedInfo] = useState({}); + // console.log(props); + const {pathId} = props.match.params; const columns = [ { title: '序号', - id: 'id', - //align: 'center', - width: 100 + dataIndex: 'id', + key: 'id', + render: (text, record, i) => i + 1, + width: 100, + align: 'center' }, { title: '使用单位', - id: 'id2', - //align: 'center', - flexGrow: 1 + // key: 'school_name', + dataIndex: 'school_name', + // width: 300, + className: 'overflow_hidden', + align: 'center' }, { - title: '使用课堂/个', - id: 'id3', - //align: 'center', - flexGrow: 1, - sortable: true + // title: '使用课堂/个', + title: () => (使用课堂), + // key: 'course_count', + width: 150, + dataIndex: 'course_count', + align: 'center', + sorter: (a, b) => a.course_count - b.course_count, + // sortOrder: sortedInfo.columnKey === 'age' && sortedInfo.order + // sorter: (a, b) => true, + // sorter: (a, b) => a.age - b.age }, { - title: '课堂实训/个', - id: 'id4', - //align: 'center', - flexGrow: 1, - sortable: true + title: () => (课堂学生), + // key: 'student_count', + width:150, + dataIndex: 'student_count', + align: 'center', + sorter: (a, b) => a.student_count - b.student_count, + // sorter: (a, b) => a.age - b.age }, { - title: '选用实训/个', - id: 'id5', - //align: 'center', - flexGrow: 1, - sortable: true + title: () => (选用实训/个), + width: 150, + // key: 'choice_shixun_num', + dataIndex: 'choice_shixun_num', + align: 'center', + sorter: (a, b) => a.choice_shixun_num - b.choice_shixun_num, + // sorter: (a, b) => a.age - b.age }, { - title: '选用实训/次', - id: 'id6', - //align: 'center', - flexGrow: 1, - sortable: true + title: () => (选用实训/次), + width: 150, + // key: 'choice_shixun_frequency', + dataIndex: 'choice_shixun_frequency', + align: 'center', + sorter: (a, b) => a.choice_shixun_frequency - b.choice_shixun_frequency, + // sorter: (a, b) => a.bbb - b.bbb + } + ]; + const sxColumns = [ + { + title: '序号', + dataIndex: 'id', + render: (text, record, i) => i + 1, + width: 60, + align: 'center' + }, { + title: '章节', + dataIndex: 'stage', + width: 80, + align: 'center' + }, + { + title: '实训名称', + dataIndex: 'shixun_name', + align: 'center', + // ellipsis: true + }, + { + title: '关卡数', + dataIndex: 'challenge_count', + width: 100, + align: 'center' + }, + { + title: '使用课堂', + dataIndex: 'course_count', + width: 110, + align: 'center', + sorter: (a, b) => a.course_count - b.course_count + }, + { + title: '使用单位', + dataIndex: 'school_count', + width: 110, + align: 'center', + sorter: (a, b) => a.school_count - b.school_count + }, + { + title: '使用人数', + dataIndex: 'used_count', + width: 110, + align: 'center', + sorter: (a, b) => a.used_count - b.used_count + }, + { + title: '通关人数', + dataIndex: 'passed_count', + width: 110, + align: 'center', + sorter: (a, b) => a.passed_count - b.passed_count + }, + { + title: '评测次数', + dataIndex: 'evaluate_count', + width: 110, + align: 'center', + sorter: (a, b) => a.evaluate_count - b.evaluate_count + }, + { + title: '通关平均时间', + dataIndex: 'passed_ave_time', + width: 140, + align: 'center', + render: (text) => (text && moment(text).format('HH:mm:ss')) || '-', + sorter: (a, b) => a.passed_ave_time - b.passed_ave_time + } + ]; + const stColumns = [ + { + title: '序号', + dataIndex: 'id', + render: (text, record, i) => i + 1, + width: 60, + align: 'center' + }, + { + title: '姓名', + dataIndex: 'username', + align: 'center' + }, + { + title: '通关实训数', + dataIndex: 'passed_myshixun_count', + align: 'center', + sorter: (a, b) => a.passed_myshixun_count - b.passed_myshixun_count + }, + { + title: '完成关卡', + dataIndex: 'passed_games_count', + align: 'center', + sorter: (a, b) => a.passed_games_count - b.passed_games_count + }, + { + title: '代码行', + dataIndex: 'code_line_count', + align: 'center', + sorter: (a, b) => a.code_line_count - b.code_line_count + }, + { + title: '评测次数', + dataIndex: 'evaluate_count', + align: 'center', + sorter: (a, b) => a.evaluate_count - b.evaluate_count + }, + { + title: '所用时间', + dataIndex: 'cost_time', + align: 'center', + render: (text) => (text && moment(text).format('HH:mm:ss')) || '-', + sorter: (a, b) => a.cost_time - b.cost_time } ]; - + useEffect(() => { + changeParams({ + page: 1 + }); + pathId && staticList(pathId); + }, []); const handleFetchData = () => { + pathId && staticList(pathId); + } + + const { + study_count, + course_study_count, + initiative_study, + passed_count, + course_used_count, + school_used_count + } = subject_info; + + const maps = { + 1: 'subject_info', // 实践课程使用情况 + 2: 'shixun_info', // 实训使用情况 + 3: 'user_info' // 用户使用情况 + }; + const handleTabChange = (key) => { + const type = maps[+key]; + // console.log(type); + const params = { + page: 1, + type: type + } + // 恢复初始值 + changeParams(params); + initTotal(); + pathId && staticList(pathId); } return ( @@ -113,57 +251,60 @@ const App = () => {
    - + @@ -176,4 +317,23 @@ const App = () => { ); } -export default App; +const mapStateToProps = (state) => { + const { staticReducer: {subject_info, other_info, total} } = state; + return { + subject_info, + other_info, + total + } +}; + +const mapDispatchToProps = (dispatch) => ({ + staticList: (id) => dispatch(actions.staticList(id)), + changeParams: (params) => dispatch(actions.changeParams(params)), + initTotal: () => dispatch(actions.initTotal()) +}); + +export default connect( + mapStateToProps, + mapDispatchToProps +)(App); +// export default App; diff --git a/public/react/src/modules/paths/statics/index.scss b/public/react/src/modules/paths/statics/index.scss index 945fa2740..33c65136a 100644 --- a/public/react/src/modules/paths/statics/index.scss +++ b/public/react/src/modules/paths/statics/index.scss @@ -81,51 +81,72 @@ } } } - .statc_table{ + // .static_table{ + // // .ant-table-header{ + // // overflow: hidden !important; + // // margin-bottom: 0px !important; + // // } + // // .ant-table-row-cell-break-word{ + // // background: rgba(241,248,255,1) !important; + // // } + + // // .overflow_hidden{ + // // max-width: 280px; + // // overflow: hidden; + // // text-overflow:ellipsis; + // // white-space: nowrap; + // // } + // } + .static_table{ .ant-table-header{ - overflow-x: hidden !important; margin-bottom: 0px !important; - // border-bottom: 2px solid rgba(241,248,255,1); - // background: green; + overflow: hidden !important; } - // .ant-table-footer .ant-table-content{ - // border-top: 1px solid #e8e8e8; - // box-sizing: border-box; - // } - - .overflow_hidden{ - max-width: 300px; - overflow: hidden; - text-overflow:ellipsis; - white-space: nowrap; + .ant-table-thead{ + th{ + background: rgba(241,248,255,1); + + } + .ant-table-column-title{ + color: #303133; + font-weight: bold; + } } - table th, - table td{ - line-height: 1; - padding: 15px 0 + .ant-table-tbody tr:nth-child(2n) { + td{ + background: rgba(241,248,255,.4); + } } - table th{ - background: rgba(241,248,255,1); + .ant-table-tbody tr td{ + color: #303133; } + } - table tr:nth-child(2n) td{ - background: rgba(241,248,255,.4); - } + .ant-table-footer{ + background-color: rgba(241,248,255,1); + padding: 16px 0px; + } + .footer_list{ + display: flex; + // background: #fff; + box-sizing: border-box; + text-align: center; - // .ant-table-thead>tr>th .ant-table-column-sorters:before{ - // background: rgba(241,248,255,1); - // } - .ant-table-thead>tr>th .ant-table-column-sorters:before { - position: absolute; - content: ""; - top: 0; - left: 0; - right: 0; - bottom: 0; - background: rgba(241,248,255,1); - -webkit-transition: all .3s; - -o-transition: all .3s; - transition: all .3s; + li{ + color: #303133; + } + // border-top: 1px solid green; + .footer_item{ + width: 150px; + } + .footer_item:not(:first-child) { + padding-right: 10px; + } + .footer-total{ + width: 100px; + } + .footer_name{ + flex: 1; } } } diff --git a/public/react/src/modules/paths/statics/mockData.js b/public/react/src/modules/paths/statics/mockData.js index 54d34a3ff..693bb051c 100644 --- a/public/react/src/modules/paths/statics/mockData.js +++ b/public/react/src/modules/paths/statics/mockData.js @@ -4,7 +4,7 @@ * @Github: * @Date: 2020-01-11 10:55:33 * @LastEditors : tangjiang - * @LastEditTime : 2020-01-11 17:48:02 + * @LastEditTime : 2020-01-14 09:11:36 */ import { random } from 'lodash'; @@ -59,28 +59,28 @@ const columns = [ width: 200, dataIndex: 'age', align: 'center', - sorter: (a, b) => a.age - b.age + // sorter: (a, b) => a.age - b.age }, { title: '课堂学生/个', width: 200, dataIndex: 'address', align: 'center', - sorter: (a, b) => a.age - b.age + // sorter: (a, b) => a.age - b.age }, { title: '选用实训/个', width: 200, dataIndex: 'address2', align: 'center', - sorter: (a, b) => a.age - b.age + // sorter: (a, b) => a.age - b.age }, { title: '选用实训/个', width: 200, dataIndex: 'bbb', align: 'center', - sorter: (a, b) => a.bbb - b.bbb + // sorter: (a, b) => a.bbb - b.bbb } ]; diff --git a/public/react/src/redux/actions/actionTypes.js b/public/react/src/redux/actions/actionTypes.js index efe3ff35c..e3c2f65a9 100644 --- a/public/react/src/redux/actions/actionTypes.js +++ b/public/react/src/redux/actions/actionTypes.js @@ -88,7 +88,11 @@ const types = { CHANGE_COMMENT_PAGINATION_PARAMS: 'CHANGE_COMMENT_PAGINATION_PARAMS', // 改变分页 /** tpi */ SHOW_OR_HIDE_TPI_TEST_CASE: 'SHOW_OR_HIDE_TPI_TEST_CASE', // 显示或隐藏tpi测试集弹框 - IS_COLLAPSE_TEST_CASE: 'IS_COLLAPSE_TEST_CASE' // 是否展开测试集 + IS_COLLAPSE_TEST_CASE: 'IS_COLLAPSE_TEST_CASE', // 是否展开测试集 + /** 统计 */ + GET_STATIC_INFO: 'GET_STATIC_INFO', + CHANGE_STATIC_PARAMS: 'CHANGE_STATIC_PARAMS', + CHANGE_STATIC_TOTAL: 'CHANGE_STATIC_TOTAL' } export default types; diff --git a/public/react/src/redux/actions/index.js b/public/react/src/redux/actions/index.js index 0376b529d..f7b7a41d9 100644 --- a/public/react/src/redux/actions/index.js +++ b/public/react/src/redux/actions/index.js @@ -103,6 +103,12 @@ import { isCollpaseTsetCase } from './tpi'; +import { + staticList, + changeParams, + initTotal +} from './static'; + export default { toggleTodo, getOJList, @@ -181,5 +187,9 @@ export default { changePagination, // tpi showOrHideTpiTestCase, - isCollpaseTsetCase + isCollpaseTsetCase, + // 统计 + staticList, + changeParams, + initTotal } \ No newline at end of file diff --git a/public/react/src/redux/actions/static.js b/public/react/src/redux/actions/static.js new file mode 100644 index 000000000..3159d35c2 --- /dev/null +++ b/public/react/src/redux/actions/static.js @@ -0,0 +1,41 @@ +/* + * @Description: + * @Author: tangjiang + * @Github: + * @Date: 2020-01-14 09:44:02 + * @LastEditors : tangjiang + * @LastEditTime : 2020-01-14 17:02:45 + */ +import types from "./actionTypes"; +import { fetchStaticList } from "../../services/staticService"; + +export const staticList = (id) => { + return (dispatch, getState) => { + const { params, total_count, other_info } = getState().staticReducer; + + if (total_count !== 0 && total_count === other_info.length) return; + fetchStaticList(id, params).then(res => { + // console.log('统计数据=====>>>>>', res); + const {data} = res; + if (data.status === 0) { + dispatch({ + type: types.GET_STATIC_INFO, + payload: data.data + }); + } + }); + } +}; + +export const changeParams = (params) => { + return { + type: types.CHANGE_STATIC_PARAMS, + payload: params + } +} + +export const initTotal = () => { + return { + type: types.CHANGE_STATIC_TOTAL + } +} diff --git a/public/react/src/redux/reducers/index.js b/public/react/src/redux/reducers/index.js index 7c9601d52..6506cf584 100644 --- a/public/react/src/redux/reducers/index.js +++ b/public/react/src/redux/reducers/index.js @@ -16,6 +16,7 @@ import userReducer from './userReducer'; import jupyterReducer from './jupyterReducer'; import commentReducer from './commentReducer'; import tpiReducer from './tpiReducer'; +import staticReducer from './staticReducer'; export default combineReducers({ testReducer, @@ -26,5 +27,6 @@ export default combineReducers({ userReducer, jupyterReducer, commentReducer, - tpiReducer + tpiReducer, + staticReducer }); diff --git a/public/react/src/redux/reducers/staticReducer.js b/public/react/src/redux/reducers/staticReducer.js new file mode 100644 index 000000000..7d2202d03 --- /dev/null +++ b/public/react/src/redux/reducers/staticReducer.js @@ -0,0 +1,69 @@ +/* + * @Description: 统计 + * @Author: tangjiang + * @Github: + * @Date: 2020-01-14 09:34:49 + * @LastEditors : tangjiang + * @LastEditTime : 2020-01-14 15:49:55 + */ +import types from "../actions/actionTypes"; + +// const maps = { +// 1: 'shixun_info', // 实训使用情况 +// 2: 'user_info', // 用户使用情况 +// 3: 'subject_info' // 实践课程使用情况 +// } +const initalState = { + subject_info: {}, + other_info: [], + total_count: 0, + total: {}, + params: { + // sort_by: '', + // sort_direction: 'desc', // desc || asc + limit: 20, // 一页多少条 + page: 1, // 第几页 + type: 'subject_info' // 类型: 实训 shixun_info, + } +}; + +// const getGuid = () => +// 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, c => { +// /* eslint-disable */ +// let r = (Math.random() * 16) | 0, +// v = c == 'x' ? r : (r & 0x3) | 0x8; +// return v.toString(16); +// }); + +const staticReducer = (state = initalState, action) => { + const { payload = {}, type } = action; + const {subject_info, other_info = [], total = {}, total_count} = payload; + switch (type) { + case types.GET_STATIC_INFO: + return { + ...state, + subject_info, + other_info: state.other_info.concat(other_info), + total, + total_count, + params: Object.assign({}, state.params, { page: state.params.page + 1 }) + } + case types.CHANGE_STATIC_PARAMS: { + return { + ...state, + params: Object.assign({}, state.params, payload) + }; + } + case types.CHANGE_STATIC_TOTAL: { + return { + ...state, + other_info: [], + total: {} + } + } + default: + return state; + } +} + +export default staticReducer; diff --git a/public/react/src/services/staticService.js b/public/react/src/services/staticService.js new file mode 100644 index 000000000..23e4f1b93 --- /dev/null +++ b/public/react/src/services/staticService.js @@ -0,0 +1,14 @@ +import axios from "axios"; + +/* + * @Description: + * @Author: tangjiang + * @Github: + * @Date: 2020-01-14 09:40:53 + * @LastEditors : tangjiang + * @LastEditTime : 2020-01-14 10:47:19 + */ +export async function fetchStaticList (id, params) { + const url = `/paths/${id}/statistics_info.json`; + return axios.get(url, { params }); +} From 9857ad869c3453c5eca7e927cc91970f96159125 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 17:11:37 +0800 Subject: [PATCH 077/204] 1 --- app/services/subjects/user_used_info_service.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/services/subjects/user_used_info_service.rb b/app/services/subjects/user_used_info_service.rb index 3b1b969f0..52d6be005 100644 --- a/app/services/subjects/user_used_info_service.rb +++ b/app/services/subjects/user_used_info_service.rb @@ -10,7 +10,7 @@ class Subjects::UserUsedInfoService < ApplicationService def call users_info = [] users = User.includes(myshixuns: :games).where(myshixuns: {shixun_id: shixun_ids}, games: {status: 2}) - users.each do |user| + users.find_each do |user| myshixuns = user.myshixuns.select{|m| shixun_ids.include?(m.shixun_id)} name = "#{user.lastname}#{user.firstname}" passed_myshixun_count = myshixuns.select{|m| m.status == 1}.size From a259a4625684c20732eb48bf00e53bf5cc54a6c3 Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 17:21:00 +0800 Subject: [PATCH 078/204] 1 --- lib/tasks/statistic_subject_info.rake | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/tasks/statistic_subject_info.rake b/lib/tasks/statistic_subject_info.rake index d9591c065..0385e3b5a 100644 --- a/lib/tasks/statistic_subject_info.rake +++ b/lib/tasks/statistic_subject_info.rake @@ -117,7 +117,7 @@ namespace :subjects do task user_info_statistic: :environment do puts("---------------------user_info_statistic_begin") Rails.logger.info("---------------------user_info_statistic_begin") - subjects = Subject.where(status: 2, id: 211) + subjects = Subject.where(status: 2) str = "" buffer_size = 0 column_value = "user_id, subject_id, username, passed_myshixun_count, passed_games_count, " + From 146c9a0f78e52fa50e305ce5a90831b8f3d90153 Mon Sep 17 00:00:00 2001 From: cxt <853663049@qq.com> Date: Tue, 14 Jan 2020 17:56:47 +0800 Subject: [PATCH 079/204] =?UTF-8?q?=E4=BD=9C=E4=B8=9A=E7=9A=84=E5=8F=91?= =?UTF-8?q?=E5=B8=83?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/homework_commons_controller.rb | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/app/controllers/homework_commons_controller.rb b/app/controllers/homework_commons_controller.rb index 96a73b08b..db8c688ad 100644 --- a/app/controllers/homework_commons_controller.rb +++ b/app/controllers/homework_commons_controller.rb @@ -909,7 +909,7 @@ class HomeworkCommonsController < ApplicationController def publish_homework tip_exception("请至少选择一个分班") if params[:group_ids].blank? && @course.course_groups.size != 0 - group_ids = params[:group_ids]&.reject(&:blank?) + group_ids = params[:group_ids]&.reject(&:blank?).map(&:to_i) if params[:detail].blank? tip_exception("缺少截止时间参数") if params[:end_time].blank? tip_exception("截止时间不能早于当前时间") if params[:end_time] <= strf_time(Time.now) @@ -1048,7 +1048,8 @@ class HomeworkCommonsController < ApplicationController homeworks = homeworks.published_no_end.includes(:homework_group_settings, :homework_detail_manual, :homework_challenge_settings) course_students = @course.students charge_group_ids = @course.charge_group_ids(current_user) - end_groups = charge_group_ids & params[:group_ids] if params[:group_ids] + group_ids = params[:group_ids]&.reject(&:blank?).map(&:to_i) + end_groups = charge_group_ids & group_ids if group_ids begin homeworks.each do |homework| From d716172ba0df62accdd1de85c242d931d965587c Mon Sep 17 00:00:00 2001 From: daiao <358551898@qq.com> Date: Tue, 14 Jan 2020 17:56:57 +0800 Subject: [PATCH 080/204] =?UTF-8?q?=E5=B0=8F=E7=A8=8B=E5=BA=8F=E5=8F=AF?= =?UTF-8?q?=E7=94=A8=E7=9A=84=E5=AE=9E=E8=AE=AD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- app/controllers/admins/shixun_settings_controller.rb | 6 ++++-- app/views/admins/shixun_settings/shared/_list.html.erb | 2 +- app/views/admins/shixun_settings/shared/_td.html.erb | 1 + 3 files changed, 6 insertions(+), 3 deletions(-) diff --git a/app/controllers/admins/shixun_settings_controller.rb b/app/controllers/admins/shixun_settings_controller.rb index 37ca45674..2f139279b 100644 --- a/app/controllers/admins/shixun_settings_controller.rb +++ b/app/controllers/admins/shixun_settings_controller.rb @@ -17,7 +17,8 @@ class Admins::ShixunSettingsController < Admins::BaseController homepage_show: params[:homepage_show].present? ? params[:homepage_show] : false, task_pass: params[:task_pass].present? ? params[:task_pass] : false, code_hidden: params[:code_hidden].present? ? params[:code_hidden] : false, - vip: params[:vip].present? ? params[:vip] : false + vip: params[:vip].present? ? params[:vip] : false, + is_wechat_support: params[:is_wechat_support].present? ? params[:is_wechat_support] : false } @shixuns_type_check = MirrorRepository.pluck(:type_name,:id) @@ -131,6 +132,7 @@ class Admins::ShixunSettingsController < Admins::BaseController end def setting_params - params.permit(:use_scope,:excute_time,:close,:status,:can_copy,:webssh,:hidden,:homepage_show,:task_pass,:code_hidden,:vip,:page_no,:id,tag_repertoires:[]) + params.permit(:use_scope,:excute_time,:close,:status,:can_copy,:webssh,:hidden,:homepage_show,:task_pass, + :code_hidden,:vip,:page_no,:id, :is_wechat_support, tag_repertoires:[]) end end diff --git a/app/views/admins/shixun_settings/shared/_list.html.erb b/app/views/admins/shixun_settings/shared/_list.html.erb index 549c7edf4..b02fc420c 100644 --- a/app/views/admins/shixun_settings/shared/_list.html.erb +++ b/app/views/admins/shixun_settings/shared/_list.html.erb @@ -15,7 +15,7 @@
    diff --git a/app/views/admins/shixun_settings/shared/_td.html.erb b/app/views/admins/shixun_settings/shared/_td.html.erb index fc5af645a..a77cc40fa 100644 --- a/app/views/admins/shixun_settings/shared/_td.html.erb +++ b/app/views/admins/shixun_settings/shared/_td.html.erb @@ -49,6 +49,7 @@ <%= check_box_tag :task_pass,!shixun.task_pass,shixun.task_pass,remote:true,data:{id:shixun.id,toggle:"tooltip",placement:"top"},class:"shixun-setting-form" ,title:"跳关"%> <%= check_box_tag :code_hidden,!shixun.code_hidden,shixun.code_hidden,remote:true,data:{id:shixun.id,toggle:"tooltip",placement:"top"},class:"shixun-setting-form" ,title:"隐藏目录"%> <%= check_box_tag :vip,!shixun.vip,shixun.vip,remote:true,data:{id:shixun.id,toggle:"tooltip",placement:"top"},class:"shixun-setting-form" ,title:"vip"%> + <%= check_box_tag :is_wechat_support,!shixun.is_wechat_support?,shixun.is_wechat_support?,remote:true,data:{id:shixun.id,toggle:"tooltip",placement:"top"},class:"shixun-setting-form" ,title:"小程序可用"%>
    操作
    - ssh/隐藏/首页/跳关/隐藏目录/vip + ssh/隐藏/首页/跳关/隐藏目录/vip/小程序