diff --git a/packages/hydrooj/package.json b/packages/hydrooj/package.json index cd3308411..5c780aef2 100644 --- a/packages/hydrooj/package.json +++ b/packages/hydrooj/package.json @@ -1,6 +1,6 @@ { "name": "hydrooj", - "version": "2.28.59", + "version": "2.29.0", "bin": "bin/hydrooj.js", "main": "dist/loader.js", "typings": "dist/loader.d.ts", diff --git a/packages/hydrooj/src/handler/contest.ts b/packages/hydrooj/src/handler/contest.ts index 2d571588c..60043ff6b 100644 --- a/packages/hydrooj/src/handler/contest.ts +++ b/packages/hydrooj/src/handler/contest.ts @@ -353,10 +353,12 @@ export class ContestDetailProblemSubmitHandler extends ContestProblemHandler { type: document.TYPE_CONTEST, tid, }); + const pdomainId = typeof pid === 'string' ? pid.split(':')[0] : domainId; + const ppid = typeof pid === 'number' ? pid : +pid.split(':')[1]; const rdoc = await record.get(domainId, rid); if (!pretest) { await Promise.all([ - problem.inc(domainId, pid, 'nSubmit', 1), + (this.tsdoc.journal || []).filter((i) => i.pid === pid).length ? Promise.resolve() : problem.inc(pdomainId, ppid, 'nSubmit', 1), domain.incUserInDomain(domainId, this.user._id, 'nSubmit'), contest.updateStatus(domainId, tid, this.user._id, rid, pid), ]); diff --git a/packages/hydrooj/src/handler/homework.ts b/packages/hydrooj/src/handler/homework.ts index 8999b7ce6..e13b18dc2 100644 --- a/packages/hydrooj/src/handler/homework.ts +++ b/packages/hydrooj/src/handler/homework.ts @@ -233,7 +233,7 @@ class HomeworkDetailProblemSubmitHandler extends HomeworkDetailProblemHandler { const rdoc = await record.get(domainId, rid); if (pretest) { await Promise.all([ - problem.inc(pdomainId, ppid, 'nSubmit', 1), + (this.tsdoc.journal || []).filter((i) => i.pid === pid).length ? Promise.resolve() : problem.inc(pdomainId, ppid, 'nSubmit', 1), domain.incUserInDomain(domainId, this.user._id, 'nSubmit'), contest.updateStatus(domainId, tid, this.user._id, rid, pid, false, 0, document.TYPE_HOMEWORK), diff --git a/packages/hydrooj/src/handler/judge.ts b/packages/hydrooj/src/handler/judge.ts index e7fbce784..f74a64d13 100644 --- a/packages/hydrooj/src/handler/judge.ts +++ b/packages/hydrooj/src/handler/judge.ts @@ -35,9 +35,7 @@ export async function postJudge(rdoc: RecordDoc) { ? await problem.inc(rdoc.pdomain, rdoc.pid, 'nAccept', 1) : await problem.get(rdoc.pdomain, rdoc.pid); const difficulty = difficultyAlgorithm(pdoc.nSubmit, pdoc.nAccept); - if (!updated) await record.updateMulti(rdoc.domainId, { uid: rdoc.uid, status: builtin.STATUS.STATUS_ACCEPTED }, { effective: false }); await Promise.all([ - record.update(rdoc.domainId, rdoc._id, { effective: true }), problem.edit(pdoc.domainId, pdoc.docId, { difficulty }), problem.inc(pdoc.domainId, pdoc.docId, `stats.${builtin.STATUS_SHORT_TEXTS[rdoc.status]}`, 1), problem.inc(pdoc.domainId, pdoc.docId, `stats.s${rdoc.score}`, 1), diff --git a/packages/hydrooj/src/handler/problem.ts b/packages/hydrooj/src/handler/problem.ts index adf5658c1..f123907bd 100644 --- a/packages/hydrooj/src/handler/problem.ts +++ b/packages/hydrooj/src/handler/problem.ts @@ -257,7 +257,7 @@ export class ProblemSubmitHandler extends ProblemDetailHandler { const rdoc = await record.get(domainId, rid); if (!pretest) { await Promise.all([ - problem.inc(domainId, this.pdoc.docId, 'nSubmit', 1), + this.psdoc?.rid ? Promise.resolve() : problem.inc(domainId, this.pdoc.docId, 'nSubmit', 1), problem.incStatus(domainId, this.pdoc.docId, this.user._id, 'nSubmit', 1), domain.incUserInDomain(domainId, this.user._id, 'nSubmit'), ]); diff --git a/packages/hydrooj/src/interface.ts b/packages/hydrooj/src/interface.ts index 18ac42832..ae2fba629 100644 --- a/packages/hydrooj/src/interface.ts +++ b/packages/hydrooj/src/interface.ts @@ -287,7 +287,6 @@ export interface RecordDoc { /** pretest */ input?: string; contest?: ContestInfo; - effective?: boolean; } export interface ScoreboardNode { diff --git a/packages/hydrooj/src/model/record.ts b/packages/hydrooj/src/model/record.ts index 2f2f714e1..df8ff8568 100644 --- a/packages/hydrooj/src/model/record.ts +++ b/packages/hydrooj/src/model/record.ts @@ -21,8 +21,7 @@ class RecordModel { static PROJECTION_LIST: (keyof RecordDoc)[] = [ '_id', 'score', 'time', 'memory', 'lang', 'uid', 'pid', 'rejudged', 'hidden', 'progress', - 'contest', 'effective', 'judger', 'judgeAt', 'status', - 'pdomain', + 'contest', 'judger', 'judgeAt', 'status', 'pdomain', ]; static async submissionPriority(uid: number, base: number = 0) { diff --git a/packages/hydrooj/src/script/problemStat.ts b/packages/hydrooj/src/script/problemStat.ts index 2adffcadc..c12bddd14 100644 --- a/packages/hydrooj/src/script/problemStat.ts +++ b/packages/hydrooj/src/script/problemStat.ts @@ -21,7 +21,7 @@ export async function udoc(report) { { $group: { _id: { domainId: '$_id.domainId', uid: '$_id.uid' }, - nSubmit: { $sum: '$nSubmit' }, + nSubmit: { $sum: { $min: ['$nSubmit', 1] } }, nAccept: { $sum: { $min: ['$nAccept', 1] } }, }, }, @@ -68,7 +68,7 @@ export async function psdoc(report) { export async function pdoc(report) { report({ message: 'Pdoc' }); const pipeline = [ - { $match: { hidden: false, type: { $ne: 'run' }, effective: true } }, + { $match: { hidden: false, type: { $ne: 'run' } } }, { $group: { _id: { domainId: '$domainId', pid: '$pid', uid: '$uid' }, diff --git a/packages/hydrooj/src/upgrade.ts b/packages/hydrooj/src/upgrade.ts index 387fee075..57ba1b45c 100644 --- a/packages/hydrooj/src/upgrade.ts +++ b/packages/hydrooj/src/upgrade.ts @@ -1,6 +1,6 @@ /* eslint-disable @typescript-eslint/no-unused-vars */ /* eslint-disable no-await-in-loop */ -import { FilterQuery, ObjectID } from 'mongodb'; +import { ObjectID } from 'mongodb'; import AdmZip from 'adm-zip'; import Queue from 'p-queue'; import yaml from 'js-yaml'; @@ -8,7 +8,6 @@ import { pick } from 'lodash'; import { convertIniConfig } from '@hydrooj/utils/lib/cases'; import { BucketItem } from 'minio'; import { Progress } from './ui'; -import { RecordDoc } from './interface'; import { Logger } from './logger'; import { streamToBuffer } from './utils'; import { @@ -24,7 +23,7 @@ import * as discussion from './model/discussion'; import domain from './model/domain'; import * as document from './model/document'; import * as system from './model/system'; -import { PRIV, STATUS } from './model/builtin'; +import { PRIV } from './model/builtin'; import RecordModel from './model/record'; import StorageModel from './model/storage'; import { size } from './lib/misc'; @@ -242,37 +241,7 @@ const scripts: UpgradeScript[] = [ }); return true; }, - async function _19_20() { - const _FRESH_INSTALL_IGNORE = 1; - const data = db.collection('record').aggregate([ - { $match: { hidden: false, type: { $ne: 'run' } } }, - { - $group: { - _id: { domainId: '$domainId', pid: '$pid', uid: '$uid' }, - nAccept: { - $sum: { - $cond: [{ $eq: ['$status', STATUS.STATUS_ACCEPTED] }, 1, 0], - }, - }, - }, - }, - ]); - while (await data.hasNext()) { - const d: any = await data.next(); - logger.info('%o', d); - const filter: FilterQuery = { domainId: d._id.domainId, pid: d._id.pid, uid: d._id.uid }; - if (d.nAccept) { - const [first] = await db.collection('record') - .find({ ...filter, status: STATUS.STATUS_ACCEPTED }) - .sort({ _id: 1 }).limit(1) - .project({ _id: 1 }) - .toArray(); - filter._id = { $lte: first._id }; - } - await db.collection('record').updateMany(filter, { $set: { effective: true } }); - } - return true; - }, + null, async function _20_21() { const _FRESH_INSTALL_IGNORE = 1; await iterateAllProblem([], async (pdoc) => { @@ -428,6 +397,11 @@ const scripts: UpgradeScript[] = [ await iterateAllDomain((ddoc) => domain.edit(ddoc._id, { lower: ddoc._id.toLowerCase() })); return true; }, + async function _35_36() { + const _FRESH_INSTALL_IGNORE = 1; + await RecordModel.coll.updateMany({}, { $unset: { effective: '' } }); + return true; + }, ]; export default scripts; diff --git a/packages/ui-default/locales/zh.yaml b/packages/ui-default/locales/zh.yaml index 7aa202af0..f3acd0099 100644 --- a/packages/ui-default/locales/zh.yaml +++ b/packages/ui-default/locales/zh.yaml @@ -754,6 +754,7 @@ training_create: 创建训练 training_edit: 编辑训练 training_main: 训练 Training: 训练 +Tried: 尝试 Type: 类型 UI Language: 用户界面语言 Uncompleted: 未完成 diff --git a/packages/ui-default/package.json b/packages/ui-default/package.json index 5adb44cf3..972fa8ba8 100644 --- a/packages/ui-default/package.json +++ b/packages/ui-default/package.json @@ -1,6 +1,6 @@ { "name": "@hydrooj/ui-default", - "version": "4.11.45", + "version": "4.11.46", "author": "undefined ", "license": "AGPL-3.0", "main": "hydro.js", diff --git a/packages/ui-default/pages/problem_main.page.styl b/packages/ui-default/pages/problem_main.page.styl index 817885488..beb1da6b0 100644 --- a/packages/ui-default/pages/problem_main.page.styl +++ b/packages/ui-default/pages/problem_main.page.styl @@ -10,23 +10,23 @@ width: rem(140px) position: relative - .col--submit_n, .col--ac_rate, .col--difficulty + .col--tried, .col--ac, .col--difficulty width: rem(70px) text-align: center .col--status border-right: 1px solid $table-border-color - .col--submit_n, .col--difficulty + .col--tried, .col--difficulty border-left: 1px solid $table-border-color +mobile() .col--status, - .col--submit_n, + .col--tried, .col--difficulty display: none - .col--ac_rate + .col--ac border-left: 1px solid $table-border-color diff --git a/packages/ui-default/pages/training_detail.page.styl b/packages/ui-default/pages/training_detail.page.styl index 636d0b1f6..99dbae54d 100644 --- a/packages/ui-default/pages/training_detail.page.styl +++ b/packages/ui-default/pages/training_detail.page.styl @@ -3,23 +3,23 @@ width: rem(150px) position: relative - .col--submit_n, .col--ac_rate, .col--difficulty + .col--tried, .col--ac, .col--difficulty width: rem(70px) text-align: center .col--status border-right: 1px solid $table-border-color - .col--submit_n, .col--difficulty + .col--tried, .col--difficulty border-left: 1px solid $table-border-color +mobile() .col--status, - .col--submit_n, + .col--tried, .col--difficulty display: none - .col--ac_rate + .col--ac border-left: 1px solid $table-border-color .training__section diff --git a/packages/ui-default/templates/partials/problem-sidebar-information.html b/packages/ui-default/templates/partials/problem-sidebar-information.html index d750cfd72..e9dfa6a9a 100644 --- a/packages/ui-default/templates/partials/problem-sidebar-information.html +++ b/packages/ui-default/templates/partials/problem-sidebar-information.html @@ -35,16 +35,8 @@
{{ _('# Submissions') }}
{{ pdoc.nSubmit }}
- {% if page_name != 'discussion_node' and page_name != 'discussion_detail' %} - {% if handler.user.hasPriv(PRIV.PRIV_USER_PROFILE) %} -
{{ _('# My Submissions') }}
-
{{ pdoc['psdoc'].nSubmit|default(0) }}
- {% endif %} - {% endif %}
{{ _('Accepted') }}
{{ pdoc.nAccept }}
-
{{ _('Accepted Ratio') }}
-
{% if pdoc.nSubmit > 0 %}{{ (100 * pdoc.nAccept / pdoc.nSubmit)|round|int }}%{% else %}{{ _('?') }}{% endif %}
{{ _('Uploaded By') }}
{{ user.render_inline(owner_udoc, badge=false) }}
diff --git a/packages/ui-default/templates/partials/problem_list.html b/packages/ui-default/templates/partials/problem_list.html index 78de58d28..0934f5c60 100644 --- a/packages/ui-default/templates/partials/problem_list.html +++ b/packages/ui-default/templates/partials/problem_list.html @@ -61,8 +61,8 @@ {{ problem.render_problem_title(pdoc) }} - {{ pdoc['nSubmit'] }} - {{ (100 * pdoc['nAccept'] / pdoc['nSubmit'])|round|int if pdoc['nSubmit'] > 0 else _('?') }} + {{ pdoc.nSubmit }} + {{ pdoc.nAccept }} {{ pdoc['difficulty'] or _('(None)') }} {%- endfor -%} diff --git a/packages/ui-default/templates/problem_detail.html b/packages/ui-default/templates/problem_detail.html index 6cf9f1ff5..ab84fbb35 100644 --- a/packages/ui-default/templates/problem_detail.html +++ b/packages/ui-default/templates/problem_detail.html @@ -44,9 +44,8 @@ {{ _('Time') }}: {{ pdoc.config.timeMax if pdoc.config.timeMax == pdoc.config.timeMin else pdoc.config.timeMin+'~'+pdoc.config.timeMax }}ms {{ _('Memory') }}: {{ pdoc.config.memoryMax if pdoc.config.memoryMax == pdoc.config.memoryMin else pdoc.config.memoryMin+'~'+pdoc.config.memoryMax }}MiB {% endif %} - {{ _('Submitted') }}: {{ pdoc.nSubmit }} + {{ _('Tried') }}: {{ pdoc.nSubmit }} {{ _('Accepted') }}: {{ pdoc.nAccept }} - {{ _('Accepted Ratio') }}: {% if pdoc.nSubmit > 0 %}{{ (100 * pdoc.nAccept / pdoc.nSubmit)|round|int }}%{% else %}{{ _('?') }}{% endif %} {{ _('Difficulty') }}: {{ pdoc['difficulty'] or _('(None)') }} {{ _('Uploaded By') }}: {{ user.render_inline(udoc, badge=false) }} {% if pdoc.tag.length %} diff --git a/packages/ui-default/templates/training_detail.html b/packages/ui-default/templates/training_detail.html index 7fd386a16..9c0668b1f 100644 --- a/packages/ui-default/templates/training_detail.html +++ b/packages/ui-default/templates/training_detail.html @@ -76,82 +76,82 @@ {{ node['content']|markdown|safe }} {% endif %} -
- - - {% if handler.user.hasPriv(PRIV.PRIV_USER_PROFILE) %} - - {% endif %} - - - - - - - - {% if handler.user.hasPriv(PRIV.PRIV_USER_PROFILE) %} - - {% endif %} - - - - - - - - {%- for pid in node['pids'] -%} - {% if pid in pdict %} - {% set pdoc=pdict[pid] %} - {% set psdoc=psdict[pid] %} - - {% if handler.user.hasPriv(PRIV.PRIV_USER_PROFILE) %} - {% if psdoc['rid'] %} - {{ record.render_status_td(psdoc, rid_key='rid') }} - {% else %} - - {% endif %} - {% endif %} - + + + + + + + {% if handler.user.hasPriv(PRIV.PRIV_USER_PROFILE) %} + + {% endif %} + + + + + + + + {%- for pid in node['pids'] -%} + {% if pid in pdict %} + {% set pdoc=pdict[pid] %} + {% set psdoc=psdict[pid] %} + + {% if handler.user.hasPriv(PRIV.PRIV_USER_PROFILE) %} + {% if psdoc['rid'] %} + {{ record.render_status_td(psdoc, rid_key='rid') }} + {% else %} + + {% endif %} + {% endif %} + + + + + + {% else %} + {% set pdoc = {'_id': pid, 'hidden': true, 'title': '*'} %} + + + + + + + + {% endif %} + {%- endfor -%} + +
{{ _('Status') }}{{ _('Problem') }}{{ _('Submit') }}% {{ _('AC') }}{{ _('Difficulty') }}
+
+ + {% if handler.user.hasPriv(PRIV.PRIV_USER_PROFILE) %} - - - - - - + {% endif %} - {{ problem.render_problem_title( - pdoc, - invalid=not tsdoc['enroll'], - show_tags=false - ) }} - - - - - - {% else %} - {% set pdoc = {'_id': pid, 'hidden': true, 'title': '*'} %} - - - - - - - - {% endif %} - {%- endfor -%} - -
{{ pdoc.nSubmit }}{{ (100 * pdoc.nAccept / pdoc.nSubmit)|round|int if pdoc.nSubmit > 0 else _('?') }}{{ pdoc['difficulty'] or _('(None)') }}
- - {{ problem.render_problem_title(pdoc, invalid=true) }} - ***
+
{{ _('Status') }}{{ _('Problem') }}{{ _('Tried') }}% {{ _('AC') }}{{ _('Difficulty') }}
+ {% if handler.user.hasPriv(PRIV.PRIV_USER_PROFILE) %} +
+ + + + +
+ {% endif %} + {{ problem.render_problem_title( + pdoc, + invalid=not tsdoc['enroll'], + show_tags=false + ) }} +
{{ pdoc.nSubmit }}{{ pdoc.nAccept }}{{ pdoc['difficulty'] or _('(None)') }}
+ + {{ problem.render_problem_title(pdoc, invalid=true) }} + ***
+
- {%- endfor -%}