우커머스 판매 종료까지 남은 시간 표시하기

우커머스 판매 종료 시간 설정/표시하기에서 판매 종료 시간을 설정하고 표시하는 방법을 살펴보았습니다. 이 글에서는 조금 더 발전시켜 판매 종료 시까지 남은 시간을 표시하는 방법을 살펴보겠습니다.

기본적인 아이디어는 PublishPress Future: Automatically Unpublish WordPress Posts 플러그인(기존 명칭 "Post Expirator")을 사용하여 개별 글에서 판매 종료 날짜와 시간을 설정하면, 그 날짜를 현재 날짜와 비교하여 차이를 표시하는 것입니다. 이를 위해서는 PublishPress Future 플러그인의 파일을 약간 수정하여 날짜를 반환하는 새로운 숏코드를 만들고, 그 쇼트코드를 이용하여 현재 날짜와 비교하는 방법을 생각해 보았습니다.

[ 이 글을 2022년 3월 30일에 최종 업데이트되었습니다. ]

우커머스 판매 종료까지 남은 시간 표시하기

최종 코드 - 최신 버전에서 작동함 (업데이트)

최신 우커머스 버전에 맞게 아래의 코드를 수정했습니다. 최종적으로 다음 코드를 사용 중인 테마(차일드 테마를 만들어 작업하세요)의 함수 파일에 추가하여 테스트해보시기 바랍니다.

function postexpiratordiffer_shortcode($atts)
{
    global $post;

    $enabled = PostExpirator_Facade::is_expiration_enabled_for_post($post->ID);
    $expirationdatets = get_post_meta($post->ID, '_expiration-date', true);
    if (! $enabled || empty($expirationdatets)) {
        return false;
    }

    // @TODO remove extract
    // phpcs:ignore WordPress.PHP.DontExtract.extract_extract
    extract(
        shortcode_atts(
            array(
                'dateformat' => get_option('expirationdateDefaultDateFormat', POSTEXPIRATOR_DATEFORMAT),
                'timeformat' => get_option('expirationdateDefaultTimeFormat', POSTEXPIRATOR_TIMEFORMAT),
                'type' => 'full',
                'tz' => date('T'),
            ),
            $atts
        )
    );

    if (empty($dateformat)) {
        global $expirationdateDefaultDateFormat;
        $dateformat = $expirationdateDefaultDateFormat;
    }

    if (empty($timeformat)) {
        global $expirationdateDefaultTimeFormat;
        $timeformat = $expirationdateDefaultTimeFormat;
    }

    if ($type === 'full') {
        $format = $dateformat . ' ' . $timeformat;
    } elseif ($type === 'date') {
        $format = $dateformat;
    } elseif ($type === 'time') {
        $format = $timeformat;
    }

    $date = gmdate('Y-m-d H:i:s', $expirationdatets);
    return $date;
}

add_shortcode( 'postexpiratordiffer', 'postexpiratordiffer_shortcode' );


// display: expiration date for WooCommerce Products
// 우커머스 상품의 만료일 표시

function woocommerce_expiration_date ( $desc ){
global $product;

if ( is_single( $product->get_id() ) ){

$tempCheck = do_shortcode( '[postexpirator]' );
if(empty($tempCheck)) {
$desc .= '<div class="expriacy-date">종료일: 없음</div>';
} else {
$desc .= '<div class="expiracy-date">종료일: ' . do_shortcode( '[postexpirator]' ) . '</div>';

$expriationdate = do_shortcode( '[postexpiratordiffer]' );
$now = date('Y-m-d H:i:s');

$desc .= '<div id="autoexpirationdate" style="font-size: 12px; color: red">(';

$diff = abs(strtotime($now) - strtotime($expriationdate));

$years = floor($diff / (365*60*60*24));
$months = floor(($diff - $years * 365*60*60*24) / (30*60*60*24));
$days = floor(($diff - $years * 365*60*60*24 - $months*30*60*60*24)/ (60*60*24));
$days2 = floor(($diff - $years * 365*60*60*24)/ (60*60*24));
$hours = floor(($diff - $years * 365*60*60*24 - $months*30*60*60*24 - $days*60*60*24)/ (60*60));
$minutes = floor(($diff - $years * 365*60*60*24 - $months*30*60*60*24 - $days*60*60*24 - $hours*60*60)/ (60));
$seconds = floor(($diff - $years * 365*60*60*24 - $months*30*60*60*24 - $days*60*60*24 - $hours*60*60 - $minutes*60));

$seconds = floor(($diff - $years * 365*60*60*24 - $months*30*60*60*24 - $days*60*60*24 - $hours*60*60 - $minutes*60));

$desc .= $days2 . '일 ' . $hours . '시간 ' . $minutes . '분 ' . $seconds . '초';

$desc .= ' 남음)</div><br>';
}
 return $desc;
}
}
add_filter( 'woocommerce_short_description', 'woocommerce_expiration_date' );

날짜 형식이나 스타일(글자색 등)은 적절히 수정하시기 바랍니다. 플랫섬(Flatsome) 테마에서 테스트해보니 아래 그림과 같이 잘 작동하는 것을 확인했습니다.

우커머스 판매 종료까지 남은 시간 표시하기

종료일(만료일)을 지정하지 않은 경우에는 "종료일: 없음"으로 표시됩니다.

아래에 제시된 코드를 사용하면 에러가 발생합니다. 해당 에러는 "string(2) "id" Notice: id was called incorrectly. Product properties should not be accessed directly. Backtrace:" 문서에서 다루고 있습니다.

기존 내용은 기록 차원에서 삭제하지 않고 남겨두겠습니다. 관심이 있는 분은 참고해보시기 바랍니다.


기존 코드(참고용)

post-expirator.php 파일 수정

수정할 파일은 Post Expirator 플러그인 내에 있는 post-expirator.php 파일입니다. 이 파일에서 function postexpirator_shortcode($atts) 부분을 찾습니다. 그런 다음 이 함수 전체를 복사하여 바로 아래에 붙여넣기 하도록 합니다. 함수 이름과 숏코드 이름을 적절히 수정해 줍니다. 맨 끝부분에서 반환하는 값만 수정해 주면 됩니다.

return get_date_from_gmt(gmdate('Y-m-d H:i:s',$expirationdatets),$format);
우커머스 판매 종료까지 남은 시간 표시하기

이 부분을 아래의 그림 부분에 표시된 형태로 수정해 주도록 합니다.

다시 정리해 보면:

  1. Post Expirator 플러그인 내에 있는 post-expirator.php 파일을 엽니다.
  2. function postexpirator_shortcode($atts) 부분을 찾습니다.
  3. function postexpirator_shortcode($atts) 부분을 통째로 복사하여 바로 아래에 복사합니다.
  4. 복사한 함수의 이름과 숏코드를 적절히 수정합니다. (저는 postexpiratorpostexpiratordiffer로 수정했습니다. 원하는 이름으로 수정하시면 됩니다.)
  5. return get_date_from_gmt(gmdate('Y-m-d H:i:s',$expirationdatets),$format); 부분을 위의 그림과 같이 수정해 줍니다. 실제로는 get_date_from_gmt 부분만 제거했습니다.

WooCommerce 파일 수정

다음으로 할 일은 앞의 글에서 수정했던 woocommerce/wp-content/plugins/woocommerce/templates/single-product 폴더 아래의 short-description.php 파일에 날짜를 비교하여 출력해주는 코드를 추가합니다. 글의 만료 날짜(종료 날짜)와 현재 날짜는 다음 코드를 사용하시면 됩니다.

$expriationdate = do_shortcode( '[postexpiratordiffer]' );
$now = date('Y-m-d H:i:s');

그리고 날짜 비교 함수는 이 페이지의 코드를 사용하도록 합니다.
그러면 다음과 같은 코드를 추가로 삽입하면 남은 날짜가 표시됩니다.

$expriationdate = do_shortcode( '[postexpiratordiffer]' );
$now = date('Y-m-d H:i:s');
$diff = abs(strtotime($now) - strtotime($expriationdate));
$years = floor($diff / (365*60*60*24));
...
우커머스 판매 종료까지 남은 시간 표시하기

"..."으로 생략 표시된 부분은 날짜 비교 함수 diff()의 나머지 부분으로 대체하시면 됩니다. 그러면 다음과 같이 남은 날짜가 표시됩니다.

추가

이때까지의 코드를 정리해보면 다음과 같습니다. 상황에 맞게 수정하여 사용하시면 됩니다.

<?php
$tempCheck = do_shortcode( '[postexpirator]' );
if(empty($tempCheck)) {
echo '<div class="expriacy-date">종료일: 없음</div>';
} else {
echo '<div class="expiracy-date">종료일: ' . do_shortcode( '[postexpirator]' ) . '</div>';


$expriationdate = do_shortcode( '[postexpiratordiffer]' );
$now = date('Y-m-d H:i:s');

echo '<div id="autoexpirationdate" style="font-size: 12px; color: red">(';

$diff = abs(strtotime($now) - strtotime($expriationdate));

$years = floor($diff / (365*60*60*24));
$months = floor(($diff - $years * 365*60*60*24) / (30*60*60*24));
$days = floor(($diff - $years * 365*60*60*24 - $months*30*60*60*24)/ (60*60*24));
$days2 = floor(($diff - $years * 365*60*60*24)/ (60*60*24));
$hours = floor(($diff - $years * 365*60*60*24 - $months*30*60*60*24 - $days*60*60*24)/ (60*60));
$minutes = floor(($diff - $years * 365*60*60*24 - $months*30*60*60*24 - $days*60*60*24 - $hours*60*60)/ (60));
$seconds = floor(($diff - $years * 365*60*60*24 - $months*30*60*60*24 - $days*60*60*24 - $hours*60*60 - $minutes*60));


printf("%d일 %d시간 %d분 %d초\n", $days2, $hours, $minutes, $seconds);

echo ' 남음)</div>';

}
?>

올바른 방법 - 심화

이때까지는 플러그인을 수정하고 우커머스 파일을 수정하는 방식으로 적용했습니다. 하지만 이러한 방법은 별로 좋은 방법이 아닙니다. 동일한 내용을 함수 파일에 직접 추가해주면 굳이 플러그인 코어 파일을 수정할 필요가 없고, WooCommerce 파일을 수정할 필요도 없습니다. (그러면 이 때까지의 과정이 무의미했는가 하면, 그렇지 않습니다. 앞의 과정이 있기 때문에 아래의 과정으로 응용이 가능합니다.)

이를 위해, 먼저 위의 post-expirator.php 파일 수정 부분에서 새롭게 추가한 함수 부분을 post-expirator.php 파일에 추가하지 말고 테마의 함수 파일에 추가하도록 합니다.

다음으로, 위의 WooCommerce 파일 수정 부분을 직접 우커머스 템플릿 파일에 추가하지 말고 함수 파일에 추가하도록 합니다. 그러기 위해서는 다음과 같이 filter를 사용하여 우커머스 템플릿 파일을 수정하지 않고 원하는 컨텐츠를 추가할 수 있습니다.

// display: expiration date for WooCommerce Products 

function woocommerce_expiration_date ( $desc ){
global $product;

if ( is_single( $product->id ) ){

$tempCheck = do_shortcode( '[postexpirator]' );
if(empty($tempCheck)) {
$desc .= '<div class="expriacy-date">종료일: 없음</div>';
} else {
$desc .= '<div class="expiracy-date">종료일: ' . do_shortcode( '[postexpirator]' ) . '</div>';

$expriationdate = do_shortcode( '[postexpiratordiffer]' );
$now = date('Y-m-d H:i:s');

$desc .= '<div id="autoexpirationdate" style="font-size: 12px; color: red">(';

$diff = abs(strtotime($now) - strtotime($expriationdate));

// 위의 코드와 동일
$seconds = floor(($diff - $years * 365*60*60*24 - $months*30*60*60*24 - $days*60*60*24 - $hours*60*60 - $minutes*60));

$desc .= $days2 . '일 ' . $hours . '시간 ' . $minutes . '분 ' . $seconds . '초';

$desc .= ' 남음)</div><br>';
}
return $desc;
}
}
add_filter( 'woocommerce_short_description', 'woocommerce_expiration_date' );

그러면 다음 그림과 같이 추가됩니다.

우커머스 판매 종료까지 남은 시간 표시하기

레이아웃은 CSS를 사용하여 적절히 수정하도록 합니다.

남은 시간을 5초 혹은 10초마다 자동 로드되게 하려면 DIV 자동 새로 고침 javascript 글에 나오는 스크립트를 사용하면 됩니다.

참고:

일부 글에 제휴 링크가 포함될 수 있으며 파트너스 활동으로 일정액의 수수료를 받을 수 있습니다.

7개 댓글

  1. 안녕하세요
    하나 질문 드릴게 있습니다!
    심화 부분의 내용을 가져와서 작업을 해봤는데 strtotime($now)는 정상 동작하는데 strtotime($expriationdate)가 빈 값으로 나오더라구요.

    그래서 $now와 $expriationdate를 각각 확인해보니 $now는 현재 시간을 'Y-m-d H:i:s' 형식으로 출력하는 반면에 $expriationdate는 '2022년 3월 30일' 이런식으로 출력합니다.

    이럴 경우에는 $expriationdate 형식을 $now와 같은 형식으로 바꿔줘야 하는걸까요? date함수로 이래저래 형식을 변경해봤는데 뜻대로 되지 않아서 문의드립니다!

      1. 이렇게 빨리 해결해주실 줄은 몰랐습니다 ㅎㅎ
        워드프레스 작업 할 때마다 많은 도움을 받고 있는데 늘 고맙습니다!

    1. 방문해주셔서 감사합니다. 글이 작성된지 오래되어서 위의 내용이 잘 적용될지는 장담할 수 없습니다. "다른 방법 – 심화" 부분의 내용을 적용해보시기 바랍니다. 적용해보시고 잘 되는지도 피드백 부탁드립니다. 즐거운 저녁 시간 되세요.

댓글 남기기

이메일 주소는 공개되지 않습니다. 필수 필드는 *로 표시됩니다