package com.icomsys.main_vm.db.jpa.repo.system.dsl;

import com.icomsys.main_vm.biz.rcp.conversation.vo.ConversationScenarioWorkHistoryRes;
import com.icomsys.main_vm.biz.rcp.monitoring.vo.RetrieveWorkHstListVo;
import com.icomsys.main_vm.biz.rcp.monitoring.vo.SearchWorkHstVo;
import com.icomsys.main_vm.common.code.enumresource.MenuResource;
import com.icomsys.main_vm.db.jpa.entity.conversation.QTbIcsLog;
import com.icomsys.main_vm.db.jpa.entity.system.QTbBotCommonCode;
import com.icomsys.main_vm.db.jpa.entity.system.QTbBotUser;
import com.icomsys.main_vm.db.jpa.entity.system.QTbIcsOprMngInfo;
import com.icomsys.main_vm.db.jpa.entity.system.QTbServiceGrouop;
import com.querydsl.core.QueryResults;
import com.querydsl.core.types.ConstantImpl;
import com.querydsl.core.types.Projections;
import com.querydsl.core.types.dsl.Expressions;
import com.querydsl.core.types.dsl.StringTemplate;
import com.querydsl.jpa.impl.JPAQueryFactory;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.aspectj.lang.annotation.Aspect;

@Aspect
@Slf4j
@RequiredArgsConstructor
public class TbIcsLogDslImpl implements TbIcsLogDsl {

    private final JPAQueryFactory queryFactory;
    QTbIcsLog qTbIcsLog = QTbIcsLog.tbIcsLog;
    QTbBotUser qTbBotUser = QTbBotUser.tbBotUser;
    QTbServiceGrouop qTbServiceGrouop = QTbServiceGrouop.tbServiceGrouop;
    QTbIcsOprMngInfo qTbIcsOprMngInfo = QTbIcsOprMngInfo.tbIcsOprMngInfo;

    StringTemplate dateTemplate = Expressions.stringTemplate(
            "DATE_FORMAT({0}, {1})"
            , qTbIcsLog.registDate
            , ConstantImpl.create("%Y-%m-%d")
    );

    @Override
    public QueryResults<RetrieveWorkHstListVo> retrieveWorkHst(SearchWorkHstVo searchWorkHstVo) {
        QueryResults<RetrieveWorkHstListVo> result = null;

            var query = queryFactory.select(
                            Projections.fields(RetrieveWorkHstListVo.class
                                    , qTbIcsLog.seq
                                    , Expressions.stringTemplate(
                                            "DATE_FORMAT({0}, {1})"
                                            , qTbIcsLog.registDate
                                            , ConstantImpl.create("%Y-%m-%d %H:%i:%s")
                                    ).as("registDate")
//                                    , qTbIcsLog.serviceGroup.coalesce("-").as("serviceGroup")
                                    , qTbServiceGrouop.serviceGroupName.coalesce("-").as("serviceGroup")
                                    , qTbIcsLog.userId
                                    , qTbBotUser.userName
                                    , qTbIcsLog.menuAuth
                                    , qTbIcsLog.actionCode
                                    , qTbIcsLog.ip
                                    , qTbIcsLog.remark.coalesce("-").as("remark")))
                    .from(qTbIcsLog)
                    .innerJoin(qTbBotUser).on(qTbIcsLog.userId.eq(qTbBotUser.userId))
                    .innerJoin(qTbServiceGrouop).on(qTbIcsLog.serviceGroup.eq(qTbServiceGrouop.serviceGroup))
                    .where(dateTemplate.goe(searchWorkHstVo.getStartDate())
                            .and(dateTemplate.loe(searchWorkHstVo.getEndDate())));
            query.limit(searchWorkHstVo.getSize()).offset(searchWorkHstVo.getPage() * searchWorkHstVo.getSize());
            //조회조건
            if (searchWorkHstVo.getSearchKey1().equals("id")) {
                query.where(qTbIcsLog.userId.upper().contains(searchWorkHstVo.getCodeText().toUpperCase()));
            }
            if (searchWorkHstVo.getSearchKey1().equals("userName")) {
                query.where(qTbBotUser.userName.upper().contains(searchWorkHstVo.getCodeText().toUpperCase()));
            }
            if (searchWorkHstVo.getSearchKey1().equals("ip")) {
                query.where(qTbIcsLog.ip.upper().contains(searchWorkHstVo.getCodeText().toUpperCase()));
            }
            if (searchWorkHstVo.getSearchKey1().equals("remark")) {
                query.where(qTbIcsLog.remark.upper().contains(searchWorkHstVo.getCodeText().toUpperCase()));
            }
            if (searchWorkHstVo.getServiceGroup() != null && !(searchWorkHstVo.getServiceGroup().equals("ALL"))) {
                query.where(qTbIcsLog.serviceGroup.eq(searchWorkHstVo.getServiceGroup()));
            }
            if (searchWorkHstVo.getMenuCategory() != null && !(searchWorkHstVo.getMenuCategory().equals("ALL"))) {
                query.where(qTbIcsLog.actionCode.eq(searchWorkHstVo.getMenuCategory()));
            }
            if (searchWorkHstVo.getMenuName() != null && !(searchWorkHstVo.getMenuName().equals("ALL"))) {
                query.where(qTbIcsLog.menuAuth.eq(searchWorkHstVo.getMenuName()));
            }
            //order By
            query.orderBy(qTbIcsLog.seq.desc());
            result = query.fetchResults();

            return result;
    }

    public QueryResults<ConversationScenarioWorkHistoryRes> scenarioWorkHistory(String menuAuth, String scenarioSeq) {
        QueryResults<ConversationScenarioWorkHistoryRes> result = queryFactory.select(
                Projections.fields(
                    ConversationScenarioWorkHistoryRes.class,
                        qTbIcsLog.seq,
                        qTbIcsLog.registDate,
                        qTbIcsLog.actionCode,
                        qTbIcsLog.actionCode.as("action"),               // Todo: Common Code 정의 후 다시 생성
//                        qTbBotCommonCode.description.as("action"),
                        qTbIcsLog.userId,
                        qTbBotUser.userName,
                        qTbIcsLog.ip,
                        qTbIcsLog.remark,
                        qTbIcsLog.attribute1,
                        qTbIcsLog.attribute2,
                        qTbIcsLog.attribute3,
                        qTbIcsLog.attribute4
                    )
                )
                .from(qTbIcsLog)
                .innerJoin(qTbBotUser).on(qTbIcsLog.userId.eq(qTbBotUser.userId))
//                .innerJoin(qTbBotCommonCode).on(qTbIcsLog.actionCode.eq(qTbBotCommonCode.minorCode))
                .where( qTbIcsLog.menuAuth.eq(menuAuth),
                        qTbIcsLog.attribute1.eq(scenarioSeq)
                )
                .orderBy(qTbIcsLog.registDate.asc())
                .fetchResults();

        return result;
    }


}

