package com.gzzm.lobster.pending;

import com.gzzm.lobster.common.PendingRequestStatus;
import net.cyan.thunwind.annotation.OQL;
import net.cyan.thunwind.annotation.OQLUpdate;
import net.cyan.thunwind.dao.GeneralDao;

import java.util.Date;
import java.util.List;

/**
 * PendingRequestDao —— PendingRequest 持久化 / PendingRequest persistence.
 *
 * <p>status 枚举字段 thunwind 默认存 smallint ordinal，OQL 里一律用参数绑定，不要写字符串字面量。
 */
public abstract class PendingRequestDao extends GeneralDao {

    @OQL("select p from PendingRequest p where p.requestId=:1")
    public abstract PendingRequest getRequest(String requestId) throws Exception;

    @OQL("select p from PendingRequest p where p.threadId=:1 and p.status=?2 order by p.createTime desc")
    public abstract List<PendingRequest> listOpenByThread(String threadId, PendingRequestStatus status) throws Exception;

    @OQL("select p from PendingRequest p where p.userId=:1 and p.status=?2 order by p.createTime desc limit :3,:4")
    public abstract List<PendingRequest> listOpenByUser(String userId, PendingRequestStatus status, int offset, int limit) throws Exception;

    @OQL("select count(p.requestId) from PendingRequest p where p.threadId=:1 and p.status=?2")
    public abstract Long countOpenByThread(String threadId, PendingRequestStatus status) throws Exception;

    @OQLUpdate("update PendingRequest set status=?1, responsePayloadJson=?2, resolvedAt=?3 where requestId=?4 and status=?5")
    public abstract int resolve(PendingRequestStatus status, String responsePayloadJson, Date resolvedAt,
                                String requestId, PendingRequestStatus expectedStatus) throws Exception;

    @OQLUpdate("update PendingRequest set status=?1, responsePayloadJson=null, resolvedAt=null where requestId=?2 and status=?3")
    public abstract int reopen(PendingRequestStatus status, String requestId, PendingRequestStatus expectedStatus) throws Exception;

    @OQLUpdate("update PendingRequest set status=?1, resolvedAt=?2 where sourceRunId=?3 and status=?4")
    public abstract int cancelOpenBySourceRun(PendingRequestStatus status, Date resolvedAt,
                                              String sourceRunId, PendingRequestStatus expectedStatus) throws Exception;

    @OQLUpdate("update PendingRequest set status=?1 where status=?2 and expiredAt is not null and expiredAt<=?3")
    public abstract int expireAll(PendingRequestStatus to, PendingRequestStatus from, Date now) throws Exception;
}
