- Implementierung von Methoden zur Hinzufügung und Abfrage von Lagerbeständen im AdminController und AdminService. - Erweiterung der Routen im AdminRouter zur Unterstützung der neuen Lagerverwaltungsfunktionen. - Anpassung der Benutzeroberfläche zur Integration eines Dialogs für die Lagerhinzufügung und zur Anzeige von Lagertypen. - Aktualisierung der Übersetzungen in den Sprachdateien für die neuen Funktionen und Fehlermeldungen.
759 lines
26 KiB
JavaScript
759 lines
26 KiB
JavaScript
import RoomType from '../models/chat/room_type.js';
|
|
import ChatRight from '../models/chat/rights.js';
|
|
import UserRight from "../models/community/user_right.js";
|
|
import UserRightType from "../models/type/user_right.js";
|
|
import InterestType from "../models/type/interest.js";
|
|
import InterestTranslationType from "../models/type/interest_translation.js";
|
|
import User from "../models/community/user.js";
|
|
import UserParamValue from "../models/type/user_param_value.js";
|
|
import UserParamType from "../models/type/user_param.js";
|
|
import ContactMessage from "../models/service/contactmessage.js";
|
|
import ContactService from "./ContactService.js";
|
|
import { sendAnswerEmail } from './emailService.js';
|
|
import { Op } from 'sequelize';
|
|
import FalukantUser from "../models/falukant/data/user.js";
|
|
import FalukantCharacter from "../models/falukant/data/character.js";
|
|
import FalukantPredefineFirstname from "../models/falukant/predefine/firstname.js";
|
|
import FalukantPredefineLastname from "../models/falukant/predefine/lastname.js";
|
|
import Branch from "../models/falukant/data/branch.js";
|
|
import FalukantStock from "../models/falukant/data/stock.js";
|
|
import FalukantStockType from "../models/falukant/type/stock.js";
|
|
import RegionData from "../models/falukant/data/region.js";
|
|
import BranchType from "../models/falukant/type/branch.js";
|
|
import Room from '../models/chat/room.js';
|
|
|
|
class AdminService {
|
|
async hasUserAccess(userId, section) {
|
|
const userRights = await UserRight.findAll({
|
|
include: [{
|
|
model: UserRightType,
|
|
as: 'rightType',
|
|
where: {
|
|
title: [section, 'mainadmin'],
|
|
}
|
|
},
|
|
{
|
|
model: User,
|
|
as: 'user_with_rights',
|
|
where: {
|
|
hashedId: userId,
|
|
}
|
|
}
|
|
]
|
|
|
|
});
|
|
return userRights.length > 0;
|
|
}
|
|
|
|
async getOpenInterests(userId) {
|
|
if (!this.hasUserAccess(userId, 'interests')) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const openInterests = await InterestType.findAll({
|
|
where: {
|
|
allowed: false
|
|
},
|
|
include: {
|
|
model: InterestTranslationType,
|
|
as: 'interest_translations',
|
|
}
|
|
})
|
|
return openInterests;
|
|
}
|
|
|
|
async changeInterest(userId, interestId, active, adultOnly) {
|
|
if (!this.hasUserAccess(userId, 'interests')) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const interest = await InterestType.findOne({
|
|
where: {
|
|
id: interestId
|
|
}
|
|
});
|
|
if (interest) {
|
|
interest.allowed = active;
|
|
interest.adultOnly = adultOnly;
|
|
await interest.save();
|
|
}
|
|
}
|
|
|
|
async deleteInterest(userId, interestId) {
|
|
if (!this.hasUserAccess(userId, 'interests')) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const interest = await InterestType.findOne({
|
|
where: {
|
|
id: interestId
|
|
}
|
|
});
|
|
if (interest) {
|
|
await interest.destroy();
|
|
}
|
|
}
|
|
|
|
async changeTranslation(userId, interestId, translations) {
|
|
if (!this.hasUserAccess(userId, 'interests')) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const interest = await InterestType.findOne({
|
|
id: interestId
|
|
});
|
|
if (!interest) {
|
|
throw new Error('notexisting');
|
|
}
|
|
for (const languageId of Object.keys(translations)) {
|
|
const languageObject = await UserParamValue.findOne(
|
|
{
|
|
where: {
|
|
id: languageId
|
|
}
|
|
}
|
|
);
|
|
if (!languageObject) {
|
|
throw new Error('wronglanguage');
|
|
}
|
|
const translation = await InterestTranslationType.findOne(
|
|
{
|
|
where: {
|
|
interestsId: interestId,
|
|
language: languageObject.id
|
|
}
|
|
}
|
|
);
|
|
if (translation) {
|
|
translation.translation = translations[languageId];
|
|
translation.save();
|
|
} else {
|
|
await InterestTranslationType.create({
|
|
interestsId: interestId,
|
|
language: languageObject.id,
|
|
translation: translations[languageId]
|
|
|
|
});
|
|
}
|
|
}
|
|
}
|
|
|
|
async getOpenContacts(userId) {
|
|
if (!this.hasUserAccess(userId, 'contacts')) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const openContacts = await ContactMessage.findAll({
|
|
where: {
|
|
isFinished: false,
|
|
}
|
|
})
|
|
return openContacts;
|
|
}
|
|
|
|
async answerContact(contactId, answer) {
|
|
const contact = await ContactService.getContactById(contactId);
|
|
await ContactService.saveAnswer(contact, answer);
|
|
await sendAnswerEmail(contact.email, answer, contact.language || 'en');
|
|
}
|
|
|
|
async getFalukantUser(userId, userName, characterName) {
|
|
if (!(await this.hasUserAccess(userId, 'falukantusers'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
let users;
|
|
if (userName) {
|
|
users = await User.findAll({
|
|
where: {
|
|
username: {
|
|
[Op.like]: '%' + userName + '%'
|
|
}
|
|
},
|
|
include: [{
|
|
model: FalukantUser,
|
|
as: 'falukantData',
|
|
required: true,
|
|
include: [{
|
|
model: FalukantCharacter,
|
|
as: 'character',
|
|
required: true,
|
|
include: [{
|
|
model: FalukantPredefineFirstname,
|
|
as: 'definedFirstName',
|
|
required: true
|
|
}, {
|
|
model: FalukantPredefineLastname,
|
|
as: 'definedLastName',
|
|
required: true
|
|
}]
|
|
}]
|
|
}]
|
|
});
|
|
} else if (characterName) {
|
|
const [firstname, lastname] = characterName.split(' ');
|
|
users = await User.findAll({
|
|
include: [{
|
|
model: FalukantUser,
|
|
as: 'falukantData',
|
|
required: true,
|
|
include: [{
|
|
model: FalukantCharacter,
|
|
as: 'character',
|
|
required: true,
|
|
include: [{
|
|
model: FalukantPredefineFirstname,
|
|
as: 'definedFirstName',
|
|
required: true,
|
|
where: {
|
|
name: firstname
|
|
}
|
|
}, {
|
|
model: FalukantPredefineLastname,
|
|
as: 'definedLastName',
|
|
required: true,
|
|
where: {
|
|
name: lastname
|
|
}
|
|
}]
|
|
}]
|
|
}]
|
|
});
|
|
} else {
|
|
throw new Error('no search parameter');
|
|
}
|
|
return users.map(user => {
|
|
return {
|
|
id: user.hashedId,
|
|
username: user.username,
|
|
falukantUser: user.falukantData
|
|
}
|
|
});
|
|
}
|
|
|
|
async getFalukantUserById(userId, hashedId) {
|
|
if (!(await this.hasUserAccess(userId, 'falukantusers'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const user = await User.findOne({
|
|
where: {
|
|
hashedId: hashedId
|
|
},
|
|
attributes: ['hashedId', 'username'],
|
|
include: [{
|
|
model: FalukantUser,
|
|
as: 'falukantData',
|
|
required: true,
|
|
attributes: ['money', 'certificate', 'id'],
|
|
include: [{
|
|
model: FalukantCharacter,
|
|
as: 'character',
|
|
attributes: ['birthdate', 'health', 'title_of_nobility'],
|
|
include: [{
|
|
model: FalukantPredefineFirstname,
|
|
as: 'definedFirstName',
|
|
}, {
|
|
model: FalukantPredefineLastname,
|
|
as: 'definedLastName',
|
|
}]
|
|
}]
|
|
}]
|
|
});
|
|
return user;
|
|
}
|
|
|
|
async getFalukantUserBranches(userId, falukantUserId) {
|
|
if (!(await this.hasUserAccess(userId, 'falukantusers'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
|
|
try {
|
|
// Zuerst die Branches laden
|
|
const branches = await Branch.findAll({
|
|
where: {
|
|
falukantUserId: falukantUserId
|
|
}
|
|
});
|
|
|
|
// Dann für jede Branch die zusätzlichen Daten laden
|
|
const branchesWithData = await Promise.all(branches.map(async (branch) => {
|
|
const region = await RegionData.findByPk(branch.regionId);
|
|
const branchType = await BranchType.findByPk(branch.branchTypeId);
|
|
const stocks = await FalukantStock.findAll({
|
|
where: { branchId: branch.id },
|
|
include: [{
|
|
model: FalukantStockType,
|
|
as: 'stockType',
|
|
attributes: ['labelTr']
|
|
}]
|
|
});
|
|
|
|
return {
|
|
...branch.toJSON(),
|
|
region: region ? { name: region.name } : null,
|
|
branchType: branchType ? { labelTr: branchType.labelTr } : null,
|
|
stocks: stocks
|
|
};
|
|
}));
|
|
|
|
return branchesWithData;
|
|
} catch (error) {
|
|
console.error('Error in getFalukantUserBranches:', error);
|
|
throw error;
|
|
}
|
|
}
|
|
|
|
async updateFalukantStock(userId, stockId, quantity) {
|
|
if (!(await this.hasUserAccess(userId, 'falukantusers'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
|
|
const stock = await FalukantStock.findByPk(stockId);
|
|
if (!stock) {
|
|
throw new Error('Stock not found');
|
|
}
|
|
|
|
stock.quantity = quantity;
|
|
await stock.save();
|
|
|
|
return stock;
|
|
}
|
|
|
|
async addFalukantStock(userId, branchId, stockTypeId, quantity) {
|
|
if (!(await this.hasUserAccess(userId, 'falukantusers'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
|
|
// Prüfe ob Branch existiert
|
|
const branch = await Branch.findByPk(branchId);
|
|
if (!branch) {
|
|
throw new Error('Branch not found');
|
|
}
|
|
|
|
// Prüfe ob StockType existiert
|
|
const stockType = await FalukantStockType.findByPk(stockTypeId);
|
|
if (!stockType) {
|
|
throw new Error('Stock type not found');
|
|
}
|
|
|
|
// Prüfe ob bereits ein Stock dieses Typs für diesen Branch existiert
|
|
const existingStock = await FalukantStock.findOne({
|
|
where: {
|
|
branchId: branchId,
|
|
stockTypeId: stockTypeId
|
|
}
|
|
});
|
|
|
|
if (existingStock) {
|
|
throw new Error('Stock of this type already exists for this branch');
|
|
}
|
|
|
|
// Erstelle neuen Stock
|
|
const newStock = await FalukantStock.create({
|
|
branchId: branchId,
|
|
stockTypeId: stockTypeId,
|
|
quantity: quantity
|
|
});
|
|
|
|
// Lade den neuen Stock mit allen Beziehungen
|
|
const stockWithData = await FalukantStock.findByPk(newStock.id, {
|
|
include: [{ model: FalukantStockType, as: 'stockType', attributes: ['labelTr'] }]
|
|
});
|
|
|
|
return stockWithData;
|
|
}
|
|
|
|
async getFalukantStockTypes(userId) {
|
|
if (!(await this.hasUserAccess(userId, 'falukantusers'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
|
|
const stockTypes = await FalukantStockType.findAll({
|
|
attributes: ['id', 'labelTr']
|
|
});
|
|
|
|
return stockTypes;
|
|
}
|
|
|
|
async changeFalukantUser(userId, falukantUserId, falukantData) {
|
|
if (!(await this.hasUserAccess(userId, 'falukantusers'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const falukantUser = await FalukantUser.findOne({
|
|
where: {
|
|
id: falukantUserId
|
|
}
|
|
});
|
|
if (!falukantUser) {
|
|
throw new Error('notfound');
|
|
}
|
|
const character = await FalukantCharacter.findOne({
|
|
where: {
|
|
userId: falukantUserId
|
|
}
|
|
});
|
|
if (!character) {
|
|
throw new Error('notfound');
|
|
}
|
|
if (Object.keys(falukantData).indexOf('age') >= 0) {
|
|
const birthDate = (new Date()) - (falukantData.age * 24 * 3600000);
|
|
await character.update({
|
|
birthdate: birthDate
|
|
});
|
|
}
|
|
if (Object.keys(falukantData).indexOf('money') >= 0) {
|
|
await falukantUser.update({
|
|
money: falukantData.money
|
|
});
|
|
}
|
|
if (Object.keys(falukantData).indexOf('title_of_nobility') >= 0) {
|
|
await character.update({
|
|
titleOfNobility: falukantData.title_of_nobility
|
|
});
|
|
}
|
|
await falukantUser.save();
|
|
await character.save();
|
|
}
|
|
|
|
// --- Chat Room Admin ---
|
|
async getRoomTypes(userId) {
|
|
if (!(await this.hasUserAccess(userId, 'chatrooms'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
return await RoomType.findAll();
|
|
}
|
|
|
|
async getGenderRestrictions(userId) {
|
|
if (!(await this.hasUserAccess(userId, 'chatrooms'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
// Find the UserParamType for gender restriction (e.g. description = 'gender')
|
|
const genderType = await UserParamType.findOne({ where: { description: 'gender' } });
|
|
if (!genderType) return [];
|
|
return await UserParamValue.findAll({ where: { userParamTypeId: genderType.id } });
|
|
}
|
|
|
|
async getUserRights(userId) {
|
|
if (!(await this.hasUserAccess(userId, 'chatrooms'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
return await ChatRight.findAll();
|
|
}
|
|
|
|
async getRooms(userId) {
|
|
if (!(await this.hasUserAccess(userId, 'chatrooms'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
// Only return necessary fields to the frontend
|
|
return await Room.findAll({
|
|
attributes: [
|
|
'id',
|
|
'title',
|
|
'roomTypeId',
|
|
'isPublic',
|
|
'genderRestrictionId',
|
|
'minAge',
|
|
'maxAge',
|
|
'friendsOfOwnerOnly',
|
|
'requiredUserRightId',
|
|
'password' // only if needed for editing, otherwise remove
|
|
],
|
|
include: [
|
|
{ model: RoomType, as: 'roomType' },
|
|
{ model: UserParamValue, as: 'genderRestriction' },
|
|
]
|
|
});
|
|
}
|
|
|
|
async updateRoom(userId, id, data) {
|
|
if (!(await this.hasUserAccess(userId, 'chatrooms'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const room = await Room.findByPk(id);
|
|
if (!room) throw new Error('Room not found');
|
|
await room.update(data);
|
|
return room;
|
|
}
|
|
|
|
async createRoom(userId, data) {
|
|
if (!(await this.hasUserAccess(userId, 'chatrooms'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
return await Room.create(data);
|
|
}
|
|
|
|
async deleteRoom(userId, id) {
|
|
if (!(await this.hasUserAccess(userId, 'chatrooms'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
return await Room.destroy({ where: { id } });
|
|
}
|
|
|
|
// --- Match3 Admin Methods ---
|
|
async getMatch3Campaigns(userId) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Campaign = (await import('../models/match3/campaign.js')).default;
|
|
return await Match3Campaign.findAll({
|
|
include: [{
|
|
model: (await import('../models/match3/level.js')).default,
|
|
as: 'levels',
|
|
include: [{
|
|
model: (await import('../models/match3/objective.js')).default,
|
|
as: 'objectives',
|
|
required: false
|
|
}],
|
|
required: false
|
|
}]
|
|
});
|
|
}
|
|
|
|
async getMatch3Campaign(userId, id) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Campaign = (await import('../models/match3/campaign.js')).default;
|
|
return await Match3Campaign.findByPk(id, {
|
|
include: [{
|
|
model: (await import('../models/match3/level.js')).default,
|
|
as: 'levels',
|
|
include: [{
|
|
model: (await import('../models/match3/objective.js')).default,
|
|
as: 'objectives',
|
|
required: false
|
|
}],
|
|
required: false
|
|
}]
|
|
});
|
|
}
|
|
|
|
async createMatch3Campaign(userId, data) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Campaign = (await import('../models/match3/campaign.js')).default;
|
|
return await Match3Campaign.create(data);
|
|
}
|
|
|
|
async updateMatch3Campaign(userId, id, data) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Campaign = (await import('../models/match3/campaign.js')).default;
|
|
const campaign = await Match3Campaign.findByPk(id);
|
|
if (!campaign) throw new Error('Campaign not found');
|
|
await campaign.update(data);
|
|
return campaign;
|
|
}
|
|
|
|
async deleteMatch3Campaign(userId, id) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Campaign = (await import('../models/match3/campaign.js')).default;
|
|
return await Match3Campaign.destroy({ where: { id } });
|
|
}
|
|
|
|
async getMatch3Levels(userId) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Level = (await import('../models/match3/level.js')).default;
|
|
return await Match3Level.findAll({
|
|
include: [
|
|
{
|
|
model: (await import('../models/match3/campaign.js')).default,
|
|
as: 'campaign',
|
|
required: false
|
|
},
|
|
{
|
|
model: (await import('../models/match3/objective.js')).default,
|
|
as: 'objectives',
|
|
required: false
|
|
}
|
|
],
|
|
order: [['order', 'ASC']]
|
|
});
|
|
}
|
|
|
|
async getMatch3Level(userId, id) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Level = (await import('../models/match3/level.js')).default;
|
|
return await Match3Level.findByPk(id, {
|
|
include: [
|
|
{
|
|
model: (await import('../models/match3/campaign.js')).default,
|
|
as: 'campaign',
|
|
required: false
|
|
},
|
|
{
|
|
model: (await import('../models/match3/objective.js')).default,
|
|
as: 'objectives',
|
|
required: false
|
|
}
|
|
]
|
|
});
|
|
}
|
|
|
|
async createMatch3Level(userId, data) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Level = (await import('../models/match3/level.js')).default;
|
|
|
|
// Wenn keine campaignId gesetzt ist, setze eine Standard-Campaign-ID
|
|
if (!data.campaignId) {
|
|
// Versuche eine Standard-Campaign zu finden oder erstelle eine
|
|
const Match3Campaign = (await import('../models/match3/campaign.js')).default;
|
|
let defaultCampaign = await Match3Campaign.findOne({ where: { isActive: true } });
|
|
|
|
if (!defaultCampaign) {
|
|
// Erstelle eine Standard-Campaign falls keine existiert
|
|
defaultCampaign = await Match3Campaign.create({
|
|
name: 'Standard Campaign',
|
|
description: 'Standard Campaign für Match3 Levels',
|
|
isActive: true,
|
|
order: 1
|
|
});
|
|
}
|
|
|
|
data.campaignId = defaultCampaign.id;
|
|
}
|
|
|
|
// Validiere, dass campaignId gesetzt ist
|
|
if (!data.campaignId) {
|
|
throw new Error('CampaignId ist erforderlich');
|
|
}
|
|
|
|
return await Match3Level.create(data);
|
|
}
|
|
|
|
async updateMatch3Level(userId, id, data) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Level = (await import('../models/match3/level.js')).default;
|
|
const level = await Match3Level.findByPk(id);
|
|
if (!level) throw new Error('Level not found');
|
|
await level.update(data);
|
|
return level;
|
|
}
|
|
|
|
async deleteMatch3Level(userId, id) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Level = (await import('../models/match3/level.js')).default;
|
|
return await Match3Level.destroy({ where: { id } });
|
|
}
|
|
|
|
// Match3 Objectives
|
|
async getMatch3Objectives(userId) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Objective = (await import('../models/match3/objective.js')).default;
|
|
return await Match3Objective.findAll({
|
|
include: [{
|
|
model: (await import('../models/match3/level.js')).default,
|
|
as: 'level',
|
|
required: false
|
|
}],
|
|
order: [['order', 'ASC']]
|
|
});
|
|
}
|
|
|
|
async getMatch3Objective(userId, id) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Objective = (await import('../models/match3/objective.js')).default;
|
|
return await Match3Objective.findByPk(id, {
|
|
include: [{
|
|
model: (await import('../models/match3/level.js')).default,
|
|
as: 'level',
|
|
required: false
|
|
}]
|
|
});
|
|
}
|
|
|
|
async createMatch3Objective(userId, data) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Objective = (await import('../models/match3/objective.js')).default;
|
|
|
|
// Validiere, dass levelId gesetzt ist
|
|
if (!data.levelId) {
|
|
throw new Error('LevelId ist erforderlich');
|
|
}
|
|
|
|
// Validiere, dass target eine ganze Zahl ist
|
|
if (data.target && !Number.isInteger(Number(data.target))) {
|
|
throw new Error('Target muss eine ganze Zahl sein');
|
|
}
|
|
|
|
return await Match3Objective.create(data);
|
|
}
|
|
|
|
async updateMatch3Objective(userId, id, data) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Objective = (await import('../models/match3/objective.js')).default;
|
|
const objective = await Match3Objective.findByPk(id);
|
|
if (!objective) throw new Error('Objective not found');
|
|
|
|
// Validiere, dass target eine ganze Zahl ist
|
|
if (data.target && !Number.isInteger(Number(data.target))) {
|
|
throw new Error('Target muss eine ganze Zahl sein');
|
|
}
|
|
|
|
await objective.update(data);
|
|
return objective;
|
|
}
|
|
|
|
async deleteMatch3Objective(userId, id) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3Objective = (await import('../models/match3/objective.js')).default;
|
|
return await Match3Objective.destroy({ where: { id } });
|
|
}
|
|
|
|
async getMatch3TileTypes(userId) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3TileType = (await import('../models/match3/tileType.js')).default;
|
|
return await Match3TileType.findAll({
|
|
order: [['name', 'ASC']]
|
|
});
|
|
}
|
|
|
|
async createMatch3TileType(userId, data) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3TileType = (await import('../models/match3/tileType.js')).default;
|
|
return await Match3TileType.create(data);
|
|
}
|
|
|
|
async updateMatch3TileType(userId, id, data) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3TileType = (await import('../models/match3/tileType.js')).default;
|
|
const tileType = await Match3TileType.findByPk(id);
|
|
if (!tileType) throw new Error('Tile type not found');
|
|
await tileType.update(data);
|
|
return tileType;
|
|
}
|
|
|
|
async deleteMatch3TileType(userId, id) {
|
|
if (!(await this.hasUserAccess(userId, 'match3'))) {
|
|
throw new Error('noaccess');
|
|
}
|
|
const Match3TileType = (await import('../models/match3/tileType.js')).default;
|
|
return await Match3TileType.destroy({ where: { id } });
|
|
}
|
|
}
|
|
|
|
export default new AdminService(); |