글

라벨이 MYSQL인 게시물 표시

[MySQL/PHP] "Server sent charset (255) unknown to the client" 에러 원인과 해결 방법 (AWS Aurora/RDS 적용)

[MySQL 8.0/PHP] Server sent charset (255) unknown to the client 에러 해결기 레거시 PHP 환경에서 MySQL 8.0 / Aurora v3 연동 시 발생하는 문자셋(utf8mb4) 에러 원인 및 AWS RDS 파라미터 조치법 개발을 하다 보면 간혹 잘 작동하던 서비스나 새로 이전한 환경에서 뜬금없는 DB 연결 에러를 마주하곤 합니다. 오늘 정리할 오류는 PHP(특히 CodeIgniter 등 구형 프레임워크나 레거시 환경)에서 MySQL 8.0 이상(또는 AWS Aurora MySQL v3 등) 버전에 연결할 때 발생하는 전형적인 문자셋(Character Set) 에러입니다. 1. 발생한 에러 메시지 어느 날 갑자기 아래와 같은 PHP Warning 에러가 발생하며 DB 연결이 끊어지는 현상이 나타납니다. Severity: Warning Message: mysqli::real_connect(): Server sent charset (255) unknown to the client. Please, report to the developers Filename: mysqli/mysqli_driver.php Line Number: 161 이어서 (HY000/2054): Server sent charset unknown to the client 라는 메시지도 함께 출력됩니다. 2. 왜 발생했을까? (원인 분석) 이 에러의 핵심은 "DB 서버가 쓰는 최신 표준 언어(문자셋)를 구형 PHP 클라이언트가 알아듣지 못해서" 발생합니다. MySQL 8.0+ / Aurora v3+의 변화: MySQL 8.0 버전부터 기본 문자셋(Default Character Set)이 기존 utf8 에서 이모지까지 완벽 지원하는 utf8mb4 로 변경되었습니다. 이때 서버가 클라이언트에 전달하는 ...

MySQL password 대응

MySQL 8에서 사라진 PASSWORD() 함수, 어떻게 대처해야 할까? MySQL 8.0 업그레이드 후 발생한 PASSWORD() 삭제 문제와 임시 대처법 및 권장 해결책 MySQL을 5.x 버전대에서 8.0 이상으로 업그레이드한 개발자라면 한 번쯤 마주쳤을 법한 오류가 있습니다. 바로 이전에 잘 사용하던 PASSWORD() 함수가 더 이상 작동하지 않는 문제입니다. 기존에는 아래와 같은 쿼리로 사용자의 비밀번호를 손쉽게 해시하여 저장할 수 있었습니다. -- MySQL 8.0 이전 버전에서 사용되던 방식 UPDATE user SET password_column = PASSWORD('my_password'); 하지만 MySQL 8.0부터 PASSWORD() 함수는 지원 중단(deprecated) 후 완전히 제거되었기 때문에, 위 쿼리를 실행하면 오류가 발생합니다. 왜 PASSWORD() 함수가 사라졌을까? 가장 큰 이유는 보안 입니다. PASSWORD() 함수는 'mysql_native_password' 인증 방식에 사용되는 해시 값을 생성했는데, 이 해싱 알고리즘은 솔트(salt)를 사용하지 않는 오래된 방식입니다. 최신 보안 표준에 비해 취약점이 존재하여, MySQL 8.0부터는 기본 인증 플러그인이 더 강력한 caching_sha2_password 로 변경되면서 PASSWORD() 함수도 자연스럽게 사라지게 된 것입니다. 임시 해결책: PASSWORD() 함수 직접 구현하기 만약 기존 시스템과의 호환성 문제로 PASSWORD() 함수와 동일한 결과값이 반드시 필요한 상황이라면, 아래와 같이 수동으로 해시 값을 생성할 수 있습니다. 이는 기존 함수의 내부 동작을 SQL로 그대로 구현한 것입니다. UPDATE user SET password_column = CONCAT('*', UPP...

MySQL 8.0 Incorrect date value error

[Aurora MySQL 8.0] DATE 컬럼 조회 시 Incorrect DATE value: '' 에러 분석 MySQL 5.7 ➡️ 8.0 업그레이드 후 WHERE date_col = '' 쿼리가 에러(ERROR 1525)를 내는 이유와 sql_mode 동작 원리 AWS Aurora MySQL 5.7에서 8.0으로 업그레이드를 진행한 후, 기존 서비스에서 잘 작동하던 DATE 타입 컬럼 조건문에서 뜬금없이 에러가 발생하는 현상을 마주쳤습니다. 결론부터 말하면 WHERE date_col = '' 처럼 빈 문자열을 조건으로 넣었을 때 에러가 발생하는데, 정작 WHERE date_col = '0000-00-00' 조회를 시도하면 정상 작동하는 이상한 상황이 펼쳐집니다. 원인을 단계별로 정리해 둡니다. 1. 문제의 배경: sql_mode 옵션 (NO_ZERO_DATE / NO_ZERO_IN_DATE) MySQL에는 날짜 처리 방식을 결정하는 두 가지 핵심 sql_mode 옵션이 존재합니다. NO_ZERO_DATE • Enable: 0000-00-00 값을 유효하지 않은 날짜(Invalid date)로 인식하여 저장/조회를 제한합니다. • Disable: 0000-00-00 값 저장을 허용합니다. NO_ZERO_IN_DATE • Enable: Month나 Day 부분에 0이 포함된 날짜(예: 2022-12-00 , 2022-00-01 )를 Invalid date로 처리합니다. • Disable: 해당 형태의 날짜 입력을 허용합니다. MySQL 5.7 및 8.0부터는 기본적으로 이 두 옵션이 활성화되어 있어, 데이터가 없는 테이블에 아래 조회를 수행하면 ...

[DB] mysql 부하 확인 _show processlist/slow_log

[MySQL/MariaDB] DB CPU 70% 폭주 원인 분석과 Slow Query 트러블슈팅 웹사이트 지연 장애 발생 시 SHOW PROCESSLIST 및 slow_log(BLOB 변환)를 활용한 실무 해결 가이드 웹서비스 운영 중 अचानक 사이트 접속이 느려지거나 500 에러가 간헐적으로 발생한다는 제보를 받았습니다. DB 모니터링을 즉시 확인해보니 DB Server의 CPU 점유율이 70% 이상 까지 급증한 상태였습니다. 실제 장애 현장에서 어떤 순서로 원인을 추적하고 해결했는지 단계별로 정리해 둡니다. 1. 현재 실행 중인 스레드 확인 (SHOW PROCESSLIST) 가장 먼저 DB에서 병목을 일으키는 쿼리가 무엇인지 확인하기 위해 현재 실행 중인 스레드 목록을 조회했습니다. SHOW PROCESSLIST; 출력 주요 컬럼: ID , USER , HOST , DB , COMMAND , TIME , STATE , INFO 조회 결과, TIME 이 100초 이상 지속되며 실행 중인 스레드가 다수 발견되었습니다. COMMAND 가 Query인 항목의 INFO 컬럼을 보니 특정 SELECT 문이 문제였습니다. 💡 TIP: 긴 쿼리가 중간에 잘려서 보일 때 기본 SHOW PROCESSLIST; 는 INFO 컬럼의 긴 쿼리를 일부만 보여줍니다. 이때 SHOW FULL PROCESSLIST; 를 사용하면 잘림 없이 전체 쿼리문 확인이 가능합니다. ⚠️ 주의: KILL {ID} 명령어 사용 시 참고할 점 부하를 급하게 줄이기 위해 문제 스레드를 강제 종료( KILL ID; )할 수 있습니다. 단, INSERT , UPDATE , DELETE 같은 CUD 작업은 강제 종료 시 트랜잭션 롤백 지연 이나 데이터 불일치 위험이 있으므로, 단순 조회( SELE...

[DB] Mysql UPDATE 에서 WHERE SUBQUERY(같은 테이블) 하기.

 오랜만에 대량건으로 DB 업데이트 할 일이 있어서... (SELECT 빼고는 간단한거라도 무섭다....) 테스트를 하는데 에러 발생. 이유는 업데이트 칠 테이블과 조건안에 있는 서브쿼리 테이블이 같아서 안됨. 구글링 하니 가상테이블로 한번 더 감싸면 됨. update BBBB SET DEL_YN = 'Y' where IDX in  ( select IDX FROM ( SELECT b.IDX FROM AAAA as a INNER JOIN BBBB as b on a.FILE_KEY = b.FILE_KEY INNER JOIN CCCC as c on b.BBS_CATEGORY = c.CAMPUS_ID where a.FILE_PATH like '%board2%' and a.BBS_ID != 'MOVIE' and b.DEL_YN = 'N'  ) aa ); 첨에는 보라색만으로만 했는데 BBBB 테이블 땜에 안됨.  그래서 노란색(?)으로 한번 테이블 만들었더니 됨. 참고 : https://link2me.tistory.com/932

[Tool] Putty SSH Tunnels 및 SSH DB 접속.

DB를 AWS aurora serverless로 사용해서 AWS 내부에서만 접속이 가능. bation host server로 통해 DB 접속. 1. MYSQL Workbench Manage Server Connections 에서   가. Connection Method : Standard TCP/IP over SSH 선택.   나. Parameters 탭에서        bation host server 및 DB에 맞게 설정. 2. Putty SSH Tunnels Category 에서   가. SSH --> Tunnels 에서        Source port : 잘 안 쓰는 포트로        Destination : DB 주소        Local ,Auto 라디오 버튼 활성화.   나. 연결 될 bation host server 서버 맞게 설정.   연결 후 코드에서 host :  localhost                          port :  Putty에서 설정한 잘 안 쓰는 포트   그리면 잘 됨.   

[DB] Mysql Join (inner, left, right, full 이미지로)

이미지
mysql 조인방법중에 이미지 기준으로 왼쪽 두번째 방법을 검색중에 찾은 자료. 이미지로 보니 쉽게 이해가 됨. 예는 패스~~ 다른 방법도 실제로 되는지 확인은 안 했지만 참고 할만해서 저장.  참고한 Link == http://rapapa.net/?p=311

[DB] Mysql 숫자 기준으로 정렬하기.

숫자가 있는(varchar 타입이지만) 필드를 정렬하는데 생각처럼 안됨. 예를들어 1 10 11 2    이렇게 가지고 옴.  검색했더니 Mysql은 order by 필드*1 로 하면 됨. 졍렬을 원하는 필드 바로뒤에 *1  SELECT * FROM result_total order by COUNT*1; 했더니  1 2 10 11 원하는대로 가지고 옴.  숫자 + 문자 데이터도 가능.

[DB] MySQL triggrt 생성하기

예전에 IDC에서 AWS RDS로 DB 이전을 하는데 DB백업하고 복원을 하는데 trigger 때문에 복원이 되지 않는 문제가 있었다. 그래서 trigger 제외하여 백업 후 복원을 했더니 잘 되었다. 암튼 복원 DB에 trigger 생성을 해야하기 때문에 찾아봄. (그때는 누가 만들어주었나?) 문법 CREATE TRIGGER trigger_name trigger_time trigger_event ON tbl_name FOR EACH ROW trigger_stmt trigger_name: 트리거 이름. trigger_time: 트리거 시기, 순위 BEFORE 또는 AFTER.  trigger_event: 트리거 이벤트, 순위, UPDATE 또는 DELETE INSERT.  tbl_name: 동작 할 테이블 명. trigger_stmt: 트리거 실행문. 예) stamp_logs 테이블에 INSERT 후 트리거 실행문 실행 CREATE TRIGGER `update_userinfo_stampcnt` AFTER INSERT ON `stamp_logs` FOR EACH ROW BEGIN  update userinfo a  set a.stamp_cnt=NEW.sub_total  where a.user_id=NEW.user_id; END; Tip HeidiSQL에서 trigger 관련 실행방법 생성  - 생성을 원하는 DB에서 오른쪽 마우스 클릭  - 새로생성>트리거 수정  - 생성을 하면 테이블 하단에 트리거 리스트가 나온다 이를 클릭하여 수정 삭제  - 해당 트리거를 마우스 오른쪽 버튼 클릭하여 삭제

[DB] MySQL 사용자(USER) 생성,삭제,권한부여 하기

MS SQL은 DB별로 USER 생성 사용 했는데 AWS RDS MySQL은 루트계정(최상위계정)으로만 사용을 해서 잊고 있다가 DB별로 USER 사용하는 MySQL에 잠깐 당황을 해서 (루트계정으로 실행되는 명령어가 안되어서.....) 알고자 씀. 1. 먼저 mysql DB를 선택하고 사용자 확인하기. use mysql; select host, user, password from user; (select * from user; 는 컬럼이 넘 많아서....) 2. 사용자(user) 추가 create user 'userID'@'%' identified by 'userpassword'; user 테이블 host 컬럼보면 값이 % ,localhost가 있는데 %는 외부접근 localhost는 내부접근 그러므로 위에 명령어는 외부접근이 되는 사용자 계정. 또는 '111.222.%' IP 주소가 111.222.xxx.xxx 로 시작하는 IP 대역        '111.222.333.444' 는 111.222.333.444로 시작하는 특정 IP 외부 허용. 또는 insert into user (host,user,password) values('%','userID',password('userpassword'));         FLUSH PRIVILEGES; FLUSH PRIVILEGES란? INSERT, DELETE, UPDATE를 통해 사용자를 추가, 삭제, 권한 변경 등을 수행하였을 때 이 변경 사항을 반영하기 위하여 사용한다. 이 때 FLUSH PRIVILEGES는 grant 테이블을 reload함으로서 변경 사항을 즉시 반영하도록 한다. 그런데 이 FLUSH PRIVILEGES는 굉장히 성능에 영향을 준다. 특히 습관적으로 FLUSH PRIVILEGES를 사용하는 경우가 있는데 이는 엄청난 부하가...

[AWS] RDS mysql slow_query 설정

AWS RDS MySQL에서 slow_query 설정. 1. AWS console >> RDS >> Instances >> 해당 DB 체크 >> Logs 보면  Logs 목록에    slowquery/mysql-slowquery.log이 없음. 2. Parameter Groups >> 해당 Parameter 체크 후 Edit Parameters 클릭    가. slow_query_log  = 1 (사용)  (기본값은  <engine-default> 또는  0 )    나. long_query_time  = 10 (기본값은 10(초단위) )    : slow_query 기준값 즉 10초가 넘으면 slow_query로 log에 남음.    다.  log_queries_not_using_indexes : 인덱스를 사용하지 않는 모든 쿼리를           느린 쿼리 로그에 기록하려면 1로 설정합니다. 기본값은 0입니다. 인덱스를 사용하지           않는 쿼리는 실행 시간이  long_query_time  파라미터의 값보다 짧아도 로그에            기록됩니다.(안 하는걸로....)     라. 암튼 가. 부분을 수정 후 저장 DB 리셋 후  1. logs 부분을 보면          slowquery/mysql-slowquery.log 나옴.    마. SHOW VARIABLES LIKE 'slow_query_%';  ,SHOW VARIABLES LIKE ...

[WEB] PHP에서 Mysql 데이터(레코드) 가져오기 그리고 그외....

mysqli_fetch_row,  mysqli_fetch_assoc, mysqli_fetch_array :  mysqli_query를 통해 얻은 result에서 데이터(레코드)를 1개씩 리턴해주는 함수. 1. 차이점 : 리턴하는 배열의 형태가 다름. mysqli_fetch_row 일반 배열 mysqli_fetch_assoc 연관 배열 mysqli_fetch_array 일반 + 연관 배열 2. 사용법 : ebook_no author 1002 Scott Nickel 1003 Christianne C. Jones 1004 일반 + 연관 배열 1) $conn = new mysqli(DB_HOST, DB_USER_ID, DB_PASSWORD,DB_NAME); $query = "select ebook_no, author from bookss limit 3 "; $result = mysqli_query($conn, $query); while($data = mysqli_fetch_array ($result)){    print_r($data);    echo '<br>'; } 2) 리턴되는 결과값 가. mysqli_fetch_row : Array ( [0] => 1002 [1] => Scott Nickel ) Array ( [0] => 1003 [1] => Scott Nickel ) Array ( [0] => 1004 [1] => Christianne C. Jones ) 나. mysqli_fetch_assoc Array ( [ebook_no] => 1002 [author] => Scott Nickel ) Array ( [ebook_no] => 1003 [author] => Scott Nickel ) Array ( [ebook_no] => 1004 [auth...

[WEB] php에서 Mysql 연결 및 확인 그리고 실행,해제.

Mysqli_connect : php에서 Mysqli 연결하는 함수. Mysqli_query : Mysqli_connect 함수로 연결된 DB에 쿼리를 실행하는 함수. Mysqli_close : Mysqli_connect 함수로 연결된 DB 연결 해제하는 함수. 1. 단순하게 연결 및 확인. // DB 연결 $conn = new mysqli(DB_HOST, DB_USER_ID, DB_PASSWORD); // 연결 확인 if ($conn->connect_error) {     die("Connection failed: " . $conn->connect_error); } echo "Connected successfully"; 2. 실제로 사용할때 mysqli_connect(호스트,아이디,비밀번호,DB명,포트); 기본포트 사용이면 포트 부분은 입력제외. 1)연결 $conn= mysqli_connect(DB_HOST,DB_USER_ID,DB_PASSWORD,DB_NAME); 2)사용 mysqli_query($conn,쿼리 또는 쿼리 들어간 변수); 3)해제 mysqli_close($conn);

[DB] MySQL 백업 / 복원

이미지
1. Heidi SQL 1). 백업 가. 해당 DB 우클릭 >> 데이터베이스를 SQL로 내보내기 클릭.  (HeidiSQL 9.4) 나. 테이블 도구 >> 데이터베이스 : 생성                        테이블 : 생성                        데이터 : 삭제 + 삽입 (기존 데이터 초기화)                        출력 : 단일 .SQL 파일                        파일명 : 원하는이름으로... 다. 내보내기 클릭 후 지정된 폴더에 백업파일 생성. 2). 복원 가. 파일(메뉴) >> SQL 파일 실행 >> 해당 백업파일 열기.  끝. 3). 개별 테이블 백업 및 복원 (위에 이미지 참고) 가. 해당 테이블 우클릭 >> 데이터베이스를 SQL로 내보내기 클릭. 나. 테이블 도구 >> 데이터베이스 : 없음 (생성 체크하면 DB와테이블이 같이 만들어짐)                        테이블 : 생성                        데이터 : 삭제 + 삽입 (기존 데이터 초기화)      ...