Skip to content
isdnetworks
Go back

거쳐 가는 것을 설정으로 뺐다

외부 사이트에 붙어야 하는데 그 사이트가 우리 서버 대역을 막고 있었다. 다른 대역에 있는 서버를 거쳐 가기로 했다.

Table of contents

Open Table of contents

코드에 박았다가 설정으로 뺐다

처음에는 거쳐 가는 주소를 PHP 파일에 그대로 적었다. 돌아가기는 했는데 개발할 때 문제가 됐다. 개발 서버는 막혀 있지 않아서 거칠 필요가 없는데 코드가 무조건 거치게 돼 있었다. 거치는 서버가 죽으면 개발도 같이 멈췄다.

거칠지 말지를 설정으로 뺐다.

$config['use_relay'] = true;
$config['relay_url'] = 'http://proxy.internal/relay.php';

호출하는 쪽은 $config 를 보고 urlencode 로 주소를 만든다. 개발에서는 끄고 운영에서는 켜면 되고, 나중에 대역 차단이 풀리면 운영에서도 끈다.

$url = $config['use_relay']
     ? $config['relay_url'] . '?target=' . urlencode($target)
     : $target;

실패하면 직접 붙어 봤다

거치는 서버가 응답을 안 하면 curl_exec 가 거짓을 돌려주고 그대로 끝났다. 거기에 직접 붙어 보는 것을 한 번 더 넣었다.

if ($body === false && $config['use_relay']) {
    error_log('릴레이 실패. 직접 시도한다: ' . $target);
    $body = httpGet($target);
}

여전히 막혀 있으면 이것도 실패하지만 차단이 풀린 뒤라면 이걸로 돈다. error_log 를 남겨서 릴레이가 언제 실패하는지 보게 했다.

코드만 보면 왜 이런 것이 붙어 있는지 알 수 없어서 주석에 이유를 적었다. 대상 사이트가 우리 IDC 대역을 차단해서 다른 대역을 거친다는 것과, 차단이 풀리면 설정을 끄면 된다는 것이다. 언제 끌 수 있는지를 같이 적었다. 안 적으면 몇 년 뒤에도 거쳐 가게 된다.

거치는 서버가 다 본다

거쳐 가면 그 서버가 오가는 내용을 전부 본다. 우리가 넘기는 주소에 키가 그대로 들어 있었다.

target=http://example.com/api?key=SECRET&id=123

그 서버가 우리 것이라 큰 문제는 아니지만 로그에 남는 것이 걸렸다. 릴레이 쪽에서 error_log 를 쓸 때 preg_replace 로 키를 가리게 했다.

error_log('relay: ' . preg_replace('/key=[^&]+/', 'key=***', $target));

지나가는 것을 그대로 적으면 로그를 보는 사람이 다 보게 된다.

차단이 풀렸는지 가끔 확인해야 하는데 그것도 잊는다. 하루 한 번 직접 붙어 보고 되면 알려 주는 스크립트를 뒀다. 안 만들었으면 한참 지나서 이게 왜 있는지 모르게 됐을 것이다.

임시 조치 34개와 시간 제한

같은 성격의 것이 더 있는지 찾아봤다. 임시나 일단 같은 말이 붙은 자리를 세니 34개였다. 하나씩 열어 보니 절반은 왜 그렇게 뒀는지 아무도 몰랐다. 전부 정리하지는 못했지만 목록을 만들고 언제 다시 볼지를 적어 뒀다. 목록이 있는 것과 없는 것이 달랐다.

시간 제한도 다시 봐야 했다. 거쳐 가면 한 번 붙던 것이 두 번이 되고 시간도 그만큼 든다. CURLOPT_TIMEOUT 을 원래 10초로 두었는데 부족해서 늘렸다.

늘리면서 안쪽과 바깥쪽 제한을 맞췄다. 릴레이 안쪽 CURLOPT_TIMEOUT 이 15초이고 바깥에서 주는 것이 20초다. 바깥이 더 짧으면 안쪽이 끝나기 전에 끊기고, 그러면 릴레이 쪽에는 성공으로 남고 우리 쪽에는 실패로 남는다. 거쳐 가는 구간이 늘면 제한을 안쪽부터 바깥쪽 순으로 맞춰야 한다.

정리


Share this post on:

Previous Post
PHP에 없는 것들
Next Post
일이 없던 기간에 읽은 것들 — 빅데이터라는 말이 막 퍼지던 때