core: bug fix

fix #68
fix #70
fix #71
This commit is contained in:
undefined committed 2021-03-29 01:57:13 +08:00
1 parent ee4dc90cf3
commit 1472c1567c
8 files changed
+48 -23

No files matched your search

+1 -1
View File
@@ -1,6 +1,6 @@
{ {
"name": "hydrooj", "name": "hydrooj",
"version": "2.20.44", "version": "2.20.45",
"bin": "bin/hydrooj.js", "bin": "bin/hydrooj.js",
"main": "dist/loader.js", "main": "dist/loader.js",
"typings": "dist/loader.d.ts", "typings": "dist/loader.d.ts",
+10 -3
View File
@@ -104,7 +104,7 @@ class DomainUserHandler extends ManageHandler {
const [dudocs, roles] = await Promise.all([ const [dudocs, roles] = await Promise.all([
domain.getMultiUserInDomain(domainId, { domain.getMultiUserInDomain(domainId, {
$and: [ $and: [
{ role: { $ne: 'default' } }, { role: { $nin: ['default', 'guest'] } },
{ role: { $ne: null } }, { role: { $ne: null } },
], ],
}).toArray(), }).toArray(),
@@ -115,7 +115,7 @@ class DomainUserHandler extends ManageHandler {
for (const role of roles) rudocs[role._id] = []; for (const role of roles) rudocs[role._id] = [];
for (const dudoc of dudocs) { for (const dudoc of dudocs) {
const ud = udict[dudoc.uid]; const ud = udict[dudoc.uid];
rudocs[ud.role].push(ud); rudocs[ud.role || 'default'].push(ud);
} }
const rolesSelect = roles.map((role) => [role._id, role._id]); const rolesSelect = roles.map((role) => [role._id, role._id]);
const path = [ const path = [
@@ -135,6 +135,13 @@ class DomainUserHandler extends ManageHandler {
await domain.setUserRole(domainId, uid, role); await domain.setUserRole(domainId, uid, role);
this.back(); this.back();
} }
@param('uid', Types.Array)
@param('role', Types.String)
async postSetUsers(domainId: string, uid: number[], role: string) {
await domain.setUserRole(domainId, uid, role);
this.back();
}
} }
class DomainPermissionHandler extends ManageHandler { class DomainPermissionHandler extends ManageHandler {
@@ -170,7 +177,7 @@ class DomainPermissionHandler extends ManageHandler {
class DomainRoleHandler extends ManageHandler { class DomainRoleHandler extends ManageHandler {
async get({ domainId }) { async get({ domainId }) {
const roles = await domain.getRoles(domainId); const roles = await domain.getRoles(domainId, true);
const path = [ const path = [
['Hydro', 'homepage'], ['Hydro', 'homepage'],
['domain', null], ['domain', null],
+1 -1
View File
@@ -296,7 +296,7 @@ class HomeDomainCreateHandler extends Handler {
gravatar = gravatar || this.user.gravatar || this.user.mail || 'guest@hydro.local'; gravatar = gravatar || this.user.gravatar || this.user.mail || 'guest@hydro.local';
const domainId = await domain.add(id, this.user._id, name, bulletin); const domainId = await domain.add(id, this.user._id, name, bulletin);
await domain.edit(domainId, { gravatar }); await domain.edit(domainId, { gravatar });
await domain.setUserRole(domainId, this.user._id, 'admin'); await domain.setUserRole(domainId, this.user._id, 'root');
this.response.redirect = this.url('domain_dashboard', { domainId }); this.response.redirect = this.url('domain_dashboard', { domainId });
this.response.body = { domainId }; this.response.body = { domainId };
} }
+1 -1
View File
@@ -304,7 +304,7 @@ export const BUILTIN_USERS: Udoc[] = [
export const BUILTIN_ROLES = { export const BUILTIN_ROLES = {
guest: PERM.PERM_BASIC, guest: PERM.PERM_BASIC,
default: PERM.PERM_DEFAULT, default: PERM.PERM_DEFAULT,
admin: PERM.PERM_ADMIN, root: PERM.PERM_ALL,
}; };
export const DEFAULT_NODES = { export const DEFAULT_NODES = {
+26 -14
View File
@@ -3,7 +3,7 @@ import { FilterQuery } from 'mongodb';
import { BUILTIN_ROLES, PRIV } from './builtin'; import { BUILTIN_ROLES, PRIV } from './builtin';
import { DomainDoc } from '../interface'; import { DomainDoc } from '../interface';
import { ArgMethod } from '../utils'; import { ArgMethod } from '../utils';
import { NumberKeys } from '../typeutils'; import { MaybeArray, NumberKeys } from '../typeutils';
import * as bus from '../service/bus'; import * as bus from '../service/bus';
import db from '../service/db'; import db from '../service/db';
@@ -52,6 +52,7 @@ class DomainModel {
}; };
await bus.serial('domain/create', ddoc); await bus.serial('domain/create', ddoc);
await coll.insertOne(ddoc); await coll.insertOne(ddoc);
await DomainModel.setUserRole(domainId, owner, 'root');
return domainId; return domainId;
} }
@@ -104,15 +105,23 @@ class DomainModel {
return r; return r;
} }
@ArgMethod static async countUser(domainId: string, role?: string) {
static setUserRole(domainId: string, uid: number, role: string) { if (role) return await collUser.find({ domainId, role }).count();
return collUser.updateOne({ uid, domainId }, { $set: { role } }, { upsert: true }); return await collUser.find({ domainId }).count();
} }
static async getRoles(domainId: string): Promise<any[]>;
static async getRoles(domain: DomainDoc): Promise<any[]>;
@ArgMethod @ArgMethod
static async getRoles(arg: string | DomainDoc) { static setUserRole(domainId: string, uid: MaybeArray<number>, role: string) {
if (!(uid instanceof Array)) {
return collUser.updateOne({ domainId, uid }, { $set: { role } }, { upsert: true });
}
return collUser.updateMany({ domainId, uid: { $in: uid } }, { $set: { role } }, { upsert: true });
}
static async getRoles(domainId: string, count?: boolean): Promise<any[]>;
static async getRoles(domain: DomainDoc, count?: boolean): Promise<any[]>;
@ArgMethod
static async getRoles(arg: string | DomainDoc, count: boolean = false) {
let ddoc: DomainDoc; let ddoc: DomainDoc;
if (typeof arg === 'string') ddoc = await DomainModel.get(arg); if (typeof arg === 'string') ddoc = await DomainModel.get(arg);
else ddoc = arg; else ddoc = arg;
@@ -127,6 +136,14 @@ class DomainModel {
roles.push({ _id: role, perm: BUILTIN_ROLES[role] }); roles.push({ _id: role, perm: BUILTIN_ROLES[role] });
} }
} }
if (count) {
for (const role of roles) {
if (!['default', 'guest'].includes(role._id)) {
// eslint-disable-next-line no-await-in-loop
role.count = await DomainModel.countUser(ddoc._id, role._id);
}
}
}
return roles; return roles;
} }
@@ -157,10 +174,9 @@ class DomainModel {
let dudoc = await collUser.findOne({ domainId, uid: udoc._id }); let dudoc = await collUser.findOne({ domainId, uid: udoc._id });
dudoc = dudoc || {}; dudoc = dudoc || {};
if (!(udoc.priv & PRIV.PRIV_USER_PROFILE)) dudoc.role = 'guest'; if (!(udoc.priv & PRIV.PRIV_USER_PROFILE)) dudoc.role = 'guest';
if (udoc.priv & PRIV.PRIV_MANAGE_ALL_DOMAIN) dudoc.role = 'admin'; if (udoc.priv & PRIV.PRIV_MANAGE_ALL_DOMAIN) dudoc.role = 'root';
dudoc.role = dudoc.role || 'default'; dudoc.role = dudoc.role || 'default';
const ddoc = await DomainModel.get(domainId); const ddoc = await DomainModel.get(domainId);
if (ddoc.owner === udoc._id) dudoc.role = 'admin';
dudoc.perm = ddoc.roles[dudoc.role] dudoc.perm = ddoc.roles[dudoc.role]
? BigInt(ddoc.roles[dudoc.role]) ? BigInt(ddoc.roles[dudoc.role])
: BUILTIN_ROLES[dudoc.role]; : BUILTIN_ROLES[dudoc.role];
@@ -190,17 +206,13 @@ class DomainModel {
@ArgMethod @ArgMethod
static async getDictUserByDomainId(uid: number) { static async getDictUserByDomainId(uid: number) {
const [dudocs, ddocs] = await Promise.all([ const dudocs = await collUser.find({ uid }).toArray();
collUser.find({ uid }).toArray(),
coll.find({ owner: uid }).toArray(),
]);
const dudict = {}; const dudict = {};
for (const dudoc of dudocs) { for (const dudoc of dudocs) {
// eslint-disable-next-line no-await-in-loop // eslint-disable-next-line no-await-in-loop
dudict[dudoc.domainId] = await DomainModel.get(dudoc.domainId); dudict[dudoc.domainId] = await DomainModel.get(dudoc.domainId);
dudict[dudoc.domainId].role = dudoc.role; dudict[dudoc.domainId].role = dudoc.role;
} }
for (const ddoc of ddocs) dudict[ddoc._id] = 'admin';
return dudict; return dudict;
} }
+1 -1
View File
@@ -205,7 +205,7 @@ bus.once('app/started', async () => {
bus.on('system/setting', (args) => { bus.on('system/setting', (args) => {
if (!args.lang?.texts) return; if (!args.lang?.texts) return;
SETTINGS_BY_KEY['codeLang'].range = args.lang.texts; SETTINGS_BY_KEY['codeLang'].range = yaml.load(args.lang.texts) as any;
}); });
global.Hydro.model.setting = { global.Hydro.model.setting = {
-1
View File
@@ -29,7 +29,6 @@ import {
CsrfTokenError, InvalidOperationError, MethodNotAllowedError, CsrfTokenError, InvalidOperationError, MethodNotAllowedError,
NotFoundError, HydroError, NotFoundError, HydroError,
} from '../error'; } from '../error';
import hash from '../lib/hash.hydro';
import * as misc from '../lib/misc'; import * as misc from '../lib/misc';
import user from '../model/user'; import user from '../model/user';
import domain from '../model/domain'; import domain from '../model/domain';
+8 -1
View File
@@ -21,7 +21,7 @@ const logger = new Logger('upgrade');
type UpgradeScript = () => Promise<boolean | void>; type UpgradeScript = () => Promise<boolean | void>;
async function iterateAllDomain(cb: (ddoc: DomainDoc, current?: number, total?: number) => Promise<any>) { async function iterateAllDomain(cb: (ddoc: DomainDoc, current?: number, total?: number) => Promise<any>) {
const ddocs = await domain.getMulti().project({ _id: 1 }).toArray(); const ddocs = await domain.getMulti().project({ _id: 1, owner: 1 }).toArray();
for (const i in ddocs) await cb(ddocs[i], +i, ddocs.length); for (const i in ddocs) await cb(ddocs[i], +i, ddocs.length);
} }
@@ -220,6 +220,13 @@ const scripts: UpgradeScript[] = [
}); });
return true; return true;
}, },
// Set domain owner perm
async function _13_14() {
const _FRESH_INSTALL_IGNORE = 1;
await iterateAllDomain((ddoc) => domain.setUserRole(ddoc._id, ddoc.owner, 'root'));
await db.collection('domain.user').updateMany({ role: 'admin' }, { $set: { role: 'root' } });
return true;
},
]; ];
export = scripts; export = scripts;