package com.arms.api.util.redisrepo;

import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Component;

import java.util.Collection;
import java.util.List;
import java.util.concurrent.TimeUnit;

@Component
public class RedisStringCommand {

    private final RedisTemplate<String, Object> redisTemplate;

    public RedisStringCommand(RedisTemplate<String, Object> redisTemplate) {
        this.redisTemplate = redisTemplate;
    }

    // ── 조회 ──

    /**
     * 키의 값을 조회 (GET)
     */
    public Object get(String key) {
        return redisTemplate.opsForValue().get(key);
    }

    /**
     * 여러 키의 값을 한번에 조회 (MGET)
     */
    public List<Object> getMulti(Collection<String> keys) {
        return redisTemplate.opsForValue().multiGet(keys);
    }

    /**
     * 키의 값을 조회하고 새 값으로 교체 (GETSET)
     */
    public Object getAndSet(String key, Object value) {
        return redisTemplate.opsForValue().getAndSet(key, value);
    }

    /**
     * 키의 문자열 길이를 조회 (STRLEN)
     */
    public Long size(String key) {
        return redisTemplate.opsForValue().size(key);
    }

    // ── 저장 ──

    /**
     * 키에 값을 저장 (SET)
     */
    public void set(String key, Object value) {
        redisTemplate.opsForValue().set(key, value);
    }

    /**
     * 키에 값을 저장하고 만료시간 설정 (SETEX)
     */
    public void setWithExpire(String key, Object value, long timeout, TimeUnit unit) {
        redisTemplate.opsForValue().set(key, value, timeout, unit);
    }

    /**
     * 키가 없을 때만 저장 (SETNX)
     */
    public Boolean setIfAbsent(String key, Object value) {
        return redisTemplate.opsForValue().setIfAbsent(key, value);
    }

    /**
     * 여러 키에 값을 한번에 저장 (MSET)
     */
    public void setMulti(java.util.Map<String, Object> entries) {
        redisTemplate.opsForValue().multiSet(entries);
    }

    // ── 증감 ──

    /**
     * 키의 값을 1 증가 (INCR)
     */
    public Long increment(String key) {
        return redisTemplate.opsForValue().increment(key);
    }

    /**
    /**
     * 키의 값을 정수만큼 증가 (INCRBY)
     */
    public Long increment(String key, long delta) {
        return redisTemplate.opsForValue().increment(key, delta);
    }

    /**
     * 키의 값을 실수만큼 증가 (INCRBYFLOAT)
     */
    public Double incrementFloat(String key, double delta) {
        return redisTemplate.opsForValue().increment(key, delta);
    }

    /**
     * 키의 값을 1 감소 (DECR)
     */
    public Long decrement(String key) {
        return redisTemplate.opsForValue().decrement(key);
    }

    /**
     * 키의 값을 정수만큼 감소 (DECRBY)
     */
    public Long decrement(String key, long delta) {
        return redisTemplate.opsForValue().decrement(key, delta);
    }

    // ── 문자열 조작 ──

    /**
     * 키의 값 뒤에 문자열을 추가 (APPEND)
     */
    public Integer append(String key, String value) {
        return redisTemplate.opsForValue().append(key, value);
    }

}
