Python 중복 이미지 정리와 PHP 파일 보호 소스 예시
아래 예시는 개인 프로젝트에서 자주 쓰는 패턴을 공개용으로 줄인 코드입니다. 경로 같은 자리표시자(내 환경에 맞게 바꿔야 하는 값)만 고치면 바로 쓸 수 있고, 실제 운영에서는 인증, 로그, 백업, 권한 검사를 환경에 맞게 보강해야 합니다.
Python SHA-256 중복 검사
from pathlib import Path
import hashlib
IMAGE_EXTS = {".jpg", ".jpeg", ".png", ".webp", ".gif"}
def file_hash(path: Path) -> str:
# 파일을 1MB씩 나눠 읽어 SHA-256 해시(내용 지문)를 계산
h = hashlib.sha256()
with path.open("rb") as f:
for chunk in iter(lambda: f.read(1024 * 1024), b""):
h.update(chunk)
return h.hexdigest()
def find_duplicates(root: str):
seen = {}
duplicates = []
for path in Path(root).rglob("*"):
if not path.is_file() or path.suffix.lower() not in IMAGE_EXTS:
continue # 이미지 확장자만 검사
digest = file_hash(path)
if digest in seen:
duplicates.append((seen[digest], path)) # (원본, 중복 후보)
else:
seen[digest] = path # 처음 본 해시는 원본으로 기억
return duplicates
for original, duplicate in find_duplicates("./uploads"):
print(f"{duplicate} == {original}")
PHP 비공개 미디어 라우터
<?php
session_start();
if (empty($_SESSION["user_id"])) {
http_response_code(404); // 로그인하지 않았으면 파일이 없는 것처럼 응답
exit;
}
$rel = ltrim($_GET["file"] ?? "", "/");
$path = realpath(__DIR__ . "/private_uploads/" . $rel);
$root = realpath(__DIR__ . "/private_uploads");
if (!$path || !str_starts_with($path, $root . DIRECTORY_SEPARATOR)) {
http_response_code(404); // 보호 폴더 밖 경로는 차단 (../ 우회 방지)
exit;
}
header("Content-Type: " . mime_content_type($path));
header("X-Robots-Tag: noindex, nofollow"); // 검색엔진 수집 금지
readfile($path);
Nginx 직접 접근 차단
# 보호 폴더는 웹에서 직접 열 수 없게 차단
location ~ ^/(private_uploads|logs|data)/ {
deny all;
return 404;
}
# 파일은 인증을 거치는 media.php를 통해서만 전달
location = /media.php {
include snippets/fastcgi-php.conf;
fastcgi_pass unix:/var/run/php/php8.1-fpm.sock;
}