import User from '../models/community/user.js';
import UserParam from '../models/community/user_param.js';
import UserParamType from '../models/type/user_param.js'; 
import UserParamVisibility from '../models/community/user_param_visibility.js';
import UserParamVisibilityType from '../models/type/user_param_visibility.js';
import { Op } from 'sequelize';
import UserRight from '../models/community/user_right.js';
import UserRightType from '../models/type/user_right.js';

class BaseService {
    async getUserByHashedId(hashedId) {
        console.log('async getUserByHashedId: ', hashedId);
        const user = await User.findOne({ where: { hashedId: hashedId } });
        if (!user) {
            console.log('User not found: ', hashedId);
            throw new Error('User not found: ', hashedId);
        }
        return user;
    }

    async getUserById(userId) {
        const user = await User.findOne({ where: { id: userId } });
        if (!user) {
            throw new Error('User not found');
        }
        return user;
    }

    async getUserParams(userId, paramDescriptions) {
        return await UserParam.findAll({
            where: { userId },
            include: [
                {
                    model: UserParamType,
                    as: 'paramType',
                    where: { description: { [Op.in]: paramDescriptions } }
                },
                {
                    model: UserParamVisibility,
                    as: 'param_visibilities',
                    include: [
                        {
                            model: UserParamVisibilityType,
                            as: 'visibility_type'
                        }
                    ]
                }
            ]
        });
    }

    calculateAge(birthdate) {
        const birthDate = new Date(birthdate);
        const ageDifMs = Date.now() - birthDate.getTime();
        const ageDate = new Date(ageDifMs);
        return Math.abs(ageDate.getUTCFullYear() - 1970);
    }


    async isUserAdult(userId) {
        const birthdateParam = await this.getUserParams(userId, ['birthdate']);
        if (!birthdateParam || birthdateParam.length === 0) {
            return false;
        }
        const birthdate = birthdateParam[0].value; 
        const age = this.calculateAge(birthdate);
        return age >= 18;
    }

    async checkUserAccess(hashedId) {
        const user = await this.getUserByHashedId(hashedId);
        if (!user || !user.active) throw new Error('Access denied: User not found or inactive');
        return user.id;
    }

    async getUserRights(userId) {
        const userRights = await UserRight.findAll({
            where: { userId },
            include: [
                {
                    model: UserRightType,
                    as: 'rightType',
                    attributes: ['title']
                }
            ]
        });

        return userRights.map((right) => right.rightType.title);
    }

    async hasUserRight(userId, requiredRights) {
        console.log(requiredRights);
        const userRights = await this.getUserRights(userId);
        return userRights.some((right) => requiredRights.includes(right));
    }

}

export default BaseService;
