본문 바로가기

IT

PHP: 기본을 충실히: array_search(), is_null(), 커맨드라인 옵션(-a, -S address:port) 그리고 워드프레스(WordPress)의 캐시(Cache)

관리 중인 워드프레스(WordPress)사이트에 기능 추가를 했습니다.

작업환경에서 문제없음의 확인까지 실시하고 서비스환경에 적용했음에도 불구하고 역시나 안심할 즈음에 문제는 찾아옵니다.

갑자기 RSS Feed가 전혀 출력되지 않습니다.

 

문제의 부분입니다.

$getVal=get_field('val');
if(is_null(array_search('keyword', $getVal))){
   --출력--
}

취득한 워드프레스(WordPress)의 커스텀 필드(Custom Field)(배열)의 데이터에 체크하려는 키워드가 존재하지 않는다면 출력하는 처리입니다.

 

먼저 위의 구문의 경우 당연히 아무것도 표시되지 않습니다. (이유는 뒤에서 정리합니다.)

그럼에도 불구하고 적용 후 작업환경, 서비스환경에서 문제가 없었던 이유는 워드프레스(WordPress)의 캐시(Cache)때문이었던 것 같습니다. 워드프레스(WordPress)의 RSS Feed의 경우 클라이언트 쪽의 캐시(Cache)가 적용되어있고 브라우저의 방문한 페이지 삭제를 해야 제대로 출력되었습니다. 아무것도 출력되지 않는 상태였지만 한번 열어본 캐시(Cache)로  출력에 문제없다고 판단해버렸던 것입니다.

관리페이지에서 데이터의 변경후 확인만 해봤어도 발견했었을텐데 데이터의 변경권한 없음(??)의 핑계+귀찮음으로 발견할 기회를 놓쳐버렸습니다.

 

우선 문제의 구문을 작성하게된 원인은 get_field()와 array_search()의 리턴값을 실제로 확인하지 않고 상상해버린 결과입니다.

워드프레스(WordPress)의 get_field()가 해당 데이터가 없는 경우 DB에서 읽어오니 당연히 NULL을 리턴할 것으로 상상해버립니다.

PHP의 array_search()도 NULL로 처리를 하니 NULL을 리턴할 것이고 이어서 검색 결과가 없는 경우도 NULL을 리턴하겠지의 상상까지 이어져 is_null()로 체크하는 구문이 작성됩니다.

 

실제 워드프레스(WordPress)의 get_field()는 해당 데이터가 없는 경우 빈(empty) 데이터(NULL이 아님)를 리턴합니다.

(해당 부분은 빈 배열을 리턴)

PHP의 array_search()는 검색할 키워드가 발견된 경우는 해당 배열의 키(NULL이 아님)를 발견되지 않은 경우는 FALSE(NULL이 아님)를 리턴합니다. 그러니 위의 구문의 is_null()은 항상 FALSE가 되어 아무 것도 출력하지 않게 됩니다.

 

수정을 합니다.

$getVal=get_field('val');
if(array_search('keyword', $getVal)==false){
   --출력--
}

출력이 잘 됩니다만 이것도 문제의 가능성을 내포하고  있습니다.

$getVal 배열의 첫번째 요소가 검색할 키워드인 경우 array_search()는 0을 리턴합니다.

비교연산자(==,!=)는 데이터형은 체크하지 않습니다.

0==false는 TRUE가 되어 출력하지 말아야 할 데이터를 출력하게 됩니다.

 

다시 수정을 합니다.

$getVal=get_field('val');
if(array_search('keyword', $getVal)===false){
   --출력--
}

비교연산자(===,!==)는 데이터형도 체크를 합니다.

0===false는 FALSE가 됩니다.

 

해결이 되었습니다.

간단한 작업이라고 상상으로 코딩을 하고, 제대로 확인도 하지 않으면 항상 꾸짖음을 받게 됩니다.

 

대응 작업을 하면서 연구했던 내용의 정리입니다.

 

PHP if(), isset, empty, is_null의 비교

isset($x) bool: if($x) empty($x) is_null($x)
$x=1 , $x=-1 true true false false
$x="" true false true false
$x=0 true false true false
$x=NULL false false true true
$x false false true true
$x=array() true false true false
$x=array(1) true true false false

$x=0의 경우 empty($x)가 true가 되네요.

$x="0"의 경우도 $x=0와 같은 처리가 됩니다.

$ php -a
Interactive shell
php > $x="0";
php > var_dump(empty($x));
bool(true)

 

PHP의 커맨드라인옵션

PHP는 .php파일로 저장해서 웹 서버에 업로드해서 작동시키거나 php로 로컬에서 실행시키거나 했는데 파일작성없이 대화형 모드(Interactive mode)로 실행이 가능하네요.

php -a 대화형 모드로 PHP를 실행

 

$ php -a
Interactive shell

php > $a=10;
php > $b=20;
php > echo $a+$b;
30
php > 

 

웹 서버도 포함하고 있습니다.

웹 환경이 필요한 경우 간단히 사용하기 유용합니다.

php -S address:port 지정한 address와 port로 내장 웹서버 기동
$ php -S 127.0.0.1:8080
PHP 7.3.11 Development Server started at Tue Nov  3 22:31:28 2020
Listening on http://127.0.0.1:8080
Document root is /Users/--유저명--
Press Ctrl-C to quit.
[Tue Nov  3 22:36:34 2020] 127.0.0.1:55442 [404]: / - No such file or directory
[Tue Nov  3 22:36:34 2020] 127.0.0.1:55443 [404]: /favicon.ico - No such file or directory
[Tue Nov  3 22:38:32 2020] 127.0.0.1:55505 [200]: /documents/temp
[Tue Nov  3 22:52:04 2020] 127.0.0.1:55623 [200]: /documents/temp

 

비교연산자 "==","!=","===","!=="의 속도비교

<?php
$a=1;
$b="1";
$startTime=microtime(true);
for($i=0;$i<100000000;$i++){
if($a==$b);
}
$endTime=microtime(true);
$spentTime=$endTime-$startTime;
echo "소요시간: ${spentTime}";
<?php
$a=1;
$b="2";
$startTime=microtime(true);
for($i=0;$i<100000000;$i++){
if($a!=$b);
}
$endTime=microtime(true);
$spentTime=$endTime-$startTime;
echo "소요시간: ${spentTime}";
<?php
$a=1;
$b=1;
$startTime=microtime(true);
for($i=0;$i<100000000;$i++){
if($a===$b);
}
$endTime=microtime(true);
$spentTime=$endTime-$startTime;
echo "소요시간: ${spentTime}";
<?php
$a=1;
$b=2;
$startTime=microtime(true);
for($i=0;$i<100000000;$i++){
if($a!==$b);
}
$endTime=microtime(true);
$spentTime=$endTime-$startTime;
echo "소요시간: ${spentTime}";

 

위의 샘플(간단히 비교만 하는 처리를 1억번 실행)의 결과입니다.

  1회 2회 3회 4회 5회
== 3.7760 3.7750 3.7639 3.7806 3.8143
=== 1.5553 1.5745 1.5515 1.5533 1.5428
!= 3.7603 3.6840 3.7149 3.6813 3.7259
!== 1.6312 1.5967 1.5553 1.5940 1.6031

데이터형의 체크까지 하는 경우가 그렇지 않은 경우에 비해 평균적으로도 2배 이상 빠르게 작동합니다.

 

'기본에 충실하자!'를 또 되새깁니다.

반응형