어쩌다 보니 안드로이드 스마트폰 두 대와 아이패드 미니를 동시에 사용하고 있다. 각각 플랫폼이 다르지만, KDE Connect 덕분에 꽤 수월하게 이런저런 것들을 잘 넘기고 받고 있었다. 그런데 어느 날, 문득 스마트폰의 배경화면을 설정하면서 아이패드에서 그림을 고르고 있었는데, 이게 갑자기 너무 귀찮게 느껴졌다. 그래서 NAS 에 온라인 사진 라이브러리 앱을 설치하려고 맘을 먹었다.
마침 TrueNAS 의 Community Plugin 에 Piwigo 가 있어서 설치했다. 설치 자체는 아무런 어려움이 없었다. MariaDB 에 새로운 데이터베이스와 유져를 생성해서 해당 정보만 입력 해 주면 끝이다.
설치를 끝내고, 내부 IP 로 접속해서 잘 설치되었는지를 확인했다. 그리고 Reverse Proxy 설정을 하고 다시 접속해서 살펴보니 두 가지 문제가 있었다.
- 웹을 통해 로그인을 할 때, 일단 에러 메시지가 한번 뜬 후, 새로 고침을 해야 제대로 로그인이 되었다.
- 사진을 업로드 할 때, 업로드가 끝났음에도 끝나지 않았고, 여러 장을 한꺼번에 업로드 할 수 없었다.
고치자…
첫 번째 문제
찬찬히 살펴보니 URL 에 이상한 점이 보였다. Port Number 를 따로 설정하지 않고 그냥 HTTP 로 주소를 입력했는데도 Piwigo는 자동으로 url 뒤에 포트 넘버를 붙였다. 예를 들면, 192.168.0.300 으로 접속해서 로그인을 시도하면,
http://192.168.0.300:80/identification.php
이런 식으로 제 맘대로 포트 넘버를 붙였다. 게다가 Reverse Proxy 에는 SSL이 적용되어 있어서 뒤에 443 이 붙어야 하는데, Piwigo 는 제 맘대로 80 을 붙여버렸다. 이러니 제대로 접속이 될 리가 없었다.
조금 검색을 해 보니 해결책이 있었다.
https://piwigo.org/forum/viewtopic.php?id=19353
요약하면 piwigo 가 absolute url 을 가져오는 함수를 수정하라는 말이다.
해당 함수는 “/include/functions_url.inc.php” 의 “function get_absolute_root_url($with_scheme=true)” 이고, 64번 줄부터 72번 줄까지가 HTTP, HTTPS 여부를 판단해서 Port Number 을 붙이는 부분이다. 여기를 그냥 주석처리 해 주면 된다.
else
{
$url .= $_SERVER['HTTP_HOST'];
// if ( (!$is_https && $_SERVER['SERVER_PORT'] != 80)
// ||($is_https && $_SERVER['SERVER_PORT'] != 443))
// {
// $url_port = ':'.$_SERVER['SERVER_PORT'];
// if (strrchr($url, ':') != $url_port)
// {
// $url .= $url_port;
// }
// }
}
대괄호가 딱 헷갈리기 좋다.
이걸로 접속 문제가 해결되었다. 도메인을 통한 접속도 별 문제 없었다.
두 번째 문제
핵심 증상은 파일 업로드가 끝나지를 않는 것이다. 화면에 나오는 진행 막대는 100%를 가리키고 있지만, 그 상태 그대로 그냥 멈춘다. 창을 닫거나, 다른 링크를 클릭하면 중단할 거냐고 물어보는 것은 덤.
결론부터 이야기하면, PHP 의 mime_content_type 함수가 실행되지 않는 것이 문제였다. 구글신께 여쭤 fileinfo 등등의 해결책을 적용 해 보았지만, 저 함수는 끝내 실행되지 않았다.
구글신께 더 여쭤보니, file 명령을 이용한 시도가 적힌 블로그가 있었다. 그 분은 필요한 것 보다 더 많은 정보가 출력되도록 옵션을 넣고, 불필요한 부분은 문자열을 파싱해서 잘라내어 사용하고 있었다.
그래서 man 페이지를 뒤져서 “–mime-type” 옵션을 적용하면 php의 mime_content_type 함수와 동일한 출력을 얻을 수 있다는 것을 찾아냈다. 그에 더해, 필요한 부분만 출력되도록 적당히 옵션을 조합했다.
대충 테스트를 끝내고 고쳐야 할 부분을 검색했다. 소스 전체에서 mime_content_type 함수를 호출하는 함수는
- /Piwigo/action.php
- /Piwigo/admin/include/functions_meta.php
에 있다. 두 파일의 개발자가 다른지, action.php 에는 mime_content_type 함수가 없는 경우를 대비하고 있었다.
흐음… 저것과 이것을 잘 버무리면….
/**/ // replace mime_content_type
$ctype = "";
if ( function_exists('mime_content_type') )
$ctype = mime_content_type($file);
else
$ctype = shell_exec('file -b --mime-type '.$file);
/**/
이걸 mime_content_type 함수를 사용하는 부분에 적당히 넣어주면 된다. 좀 걱정되는 점은 PHP 의 mime_content_type 은 파일의 확장자만 바꿔도 Mime Type 이 바뀌지만, file 명령은 헤더를 읽기 때문에 확장자 바꾸는 걸로는 안 바뀐다. 이걸 고려했는지 안 했는지는 모르겠다.
여튼, 각 파일을 백업하고 저렇게 수정하니 일단 잘 된다.
그러고 나서…
신나게 업로드를 걸었는데… 느리다. 그리고 IOS 용 앱에서는 느리게라도 업로드가 끝까지 되는데, 안드로이드 용 앱은 열 몇 장 업로드 하다가 에러 내고 말아버린다. 게다가 업로드 리스트 중간에 지원되지 않는 MimeType 이 있으면 그걸 빼고 업로드 하는 게 아니라, 그냥 에러 메시지 내 뱉고 멈춰버린다. 그 흔한 Webp 가 지원이 안된다…
—참고사이트—