'DB/MySQL'에 해당되는 글 22건

  1. 2016.08.04 MySQL Cluster
  2. 2016.08.04 스케일 아웃 측면에서 살펴본 MySQL의 특성
  3. 2015.05.21 MySQL root 패스워드 분실
  4. 2012.12.11 MSSQL 문자열 구분자 분리 (테이블 반환 함수)
  5. 2012.12.11 MSSQL PROC ARRAY
  6. 2011.04.22 MySQL 프로세스 리스트 보기
  7. 2010.10.27 mysql_insert_id
  8. 2010.10.27 문자 함수(RIGHT, LEFT, SUBSTRING_INDEX, SUBSTRING, UPPER, REVERSE, LTRIM, LENGTH)
  9. 2010.09.06 MySQL 날짜 관련 함수
  10. 2010.07.08 LIKE, BETWEEN, IN

MySQL Cluster

DB/MySQL 2016. 8. 4. 18:08

Introduction 

MySQL 클러스터는 분산 컴퓨팅 환경에서 high-availability와 high-redundancy를 채택하였다. MySQL 클러스터는 NDB 클러스터 스토리지 엔진을 사용하여, 클러스터에서 여러 개의 서버가 함께 돌아가도록 한다. MySQL 클러스터가 지원하는 운영 체제는 Linux, Mac OS X, Solaris 등 이다. 더 자세한 정보는 다음 사이트를 참고 하길 바란다. http://www.mysql.com/products/cluster

MySQL Cluster Overview 


MySQL 클러스터는 share-nothing 시스템에서 in-memory 데이터 베이스의 클러스터링을 가능하게 한다. 이러한 아키텍쳐는 특정한 하드웨어 및 소프트웨어를 요구하지 않으므로 비용을 절감할 수 있도록 하며, 각 콤포넌트가 고유 메모리와 디스크를 보유함으로 단일 취약점(single point of failure)을 가지지 않는다.

MySQL 클러스터는 일반 MySQL 서버에 NDB라는 스토리지 엔진을 통합하여, 다음 그림과 같이 MySQL서버, NDB 클러스터의 데이터 노드, MGM 서버가 포함된 컴퓨터와 데이터에 접근하기 위한 어플리케이션 프로그램으로 구성된다.

데이터가 NDB 클러스터 스토리지 엔진에 저장될 때, 테이블은 데이터 노드에 저장된다. 각 테이블은 클러스터의 MySQL 서버에서 직접 접근이 가능하다. 그래서 클러스터의 어떤 정보를 업데이트 하면, 다른 모든 MySQL서버에서 곧바로 확인할 수 있다.

MySQL 클러스터의 데이터 노드에 저장된 데이터는 미러링이 가능하며, 클러스터는 트랜잭션 중단 등 각 노드들의 상태에 대한 핸들링이 가능하다.

http://dev.mysql.com/doc/refman/5.0/en/images/cluster-components-1.png
MySQL 클러스터의 구성

Basic MySQL Cluster Concepts 


NDB는 높은 가용성과 데이터 지속성을 갖는 인 메모리 스토리지 엔진이다. DB 스토리지 는 failover와 로드 밸런싱 옵션을 설정할 수 있다. MySQL클러스터는 NDB 스토리지 엔진과 MySQL 서버로 구성되어 있으며, MySQL 클러스터의 클러스터 부분은 MySQL 서버에 독립적이다. MySQL 클러스터의 각 부분은 노드로 간주한다.

"노드"는 일반적으로 컴퓨터를 지칭하지만 MySQL 클러스터에서는 "프로세스"를 말한다.


클러스터 노드에는 세 가지 타입이 있으며, MySQL Cluster를 구성하기 위해 최소한 노드 세 개가 있어야 한다.

  • MGM node : 이 노드는 설정을 포함, 다른 노드를 관리하는 매니저 노드이다. 다른 노드보다 가장 먼저 실행되며 ndb_mgmd 명령으로 실행시킨다.
  • data node : 클러스터의 데이터를 저장하는 노드이다. ndbd 명령으로 실행시킨다.
  • SQL node : 클러스터 데이터에 접근하는 노드이다. MySQL 클러스터에서는 NDB 클러스터 스토리지 엔진을 사용하는 MySQL 서버가 클라이언트 노드이다. mysqld --ndbcluster나 mysqld 명령으로 실행시키는데, 이 때는 my.cnf 에 ndbcluster를 추가한다. 

MGM 노드는 클러스터 컨피그레이션 파일과 로그를 관리한다. 데이터 노드에 이벤트가 발생하면, 데이터 노드는 그에 대한 정보를 매니저 서버로 보내고, 매니저 서버는 클러스터 로그를 기록한다.


Simple Multi-Computer How-To 


다음과 같이 4대의 컴퓨터로 클러스터를 구성하는 것을 가정하고 있다. (4개의 노드로 구성되고, 각각의 노드는 편이성을 위해 IP로 지칭한다.)

아래에서 필요한 컴퓨터는 리눅스가 설치된 인텔 기반 데스크탑 PC이며, 4대 모두 동일한 이더넷 카드(100Mbps나 1기가 비트)가 필요하다.

Node IP Address

Management (MGM) node 192.168.0.10

MySQL server (SQL) node 192.168.0.20

Data (NDBD) node "A" 192.168.0.30

Data (NDBD) node "B" 192.168.0.40
http://dev.mysql.com/doc/mysql/en/images/multi-comp-1.png


설치 및 사용 시 주의할 점은 MySQL 클러스터는 클러스터 노드 간 커뮤니케이션에 암호화 및 보호 장치가 전혀 없으므로, 웹 상에서 사용하려면 방화벽을 사용하는 등의 보안상의 대책이 필요하다는 것이다.

MySQL Cluster를 사용하기 위해서는 -max 버전을 설치해야 한다. 모든 설치는 root권한으로 진행하며 작업에 필요한 파일은 /usr/local/ 에 저장한다.

1. /etc/passwd 와 /etc/group 파일에서 mysql 그룹과 유저가 있는지 확인한 후 없으면 다 음과 같이 생성한다.
# cd /usr/local
# groupadd mysql
# useradd -g mysql mysql

2. 유저와 그룹 생성 후 압축을 풀고, 심볼릭 링크를 걸어준다.
# tar -xzvf mysql-max-4.1.13-pc-linux-gnu-i686.tar.gz
# ln -s /usr/local/ mysql-max-4.1.13-pc-linux-gnu-i686 mysql

3. mysql 디렉토리로 이동하여 시스템 데이터베이스 생성을 위한 스크립트를 실행시킨다.
# cd mysql
# scripts/mysql_install_db --user=mysql

4. MySQL 서버와 데이터 디렉토리의 퍼미션을 설정한다.
# chown -R root .
# chown -R mysql data
# chgrp -R mysql .

5. 시스템 부팅 시 자동적으로 Mysql을 실행할 수 있도록 설정한다.
# cp support-files/mysql.server /etc/rc.d/init.d/
# chmod +x /etc/rc.d/init.d/mysql.server
# chkconfig --add mysql.server

6. MGM (management) 노드를 별도의 PC에 설치할 경우 mysql 데몬은 설치하지 않아도 무방하다. 위와 같이 설치한 후 MGM 서버는 다음과 같이 설치를 계속한다.
# cd /usr/local/mysql/bin/
# cp ndb_mgm* /usr/local/bin/
# chmod +x ndb_mgm*

7. 각 데이터 노드와 SQL 노드는 MySQL서버 옵션과 connectstring에 대한 정보가 포함된 my.cnf파일이 필요하고, MGM노드는 config.ini 파일이 필요하다. 에디터를 열어 다음과 같이 편집한 후 파일을 저장한다.
# vi /etc/my.cnf 
[MYSQLD]			      # Options for mysqld process:
Ndbcluster			# run NDB engine
ndb-connectstring=192.168.0.10	# location of MGM node

[MYSQL_CLUSTER]		      # Options for ndbd process:
ndb-connectstring=192.168.0.10	# location of MGM node

8. MGM 노드의 설정 파일을 만들기 위해 적당한 디렉토리를 만든 후 에디터를 열어 다음과 같이 편집한다.
 # mkdir /var/lib/mysql-cluster
# cd /var/lib/mysql-cluster
# vi config.ini

[NDBD DEFAULT]		# Options affecting ndbd processes on all data nodes:
NoOfReplicas=2		# Number of replicas
DataMemory=80M	         # How much memory to allocate for data storage
IndexMemory=18M	         # How much memory to allocate for index storage
                  		# For DataMemory and IndexMemory, we have used the
                  		# default values. Since the "world" database takes up
                  		# only about 500KB, this should be more than enough
                  		# for this example Cluster setup.

[TCP DEFAULT]		# TCP/IP options:
portnumber=2202	         # This the default; however, you can use any
                  		# port that is free for all the hosts in cluster
                  		# Note: In MySQL 5.0, this parameter is deprecated;
                  		# it is recommended that you do not specify the 
                  		# portnumber at all and simply allow the port to be
                  		# allocated automatically

[NDB_MGMD]			# Management process options:
hostname=192.168.0.10		# Hostname or IP address of MGM node
datadir=/var/lib/mysql-cluster	# Directory for MGM node logfiles

[NDBD]				# Options for data node "A":
				# (one [NDBD] section per data node)
hostname=192.168.0.30		# Hostname or IP address
datadir=/usr/local/mysql/data	# Directory for this data node's 
				# datafiles

[NDBD]				# Options for data node "B":
hostname=192.168.0.40		# Hostname or IP address
datadir=/usr/local/mysql/data	# Directory for this data node's 
				# datafiles

[MYSQLD]			         # SQL node options:
hostname=192.168.0.20	         # Hostname or IP address
datadir=/usr/local/mysql/data	# Directory for SQL node's datafiles
				# (additional mysqld connections can be
				# specified for this node for various
				# purposes such as running ndb_restore)

설치와 설정 과정이 끝났다. 이제 실행을 해 보자.

클러스터 노드들은 각각 실행되어야 한다. 실행 순서는 매니지먼트 노드를 가장 먼저 실행할 것을 권한다. 그 다음은 스토리지 노드와 SQL노드 순이다.
1. 매니지먼트 호스트에서 MGM 노드 프로세스를 실행시켜 보자. 컨피그레이션 파일을 찾을 수 있도록 -f 옵션을 주도록 한다.
# ndb_mgmd -f /var/lib/mysql-cluster/config.ini
MGM 노드를 다운시킬 때에는 다음과 같이 하면 된다.
# ndb_mgm -e shutdown

2. 다음으로 데이터 노드 호스트에서 NDBD프로세스를 실행시킨다. --initial 이란 인수는 ndbd를 처음 실행할 때와 컨피그레이션이 바뀐 후 재시작 할 때만 사용한다.
# ndbd --initial

3. SQL 노드는 다음과 같이 mysql.server를 실행시킨다.
# /etc/rc.d/init.d/mysql.server start

4. 이제 모든 노드가 실행되었으니 MGM 노드 클라이언트를 띄워 간단히 테스트를 해보자.

Ndb_mgm명령어를 입력하였을 때 정상적으로 동작하는 모습은 다음과 같이 프롬프트가 떨어지는 모습이다.
# ndb_mgm
-- NDB Cluster -- Management Client --
ndb_mgm> 

5. 이제 show명령어를 사용하여 클러스터의 모든 노드들이 정상적으로 연동되는지 확인을 해 보자. HELP 를 입력하면 다른 명령어들도 확인해 볼 수 있다. 다음과 같이 4개의 노드를 구성하는 것에 성공하였다.
ndb_mgm> show
Connected to Management Server at: 192.168.0.10:1186
Cluster Configuration
---------------------
[ndbd(NDB)]     2 node(s)
id=2    @192.168.0.30  (Version: 4.1.13, Nodegroup: 0, Master)
id=3    @192.168.0.40 (Version: 4.1.13, Nodegroup: 0)

[ndb_mgmd(MGM)] 1 node(s)
id=1    @192.168.0.10 (Version: 4.1.13)

[mysqld(API)]   1 node(s)
id=4   (Version: 4.1.13)

ndb_mgm>

MySQL 클러스터의 제한 


MySQL Cluster 4.1.x 버전은 다음과 같은 사용상의 제한점을 지닌다.

  • 트랙잭션 수행 중의 롤백을 지원하지 않으므로, 작업 수행 중에 문제가 발생하였다면, 전체 트랙잭션 이전으로 롤백하여야 한다.
  • 실제 논리적인 메모리의 한계는 없으므로 물리적으로 허용하는 만큼 메모리를 설정하는 것이 가능하다.
  • 컬럼 명의 길이는 31자, 데이터베이스와 테이블 명은 122자까지 길이가 제한된다. 데이터베이스 테이블, 시스템 테이블, BLOB인덱스를 포함한 메타 데이터(속성정보)는 1600개까지만 가능하다.
  • 클러스터에서 생성할 수 있는 테이블 수는 최대 128개이다.
  • 하나의 로우 전체 크기가 8KB가 최대이다(BLOB를 포함하지 않은 경우).
  • 테이블의 Key는 32개가 최대이다.
  • 모든 클러스터의 기종은 동일해야 한다. 기종에 따른 비트저장방식이 다른 경우에 문제가 발생하기 때문이다.
  • 운영 중 스키마 변경이 불가능하다.
  • 운영 중 노드를 추가하거나 삭제할 수 없다.
  • 최대 데이터 노드의 수는 48개이다.
  • 모든 노드는 63개가 최대이다. (SQL node, Data node, 매니저를 포함) 


MySQL Cluster FAQ 


Cluster 와 Replication의 차이

리플리케이션은 비동기화 방식이고, 클러스터는 동기화 방식이다. 따라서 리플리케이션은 일방적으로 데이타를 전달하여 복제를 하지만 클러스터는 동기방식이므로 데이타를 복제한 후 결과를 확인하기 때문에 데이타 누락이 발생하지 않는다. 다만 복제한 결과를 확인해야 하기 때문에 Cluster가 Replication보다는 속도가 느리다. 또한 Replication의 경우 복제된 데이터에 대한 신뢰를 할 수 없다.


Cluster가 사용하는 네트워크 (How do computers in a cluster communicate?)

MySQL 클러스터는 TCP/IP를 통해 서로 통신한다. 최소한 100Mbps의 이더넷을 사용해야 하며 원활한 통신을 위해 gigabit 이더넷을 권고한다. 실제 데이터가 메모리에 존재하여 사용되며 물리적인 측면에서 봤을 때 CPU, 메모리, 각 노드간의 통신을 위한 네트워킹이 주를 이룬다. 이중 가장 속도가 느린 네트워크의 속도를 높임으로써 전체적인 빠른 동작이 가능하도록 해야 한다. 또한, 더욱 빠른 SCI 프로토콜도 지원하며, 이는 특정 하드웨어를 필요로 한다.


클러스터를 구성하기 위해 컴퓨터가 얼마나 필요한가?

최소한 3대가 있어야 클러스터 구성이 가능하나, MGM 노드와 SQL 노드, 스토리지 노드 둘, 이렇게 4 대로 구성하길 권한다. 하나의 노드가 실패했을 때 지속적인 서비스를 하기 위해서 MGM노드는 분리된 컴퓨터에서 실행되어야 한다.


클러스터에서 각 컴퓨터들이 하는 일은?

MySQL 클러스터는 물리적, 논리적으로 구성된다. 컴퓨터는 물리적 요소이며 호스트라고 불리기도 한다. 논리적, 기능적 요소는 노드이다. 노드는 역할에 따라 MGM 노드, data 노드(ndbd), SQL 노드로 나뉜다.


어떤 OS에서 사용할 수 있는가?
MySQL 4.1.12 현재 MySQL 클러스터는 공식적으로 Linux, Mac OS X, Solaris를 지원한다.


MySQL 클러스터가 요구하는 하드웨어 사양은?

NDB가 설치되고 실행되는 모든 플랫폼이면 가능하나, 당연히 빠른 CPU, 높은 메모리에서 더 성능이 좋다(64-bit CPU에서 더 빠르다). 네트워크은 일반 TCP/IP를 지원하면 되고, SCI 를 지원하려면 특정 하드웨어가 요구된다.


MySQL 클러스터가 TCP/IP를 이용한다면 하나 이상의 노드를 인터넷을 통해 다른 곳에서 실행시킬 수 있는가?

가능하다. 하지만 MySQL 클러스터는 어떠한 보안도 제공되지 않으므로, 외부에서 클러스터 데이터 노드나 매니저 노드에 직접 접근하지 못하도록 해야 한다.


클러스터 사용을 위해 새로운 프로그래밍 언어나 쿼리를 배워야 하나?

표준 (My)SQL 쿼리나 명령을 사용하므로 그러지 않아도 된다.


클러스터 사용 시 에러나 경고 메시지는 어디서 찾나 ?
두 가지 방법이 있다. MySQL창에서 SHOW ERRORS나 SHOW WARNINGS로 확인하는 방법과 프롬프트 상태에서 perror --ndb error-code 를 사용하는 방법이 있다.


MySQL Cluster transaction-safe? 어떤 테이블 타입이 클러스터를 지원하나?
MySQL에서 NDB 스토리지 엔진과 생성된 테이블은 트랜잭션을 지원한다. NDB는 클러스터링만 지원하는 MySQL 스토리지 엔진이다.


"NDB" 의 의미는?
"Network Database".


클러스터를 지원하는 MySQL 버전은? 소스를 컴파일 해야 하나?

MySQL-max 4.1.3부터 지원한다. 바이너리 파일은 컴파일을 할 필요가 없다.


RAM은 얼마나 필요한가? 디스크는 사용하지 못하나?

클러스터는 오직 in-memory이며, 모든 테이블 데이터(인덱스 포함)가 RAM에 저장된다. 클러스터에서 필요한 RAM용량은 다음 공식으로 계산한다. (SizeofDatabase * NumberOfReplicas * 1.1 ) / NumberOfDataNodes


ERROR 1114: The table 'my_cluster_table' is full

위와 같은 에러가 발생했을 때는 할당된 메모리가 부족한 경우이다.


FULL TEXT 인덱스를 지원하는가?

현재 지원하지 않는다.


하나의 컴퓨터에서 여러 개의 노드가 돌아가는가?

가능하긴 하지만 권하진 않는다. 각 노드들이 다른 컴퓨터에서 실행되는 것이 더 안정적이다.


클러스터를 재시작하지 않고 노드를 추가할 수 있는가?

할 수 없다. MGM 이나 SQL 노드를 추가하려면 새로 시작해야 한다.


어떻게 기존의 MySQL 데이터베이스를 클러스터로 임포트 하는가?

ENGINE=NDB 나 ENGINE=NDBCLUSTER 옵션을 가진 테이블은 임포트할 수 있다. 또는 ALTER 기능으로 기존의 테이블을 클러스터로 변환 사용할 수 있다.

- ALTER TABLE OLD_TABLE ENGINE=NDBCLUSTER;


Arbitrator란 ?

클러스터에서 한 개 혹은 그 이상의 노드가 실패할 경우, MGM 서버나 다른 노드가 그 노드의 역할을 대신하여 다른 노드들로 하여금 실패한 노드와 같은 노드로 인식하게 하는 기능을 한다. 이런한 역할을 하는 노드를 중재인이라고 한다.


클러스터 shut down시에 어떤 일이 일어나는가?

클러스터 데이터 노드의 메모리에 있던 데이터가 디스크에 쓰여지고, 그 다음에 클러스터가 시작될 때 다시 메모리에 로드된다.


클러스터에서 다른 매니저 노드를 구성하는 것은?

fail-safe에 있어서 도움이 된다. 단지 하나의 MGM 노드 만이 클러스터를 컨트롤 할 수 있지만 MGM 노드 하나를 primary로, 추가의 매니저 노드를 primary MGM 노드가 실패했을 때 인계받도록 하면 된다.


5. MySQL Cluster Glossary 


Cluster

일반적으로 Cluster는 하나의 업무를 수행하기 위해 함께 동작하는 컴퓨터 세트이다. NDB Cluster는 자료저장, 복구, 컴퓨터 간의 분배 관리 등을 시행하기 위해 MySQL을 사용하는 Storge Engine 이다. MySQL Cluster는 in-memory storage를 사용한 shared-noting 아키텍쳐에서 분산된MySQL DB를 지원하기 위해 NDB엔진을 사용하여 함께 돌아가는 컴퓨터 그룹이다.


Configuration Files

클러스터, 호스트, 노드에 관계된 직접적인 정보를 포함하는 파일이다. 클러스터 시작 시 Cluster의 MGM 노드가 읽어들인다.


Backup

디스크나 다른 Long-term Storage에 저장되는 모든 클러스터 데이타, 트랜젝션, 로그의 완전한 카피를 말한다.


Restore

백업에 저장되는 것과 같이 클러스터에 그 전 상태로 되돌리는 것을 말한다.


CheckPoint

일반적으로 데이타가 디스크에 저장될 때 체크포인트에 도달한다고 말한다. 클러스터에서는 Committed된 트랜잭션을 디스크에 저장하는 시간을 말한다. NDB Storage Engine에는 일관되게 클러스터의 데이타를 보존하기 위해 두 종류의 CheckPoint가 있다. LocalCheckPoint(LCP) : 싱글 노드의 체크포인트. 그러나 클러스터의 모든 노드에서 LCP를 사용한다. LCP는 디스크에 노드의 모든 데이타를 저장하도록 한다(보통 매 몇 분마다). 클러스터 Activity의 노드와 레벨, 다른 요인에 의해 저장되는 데이타의 양은 의존적이다. GlobalCheckPoint(GCP) : GCP는 모든 노드의 트랜잭션이 동기화되고, redo-log가 Disk에 저장될 때 몇 분마다 발생한다.


Cluster Host

MySQL Cluster의 구성 컴퓨터. 클러스터는 물리적 구조와 논리적 구조를 가진다. 물리적으로 클러스터는 Cluster Host라는 컴퓨터의 수로 구성된다.


Node

MySQL Cluster의 논리적, 기능적 요소를 말하며 Cluster Node라고도 한다. MySQL Cluster에서는 node란 용어를 Cluster의 물리적 Component인 Process를 지칭한다. MySQL Cluster가 동작하기 위해 3가지 타입의 노드가 있다.


MGM node - MySQL Cluster에서 다른 노드들의 설정 정보, 노드의 시작과 정지, 네트워크 파티셔닝, 백업과 저장 등을 포함하여 다른 노드들을 관리한다.


SQL node (MySQL Server) - 클러스터의 데이터 노드안에 저장된 데이터를 Serve 하는 MySQL Server 인스턴스. 데이타를 저장, 분배, 업데이트하는 클라이언트는 MySQL Server를 통해 접근 가능하다.


Data node - 이 노드는 실제 데이타를 저장한다. 현재 싱글 클러스터는 총 48개의 데이타 노드를 지원한다.

싱글 머신에 한 개 이상의 노드가 공존할 수도 있고, 한 머신에 완전한 클러스터를 구성하는 것도 가능하다. MySQL 클러스터에서 호스트는 클러스터의 물리적 컴퍼넌트이며, 노드는 논리적 혹은 기능적인 컴퍼넌트, 즉 프로세스라는 것을 잊지 말자.


Node group

데이터 노드의 집합. 노드 그룹 안의 모든 데이터 노드는 같은 데이터(fragment)를 포함한다. 그리고 싱글 그룹의 모든 노드는 다른 호스트에 존재해야 한다.


Node failure

MySQL 클러스터는 클러스터를 구성하는 어느 한 노드의 기능에만 의존적이지 않다. 클러스터는 하나 혹은 몇 개의 노드가 실패해도 계속될 수 있다.


Node restart

실패한 클러스터 노드의 리스타팅 과정.


Initial node restart

노드의 이전의 파일 시스템을 지우고 시작하는 클러스터 노드의 과정. 소프트웨어 향상과 그 밖의 특별한 상황 등에 사용된다.


System crash(or System fail)

클러스터의 상태가 확인되지 않는 등 많은 클러스터 노드가 실패했을 때 일어날 수 있다.


System restart

클러스터의 리스타팅과 디스크 로그 및 체크 포인트로부터 reinstall하는 프로세스를 말한다. 클러스터를 shutdown 한 이후에 일어나는 과정이다.


fragment

데이터베이스 테이블의 한 부분. NDB스토리지 엔진에서 테이블을 나누어 fragments의 수에 따라 저장한다. Fragment는 파티션이라 불리기도 한다. MySQL 클러스터에서 테이블은, 머신과 노드 간의 로드 밸런싱을 용이하게 할 수 있도록 fragment된다.


Replica

NBD 스토리지 엔진에서 각 테이블 프레그먼트는 여분을 포함하여 다른 데이터 노드에 저장된 많은 replica를 갖는다. 현재는 fragment 당 4개 이상의 replica가 가능하다.


Transpoter

노드들 간의 데이터 이동을 제공하는 프로토콜 TCP/IP(local), TCP/IP(remote), SCI, SHM(MySQL 4.1 버전에서 실험적임)


NDB(Network DataBase)

NDB는 MySQL클러스터에서 사용하는 스토리지 엔진을 말 함. NDB 스토리지 엔진은 모든 일반적인 MySQL 컬럼 타입과 SQL문을 지원하며, ACID(DB무결성 보장을 위한 트랜잭션)성질을 가진다.


Shared-nothing architecture

MySQL 클러스터의 이상적인 아키텍쳐. 진정한 Shared-nothing setup 에서 각 노드는 분리된 호스트에서 실행된다. 이러한 배열은 싱글 호스트나 싱글 노드가 아니면 SOF나 시스템 병목현상이 전체적으로 발생할 수 있다는 데 있다.


In-memory storage

각 데이터 노드에 저장된 모든 데이터는 그 노드의 호스트 컴퓨터의 메모리에 유지된다. 클러스터의 각 데이터 노드를 위해, (데이터 노드의 수로 나뉜 replica의 수 * 데이터베이스 사이즈)만큼의 가용 RAM의 양을 확보해 두어야 한다. 그러니까, 데이터베이스가 1기가의 메모리를 차지하고, 4개의 replica와 8개의 노드로 클러스터를 구성하고자 하면, 각 노드당 최소 500MB의 메모리가 필요하다. 그리고 OS와 다른 어플리케이션 프로그램이 쓰는 메모리가 추가로 필요하다.


Table

관계형 데이터베이스에서는 table은 일반적으로 동일하게 구조화된 레코드의 set을 가리킨다. MySQL 클러스터에서 데이터베이스 테이블은 fragment의 set으로써 데이터 노드에 저장되고, 각 fragment는 추가로 데이터 노드에 복제된다. 같은 fragment를 replicate한 데이터 노드의 set이나 fragment의 set을 노드 그룹이라 한다.


Cluster Programs : 명령어들

서버 데몬
  • ndbd : 데이터 노드 데몬
  • ndb_mgmd : MGM서버 데몬
클라이언트 프로그램
  • ndb_mgm : MGM 클라이언트
  • ndb_waiter : 클러스터의 모든 노드들의 상태를 확인할 때 사용
  • ndb_restore : 백업으로부터 클러스터의 데이터를 복구할 때 사용

Contributors 

처음 작성자 : 송은영,f405(ccotti22) f405@naver.com (2006.2.1 15:37)

작성일 : 2005년 8월 10일 수요일

이 문서는 MySQL Cluster 4.0대의 매뉴얼을 번역, 정리한 것으로 틀린 부분을 다소 포함할 수 있으며, 저는 그에 대한 책임을 지지 않겠습니다.

부족하지만 다른 분들도 공부하는데 도움이 되길 바랍니다.

그리고 이 문서를 작성하기 전 참고한 리눅스 및 MySQL 문서들을 작성하신 많은 선배님들에게 감사의 말씀을 드립니다. 그리고 이 경어는 생략하였습니다. 양해의 말씀을...

출처 - http://nuninaya.tistory.com/127

:

스케일 아웃 측면에서 살펴본 MySQL의 특성

DB/MySQL 2016. 8. 4. 18:07

스케일 아웃 측면에서 살펴본 MySQL의 특성

최근 인터넷 서비스들은 글로벌을 지향하고 소셜 네트워크 기능들을 추가하다 보니 데이터의 양과 트래픽의 양이 급속히 증가하고 있다. 또한 가용성 확보 목적으로 RDBMS도 이젠 스케일아웃(Scale-Out)에 자유롭지 못한 상황에 놓이게 되었다. RDBMS가 여러 측면에서 최상의 조합 기능을 제공하지만, 개별 영역의 장점을 추구하는 솔루션들보다 좋은 성능을 낼 수 없는 건 당연하다. 스케일아웃 관점에 맞는 솔루션을 찾을 필요가 있어 MySQL의 스케일아웃 측면에서 어떤 솔루션들이 있는지 살펴보고자 한다. 

[필자] 하호진 | KTH에서 포털 서비스 및 플랫폼(Identity/Payment) 개발 업무를 수행했으며, 현재 와이즈에코에서 이사로 일하고 있다. 개인 블로그 mimul.com/pebble/default를 운영한다.


1. MySQL Partitioning

1) 개요

파티셔닝은 대규모 테이블을 여러 개의 작은 파티션으로 분할해 성능을 높이는 기술이다. 각 행에 대해 각각의 파티션에 분할하며, MySQL에서는 5.1버전부터 지원한다. 파티셔닝은 주로 데이터 웨어하우스와 같은 거대한 테이블을 사용하는 경우에 위력을 발휘한다. 일반적으로 B 트리 인덱스가 커지면서 검색 및 삽입 속도가 저하된다(계산 순서는 O(log m N)). 하지만, 테이블을 파티션으로 나누는 것으로, B 트리 인덱스의 오버헤드를 줄일 수 있다.


 
그림 1 파티션된 테이블

파티션 테이블은 데이터의 분류 조건에 의해 여러 개의 작은 파티션으로 나뉘어 저장된다. 

+ 제약 사항
- 파티셔닝된 테이블은 스토리지 엔진이 같아야 한다. 
-외부키 제약은 사용할 수 없다.
-FULLTEXT 인덱스를 사용할 수 없다. 
-GIS 컬럼을 사용할 수 없다.
-임시 테이블, MERGE 스토리지 엔진, CSV 스토리지 엔진은 파티셔닝할 수 없다.


2) 방식

+ RANGE 
파티션마다 칼럼의 값이 취할 범위를 지정하는 방식이다.

 


 + LIST

파티션 마다 칼럼의 값을 직접 지정하는 방식이다.

 

+ HASH
HASH 값을 갖고 파티션을 할당하고, 할당이 사용자에 의해 정해지는 것이 아니라 MySQL에 맡기는 방식이다.

 

파티션 방식의 수식을 좀 더 이해하기 쉽게 설명하면, 내부적으로‘2012-05-15’라는 입력 값이 들어간다면 birthday가 아래와 같이 처리되어 파티션 1에 저장된다.


+ KEY

HASH와 비슷하나 분할 결정 값은 Primary Key(혹은 Unique Key)에 대해 서버 측의 결정 알고리즘(MySQL 클러스터:MD5, 다른 스토리지 엔진:PASSWORD())에 의해 결정되는 방식이다.
- PRIMARY/UNIQUE 키가 없으면 사용 불가
- UNIQUE 키가 NOT NULL이 아니면 불가(NULL 값은 MD5, PASSWORD 함수 적용 불가)

 

+ 서브 파티셔닝 RANGE와 LIST일 때 각 파티션을 더 분할할 수가 있다. 이것을 서브파티션이라고 한다.



  


3) 장단점

+ 장점
- 대량의 데이터 저장
- 테이블을 분할할 수 있기 때문에 많은 양의 데이터를 저장할 수 있다.

- 부하 경감
- 테이블의 데이터를 분할할 수 있어서 쿼리에 검색되는 데이터가 줄어든다.
- 해당 디스크에 남아있는 분할 데이터를 받을 확률이 높기 때문에 캐시 히트율도 높아진다.
- 집계 함수(SUM/COUNT)가 병렬 처리가 가능해 속도 향상을 가져 온다.

+ 단점
- 분할 방법의 정의, 관리, 그것을 취급하는 애플리케이션 측의 구현, 조사 비용 등이 증가한다.


4) 고려사항

+ 장점
 -테이블 설계 시 PK는 파티셔닝키와 연관돼야 하고 PK를 제외한 추가 제약 조건은 불가능하만, 테이블 특성에 맞는 것들만 파티셔닝 테이블로 설계해야 한다. 그리고 파티셔닝 키가 모든 조회 조건에 들어가야 한다는 점도 유의해야 한다. ? 
그 외는 1) 개요의 제약 사항을 참고하기 바란다.



2. MySQL Cluster

1) 개요

MySQL Cluster는 공유 디스크를 사용하지 않는 Active-Active 형태의 데이터베이스 클러스터에서 트랜잭션을 지원하고 MySQL의 SQL 문장을 사용할 수 있는 관계형 데이터베이스이다. 단일 장애 지점을 없애기 위하여 99.999%의 가용성(연간 5분 정도의 정지시간)을 달성하기 위한 설계가 반영돼 있다. 데이터를 여러 서버에 분산함으로써 동시 다발적으로 대량으로 발생하는 데이터 업데이트를 신속하게 처리하고, 확장성을 높인 접근이다. 온라인 백업뿐만 아니라 클러스터에 서버 추가와 업데이트도 온라인 상태에서 할 수 있기 때문에 클러스터를 중단 없이 운용할 수 있다. MySQL Cluster의 시발점은 통신장비 업체 에릭슨 휴대 통신망의 가입자 데이터베이스용으로 개발된 Ericsson Network DataBase(NDB)라고 한다. 2003년부터 MySQL 서버의 기능과 통합해 제품화하고, 현재 MySQL 서버와 별도의 제품으로 개발?판매가 진행되고 있다. 

+아키텍처
MySQL Cluster에서 공유 디스크를 사용하지 않는 대신 여러 서버에 데이터를 분산 배치하고, 항상 여러 서버가 동일한 데이터 사본을 갖고 있게 한 접근이다. 각 노드의 특성은 다음 <표 1>과 같다.



 

각 테이블의 기본 키 또는 고유 키의 해시를 계산해 파티션을 내부적으로 만들고, 해시 값과 데이터 노드의 수에 따라 각 파티션의 데이터를 데이터 노드에 분산한다. 분산된 데이터는 같은 그룹 데이터 노드의 복제본에 중복 저장된다. 파티션의 데이터가 변경되면 동일한 파티션을 가진 데이터 노드에 동기적으로 변경 사항이 반영되기 때문에 각 데이터 노드의 데이터는 항상 동일하게 유지된다.



 
그림 2 Cluster

클러스터에 있는 데이터 노드? 비트 패킷을 보내 모니터링하고 데이터 노드가 중지된 경우 클러스터에서 자동으로 분리된다. 또한 재해 복구 데이터 노드는 같은 그룹의 데이터 노드에서 최신 변경사항까지 차이를 취득해 데이터를 자동으로 반영하고 데이터를 동기화할 때 클러스터에 다시 참여한다.


+ 특징
- 자동 파티셔닝
- 분산 프라그먼트
- 동기화 방식
- 자동으로 이뤄지는 고속 데이터 노드

+ 페일오버
- 자동 재동기화
-트랜잭션 지원

+ 제약 사항
- 인메모리 인덱스
- 크로스 테이블 조인, 레인지 스캔 등을 지원 안 함
- 포린키 지원 안 함
- 롱 트랜젝션 지원 안 함
- 네트워크 지연 시 치명적
- 모든 클러스터의 기종은 동일해야 함. 기종에 따른 비트 저장방식이 다른 경우에 문제 발생



2) 방식

+ Shared-Nothing



 
그림 3 Shared-Nothing

각 데이터 노드별 독립적인 스토리지를 연결하고 스토리지 공유를 하지 않기 때문에 오라클 RAC와는 달라 스토리지 장애 발생 가능성을 차단하는 구조이다.


+Data Partitioning(데이터 분산 구조)

 
그림 4 Data Partitioning

테이블 Row 단위의 여러 노드에 분산해 쓰기 성능 확장이 가능하고 하나의 노드 그룹 시스템에 동일한 복제본으로 이중화 구성을 했다.


3) 장단점


+ 장점
  -고성능?고가용성
  - 어플리케이션에서 샤딩 기능이 필요 없어 개발 및 유지보수 비용 절감
  - Join 실행 가능
  - 샤드(Shard) 간 ACID 보장
  - 네트워크 홉이 크게 줄어 높은 처리 성능과 짧은 대기 시간 제공
  - 즉각적인 페일오버 및 복구 지원

+ 단점
  - MySQL Cluster 7.2에서 많은 개선이 있었지만 테이블 조인 성능이 떨어짐
  - 클러스터 격리 수준이 READ-COMMITTED



4) 고려사항

+ Distribution Awareness 고려한 설계 MySQL Cluster 내에서 데이터의 분산은 이른바 Sharding과 같은 원리로 이뤄지고 있다. 그래서 Distribution Awareness가 제대로 고려되지 않은, 데이터 노드 수가 증가하면 네트워크 병목현상이 일어나 성능 저하를 유발한다. 이를 위해서는 Sharding 방식으로 테이블을 정의하고 응용 프로그램에서 사용하는 쿼리도 조정한다면 효율을 높일 수 있다. 예를 들어 아래와 같이 Distribution Awareness를 이용하기 위해서는 테이블 정의와 쿼리를 조정해야 한다.


 

그리고 Distribution Awareness가 효과가 있는지 확인하려면 'EXPLAIN PARTITIONS SELECT ...'를 이용해 파티션이 하나만 선택됐는지 확인한다.

+ 키 설계도 중요하다.
MySQL Cluster는 Hash 인덱스 및 Ordered 인덱스라는 두 유형의 인덱스가 있다. Ordered 인덱스는 한 테이블에서 여러 개를 만들 수 있지만, 해시 인덱스는 테이블마다 하나만 만들 수 있다. 즉, 해시 인덱스로 구성되는 기본 키뿐이다. 한편, UNIQUE KEY 제약 조건을 이용하는 경우에는 해시 인덱스가 될 수 있다. 하지만 MySQL Cluster에서는 UNIQUE 키를 정의하면 내부적으로 지원 테이블이라는 다른 테이블이 생성된다. 지원 테이블만큼 테이블에 대한 참조가 증가하므로 UNIQUE KEY 제약 조건을 이용하는 키는 성능이 떨어짐을 알아야 한다.



3. MySQL Replication

1) 개요

MySQL은 마스터/슬레이브 복제 기능을 제공한다. MySQL에서 지원하는 것은 비동기식 복제로 마스터 서버에서 실행되는 SQL 문을 슬레이브 서버로 전송하고 슬레이브로 다시 실행해 데이터를 일관되게 유지하는 기법을 사용하고 있다. 이것은 스테이트먼트 기반 리플리케이션(SBR, Statement Based Replication)이라고 한다. SBR는 그 구조에 근본적인 문제가 있다. 예를 들어 UUID() 함수를 사용할 경우 마스터와 슬레이브에서 각각 UUID()를 실행하면, 각기 다른 결과로 나타난다. 그 결과, 마스터와 슬레이브는 데이터가 불일치하게 된다. 이 문제를 해결하려면 슬레이브로 전달되는 정보를 스테이트먼트 대신 실제로 테이블에 기록된 내용 또는 행 자체를 복제한다. 그것을 구현하는 것이 로우 기반 리플리케이션(RBR, Row Based Replication)이다. 

MySQL 5.1에서 UUID()을 복제하지 못할 스테이트먼트를 포함할 때만 자동으로 SBR에서 RBR로 전환 MIXED 모드가 기본값(binlog_format)으로 돼 있다. 

+아키텍처

 
그림 5 Replication

MySQL Replication은 READ 관련 스케일아웃만 가능할 뿐, WRITE 관련 스케일아웃은 불가하다. 만약 Replication 운영 시 마스터 트래픽이 과도하게 발생하면, 마스터와 슬레이브 간 데이터 동기화 지연 현상이 발생하기도 한다는 점을 염두에 둬야 한다. 동작의 흐름을 살펴본다면 아래와 같다.

① Slave I/O 스레드가 Master에 접속
② Master가 Slave를 인증하고 Slave와의 세션 개시
③ Slave I/O 스레드가 바이너리 로그파일(파일명, 위치)을 요구
④ Master(binlog dump 스레드)가 요구된 지점으로부터 이벤트를 바이너리 로그에서 읽어 들여 Slave에 전송
⑤ Slave I/O 스레드는 받아 낸 이벤트를 relay-log에 기록
⑥ Slave SQL 스레드가 relay-log 내용을 읽어 들여 SQL문을 실행
⑦ Master에 새로운 이벤트가 있으면 Master가 Slave에 송신



2) 방식

+ Linux Heartbeat + MySQL Replication

 
그림 6 Heartbeat + MySQL replication

Heartbeat 프로토콜을 사용해 노드 간 생존 확인 메시지를 송수신해 장애 여부를 인지한다. 두 서버 사이에는 가상(Virtual) IP가 위치해 장애 시 가상 IP는 살아있는 서버로 송수신해 장애를 피한다.


+ L/B + MySQL Replication

 
그림 7 L/B + MySQL Replication

여러 대의 슬레이브를 앞에 두고 부하 분산을 목표로 하며??서 마스터에서 장애가 발생하면 L/B는 자동 IP를 슬레이브로 향하게 해 서비스가 중단 없이 가능하게 된다.


+Linux Heartbeat + DRBD + MySQL Replication

 
그림 8 Heartbeat + DRBD + MySQL Replication

디스크 미러링 소프트웨어(DRBD; 단방향 복제, 동기 복제, 오픈소스)를 활용해 HA를 구성하는 방식이다. 이는 동기 방식으로 데이터 복제가 이뤄져 데이터 불일치가 없는 장점을 갖고 있다.

3) 장단점

+ 장점
  - MySQL 서버의 부하 분산 가능
  - 실시간 백업 가능


+ 단점
  - 장애가 발생시 슬레이브에 반영이 안 될 가능성 존재
  - Master와 Slave 간 데이터 동기화 지연 발생 가능성 존재
  - 장애 복구가 수동으로 이뤄짐



4) 고려 사항

+ MySQL 5.6.3에서는 slave multithread를 지원하지만, 이전 버전의 경우 Slave는 하나의 스레드로만 SQL을 실행하기 때문에 서버 간 동기화 지연 현상이 발생한다. 따라서 replicate_do_db 혹은 replicate_do_table 옵션을 사용해 실제로 적용할 객체들만 선별적으로 동기화하는 것이다. 이는 서비스 단위로 기능을 나눌 수도 있고, 역할별로 기능을 나눌 수 있게 할 수 있다. 그 외에 롱 트렌젝션을 제거하고, Slave 개수를 잘 조절하고, 작업 집합이 InnoDB 버퍼 풀보다 훨씬 큰 경우는 Slave pre-fetching 기술도 활용해 볼 만하다.

+ MySQL Replication에서 5.5버전부터 Semi-syncronous 기능이 추가됐다. 부하량이 적은 환경에서 마스터와 슬레이브 간의 데이터 정합성을 강화시키는 방법이므로 필요 시 활용하면 좋다.



4. MySQL Sharding

샤딩은 물리적으로 다른 데이터베이스에 데이터를 수평 분할 방식으로 분산 저장하고 조회하는 방법을 말한다. 여러 데이터베이스를 대상으로 작업해야 하기 때문에 경우에 따라서는 기능에 제약이 있을 수 있고(JOIN 연산 등) 일관성(consistency)과 복제(replication) 등에서 불리한 점이 많다. 과거의 샤딩은 애플리케이션 서버 레벨에서 구현하는 경우가 많았는데 최근에는 이를 플랫폼 차원에서 제공하려는 시도가 많다. 그중 미들티어에 샤딩 플랫폼을 둔 Gizzard, Spider, Spock Proxy에 대해 알아본다.


1) Gizzard


+ 개요
트위터(Twitter)에서 자체 개발한 데이터를 분산 환경에 쉽게 구성?관리하고, 장애 발생에 유연하게 대처할 수 있는 오픈소스이면서 미들웨어다. Gizzard 의 핵심이 되는 것은 샤딩(Sharding)이라는 기술이다. 트위터에 따르면, 샤딩은 파티션과 복제라는 두 기술로 구성됐다. 파티션은 하나의 데이터베이스를 해시 등을 사용해 여러 부분으로 나눔으로써 여러 데이터베이스에 분산하는 것을 말하고, 복제는 한 데이터 복제를 다른 서버에 만드는 것이다. 데이터를 복제해 전체 탄력성이 증가함과 동시에 대량의 액세스에 대해 복수의 서버가 동시에 응답할 수 있기 때문에 성능 향상을 기대할 수 있다. 

+ 아키텍처



 
그림 9 Replication

Gizzard는 데이터 저장소와 클라이언트 애플리케이션 사이에 위치해 모든 질의는 Gizzard를 통해 이뤄지고 있어 Gizzard가 분할?복제 키를 쥐고 있다.

 
그림 10 Gizzard Partition

① Gizzard 는 데이터 매핑 선행 테이블에서 데이터 조각을 관리한다. 키에 해당하는 값이 어디에 저장됐는지 샤드 정보를 갖고 있다. 특정 데이터에 관한 키 값을 해시 함수로 돌리고 결과값을 Gizzard에 전달하면, Gizzard는 해당 데이터가 어떤 구역에 속할지 숫자 정보를 생성한다. 이러한 함수는 프로그래밍 가능하기 때문에 사용자 성향에 맞춰 지역성 혹은 균형성 면에서 최적화할 수 있다.



 
그림 11 Gizzard Replication

② Gizzard는 'Replication Tree'로 복제 데이터를 관리한다. 매핑 테이블이 지칭하는 각 데이터 조각들은 물리적 또는 논리적인 형태로 구현될 수 있다. 즉, 물리적인 형태는 특정 데이터 저장소를 의미하고, 논리적인 형태는 데이터 조각에 관한 트리를 의미한다. 트리 안의 각 브랜치들은 데이터의 논리적인 변형을 나타내고, 각 노드들은 데이터 저장소를 의미한다.

③ Gizzard는 장애 상황에도 강한 시스템이다. 특정 파티션 내에 있는 복제 데이터가 유실됐을 지라도, Gizzard는 남은 다른 정상적인 복제 데이터 시스템에 읽기/쓰기를 전환 요청한다. 대응 시나리오는 데이터 조각 안의 특정 복제 데이터 불능이 발생하면 Gizzard는 최대한 빠르게 다른 정상적인 복제 데이터에 읽기/쓰기 작업을 시도해서 정상적인 응답을 주고, Gizzard 내부에서도 문제가 발생했던 복제 데이터가 정상으로 돌아오면, 변경 이력을 다시 적용해 동기화한다.



 
그림 12 Gizzard Migrations

④ Gizzard는 데이터 이전 방안을 제시할 수 있다. 데이터 노드가 A에서 B로 이전한다고 가정할 때 Replicate 샤드가 A와 B 사이에 위치하고 Writeonly는 B 앞에 위치해서 A의 데이터를 B로 복제하게 된다. Writeonly 샤드는 B가 사용 가능한 시점까지 유지되다가 B가 사용 가능한 시점이 되면 WriteOnly는 빠지고 Replicate가 동시에 A와 B에 데이터를 복제하며 동기화해 준다.

 + 고려사항 Gizzard는 동일 데이터를 동시에 변경하려면 데이터 충돌(Confliction)이 발생한다. 그래서 Gizzard는 데이터가 적용 순서를 보장하지 않기 때문에 모델링 시 반드시 이러한 점을 염두에 둬야 한다.



2) SPIDER for MySQL

+ 개요
SPIDER는 Kentoku SHIBA가 개발한 스토리지 엔진이다. MySQL의 파티셔닝 기능을 사용해 파티션마다 다른 서버로 데이터를 저장할 수 있게 한 구조이다. Sharding 기능이 가능한 스토리지 엔진이라고 할 수 있다. 물론 데이터가 저장된 서버가 다른 경우에도 조인할 수 있는 장점이 있다. 이러한 구조를 구현할 수 있었던 배경은 MySQL의 유연한 스토리지 엔진구조가 있었기 때문이다. 

+ 아키텍처

 
그림 13 Spider for MySQL

Spider 는 위 그림처럼 테이블 링크를 통해 로컬의 MySQL 서버처럼 활용할 수 있는 구조이다. 내부적으로는 클러스터의 약점인 애플리케이션에서 구현하던 분산 환경에서의 조인과 트렌잭션 문제를 Spider가 해결해 준다. 더불어 Spider는 XA 트렌잭션과 테이블 파티셔닝을 지원한다. GPL 라이선스 정책을 갖고 있다. 여기에 병BR>+ 고려사항
① SPIDER 테이블을 드롭해도 데이터 노드의 데이터는 사라지지 않는다. SPIDER은 FEDERATED 스토리지 엔진과 마찬가지를 생성하는 스토리지 엔진으로 테이블 DROP 때는 링크만 제거된다. 더불어 TRUNCATE 명령문은 원격 MySQL Server의 데이터를 모두 클리어해 버리므로 주의하자.
② MySQL Cluster처럼 Spider도 파티션을 전제로 한 스토리지 엔진이기 때문에 Distribution Awareness를 고려한 설계를 해줘야 한다.
③ 전체 텍스트 검색과 R-Tree 인덱스를 지원하지 못한다.



3) Spock Proxy

+ 개요
Spock Proxy는 MySQL Proxy를 바탕으로 제작된 샤딩 플랫폼이다. 데이터베이스들을 수평적 분할해 여러 샤드(shard)로 나눠줘 응용 프로그램들이 직면한 중요한 문제들을 해결해 줬고, 이로써 데이터베이스는 성능과 확장성을 쉽게 높일 수 있다. 주요 역할은 Proxy가 클라이언트로부터 전송되는 쿼리를 가로채 데이터가 분할된 기법에 따라 적절한 MySQL 서버에 쿼리를 전송한다. 이후 각 MySQL 서버로부터의 응답을 모아 일반 MySQL 결과인 것처럼 클라이언트로 다시 전송한다.

+ 아키텍처


 
그림 14 Spock Proxy

Spock proxy는 MySQL DB의 Table(universal_db)에 샤딩 규칙을 저장한다. 그래서 애플리케이션 서버로부터 전달받은 SQL을 파싱해, 이 SQL에 shard key가 있는지 파악한다. 만약 shard key가 있다면 universal_db에 기록된 기준에 따라 MySQL 인스턴스를 찾아 SQL을 전달한다. 이런 방식을 사용할 경우 SQL에 shard key와 관련한 정보를 기술할 필요가 없는 장점으로 인해 기존 애플리케이션을 그대로 이용할 수 있다. 

+ MySQL Proxy와 다른 점
Spock Proxy는 MySQL Proxy에서 갈라진 것이다. 코드의 많은 부분이 변경되지 않았지만 기반 아키텍처가 다르다.

① MySQL Proxy는 최적화를 위해 Lua 스크립트 언어를 지원하지만, Spock Proxy는 그렇지 않다. 성능상의 이유로 C/C++를 활용했다.
② MySQL Proxy는 각 클라이언트가 개별 데이터베이스에 직접 인증하는 것을 허용한다. 이는 클라이언트가 proxy 작업에 앞서 최소 연결을 해야 하기 때문에 문제가 있는 방법이다. Spock Proxy는 클라이언트로부터 독립된 서버 연결을 하도록 설계됐다.
③ Spock Proxy는 클라이언트와 서버 연결을 분리해, 관리할 최소/최대 연결 크기를 허용한다. 시작 시에 proxy는 최소 연결 개 수만큼을 미리 연결해 놓는다.
④ 다중 서버 Send/Recv가 가능하다. 그래서 다수의 서버에 요청을 보내고, 이 결과들을 합치는 것 또한 가능하다. 

+ 고려사항
Spock Proxy의 제약사항을 보면 쉽게 구현 단계에서 고려 사항들이 도출될 것이다 
① 데이터베이스들간의 조인이 불가능하다.
② 저장 프로시저와 트랜잭션 지원은 제한적이다.
③ 중첩 질의는 불가능하다.
④ SELECT에서 2개 테이블의 JOIN은 지원하지만, GROUP BY는 지원하지 않는다.
⑤ INSERT에서 칼럼명은 항상 표현돼야 한다.
⑥ MySQL 함수는 데이터들이 여러 파티션에 걸쳐 있는 경우 MAX, MIN, SUM, AVERAGE만 지원한다.
⑦ Spock Proxy는 read only (slave)와 read/write (master)를 구분하지 못한다.
⑧ auto_increment 값이 다르다.



5. 결론

MySQL은 다양한 방식의 스케일아웃을 지원하는 솔루션들이 있고, 지속적으로 개발?보완되고 있다. 중요한 건 우리가 용도에 적합한 솔루션들을 선택할 수 있는 혜안을 갖고 판단할 필요가 있다는 것이다. 비즈니스에 어느 정도 제약성도 있다는 점을 기획자들이 인지할 수 있게 지속적으로 커뮤니케이션 하는 활동도 필요하다. 거기에 DBA나 프로그래머들은 제약 사항 및 고려 사항들을 숙지하고 있어야 하며, 운용하면서 발생될 수 있는 문제점을 애플리케이션이든, 자체 미들웨어를 갖추든 보완하는 자세도 필요해 보인다. 트위터나 페이스북 등에서 행해지는 MySQL을 보완해 주는 미들웨어들을 유심히 살펴본다면 힌트를 얻을 수 있을 것이다.





출처 : 한국데이터베이스진흥원

제공 : DB포탈사이트 DBguide.net


'DB > MySQL' 카테고리의 다른 글

MySQL Cluster  (0) 2016.08.04
MySQL root 패스워드 분실  (0) 2015.05.21
MSSQL 문자열 구분자 분리 (테이블 반환 함수)  (0) 2012.12.11
MSSQL PROC ARRAY  (0) 2012.12.11
MySQL 프로세스 리스트 보기  (0) 2011.04.22
:

MySQL root 패스워드 분실

DB/MySQL 2015. 5. 21. 17:04

mysqld 중지

[root@localhost ~]# service mysqld stop
Stopping MySQL:                                            [  OK  ]

mysqld_safe 실행

[root@localhost ~]# /usr/bin/mysqld_safe --skip-grant &
[1] 32055
Starting mysqld daemon with databases from /var/lib/mysql

→ 이제 패스워드 없이 mysql에 접속할 수 있게 되었다.[1]

새 패스워드 지정

mysql 콘솔로 들어가자.[2]

/usr/bin/mysql -uroot mysql

다음 SQL 명령어를 입력하여 원하는 패스워드로 변경한다.

update user set password=password('패스워드') where user='root'; 
flush privileges; 
quit
실행 예시
[root@localhost ~]# /usr/bin/mysql -uroot mysql
Reading table information for completion of table and column names
You can turn off this feature to get a quicker startup with -A
 
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 1
Server version: 5.0.77 Source distribution
 
Type 'help;' or '\h' for help. Type '\c' to clear the buffer.
 
mysql> update user set password=password('P@ssw0rd') where user='root';
Query OK, 3 rows affected (0.00 sec)
Rows matched: 3  Changed: 3  Warnings: 0
 
mysql> flush privileges;
Query OK, 0 rows affected (0.00 sec)
 
mysql> quit
Bye

mysqld 재시작

이제 패스워드를 입력해야만 mysql을 사용할 수 있도록 하기 위해, mysqld를 재시작한다.

[root@localhost ~]# service mysqld restart
STOPPING server from pid file /var/run/mysqld/mysqld.pid
120229 13:08:54  mysqld ended
 
Stopping MySQL:                                            [  OK  ]
Starting MySQL:                                            [  OK  ]
[1]+  Done                    /usr/bin/mysqld_safe --skip-grant
→ 백그라운드로 실행 중이던 무인증 안전모드 mysqld 프로세스가 중지되고 정상모드 mysqld로 재시작되었다.

같이 보기

주석

  1. 이동 로컬에서는 인증 없이 mysql의 root 권한을 사용가능하게 됨
  2. 이동 ERROR 1049 (42000): Unknown database 'mysql' 라고 나오면서 안들어 가지는 경우가 있을 수 있는데, mysql 설치 이후 한번도 root 패스워드를 지정하지 않은 상태이다. 이 때는 본 문서를 따르지 말고 service mysqld restart한다. 그러면 mysqladmin을 통한 패스워드 설정 방법이 나올 것이다.

참고 자료



출처 - http://zetawiki.com/wiki/MySQL_root_%ED%8C%A8%EC%8A%A4%EC%9B%8C%EB%93%9C_%EB%B6%84%EC%8B%A4#mysqld_.EC.A4.91.EC.A7.80

'DB > MySQL' 카테고리의 다른 글

MySQL Cluster  (0) 2016.08.04
스케일 아웃 측면에서 살펴본 MySQL의 특성  (0) 2016.08.04
MSSQL 문자열 구분자 분리 (테이블 반환 함수)  (0) 2012.12.11
MSSQL PROC ARRAY  (0) 2012.12.11
MySQL 프로세스 리스트 보기  (0) 2011.04.22
:

MSSQL 문자열 구분자 분리 (테이블 반환 함수)

DB/MySQL 2012. 12. 11. 18:02


ALTER FUNCTION [dbo].[fn_Split]
(
    @pSource    VARCHAR(MAX),
    @pSeparator VARCHAR(1)
)
RETURNS @TAB_RETURN TABLE
(
    ItemIndex   INT,
    ItemValue   VARCHAR(1000)
)
AS
BEGIN
    DECLARE @buffer VARCHAR(MAX);
    DECLARE @item   VARCHAR(MAX);
     
    DECLARE @tmp   INT;
    DECLARE @index INT;
    SET @index = 1;
   
    WHILE LEN(@pSource) > 0
    BEGIN
        SET @tmp = CHARINDEX(@pSeparator, @pSource);
         
        IF @tmp > 0
        BEGIN
            SET @item    = SUBSTRING(@pSource, 1, @tmp - 1);
            SET @pSource = RIGHT(@pSource, LEN(@pSource) - @tmp);
            INSERT INTO @TAB_RETURN VALUES(@index, @item);
             
            SET @index = @index + 1;
        END ELSE
        BEGIN
            INSERT INTO @TAB_RETURN VALUES(@index, @pSource);
             
            BREAK;
        END;
    END;
      
    RETURN
END

출처 - http://marsland.tistory.com/236

'DB > MySQL' 카테고리의 다른 글

스케일 아웃 측면에서 살펴본 MySQL의 특성  (0) 2016.08.04
MySQL root 패스워드 분실  (0) 2015.05.21
MSSQL PROC ARRAY  (0) 2012.12.11
MySQL 프로세스 리스트 보기  (0) 2011.04.22
mysql_insert_id  (0) 2010.10.27
:

MSSQL PROC ARRAY

DB/MySQL 2012. 12. 11. 18:01

MSSQL 에서는 배열을 처리할 수 없습니다.
따라서 다음과 같은 방식으로 우회하여 처리하는 방법이 있습니다.
client 에서 comma 로 구분된 자료를 Stored Procedure 로 보내면
이 SP 에서는 콤마로 구분된 자료들을 하나씩 분리하여 원하는
기능에 넣어 사용하게 되는 방법입니다.  참조되시길...


CREATE PROCEDURE pro_array @DATA VARCHAR(1000)
AS
BEGIN

  /*

   - 최대 1000 자리수의 값을 받습니다. 이 길이는 조정 가능
   - 콤마로 구분된 PK항목값 들을 UPDATE 구분에서 활용하는 예제입니다.
  */

WHILE CHARINDEX(',',@DATA)<>0
  BEGIN
        
    UPDATE 테이블명 SET 항목명 = '선택' WHERE PK항목명 = SUBSTRING(@DATA,1,CHARINDEX(',',@DATA)-1)

        SET @DATA=SUBSTRING(@DATA,CHARINDEX(',',@DATA)+1,LEN(@DATA))                

        IF CHARINDEX(',',@DATA)=0
           BEGIN
                   UPDATE 테이블명 SET 항목명 = '선택' WHERE PK항목명 = SUBSTRING(@DATA,1,LEN(@DATA))
           END
  
  END
  
END


--> 사용법 :  EXEC pro_array  '1001,1004,1102,1999,9999'


출처 - http://blog.naver.com/PostView.nhn?blogId=idtong&logNo=130071540216&redirect=Dlog&widgetTypeCall=true

:

MySQL 프로세스 리스트 보기

DB/MySQL 2011. 4. 22. 10:51

[출처] http://breakpoint.tistory.com/127

 

MySQL 프로세스 리스트 보기에는 다음의 두가지 방법을 사용

[aokio]$ mysqladmin processlist


mysql> show processlist;
+---------+------+-----------+-------+---------+------+-------+------------------+
| Id      | User | Host      | db    | Command | Time | State | Info             |
+---------+------+-----------+-------+---------+------+-------+------------------+
| 1602724 | root | localhost | test  | Sleep   | 70   |       | NULL             |
| 1603286 | root | localhost | NULL  | Query   | 0    | NULL  | show processlist |
+---------+------+-----------+-------+---------+------+-------+------------------+
2 rows in set (0.00 sec)

프로세스 죽이기.
해당 아이디 번호를 가지고 킬하면 프로세스를 종료시킬 수 있다.

mysql> kill 1602724;
Query OK, 0 rows affected (0.00 sec)


mysql> show processlist;
+---------+------+-----------+-------+---------+------+-------+------------------+
| Id      | User | Host      | db    | Command | Time | State | Info             |
+---------+------+-----------+-------+---------+------+-------+------------------+
| 1603286 | root | localhost | NULL  | Query   | 0    | NULL  | show processlist |
+---------+------+-----------+-------+---------+------+-------+------------------+
2 rows in set (0.00 sec)

Id    : 프로세스 아이디 MySQL 이 관리하는 스레드 번호。
User  : 스레드에 접속하고 있는 MySQL 유저명
Host  : 유저가 접속하고 있는 호스트명 , IP 어드레스
Command : 스레드의 현재 커맨드 상태 . 
Time  : 프로세스가 현재 커맨드상태에서 동작 시간
State : 스레드의 상태에 대해 사람이 읽을 수 있는 형태의 정보
Info  : 현 실행되고 있는 SQL .
        "SHOW PROCESSLIST" 최대 100자까지 표시
        전부 표시하려면 "SHOW FULL PROCESSLIST"
:

mysql_insert_id

DB/MySQL 2010. 10. 27. 11:20

mysql_insert_id

(PHP 3, PHP 4, PHP 5)

mysql_insert_id -- 이전의 INSERT 작업으로부터 생성된 ID를 반환

설명

int mysql_insert_id ( [resource link_identifier] )

이전의 INSERT 질의로부터 AUTO_INCREMENT 컬럼에 의해 생성된 ID를 반환한다.

인수 목록

link_identifier

The MySQL connection. If the link identifier is not specified, the last link opened by mysql_connect() is assumed. If no such link is found, it will try to create one as if mysql_connect() was called with no arguments. If by chance no connection is found or established, an E_WARNING level warning is generated.

반환값

성공하면 이전의 INSERT 질의에 의한 AUTO_INCREMENT 컬럼으로부터 생성된 ID를, 이전 질의로부터 AUTO_INCREMENT 값이 생성되지 않았다면, 0을, MySQL 접속이 되지 않은 상태였다면 FALSE를 반환한다.

예제

예 1. mysql_insert_id() 예제

<?php
$link = mysql_connect('localhost', 'mysql_user', 'mysql_password');
if (!$link) {
die('Could not connect: ' . mysql_error());
}
mysql_select_db('mydb');

mysql_query("INSERT INTO mytable (product) values ('kossu')");
printf("Last inserted record has id %d\n", mysql_insert_id());
?>

Notes

경고

mysql_insert_id()는 원시(native) MySQL C API 함수인 mysql_insert_id()long형태의 반환값을 PHP의 int로 변환한다. AUTO_INCREMENT 컬럼이 BIGINT이면, mysql_insert_id()에 의해 반환되는 값은 잘못될 것이다. 이경우, MySQL SQL 내부 함수인 LAST_INSERT_ID()를 사용하면 된다.

참고: mysql_insert_id()는 최근 수행한 질의에 대해서 동작하기 때문에, 생성된 값은 질의 직후에 mysql_insert_id()를 호출해야 된다.

참고: MySQL SQL 함수인 LAST_INSERT_ID()는 가장 최근에 생성된 AUTO_INCREMENT 값을 담고 있으며, 질의 간에 지워지지는 않는다. 

[출처] mysql_insert_id|작성자 kdepirate

'DB > MySQL' 카테고리의 다른 글

MSSQL PROC ARRAY  (0) 2012.12.11
MySQL 프로세스 리스트 보기  (0) 2011.04.22
문자 함수(RIGHT, LEFT, SUBSTRING_INDEX, SUBSTRING, UPPER, REVERSE, LTRIM, LENGTH)  (0) 2010.10.27
MySQL 날짜 관련 함수  (0) 2010.09.06
LIKE, BETWEEN, IN  (0) 2010.07.08
:

문자 함수(RIGHT, LEFT, SUBSTRING_INDEX, SUBSTRING, UPPER, REVERSE, LTRIM, LENGTH)

DB/MySQL 2010. 10. 27. 10:43

문자를 다룰 수 있는 함수 들 몇개를 소개한다. 출처는  헤드퍼스트 sql 고대로 퍼 담는거다.. ㅎㅎ;;

먼저 문자열 타입으로는 VARCHAR, CHAR 가 있다. 이 타입으로 정해진 컬럼에 관련하여 사용하는 함수들이다..

 

정해진 수의 문자 추출 함수 -  RIGHT(), LEFT()

사용법 : RIGHT()

SELECT RIGHT(location, 2) FROM my_contacts;

SELECT LEFT(location, 2) FROM my_contacts;

 

해석 : my_contacts 라는 테이블의  location의 열에 있는 문자열 에서 오른쪽에서부터 2개의 문자 선택을 의미, LEFT() 함수 일 경우 왼쪽에서 부터 2개의 문자 선택을 의미

특정 문자나 문자열 앞의 모든 문자열을 반환 - SUBSTRING_INDEX()

사용법 :

SELECT SUBSTRING_INDEX(location, ',', 1) FROM my_contacts;

 

해석 : my_contacts테이블의 location 열의 문자열 에서 작은 따옴표 안의 문자열을 찾고( 이경우에는 콤마다.) 그 앞의 모든 문자열을 찾는다. 마지막 인자의 숫자 1은 첫번째 콤마를 찾고 그 앞의 모든 것을 반환하라는 뜻이다.

 

SUBSTRING(your_starting, start_position, length)는 start_position에 있는 문자에서부터 시작해서 your_starting의 일부를 반환한다. length는 반환되는 문자열의 길이

사용법 :

SELECT SUBSTRING('San Antonio, TX', 5, 3);

 

UPPER(your_starting)과 LOWER(your_starting)은 문자열 모두를 대문자 혹은 소문자로 각각 변환 한다.

사용법:

SELECT UPPER('Usa');

SELECT LOWER('spaGHEtti');

REVERSE(your_string)은 말 그대로 문자열의 순서를 역순을 만든다.

 사용법:

SELECT REVERSE('spaGHEtti');

 

LTRIM(your_starting)과 RTRIM(your_starting)은 문자열의 앞(왼쪽 부분) 또는 뒤(오른쪽 부분)에 있는 공백 문자들을 제거한 문자열을 반환한다.

사용법:

SELECT LTRIM('  dogfood  ');

SELECT RTRIM('  catfood  ');

LENGTH(your_starting)은 문자열의 문자수를 반환한다.

사용법:

SELECT LENGTH('San Antonio, TX ');

※ 문자 함수는 테이블에 저장되어 있는 데이터를 바꾸지 않는다. 쿼리의 결과로 변경된 문자열을 반환할 뿐이다

'DB > MySQL' 카테고리의 다른 글

MySQL 프로세스 리스트 보기  (0) 2011.04.22
mysql_insert_id  (0) 2010.10.27
MySQL 날짜 관련 함수  (0) 2010.09.06
LIKE, BETWEEN, IN  (0) 2010.07.08
[MySql] JOIN 문  (0) 2010.07.02
:

MySQL 날짜 관련 함수

DB/MySQL 2010. 9. 6. 20:08

MySQL 날짜 관련 함수

- DAYOFWEEK(date) : 해당 날짜의 요일을 숫자로 반환한다. 일요일은 1, 토요일은 7 이다.
- 예 : select DAYOFWEEK('1998-02-03');



- WEEKDAY(date) : 해당 날짜에 대한 요일을 반환한다. 월요일은 0, 일요일은 6 이다.
- 예 : select WEEKDAY('1997-10-04 22:23:00');



- DAYOFYEAR(date) : 해당 날짜의 1월 1일부터의 날수를 반환한다. 결과값은 1에서 366 까지이다.
- 예 : select DAYOFYEAR('1998-02-03');



- YEAR(date) : 해당 날짜의 년을 반환한다.
- 예 : select YEAR('98-02-03');



- MONTH(date) : 해당 날짜의 월을 반환한다.
- 예 : select MONTH('1998-02-03');



- DAYOFMONTH(date) : 해당 날짜의 일을 반환한다. 결과값은 1 에서 31 까지이다.
- 예 : select DAYOFMONTH('1998-02-03');



- HOUR(time) : 해당날짜의 시간을 반환한다. 결과값은 0 에서 23 이다.
- 예 : select HOUR('10:05:03');



- MINUTE(time) : 해당날짜의 분을 반환한다. 결과값은 0 에서 59 이다.
- 예 : select MINUTE('98-02-03 10:05:03');



- SECOND(time) : 해당날짜의 초를 반환한다. 결과값은 0 에서 59 이다.
- 예 : select SECOND('10:05:03');



- DAYNAME(date) : 해당 날짜의 요일 이름을 반환한다. 일요일은 'Sunday' 이다.
- 예 : select DAYNAME("1998-02-05");



- MONTHNAME(date) : 해당 날짜의 월 이름을 반환한다. 2월은 'February' 이다.
- 예 : select MONTHNAME("1998-02-05");



- QUARTER(date) : 해당 날짜의 분기를 반환한다. 결과값은 1 에서 4 이다.



- WEEK(date,first) : 1월 1일부터 해당날가지의 주 수를 반환한다. 주의 시작을 일요일부터 할경우는 두번째 인자를 0, 월요일부터 시작할 경우는 1 을 넣는다. 결과값은 1 에서 52 이다.
- 예 : select WEEK('1998-02-20',1);



- PERIOD_ADD(P,N) : P (형식은 YYMM 또는 YYYYMM 이어야 한다.) 에 N 만큼의 달 수를 더한값을 반환한다. 주의할것은 두번째 인자는 숫자라는 것이다.
- 예 : select PERIOD_ADD(9801,2);



- PERIOD_DIFF(P1,P2) : 두개의 인자 사이의 달 수를 반환한다. 두개의 인자 모두 형식은 YYMM 또는 YYYYMM 이어야 한다.



- DATE_ADD(date,INTERVAL expr type) : 날짜를 더한 날짜를 반환한다.
- DATE_SUB(date,INTERVAL expr type) : 날짜를 뺀 날짜를 반환한다.
- ADDDATE(date,INTERVAL expr type) : DATE_ADD(date,INTERVAL expr type) 와 동일하다.
- SUBDATE(date,INTERVAL expr type) : DATE_SUB(date,INTERVAL expr type) 와 동일하다.
- EXTRACT(type FROM date) : 날짜에서 해당 부분을 추출한다.
- 예 : SELECT DATE_ADD("1997-12-31 23:59:59", INTERVAL 1 SECOND);
SELECT DATE_ADD("1997-12-31 23:59:59", INTERVAL 1 DAY);
SELECT DATE_ADD("1997-12-31 23:59:59", INTERVAL "1:1" MINUTE_SECOND);
SELECT DATE_SUB("1998-01-01 00:00:00", INTERVAL "1 1:1:1" DAY_SECOND);
SELECT DATE_ADD("1998-01-01 00:00:00", INTERVAL "-1 10" DAY_HOUR);
SELECT DATE_SUB("1998-01-02", INTERVAL 31 DAY);
SELECT EXTRACT(YEAR FROM "1999-07-02");
SELECT EXTRACT(YEAR_MONTH FROM "1999-07-02 01:02:03");
SELECT EXTRACT(DAY_MINUTE FROM "1999-07-02 01:02:03");
- 참고 : type 에 사용되는 키워드는 SECOND, MINUTE, HOUR, DAY, MONTH, YEAR, MINUTE_SECOND, HOUR_MINUTE, DAY_HOUR, YEAR_MONTH, HOUR_SECOND, DAY_MINUTE, DAY_SECOND 이다.
- 주의 : 계산한 달의 날수가 작을 경우는 해당달의 마지막 날을 반환한다. 예를 들어 select DATE_ADD('1998-01-30', Interval 1 month); 의 경우 1998-02-28 을 반환한다.



- TO_DAYS(date) : 0 년 부터의 날짜수를 반환한다. 이 함수는 1582 이전 날에 대해서는 계산하지 않는다.
- 예 : select TO_DAYS(950501);



- FROM_DAYS(N) : 해당 숫자만큼의 날짜를 반환한다. 이 함수는 1582 이전 날에 대해서는 계산하지 않는다.
- 예 : select FROM_DAYS(729669);



- DATE_FORMAT(date,format) : 날짜를 해당 형식의 문자열로 변환하여 반환한다.
- 예 : select DATE_FORMAT('1997-10-04 22:23:00', '%W %M %Y');
select DATE_FORMAT('1997-10-04 22:23:00', '%H:%i:%s');
select DATE_FORMAT('1997-10-04 22:23:00', '%D %y %a %d %m %b %j');
select DATE_FORMAT('1997-10-04 22:23:00', '%H %k %I %r %T %S %w');
- 참고 : 형식은 다음과 같다. %M (달 이름), %W (요일 이름), %Y (YYYY 형식의 년도), %y (YY 형식의 년도), %a (요일 이름의 약자), %d (DD 형식의 날짜), %e (D 형식의 날짜), %m (MM 형식의 날짜), %c (M 형식의 날짜), %H (HH 형식의 시간, 24시간 형식), %k (H 형식의 시간, 24시간 형식), %h (HH 형식의 시간, 12시간 형식), %i (MM 형식의 분), %p (AM 또는 PM)



- TIME_FORMAT(time,format) : DATE_FORMAT(date,format) 과 같은 방식으로 사용할수 있으나 날 이상의 것에 대해서는 NULL 이나 0 을 반환한다.



- CURDATE() : 현재날짜를 반환한다. 숫자와 연산을 할경우 숫자로 변환된다. 형식은 'YYYY-MM-DD' 또는 YYYYMMDD 이다.
- 예 : select CURDATE();
select CURDATE() + 0;



- CURTIME() : 현재시간을 반환한다. 숫자와 연산을 할경우 숫자로 변환된다. 형식은 'HH:MM:SS' 또는 HHMMSS 이다.
- 예 : select CURTIME();
select CURTIME() + 0;



- SYSDATE() : 현재날짜시간을 반환한다. 숫자와 연산을 할경우 숫자로 변환된다. 형식은 'YYYY-MM-DD HH:MM:SS' 또는 YYYYMMDDHHMMSS 이다.
- 예 : select NOW();
select NOW() + 0;



- NOW() : SYSDATE() 와 동일하다.



- UNIX_TIMESTAMP() : '1970-01-01 00:00:00' 부터의 초를 반환한다. 인자가 주어질 경우는 해당 날짜에 대한 유닉스 시간을 반환한다.
- 예 : select UNIX_TIMESTAMP();
select UNIX_TIMESTAMP('1997-10-04 22:23:00');



- FROM_UNIXTIME(unix_timestamp) : 유닉스시간에서 날짜 형식으로 변환한다.
- 예 : select FROM_UNIXTIME(875996580);



- FROM_UNIXTIME(unix_timestamp,format) : 유닉스시간을 날짜형식으로 변환하고 DATE_FORMAT(date,format) 에서 설명한 포맷으로 변환하여 반환한다.
- 예 : select FROM_UNIXTIME(UNIX_TIMESTAMP(), '%Y %D %M %h:%i:%s %x');



- TIME_TO_SEC(time) : 해당 시간의 0:0:0 에서부터의 초를 반환한다.
- 예 : select TIME_TO_SEC('22:23:00');



- SEC_TO_TIME(seconds) : 초를 시간으로 바꾼다.
- 예 : select SEC_TO_TIME(2378);


-출처 : http://www.happycgi.com/

'DB > MySQL' 카테고리의 다른 글

mysql_insert_id  (0) 2010.10.27
문자 함수(RIGHT, LEFT, SUBSTRING_INDEX, SUBSTRING, UPPER, REVERSE, LTRIM, LENGTH)  (0) 2010.10.27
LIKE, BETWEEN, IN  (0) 2010.07.08
[MySql] JOIN 문  (0) 2010.07.02
GROUP BY  (0) 2010.06.29
:

LIKE, BETWEEN, IN

DB/MySQL 2010. 7. 8. 18:14

◘  SQL 입문(3) - 자료검색(2) : 특수 비교 연산자와 검색 결과의 정렬

 

 

▮ LIKE 연산자


 : table의 값과 일부만 일치되는 레코드를 검색하도록 하는 연산자

 

경%

 ‘경’으로 시작하는 모든 문자열. ‘경’ 한글자 포함.

 ex) 경제, 경영...

%과

 ‘과’로 끝나는 모든 문자열. ‘과’ 한글자 포함.

 ex) 화학과, 경제학과...

%김%

 ‘김’이라는 문자가 들어간 모든 문자열

 ex) 김씨, 돌김...

화_

 ‘화’로 끝나는 두글자 단어

 ex) 화학, 화약...

___화

 ‘화’로 끝나는 세글자 단어

 ex) 해당화, 무궁화

_동_

 ‘동’이 가운데 들어간 세글자 단어

 ex) 전동차, 원동기...

 

'_'은 한글이나 영문이나 모두 1글자를 나타낸다. (byte단위가 아님)

    - select sname, major from student where sname like '마%‘;

    => 성이 마씨인 학생의 이름과 전공을 출력

    - select sname, major from student where (sname like '허%‘) and avr <= 1.0;

    => 허씨 성을 가진 학생 중에 학점이 1.0 이하인 학생의 이름과 전공을 출력

 

 

▮ 이외 연산자 : between, in


 - between ~and : 특정 범위 내의 값을 찾고자 할 때

    ex) 학점이 2.0~3.0 사이의 학생을 출력 : select sname from where avr between 2.0 and 3.0;


 - in : 여러 식 중에 하나 이상 일치하는 것을 찾을 때

   ex) 화학,물리학과 학생의 이름 출력 : select sname from student where major in('화학‘,’생물‘);

 

※ 문자열 비교 연산자는 상당수가 Full table scan을 수행하기 때문에 DB가 클 경우 좋지 않다.

'DB > MySQL' 카테고리의 다른 글

문자 함수(RIGHT, LEFT, SUBSTRING_INDEX, SUBSTRING, UPPER, REVERSE, LTRIM, LENGTH)  (0) 2010.10.27
MySQL 날짜 관련 함수  (0) 2010.09.06
[MySql] JOIN 문  (0) 2010.07.02
GROUP BY  (0) 2010.06.29
group by, having, inner join  (0) 2010.06.28
: