최초 커밋
This commit is contained in:
@@ -0,0 +1,282 @@
|
||||
<?php
|
||||
// descope_qa_write.php
|
||||
|
||||
if (!defined('_GNUBOARD_')) define('_GNUBOARD_', true);
|
||||
if (!defined('G5_URL')) define('G5_URL', '/egbim');
|
||||
if (!defined('G5_BBS_URL')) define('G5_BBS_URL', '/egbim/bbs');
|
||||
if (!defined('G5_IMG_URL')) define('G5_IMG_URL', '/egbim/img');
|
||||
|
||||
// 1) 에러 출력 (개발용)
|
||||
// ini_set('display_errors', 1);
|
||||
// error_reporting(E_ALL);
|
||||
|
||||
// 2) 세션/사용자 복원 (리스트와 동일하게)
|
||||
require_once __DIR__ . '/../skin/member/basic/descope_session.php';
|
||||
require_once $_SERVER['DOCUMENT_ROOT'].'/egbim/bbs/admin_guard.php';
|
||||
|
||||
// 🚨 비회원 차단 (리스트는 열람 가능하지만 글쓰기는 불가)
|
||||
if (empty($_SESSION['user']['userId'])) {
|
||||
echo "<script>
|
||||
alert('로그인이 필요한 서비스입니다.');
|
||||
window.location.href = '/egbim/index.php?popup=login';
|
||||
</script>";
|
||||
exit;
|
||||
}
|
||||
|
||||
// 3) DB 연결 (PDO)
|
||||
$host = 'db';
|
||||
$dbname = 'egbim';
|
||||
$user = 'egbim';
|
||||
$pass = 'baron3840!!';
|
||||
$charset = 'utf8mb4';
|
||||
$dsn = "mysql:host={$host};dbname={$dbname};charset={$charset}";
|
||||
$options = [
|
||||
PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION,
|
||||
PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_ASSOC,
|
||||
];
|
||||
try {
|
||||
$pdo = new PDO($dsn, $user, $pass, $options);
|
||||
$pdo->exec("SET time_zone = '+09:00'");
|
||||
} catch (PDOException $e) {
|
||||
exit('DB 연결 에러: ' . $e->getMessage());
|
||||
}
|
||||
|
||||
// 4) 수정 모드 판단
|
||||
$postId = isset($_GET['id']) ? (int)$_GET['id'] : 0;
|
||||
$isEdit = $postId > 0;
|
||||
|
||||
// 5) 수정 모드이면 기존 글 불러오기
|
||||
if ($isEdit) {
|
||||
$stmt = $pdo->prepare("SELECT * FROM qa_posts WHERE post_id = ?");
|
||||
$stmt->execute([$postId]);
|
||||
$post = $stmt->fetch() ?: exit('존재하지 않는 글입니다.');
|
||||
} else {
|
||||
// 등록 모드 기본값
|
||||
$post = [
|
||||
'category' => '',
|
||||
'title' => '',
|
||||
'content' => '',
|
||||
'is_secret' => 0,
|
||||
'status' => 'new',
|
||||
];
|
||||
}
|
||||
|
||||
// === 파일 업로드 처리 공통 함수 ===
|
||||
function handle_file_uploads(PDO $pdo, int $postId, array &$errors) {
|
||||
if (empty($_FILES['attach']['name'][0])) return;
|
||||
|
||||
$uploadDir = __DIR__ . '/../uploads/qa/';
|
||||
if (!is_dir($uploadDir)) {
|
||||
mkdir($uploadDir, 0777, true);
|
||||
}
|
||||
if (!is_writable($uploadDir)) {
|
||||
@chmod($uploadDir, 0777);
|
||||
}
|
||||
if (!is_writable($uploadDir)) {
|
||||
$errors[] = '업로드 폴더에 쓰기 권한이 없습니다.';
|
||||
return;
|
||||
}
|
||||
|
||||
$allowedExt = ['jpg','jpeg','png','gif','pdf','hwp','doc','docx','xls','xlsx','zip','7z','dwg','dwt','dxf','grm','ctb','shx','shp','lin','lsp','reg'];
|
||||
|
||||
foreach ($_FILES['attach']['name'] as $i => $oriName) {
|
||||
if ($_FILES['attach']['error'][$i] === UPLOAD_ERR_OK) {
|
||||
$tmpName = $_FILES['attach']['tmp_name'][$i];
|
||||
$fileSize = $_FILES['attach']['size'][$i];
|
||||
$ext = strtolower(pathinfo($oriName, PATHINFO_EXTENSION));
|
||||
|
||||
if (!in_array($ext, $allowedExt)) {
|
||||
$errors[] = "허용되지 않은 확장자: {$oriName}";
|
||||
continue;
|
||||
}
|
||||
if ($fileSize > 30 * 1024 * 1024) {
|
||||
$errors[] = "파일 용량 초과 (30MB): {$oriName}";
|
||||
continue;
|
||||
}
|
||||
|
||||
$safeName = time() . '_' . bin2hex(random_bytes(4)) . '_' . basename($oriName);
|
||||
$savePath = $uploadDir . $safeName;
|
||||
|
||||
if (@move_uploaded_file($tmpName, $savePath)) {
|
||||
$stmt = $pdo->prepare("
|
||||
INSERT INTO qa_attachments (post_id, ori_name, save_path, file_size, uploaded_at)
|
||||
VALUES (?, ?, ?, ?, NOW())
|
||||
");
|
||||
$stmt->execute([
|
||||
$postId,
|
||||
$oriName,
|
||||
'/egbim/uploads/qa/' . $safeName,
|
||||
$fileSize
|
||||
]);
|
||||
} else {
|
||||
$errors[] = "파일 업로드에 실패했습니다: {$oriName}";
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// 6) 폼 제출 처리
|
||||
$errors = [];
|
||||
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
|
||||
// 6-1) 로그인 정보
|
||||
$loginId = $_SESSION['user']['loginIds'][0] ?? '';
|
||||
$userId = $_SESSION['user']['userId'] ?? '';
|
||||
|
||||
// 내부 도메인 리스트
|
||||
$internalDomains = [
|
||||
'hanmaceng.co.kr','samaneng.com','jangheon.co.kr',
|
||||
'hallasanup.com','pre-cast.co.kr','baroncs.co.kr'
|
||||
];
|
||||
|
||||
// 도메인 추출 → 내부/외부 구분
|
||||
$emailDomain = substr(strrchr($loginId, "@"), 1);
|
||||
$isInternal = in_array($emailDomain, $internalDomains, true);
|
||||
|
||||
// 회사명
|
||||
$Internal_companyName = $_SESSION['user']['customAttributes']['familyCompany'] ?? '';
|
||||
$external_companyName = $_SESSION['user']['customAttributes']['company'] ?? '';
|
||||
// 부서
|
||||
$department = $_SESSION['user']['customAttributes']['team'] ?? '';
|
||||
|
||||
// 6-2) POST 데이터 수집
|
||||
$postLabel = trim($_POST['category'] ?? '');
|
||||
$title = trim($_POST['title'] ?? '');
|
||||
$content = trim($_POST['content'] ?? '');
|
||||
$secret = isset($_POST['secret']) ? 1 : 0;
|
||||
$status = 'new'; // 항상 답변대기
|
||||
|
||||
// 6-3) 한글 카테고리 → 코드 매핑
|
||||
$categoryMap = [
|
||||
'오류문의' => 'error',
|
||||
'개선문의' => 'improvement',
|
||||
'일반문의' => 'general',
|
||||
'공지사항' => 'notice',
|
||||
'관리글' => 'admin',
|
||||
];
|
||||
$category = $categoryMap[$postLabel] ?? '';
|
||||
|
||||
// 6-4) 유효성 검사
|
||||
if (!in_array($category, $categoryMap, true)) {
|
||||
$errors[] = '유효한 구분을 선택하세요.';
|
||||
}
|
||||
if ($title === '' || mb_strlen($title) > 100) {
|
||||
$errors[] = '제목은 1~100자 사이여야 합니다.';
|
||||
}
|
||||
if ($content === '') {
|
||||
$errors[] = '내용을 입력해주세요.';
|
||||
}
|
||||
|
||||
if (empty($errors)) {
|
||||
$pdo->beginTransaction();
|
||||
try {
|
||||
if ($isEdit) {
|
||||
// 6-5a) UPDATE (회사정보는 수정하지 않음)
|
||||
$sql = "UPDATE qa_posts
|
||||
SET category = :cat,
|
||||
title = :tit,
|
||||
content = :cont,
|
||||
is_secret = :sec,
|
||||
status = :st,
|
||||
updated_at = NOW()
|
||||
WHERE post_id = :pid";
|
||||
$stmt = $pdo->prepare($sql);
|
||||
$stmt->execute([
|
||||
':cat' => $category,
|
||||
':tit' => $title,
|
||||
':cont' => $content,
|
||||
':sec' => $secret,
|
||||
':st' => $status,
|
||||
':pid' => $postId,
|
||||
]);
|
||||
// === (수정 저장 시) 기존 첨부파일 삭제 체크 ===
|
||||
if (!empty($_POST['delete_files'])) {
|
||||
foreach ($_POST['delete_files'] as $fileId) {
|
||||
$stmt = $pdo->prepare("SELECT save_path FROM qa_attachments WHERE id=? AND post_id=?");
|
||||
$stmt->execute([$fileId, $postId]);
|
||||
if ($row = $stmt->fetch()) {
|
||||
$filePath = $_SERVER['DOCUMENT_ROOT'] . $row['save_path'];
|
||||
if (file_exists($filePath)) {
|
||||
unlink($filePath);
|
||||
}
|
||||
$pdo->prepare("DELETE FROM qa_attachments WHERE id=?")->execute([$fileId]);
|
||||
}
|
||||
}
|
||||
}
|
||||
// 새 파일 업로드 추가
|
||||
handle_file_uploads($pdo, $postId, $errors);
|
||||
if (!empty($errors)) {
|
||||
throw new RuntimeException(implode("\n", $errors));
|
||||
}
|
||||
|
||||
} else {
|
||||
// 6-5b) INSERT (내부/외부 분기)
|
||||
if ($isInternal) {
|
||||
// 내부 사용자 → family_company + department
|
||||
$sql = "INSERT INTO qa_posts
|
||||
(login_id, user_id, user_name, family_company, department, phone,
|
||||
is_internal, category, title, content, is_secret, status, created_at)
|
||||
VALUES
|
||||
(:lid, :uid, :uname, :fam, :dept, :phone,
|
||||
:is_internal, :cat, :tit, :cont, :sec, :st, NOW())";
|
||||
$stmt = $pdo->prepare($sql);
|
||||
$stmt->execute([
|
||||
':lid' => $loginId,
|
||||
':uid' => $userId,
|
||||
':uname' => ($_SESSION['user']['name'] ?? $_SESSION['user']['userName'] ?? $loginId),
|
||||
':fam' => $Internal_companyName,
|
||||
':dept' => $department,
|
||||
':phone' => ($_SESSION['user']['phone'] ?? ''),
|
||||
':is_internal' => 1, // ✅ 내부 사용자 → 1
|
||||
':cat' => $category,
|
||||
':tit' => $title,
|
||||
':cont' => $content,
|
||||
':sec' => $secret,
|
||||
':st' => $status,
|
||||
]);
|
||||
} else {
|
||||
// 외부 사용자 → company + department
|
||||
$sql = "INSERT INTO qa_posts
|
||||
(login_id, user_id, user_name, company, department, phone,
|
||||
is_internal, category, title, content, is_secret, status, created_at)
|
||||
VALUES
|
||||
(:lid, :uid, :uname, :comp, :dept, :phone,
|
||||
:is_internal, :cat, :tit, :cont, :sec, :st, NOW())";
|
||||
$stmt = $pdo->prepare($sql);
|
||||
$stmt->execute([
|
||||
':lid' => $loginId,
|
||||
':uid' => $userId,
|
||||
':uname' => ($_SESSION['user']['name'] ?? $_SESSION['user']['userName'] ?? $loginId),
|
||||
':comp' => $external_companyName,
|
||||
':dept' => $department,
|
||||
':phone' => ($_SESSION['user']['phone'] ?? ''),
|
||||
':is_internal' => 0, // ✅ 외부 사용자 → 0
|
||||
':cat' => $category,
|
||||
':tit' => $title,
|
||||
':cont' => $content,
|
||||
':sec' => $secret,
|
||||
':st' => $status,
|
||||
]);
|
||||
}
|
||||
$postId = $pdo->lastInsertId();
|
||||
// 신규 파일 업로드
|
||||
handle_file_uploads($pdo, $postId, $errors);
|
||||
if (!empty($errors)) {
|
||||
throw new RuntimeException(implode("\n", $errors));
|
||||
}
|
||||
}
|
||||
|
||||
$pdo->commit();
|
||||
|
||||
// 상세보기로 리다이렉트
|
||||
header("Location: /egbim/bbs/descope_qa_detail.php?id={$postId}");
|
||||
exit;
|
||||
} catch (Exception $e) {
|
||||
$pdo->rollBack();
|
||||
$errors[] = 'DB 오류: ' . $e->getMessage();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 7) 뷰 렌더링
|
||||
include __DIR__ . '/../skin/qa/basic/descope_qa_write.skin.php';
|
||||
Reference in New Issue
Block a user