Testing Files Generator
한국어

테스트용 손상 파일을 만드는 방법

멀쩡한 파일만 본 검증기는 제대로 테스트된 것이 아닙니다. 일부러 망가뜨렸고, 요청한 크기 그대로 나오며, 시스템이 그 파일을 어떻게 다뤄야 하는지 알려 주는 매니페스트가 딸려 오는 파일을 얻는 방법을 설명합니다.

짧은 답

tfg generate --format png --size 2mb --damage zero-head --out ./out은 정확히 2097152바이트이고 첫 바이트들이 0인 PNG를 쓰며, 옆의 매니페스트에는 시스템이 그것을 거부해야 한다고 기록됩니다.

흔한 방법

손으로 망가뜨린 파일이 좋지 않은 테스트인 이유

흔한 방법은 16진 편집기, 임의의 바이트 몇 개를 뒤집는 스크립트, 또는 head나 truncate로 파일을 잘라 내는 것입니다. 한 번은 통하지만 나중에 대가를 치릅니다.

얻는 것

손상된 파일도 요청한 크기를 유지합니다

파일은 평소대로 생성된 뒤 디스크로 가는 길에 망가집니다. 요청한 크기는 그대로이고, 같은 명령은 같은 바이트를 다시 씁니다.

tfg generate --format png --size 2mb --damage zero-head --out ./out
tfg generate --format pdf --size 1mb --count 5 --damage zero-head:bytes=16 --out ./broken

설정은 콜론 뒤에 씁니다. 옵션은 반복할 수 있고, 손상은 쓴 순서대로 적용됩니다. 26개 형식 모두에서 동작합니다.

할 수 있는 것

어떤 손상이 있나요?

이것은 프로그램이 출력하는 목록이며, 이 페이지를 빌드할 때 프로그램에서 읽어 옵니다. tfg damage는 같은 목록을 출력하고, tfg damage <id>는 그중 하나가 받는 설정을 알려 줍니다.

손상 바이트에 하는 일 가장 작은 파일 설정
zero-head 파일의 첫 바이트들을 길이는 그대로 둔 채 0으로 덮어씁니다. 대부분의 리더가 가장 먼저 그곳을 보므로 거의 모든 것이 이 손상을 알아챕니다. 8 bytes

zero-head는 파일의 시작 부분을 0으로 덮어씁니다. 대부분의 리더는 파일이 무엇인지 알려 주는 시그니처와 헤더가 있는 그곳을 가장 먼저 봅니다. 그래서 거의 모든 리더가 알아챕니다. 일반 텍스트와 로그에는 시그니처가 없지만 역시 거부됩니다. 0 바이트의 연속은 텍스트가 아니기 때문입니다. 4바이트 미만에서는 어떤 리더도 불평하지 않는 손상이 나오는 형식이 있으며, 설정이 4부터 시작하는 이유가 그것입니다.

매니페스트가 말하는 것

무엇이 일어나야 하는지 말해 주는 매니페스트

손상된 파일마다 시스템이 그것을 거부해야 한다는 항목이 붙고, 손상 내용이 그 옆에 기록됩니다.

"expected": {
  "outcome": "reject",
  "reason": "content_malformed",
  "confidence": "certain"
},
"damage": [
  {
    "type": "zero-head",
    "settings": {
      "bytes": "8"
    }
  }
]

두 가지 요청은 무엇이든 쓰기 전에 거부됩니다. 둘 다 매니페스트가 잘못 설명하는 파일을 디스크에 남기게 되기 때문입니다.

레시피에서

한 번의 실행에 멀쩡한 파일과 망가진 파일을

둘을 한 레시피에 넣으면 매니페스트가 파일마다 기대 결과를 가지므로, 테스트에 어느 것이 어느 것인지 알려 주는 목록이 필요 없습니다.

version: 1
targets:
  - id: healthy
    format: pdf
    size: 1mb
    expected: accept
  - id: broken
    format: pdf
    size: 1mb
    damage:
      - zero-head

테스트에서

테스트로 만들기

테스트는 매니페스트를 읽고 일어난 일이 선언된 것과 같은지 확인합니다. 파일 이름 목록은 필요 없습니다.

import json, os

directory = "healthy-and-broken"
manifest = json.load(open(os.path.join(directory, "manifest.json")))

for entry in manifest["files"]:
    response = upload(os.path.join(directory, entry["path"]))
    if entry["expected"]["outcome"] == "reject":
        assert not response.ok
    else:
        assert response.ok

좋은 거부는 깔끔한 거부입니다. 무엇이 잘못됐는지 알려 주는 메시지가 원하는 답입니다. 서버 오류, 멈춤, 반쯤 저장된 파일은 이 테스트가 찾아내려고 존재하는 결함입니다.

다음

여기서 어디로