본문 바로가기

Server/PHP

[php] Carbon & Date

반응형

db에서 불러온 날짜 데이터값을 계산해야 하는 일이 있었는데,

각 행 별 날짜 차이를 계산해야 했음.

지금 프로젝트의 서버는 라라벨의 루멘, carbon을 사용하고 있어서 여기에서 뭐가 있나 했는데 diff관련 함수가 있어서 사용했다.

// 차량관리->차량별 상태 변경 로그       19.05.31           sang
    public function getCarStatusLog(Request $request){
        $mCar = new Cars();
        $vin_number = $request->input('vin_number');

        $select_status = $request->input('select_status');
        if($select_status)
            $select_status = explode(',', $select_status);

        $carInfo = $mCar->getInfoVinNumber($vin_number);
        $statusLog = $mCar->getCarStatusLog($vin_number, $select_status);

        $carRegistDate = Carbon::parse($carInfo->regist_date)->format("Y-m-d");
        $carRegistDate = Carbon::parse($carRegistDate);

        $result['totCarDay'] = Carbon::now()->diffInDays($carRegistDate);
        $result['log'] = $statusLog;
        $result['totRent'] = 0;

        if($statusLog){
            for($i=count($statusLog)-1 ; $i>=0 ; $i--){
            // WebHelpers::D($statusLog[$i]->regist_date);

                // 지속기간(날짜) 계산
                if($i > 0){
                // diffInDays는 시간단위도 계산해서 24시간이 지나지 않으면 일수로 계산x
                // 시간 단위를 떼고 계산하기로
                $time1 = Carbon::parse($statusLog[$i-1]->regist_date)->format("Y-m-d");
                $time2 = Carbon::parse($statusLog[$i]->regist_date)->format("Y-m-d");
                $time1 = Carbon::parse($time1);
                $time2 = Carbon::parse($time2);
                $statusLog[$i]->contDay = $time1->diffInDays($time2);

                } else {
                $time1 = Carbon::now();
                $time2 = Carbon::parse($statusLog[$i]->regist_date);
                $time2 = Carbon::parse($time2);
                $statusLog[$i]->contDay = $time1->diffInDays($time2);
                }
                //총 구독날짜 계산
                if($statusLog[$i]->car_status=='02')
                $result['totRent'] += $statusLog[$i]->contDay;
            };
        WebHelpers::OK_AND_RETURN('', '', $result);
        } else
        WebHelpers::ERROR_AND_RETURN("차량상태 변경이력 없음");
    }

이러엏게..

floatDiffInDays() 같은 함수도 있었지만 버전이 바뀌면서 사라진건지 뭔지 찾을 수 없다길래 (지금 생각해보면 서버가 lumen이라서 그럴지도 모르겠다. 아니면 말고) 그냥 diffInDays() 를 사용했는데, 코드에 나와있는 것 처럼 DB에 시간이 함께 저장되어있다면 (Datetime type) 시간단위까지 계산해서 만 하루가 지나지 않으면 1일로 계산이 되지 않는 듯 했다. (그래서 정수형 값을 반환하는 floatDiffInDays를 쓰려고 했던거고)

결국 시간은 떼버리고 계산하기로 결정.. format() 함수로 값을 추출하는 순간 더이상 carbon 오브젝트형 객체가 아닌, String 값만 취하므로 다시 한 번 Carbon 형으로 parse해줘야 하는 번거로움도 거치고.. 계산했다 음응응..

 

+) 추가로 vue나 html 등 웹 페이지에서 날짜를 받아와서 그 날짜 범위에 해당하는 데이터만 불러와 출력해야 하는 일이 종종 있다. 뭐 주문 내역이나, 결제 내역 이외에도 등등등? 그런데 이 때 DB에 Datetime 형식으로 db에 값이 저장되어 있으면 또 다시 귀찮은 문제. 

웹, view 단에서 받아온 값은 Y-m-d 00:00:00 값으로 처리되고, db에는 해당 날짜의 시간까지 계산되어있기 때문에 내가 4월 5일~ 5월 5일의 데이터를 받아오려고 해도 마지막 날짜시간 값이 19-05-05 00:00:00 으로 설정되기 때문에 정작 5월 5일의 데이터는 받아오지 못했다.. 진자 ㅂㄷㅂㄷ... 테스트 다시 한 번 더 안 해봤으면 모르고 그냥 지나칠 뻔 했음.

아무튼 그래서 사용한게 endOfDay() 함수. 해당 일자의 마지막 시간까지 계산된 값을 return 해주는 것 같다.

$end_date = $request->input('end_date');
$end_date = Carbon::parse($end_date)->endOfDay()->format('Y-m-d H:i:s');

$memberInfo = $mMember->getInfoWithAuthCode($auth_code);
$result = $mMember->getPayLog($memberInfo->email, $start_date, $end_date);

나는 이렇게 썼음..

 

추가로 endOfWeek, Month... 등 시간 날짜별로 관련 함수가 존재하고, 시간 계산 중 {add, sub, set}UnitNoOverflow('계산시간단위', 값, '기준시간단위?') 라고 시간계산을 할 때 기준시간(날짜, 시간, 달..) 을 넘기지 않는 선에서 계산할 시간을 계산할 값 만큼 add, sub.. 해서 return 하는 함수도 있다.

 

참고한 소스페이지는 여기 

https://carbon.nesbot.com/docs/

반응형