사용자 관리
다른 사람들은 기억에만 속한 데이터의 일부를 조작 할 수 있도록 주로 권한을 제어 할 수
MySQL은 계정을 만들
계정은 세 가지 데이터를 포함
계정 이름
암호
IP 주소
IP는 주로 전용 기계에 등록 할 수있는 계정을 제한하는 데 사용됩니다
문법
create user 用户名@主机地址 identified by "密码"; # 注意:创建用户只能由root账户进行操作 # 删除用户 drop user 用户名@主机地址
권한 관리
테이블에 관련
- 사용자 및 사용자 관련 정보
- DB 사용자 데이터베이스 권한 정보
- 로 tables_priv 사용자 권한 테이블
- columns_priv 사용자의 권한 필드
문법
# 拥有所有权限
grant all on *.* to 用户名@主机地址 identified by "密码";
# 该语句会自动创建用户如果用户不存在
# 创建拥有某个库的所有权限
grant all on 库名.* to 用户名@主机地址 identified by "密码";
# 创建某个库下某个表的所有权限
grant all on 库名.表名 to 用户名@主机地址 identified by "密码";
# 创建某个库下某个表的某些字段权限
grant 事件(字段名),事件(字段名) on 库名.表名 to 用户名@主机地址 identified by "密码";
# 注意:事件包括update/select/delete....
# 收回权限
revoke all on *.* from 用户名@主机地址;
# 刷新权限
flush privileges;
# 将自己账户的权限给其他账户,自己的账户就得有授予权限的权限,可以通过with grant option进行
grant all on *.* to 用户名@主机地址 identified by "密码" with grant option;
# 注意:这种操作只能把自己拥有的权限给其他人
# 授予某个用户 可以在任何主机上登录
grant all on *.* to 用户名@"%" identified by "密码";
grant all on *.* to 用户名@localhost identified by "密码";
경우
grant select(name),update(name) on day42.table1 to rose3@localhost identified by "123";
pymysql
pymysql가 설립 우리가 연결을 캡슐화하는 데 도움 타사 사용자 인증이며, 실행하고 결과를 얻을 SQL
기본 사용
"""
1. 导入模块
2. 连接服务器
3. 用户认证
4. 发送指令
5. 提取结果
"""
import pymysql
# 连接服务器 获取连接对象(本质上就是封装号的socket)
conn = pymysql.connect(
host = "127.0.0.1", # 如果是本机 可以忽略
port = 3306, # 如果没改过 可以忽略
user = "root", # 必填
password = "123", # 必填
database = "test" # 必填
)
# 通过连接拿到游标,默认的游标返回的是元组类型,不方便使用,需要更换字典类型的游标
c = conn.cursor(pymysql.cursors.DictCursor)
# 执行sql语句
sql = "select * from table1"
res = c.execute(sql) # 返回的是查询结果的数量
# 提取结果,这边获取的结果是一个迭代器,不能往回找结果
c.fetchall() # 获取所有结果
# c.fetchmany(2) # 获取两条结果
# c.fetchone() # 获取一条结果
# 关闭连接
c.close()
conn.close()
# 如果想获取之前的结果,可以通过移动光标 scroll进行,mode指定为相对路径或者绝对路径
c.scroll(1,mode="absolute/relative")
SQL 인젝션 공격
공격 목적 기재된 SQL 문 SQL 문에 따라 데이터를 입력 할 때 사용자를 지칭하고, 원래의 실행에 일본어 문장에 삽입
예를 들어 : 로그인 기능은 사용자 이름과 암호를 입력해야합니다
다음과 같이 정상적인 로그인 기능 코드는 다음과 같습니다
try:
conn = pymysql.connect(host="127.0.0.1",port=3306,user="root",password="",db="day46",)
print("连接服务器成功!")
cursor = conn.cursor(pymysql.cursors.DictCursor)
user = input("username:")
password = input("password:")
count = cursor.execute("select *from user where name = '%s' and password = '%s'" % (user,password))
if count:
print("登录成功!")
else:
print("登录失败!")
except Exception as e:
print(type(e),e)
finally:
if cursor:cursor.close()
if conn: conn.close()
코드 주입 공격은 위험하다
尝试在用户名中输入以下内容,密码随意
23' — ass
或者连用户名都不用写
' or 1 = 1 -- asaa
해결 방법 :
클라이언트는 사전에 결정된 재에 대한 SQL Server를 보낸다
이러한 문제는 클라이언트를 시뮬레이션 할 수있는 프로그램이 서버에 직접 요청을 전송한다는 것입니다
서버 측에서 추가 처리를 위해 MySQL로는 SQL이며, 해당 코드가 실제로 pymysql 패키지 행해졌
만큼 우리가 자신의 SQL 문을 접합 할 수 있습니다 보장하지 않는 한, 스 플라이 싱 작업 매개 변수 pymysql합니다.
경우
import pymysql
conn = pymysql.connect(
host = "127.0.0.1", #如果是本机 可以忽略
port = 3306, # 如果没改过 可以忽略
user = "root", #必填
password = "111", #必填
database = "day42", #必填,
#autocommit=False # 开启自动提交 不常用....
)
c = conn.cursor(pymysql.cursors.DictCursor)
name = input("name:")
pwd = input("pwd:")
sql = "select *from user where name = %s"
if c.execute(sql,(name,)):
print("用户名已存在!")
else:
sql2 = "insert into user values(%s,%s)"
if c.execute(sql2,(name,pwd)):
print("注册成功!")
conn.commit() # 调用连接对象的提交函数
else:
print("注册失败!")
c.close()
conn.close()
참고 : pymysql, 장소에 제출 (커밋) 할 필요가 자동으로 열려있는 트랜잭션입니다 것입니다
색인
인덱스 키 데이터와의 관계를 상세 대응하는 위치 정보가 저장되는 특정 데이터 구조
왜 색인
인덱스 디렉토리는 쿼리 속도를 높일 수 있도록 쉽게 쿼리 범위가 좁혀 된 쿼리 할 수 있습니다, 책에 해당
그렇지 않으면 데이터, 시간이 많이 소요를 통과해야하는, 그래서의 인덱스를 추가하는 것은 매우 필요하다
인덱스의 본질은 가능한 한 검색 범위를 줄이는 것입니다
주 : 데이터베이스에 데이터를 삽입 인덱스를 재 구축으로 이어질 것입니다
인덱스의 영향
- 아니 인덱스가 속도를 할 수 있었다 말을, 당신은 인덱스의 적절한 사용을 쿼리해야
- 지수는 추가 데이터 공간을 필요
- 인덱스의 첨가 한 후, 추가 및 삭제 속도가 느린 이어질 것
그래서 모든 데이터는 인덱스를 추가 할 필요가
일반적으로, 더 만 쿼리, 덜 쓰고, 많은 양의 데이터는 인덱스 데이터 전에 추가해야합니다
디스크 IO
일반적인 기계적 하드 7200r / min으로, 그것은 적어도 하나의 데이터의 모습 9ms 특히 컴퓨터 기반 기준 산출 처리, 상기 프로세서는 초당 500,000,000 번 계산을 얻어이를 데이터 명확 판독 약 9ms 4,500,000 조작을 산출 할 수있다 는 CPU, 그것은 너무 느립니다
그래서 때마다 CPU가 다음 CPU를 찾는 위치, 실행하는 다른 프로그램에 데이터 스위치를 발견 할 것이다, 그래서 삭감 CPU 컷이 때문에 쿼리 속도를 높이기 위해, CPU의 효율성을 줄일 수 IO 작업을 줄이는 것입니다 횟수
인덱스 데이터 구조
데이터 구조는 B + 트리 인덱스 데이터 구조
B + 룩업 데이터 구조하여 검색된 데이터를 이송 할 필요가 없어, 이분법에 기초
왼쪽의 일치 원칙
상기 데이터 항목과 같은 화합물 B + 트리 데이터 구조 인 경우 (이름, 나이, 성별) (다중 열 접합 인덱스), B + 트리 탐색 트리는 장 (경우와 같이 왼쪽부터 순서에 따라 설정 될 때 차례로 동일한 이름과 나이 성별 비교가, 최종적으로 얻어진 데이터가 검색되면 (20), F)는 시간 데이터, B + 트리 이름 우선 비교 검색 할 수 있도록, 다음의 검색 방향을 결정하였으나 (20, F 이러한 모르는 시간, B + 트리 노드없이 이름) 데이터 어떤 조사의 다음 단계, 검색 트리 이름을 설정하는 시간이 제 1 비교 요소이기 때문에 첫 번째 경우 다음 가야할지하기 위해 이름에 따라 검색 할 수 있어야합니다 쿼리. 예를 들어, (장, F)는 데이터 B + 트리 이름 등의 검색 방향을 지정하는 데 사용할 수 있습니다 검색 할 수 있지만, 나이가 다음 필드의 부족, 그래서 이름 만은, 다음 일치 성 발견되는 데이터의 좌석과 동일 데이터 F는, 이는 매우 중요한 특성, 즉 인덱스의 가장 왼쪽의 정합 특성이다.
클러스터 된 인덱스
클러스터 된 인덱스는 기본 키가 지정되는 경우, 기본 키를 지정하지 않은 다음 검색 엔진이 자동으로 클러스터 된 인덱스로 비어 있지 않은 유일한 필드를 찾습니다, 또는하지 않을 경우 자동으로 가만히 있으면, 기본 키가 클러스터 된 인덱스가,이다, 모든 필드의 값을 포함 클러스터 된 인덱스로서 필드를 생성
- 모든 데이터를 저장하는 클러스터 된 인덱스
보조 인덱스
클러스터 된 인덱스 지수뿐만 아니라 보조 인덱스입니다
- 보조 인덱스는 현재 인덱스 일차 키 필드에 저장된
쿼리를 커버
쿼리를 커버하면 현재 인덱스 구조는 당신이 클러스터 된 인덱스 쿼리를 사용하는 경우, 쿼리가 포함되어야하며, 필요한 모든 데이터를 찾을 수있을 것입니다, 그리고 가장 빠른
위로 테이블 쿼리
위로 쿼리가 필요한 현재의 인덱스 데이터에없는 테이블에, 우리는 찾을 수있는 기본 키 인덱스에 의해 수집해야
클러스터 된 인덱스보다 느린
문법
# 创建索引
create index 索引的名字 on 表名(字段名);
# 联合索引
create index 索引的名字 on 表名(字段1,字段2);
# 删除索引
drop index 索引名称 on 表名
결론
인덱스 필드로 작은 공간을 사용하려고
너무 많은 필드가 서브 테이블 작동 될 수 있다면, 행에 너무 많은 데이터를 저장하지 마십시오
쿼리를 포함 사용해보십시오
필드가 너무 낮은 경우라면, 이해가되지 않습니다 색인, 즉 인덱스 필드로 구분 높은 수준이어야한다
퍼지 매칭, 시도하지 사설 퍼센트 기호
등호의 왼쪽에있는 작업을 수행하지 마십시오
그리고 문은 자동으로 필드는 제을 찾아 그것을 한 색인하고 문은 인덱스 적어도 필드를 포함해야합니다
속도를 높일 수 있도록하거나, 모든 필드가 인덱스되어 있는지 확인하는 것이 가장 좋습니다, 성명의 사용을 피하려고하는, 또는 우리가 사용하는 경우 문은, 모든 조건을 통과하기 때문에
공동 지수는 구별 왼쪽, 오른쪽에 가장 낮은 곳에서 높은 할 필요가
쿼리를 사용하는 경우뿐만 아니라, 가장 왼쪽 인덱스가 문에 나타납니다 보장하기 위해
참고 : 쿼리가 인덱스에 의해 가속 할 수없는 너무 큰 경우
요약 : 대신 가속화 할 수있을 것 인덱스를 추가하는, 또한 우리는 색인 색인의 질의 여부 합리적인 사용, 합리적인 고려할 필요가