package com.its.op.entity.its.road;

import com.its.op.global.CodeManager;
import com.its.op.dto.its.road.TbRoadDto;
import com.its.op.entity.its.node.TbNode;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Getter;
import lombok.NoArgsConstructor;
import org.hibernate.annotations.NotFound;
import org.hibernate.annotations.NotFoundAction;

import javax.persistence.*;
import java.io.Serializable;

/**
 * 도로 Entity Class
 */
@Getter
@NoArgsConstructor
@Builder
@AllArgsConstructor
@ApiModel("도로")
@Entity
@Table(name = "TB_ROAD")
public class TbRoad implements Serializable {
    private static final long serialVersionUID = 1L;

    @ApiModelProperty("도로 ID")  // N NUMBER(10)
    @Id
    @Column(name = "ROAD_ID", nullable = false, columnDefinition = "NUMBER", length = 10)
    private Long roadId;

    @ApiModelProperty("도로명")  // Y VARCHAR(50)
    @Column(name = "ROAD_NM", length = 50)
    private String roadNm;

    @ApiModelProperty("방향 코드")  // Y VARCHAR(7)
    @Column(name = "DRCT_CD", length = 7)
    private String drctCd;

    @ApiModelProperty("시점 명")  // Y VARCHAR(100)
    @Column(name = "STRT_NM", length = 100)
    private String strtNm;

    @ApiModelProperty("종점 명")  // Y VARCHAR(100)
    @Column(name = "END_NM", length = 100)
    private String endNm;

    @ApiModelProperty("삭제 여부")  // Y CHAR(1)
    @Column(name = "DEL_YN", columnDefinition = "CHAR", length = 1)
    private String delYn;

    @ApiModelProperty("구간 길이")  // Y NUMBER(5)
    @Column(name = "SECT_LNGT", columnDefinition = "NUMBER", length = 5)
    private Integer sectLngt;

    @ApiModelProperty("시작 노드 ID")  // Y NUMBER(10)
    @Column(name = "F_NODE_ID", columnDefinition = "NUMBER", length = 10)
    private Long fNodeId;

    @ApiModelProperty("종료 노드 ID")  // Y NUMBER(10)
    @Column(name = "T_NODE_ID", columnDefinition = "NUMBER", length = 10)
    private Long tNodeId;

    @ApiModelProperty("구간 등급 코드")  // Y VARCHAR(7)
    @Column(name = "SECT_GRAD_CD", length = 7)
    private String sectGradCd;

    @ApiModelProperty("지역 코드")  // Y VARCHAR(7)
    @Column(name = "AREA_CD", length = 7)
    private String areaCd;

    @OneToOne
    @JoinColumn(insertable=false, updatable=false, name="F_NODE_ID", referencedColumnName = "NODE_ID")
    @NotFound(action = NotFoundAction.IGNORE)
    private TbNode fromNode;

    @OneToOne
    @JoinColumn(insertable=false, updatable=false, name="T_NODE_ID", referencedColumnName = "NODE_ID")
    @NotFound(action = NotFoundAction.IGNORE)
    private TbNode toNode;

    public TbRoadDto toDto() {
        TbRoadDto dto = TbRoadDto.builder()
                .roadId(this.roadId)
                .roadNm(this.roadNm)
                .drctCd(this.drctCd)
                .strtNm(this.strtNm)
                .endNm(this.endNm)
                .delYn(this.delYn)
                .sectLngt(this.sectLngt)
                .fNodeId(this.fNodeId)
                .tNodeId(this.tNodeId)
                .sectGradCd(this.sectGradCd)
                .areaCd(this.areaCd)
                .build();

        dto.setFromNodeInfo(this.getFromNode().getNodeName() == null ? "" : this.getFromNode().getNodeName());
        dto.setToNodeInfo(this.getToNode().getNodeName() == null ? "" : this.getToNode().getNodeName());

        dto.setDrctDesc(CodeManager.getCodeDesc(CodeManager.DRCT_CD, this.drctCd));
        dto.setSectGradDesc(CodeManager.getCodeDesc(CodeManager.SECT_GRAD_CD, this.sectGradCd));

        return dto;
    }

    public TbRoad(Long roadId) {
        this.roadId = roadId;
    }

    public void updateInfo(TbRoadDto.TbRoadUpdReq req) {
        this.roadNm = req.getRoadNm();
        this.drctCd = req.getDrctCd();
        this.strtNm = req.getStrtNm();
        this.endNm = req.getEndNm();
        this.delYn = req.getDelYn();
        this.sectLngt = req.getSectLngt();
        this.fNodeId = req.getFNodeId();
        this.tNodeId = req.getTNodeId();
        this.sectGradCd = req.getSectGradCd();
        this.areaCd = req.getAreaCd();
    }

    public void updateName(TbRoadDto.TbRoadNameUpdReq req) {
        this.roadNm = req.getRoadName();
        this.strtNm = req.getStrtNm();
        this.endNm = req.getEndNm();
    }

    public void updateSectGrad(TbRoadDto.TbRoadSectGradUpdReq req) {
        this.sectGradCd = req.getSectGradCd();
    }
}
