측정의 함정 · 0과 빈 출력을 의심하라
품앗이가 AI와 함께 일하며 남긴 실패 기록을 다른 조직이 다시 쓸 수 있게 옮긴 글입니다. 묶음 전체는 AI가 「됐다」고 할 때에서 볼 수 있습니다.
요지
측정이 틀리면 고친 것도, 안 고친 것도 알 수 없습니다. 그래서 무언가를 재기 전에 내 자가 정말 그것을 재는지부터 보여야 합니다. 특히 0건, 빈 출력, 「없음」이 나왔을 때는 대상보다 내 측정을 먼저 의심합니다. 우리 기록에서 가장 자주 나온 측정 고장은 「조용히 0을 내는 자」였습니다.
1. 0은 측정기 고장의 가장 흔한 증상이다
한 번은 검색 패턴이 대상의 형태와 구조적으로 맞지 않아 무엇을 넣어도 0을 냈는데, 그 0 위에 기획안을 세웠습니다. 다행히 검토 단계에서 잡혔습니다.
0이 나오면 있는 것이 확실한 대상을 하나 넣어 봅니다. 이것을 양성 대조군이라고 부르는데, 측정기가 그 대상에서 1 이상을 내는지 먼저 확인한 뒤에야 0을 보고합니다. 반대로 한 항목이 2위와 네 배 넘게 벌어진 압도적 1위로 나와도 의심합니다. 우리 기록에서는 대개 자동으로 읽히는 경로를 「사용」으로 센 측정 오염이었습니다. 패턴을 좁게 잡으면 오류 없이 조용히 빠뜨립니다. 실제로는 146줄인 목록을 111줄로 센 적이 있습니다.
2. 측정 실패와 「값이 0」은 다른 칸이다
원격 폴더 크기를 재는 명령이 잘못 실행되어 빈 출력을 냈고, 프로그램은 그 빈 값을 기본값 0으로 바꿔 모든 폴더를 「비어 있음, 건너뜀」으로 처리했습니다. 실제 자료 2.31GB는 멀쩡히 있었고 받아 온 것은 0바이트였습니다.
측정하는 함수는 실패하면 0이 아니라 빈 값을 돌려주게 짜고, 그 값을 받는 쪽은 빈 값이 오면 멈추게 만듭니다. 「모른다」와 「없다」를 같은 숫자로 적으면 그 뒤의 판단이 전부 틀어집니다.
3. 검색 결과 없음은 「없다」가 아니다
있지도 않은 폴더를 검색해 0줄이 나오자 AI가 「우리 기록에 없다」를 세 번 적었습니다. 실제 자료는 다른 표에 있었습니다. 검색이 0건이면 검색한 자리가 존재하는지부터 보고, 반드시 잡혀야 하는 낱말 하나를 같이 넣어 대조합니다.
이상한 바이트가 섞인 파일은 검색 도구가 바이너리로 판단해 일치하는 줄을 아예 출력하지 않기도 합니다. 그때 「그런 코드는 없다」고 진단하기 쉽습니다. 전체 목록을 뽑으려던 명령이 빈 출력을 냈는데 따지지 않고 다른 방법으로 넘어가, 전수를 봤다고 믿고 「없다」를 보고한 일도 있습니다.
4. 내가 잰 것이 정말 그것인가
포트를 먼저 쥐고 있던 다른 서버가 대신 응답하는 바람에, 고친 파일을 아무리 재도 옛 값이 나온 일이 있습니다. 서버가 실제로 내주는 파일과 내 파일의 해시부터 맞췄어야 했습니다. 의심스러운 층을 하나씩 걷어 내기보다, 층이 하나도 없는 최소한의 문서를 만들어 그 자리에서 재는 편이 빠릅니다.
같은 이름의 설정 파일이 두 곳에 있었는데, 쓰이지 않는 쪽을 읽고 「보안 구멍이 있다」고 보고한 일도 있습니다. 어느 파일이 쓰이는지는 그 프로그램에게 직접 물어서 확인합니다. 접근 규칙이나 방화벽처럼 순서가 뜻을 갖는 설정은 끝 몇 줄만 보고 진단하지 않습니다. 위쪽 규칙이 이미 걸렀을 수 있기 때문입니다. 끝까지 읽지 않은 설정 파일은 통째로 덮어쓰지 않습니다.
대조군은 무엇을 재느냐보다 어디서 쏘느냐로 정해지기도 합니다. 같은 요청도 다른 자리에서 보내면 출발 주소가 바뀌어 다른 결과가 나옵니다. 설치된 버전과 지금 돌고 있는 버전도 다를 수 있습니다.
5. 판정 도구가 거짓 PASS와 거짓 FAIL을 내는 자리
판정 도구도 틀립니다. 우리 기록에 남은 예로는 합계가 지수 표기로 찍혀 문자열 비교가 영원히 거짓이 된 경우, 일부러 받지 않는 미끼 파일을 판정 대상에 넣어 영구히 FAIL이 난 경우, 바이트 합은 맞는데 파일이 엉뚱한 자리에 있던 경우, 바로가기를 따라가 같은 자료를 두 번 센 경우가 있습니다.
가짜 FAIL은 진짜 고장보다 해롭습니다. 날마다 울리는 빨간불을 무시하는 습관이 생기고, 진짜 고장이 같은 칸에서 울 때 묻히기 때문입니다. FAIL이 나오면 무엇이 FAIL했는지부터 셉니다. 데이터 칸은 전부 통과했는데 부가 정보 칸만 실패했다면 판정 도구를 먼저 의심합니다.
첫 요청만 느린 경우도 가짜 FAIL을 만듭니다. 한 주소는 첫 요청에 9.9초가 걸리고 두 번째부터는 1초 안팎이었는데, 한 번만 12초를 기다리는 판정은 그 경계에서 실패했습니다. 한 번 더 시도하고 넉넉히 기다리게 고쳤습니다.
고쳐 놓은 감시 스크립트가 실제로 설치되지 않아 옛 사본이 계속 경보를 낸 일도 있습니다. 이럴 때 가장 싼 확인은 경보 문구를 지금 코드에서 검색해 보는 것입니다. 다만 같은 기록에 따르면 그 경보는 처음 엿새 동안은 진짜였고 백업이 여섯 번 실패하고 있었습니다. 오경보로 보인다고 처음부터 오경보였다고 단정하지 않습니다.
6. 검증은 실제로 쓰는 쪽의 신분으로 한다
권한 검사를 관리자 계정으로 돌리면 대부분 통과합니다. 한 데이터베이스 권한 검사는 우리 쪽에서는 막히는 것을 확인했는데, 상대 쪽에서는 역할 전환이 거부되어 관리자로 돌았고 표가 비어 있어 0행이 나오자 합격으로 보였습니다. 검사 결과와 함께 누구로 돌았는지를 같이 찍어야 했습니다.
백업 저장소 점검을 관리자 권한으로 돌려 8일 내내 통과했는데, 실제로 그 저장소를 읽는 계정은 파일을 못 읽어 백업이 전부 실패하고 있었습니다. 최종 판정은 그 시스템이 하는 일이 한 번 실제로 성공하는 것입니다. 문자열을 바꾸는 작업이라면 파일 길이나 정상 종료가 아니라 새 문자열이 들어 있는지를 봅니다. 빈 파일도 문법 검사는 통과합니다. 「설정이 이렇게 되어 있다」와 「그 설정이 실제로 쓰인다」도 다른 질문입니다.
7. 층을 나누지 않으면 가짜 PASS가 나온다
고전 인용 21건을 「그 문구가 실제로 있는가」로 검사하자 19건이 통과했습니다. 그런데 「내가 지목한 그 책에 있는가」까지 보니 다른 책에서 나온 문구가 섞여 있었습니다. 문구 존재와 출처 귀속은 다른 검사입니다. 일부러 틀린 사례를 두 건 섞어 검사기가 그것을 떨어뜨리는지 보아야 숫자가 증거가 됩니다. 없는 말을 지어내는 것보다, 현대 관용구를 고전 인용으로 올리듯 근거의 층을 한 칸 올리는 오류가 더 잘 안 잡힙니다.
두 AI 모델이 같은 답을 냈다는 일치율은 둘 다 틀렸을 가능성을 지우지 못합니다. 정확도는 사람이 만든 정답이 있어야 말할 수 있습니다. 성능 비교표를 볼 때는 정답을 누가 만들었는지부터 봅니다.
8. 응답이 없다고 죽었다고 읽지 마라
한 현장 기계에 ping이 가지 않자 「전원이나 인터넷이 나갔으니 사람이 가 봐 달라」고 보고한 일이 있습니다. 그런데 윈도 계열은 ping을 기본으로 막아 둡니다. 원격 접속을 다시 시도하자 바로 붙었습니다. 판정은 실제로 쓰려는 통로로 하고, 같은 망의 다른 기계를 대조군으로 먼저 봅니다. 「사람을 불러야 한다」는 결론 앞에서는 한 번 더 시도합니다.
진단용 요청은 실제 부하를 대표해야 합니다. 아주 짧은 요청이 200으로 돌아온 것을 보고 무거운 작업도 된다고 판단했다가 다시 실패한 기록이 있습니다. 목록에 등록되어 있는 것과 지금 연결되어 있는 것도 다릅니다. 마지막 접속 시각이 등록 시각과 같다면 붙자마자 끊긴 것입니다.
9. 사람과 파일이 붙인 이름을 그대로 믿지 마라
파일 이름에 적힌 날짜를 믿고 사흘치 자료를 하루치로 처리한 일이 있습니다. 표를 받으면 날짜 열에 어떤 날짜가 몇 줄씩 있는지부터 찍어 봅니다. 같은 장치를 프로그램마다 다른 표기로 부르는 바람에 무인 작업이 멈춘 적도 있습니다. 만든 쪽과 읽는 쪽의 표기는 다를 수 있습니다.
숫자를 읽을 때도 같습니다. 어떤 기능의 사용 비중이 낮다고 수요가 없다고 읽지 않습니다. 비용 때문에 눌러 둔 수요일 수 있습니다. 안 쓴 것인지, 못 쓴 것인지를 먼저 묻습니다.
처방 정리
- 0, 빈 출력, 「없음」이 나오면 양성 대조군 하나를 같은 자로 재 본다.
- 측정 실패는 빈 값으로 남기고, 빈 값이 오면 멈춘다.
- 판정 도구는 알려진 고장 사례와 일부러 틀린 사례로 먼저 시험한다.
- 검사는 실제로 쓰는 계정과 자리에서 돌리고, 누구로 어디서 돌았는지를 결과와 같이 남긴다.
- FAIL이 나면 무엇이 FAIL했는지부터 센다.
도구 메모
- 검색이 0건이면: 검색한 경로가 있는지 확인하고, 반드시 잡히는 낱말로 같은 검색을 다시 해 본다. 바이너리로 판정된 파일은 텍스트로 강제해서 다시 검색한다.
- 서버가 내 파일을 내주는지: 서버 응답과 로컬 파일의 해시를 비교한다.
- 데이터베이스 권한 검사: 결과 옆에 현재 사용자 이름을 같이 출력한다.
- 표 자료: 날짜 열의 값별 건수를 먼저 찍는다.