MySQL80-新特性-说说InnoDB-Log-System的隐藏参数

InnoDB在设计lock-free的log system时,除了已有的参数外,还通过宏控制隐藏了一些参数,如果你使用源码编译时,打开cmake选项-DENABLE_EXPERIMENT_SYSVARS=1, 就可以看到这些参数了。本文主要简单的过一下这些隐藏的参数所代表的含义 A.innodb_log_write_eventsinnodb_log_flush_events两者的含义类似,表示用来唤醒等待log write/flush的event的个数,默认值都是2048比如你要等待的位置在lsnA,那么计算的slot为:slot = (lsnA - 1) /OS_FILE_LOG_BLOCK_SIZE & (innodb_log_write/flush_events - 1)这意味着:如果事务的commit log的end lsn落在相同block里,他们可能产生event的竞争当然如果不在同一个block的时候,如果调大参数,就可以减少竞争,但也会有无效的唤醒唤醒操作通常由后台线程log_write_notifier 或者log_flush_notifier异步来做,但如果推进的log write/flush还不足一个block的话,那就log_writter/flusher自己去唤醒了。 B.innodb_log_recent_written_size, 默认1MB表示recent_written这个link_buf的大小,其实控制了并发往log buffer中同时拷贝的事务日志量,向前由新的日志加入,后面由log writer通过写日志向前推进,如果写的慢的话,那这个link_buf很可能用满,用户线程就得spin等待。再慢io的系统上,我们可以稍微调大这个参数 innodb_Log_recent_closed_size, 默认2MB表示recent closed这个link_buf的大小,也是维护可以并发往flush list上插入脏页的并罚度,如果插入脏页速度慢,或者lin_buf没有及时合并推进,就会spin wait 简单说下link_buf, 这本质上是一个数组,但使用无锁的使用方式来维护lsn的推进,比如获得一个lsn开始和结束,那就通过设置buf[start_lsn] = end_lsn的类似方式来维护lsn链,基于lsn是连续值的事实,最终必然不会出现空洞,所以在演化的过程中,可以从尾部推进连续的lsn,头部插入新的值.如果新插入的值超过了尾部,表示buf满了,就需要spin wait了C.innodb_log_wait_for_write_spin_delay, innodb_log_wait_for_write_timeout 从8.0版本开始用户线程不再自己去写redo,而是等待后台线程去写,这两个变量控制了spin以及condition wait的timeout时间,当spin一段时间还没推进到某个想要的lsn点时,就会进入condition wait 另外两个变量innodb_log_wait_for_flush_spin_delayinnodb_log_wait_for_flush_timeout含义类似,但是是等待log flush到某个指定lsn 注意在实际计算过程中,最大spin次数,会考虑到cpu利用率,以及另外两个参数:innodb_log_spin_cpu_abs_lwminnodb_log_spin_cpu_pct_hwm 如果是等待flush操作的话,还收到参数innodb_log_wait_for_flush_spin_hwm限制,该参数控制了等待flush的时间上限,如果平均等待flush的时间超过了这个上限的话, 就没必要去spin,而是直接进入condition wait 关于spin次数的计算方式在函数log_max_spins_when_waiting_in_user_thread中": 函数的参数即为配置项innodb_log_wait_for_write_spin_delay或innodb_log_wait_for_flush_spin_delay值 static inline uint64_t log_max_spins_when_waiting_in_user_thread( uint64_t min_non_zero_value) { uint64_t max_spins; /* Get current cpu usage. */ const double cpu = srv_cpu_usage.utime_pct; /* Get high-watermark - when cpu usage is higher, don't spin! */ const uint32_t hwm = srv_log_spin_cpu_pct_hwm; if (srv_cpu_usage.utime_abs < srv_log_spin_cpu_abs_lwm || cpu >= hwm) { /* Don't spin because either cpu usage is too high or it's almost idle so no reason to bother. */ max_spins = 0; } else if (cpu >= hwm / 2) { /* When cpu usage is more than 50% of the hwm, use the minimum allowed number of spin rounds, not to increase cpu usage too much (risky). */ max_spins = min_non_zero_value; } else { /* When cpu usage is less than 50% of the hwm, choose maximum spin rounds in range [minimum, 10*minimum]. Smaller usage of cpu is, more spin rounds might be used. */ const double r = 1.0 * (hwm / 2 - cpu) / (hwm / 2); max_spins = static_cast<uint64_t>(min_non_zero_value + r * min_non_zero_value * 9); } return (max_spins);}D.以下几个参数是后台线程等待任务时spin及condition wait timeout的值log_writer线程:innodb_log_writer_spin_delay,innodb_log_writer_timeout ...

June 4, 2019 · 2 min · jiezi

sqlalchemy-配置多连接读写库后的关系设置

前言一般来说,解决sqlalchemy 连接多个库的最简单的方式是新建两个或多个db.session 相互没有关联,modle配置不同的db.session来连接,这样的话,relationship正常配置就行,不用特殊配置.如果这样解决的话,也就不用看下面的配置了 # -*- coding:utf-8 -*-import flaskfrom flask_sqlalchemy import SQLAlchemy # Flask-SQLAlchemy 2.3.2from datetime import datetimefrom sqlalchemy.orm import backref, foreign # SQLAlchemy 1.3.1app = flask.Flask(__name__)app.config['DEBUG'] = Trueapp.config['SQLALCHEMY_BINDS'] = { 'read_db': 'mysql://reader:test@127.0.0.1:3306/test?charset=utf8', 'write_db': 'mysql://writer:test@127.0.0.2:3306/test?charset=utf8'}app.config['SQLALCHEMY_TRACK_MODIFICATIONS'] = Falseapp.config['SQLALCHEMY_ECHO'] = Falsedb = SQLAlchemy(app)class RDriver(db.Model): __bind_key__ = 'read_db' __tablename__ = 'driver' # __table_args__ = {'schema': 'test'} # 不可以加上 id = db.Column(db.Integer, primary_key=True, autoincrement=True) fk_user_id = db.Column(db.Integer, db.ForeignKey("user.id")) driver_name = db.Column(db.String(7)) create_time = db.Column(db.TIMESTAMP, default=datetime.now)class RUser(db.Model): __bind_key__ = 'read_db' __tablename__ = 'user' # __table_args__ = {'schema': 'test'} id = db.Column(db.Integer, primary_key=True, autoincrement=True) user_name = db.Column(db.String(32), index=True, unique=True) user_password = db.Column(db.String(32)) create_time = db.Column(db.TIMESTAMP, default=datetime.now) update_time = db.Column(db.TIMESTAMP, default=datetime.now) # 如下的五种方式都是可以的 # driver_fk = db.relationship("RDriver", foreign_keys='RDriver.fk_user_id') # driver_fk = db.relationship("RDriver", primaryjoin=lambda: RDriver.fk_user_id == RUser.id, viewonly=True) # driver_fk = db.relationship("RDriver", primaryjoin=RDriver.fk_user_id == id) fk_driver = db.relationship("RDriver", primaryjoin='RDriver.fk_user_id == RUser.id') # driver_fk = db.relationship("RDriver", backref=db.backref('user', lazy=True), # primaryjoin=lambda: RDriver.fk_user_id == RUser.id, viewonly=True)class WDriver(db.Model): __bind_key__ = 'write_db' __tablename__ = 'driver' __table_args__ = {'schema': 'test', 'extend_existing': True} # 这个配置很关键 id = db.Column(db.Integer, primary_key=True, autoincrement=True) fk_user_id = db.Column(db.Integer, db.ForeignKey("test.user.id")) # test.user.id很关键 plate = db.Column(db.String(7)) create_at = db.Column(db.TIMESTAMP, default=datetime.now)class WUser(db.Model): __bind_key__ = 'write_db' __tablename__ = 'user' __table_args__ = {'schema': 'test', 'extend_existing': True} # 这个配置很关键 id = db.Column(db.Integer, primary_key=True, autoincrement=True) hash = db.Column(db.String(256), nullable=False) user_no = db.Column(db.String(32), index=True, unique=True) # 用户工号 create_time = db.Column(db.TIMESTAMP, default=datetime.now) update_time = db.Column(db.TIMESTAMP, default=datetime.now) # 以下五种方式都是可以的 # fk_driver = db.relationship("WDriver", foreign_keys='WDriver.fk_user_id', uselist=False) # fk_driver = db.relationship("WDriver", primaryjoin=lambda: WDriver.fk_user_id == WUser.id) fk_driver = db.relationship("WDriver", primaryjoin=WDriver.fk_user_id == id) # fk_driver = db.relationship("WDriver", primaryjoin='WDriver.fk_user_id == WUser.id') # fk_driver = db.relationship("WDriver", backref=db.backref('test.user', lazy=True), # primaryjoin=lambda: WDriver.fk_user_id == WUser.id)r_user_obj = RUser.query.filter_by().first()print("r_user_obj:", r_user_obj)print("r_user_obj.driver_fk:", r_user_obj.fk_driver)w_user_obj = WUser.query.filter_by(id=2188).first()print("w_user_obj:", w_user_obj)print("w_user_obj.driver_fk:", w_user_obj.fk_driver)参考文档:* https://docs.sqlalchemy.org/en/13/orm/relationship_api.html # 值得细看* https://www.osgeo.cn/sqlalchemy/orm/relationship_api.html # 同上,中文* https://www.cnblogs.com/srd945/p/9851227.html* extend_existing: (False)当表已经存在于元数据中时,如果元数据中存在与column_list中的列同名的列,column_list中同名的列会替换掉元数据中已经有的列* useexisting已被废弃, 新版本使用extend_existing总结关系配置参数真的很多,如下,很容易就会出错,需要多读读官方文档,还有就是建立modle时候尽量简洁,风格统一,不要在数据库层建立外键. ...

June 4, 2019 · 2 min · jiezi

学完这些课快速助你提升Level

本文为大家推荐一些博主已经学习过的付费课程。请放心,博主不会随便推荐课程给大家。下面这些课程质量非常高,学完你的Redis、MySQL等技能必定提升一个Level! Tips: 通过本文配图里的海报购买课程,相比直接去官网购买可以享受一定的优惠。Redis 深度历险:核心原理与应用实践大型互联网企业 Redis 实践总结,结合实际问题深入讲解 Redis 内部机制。小册在内容结构上分为 Redis 基础应用、原理、集群、拓展学习和源码分析 5 个版块: Redis 基础应用:占据篇幅最长,这也是对读者最有价值的内容,可以直接应用到实际工作中。原理和集群版块:适合对技术有着极致追求的开发者,他们希望透过简单的技术表面看到精致的底层世界。拓展学习版块:作为最核心内容之外的补充部分,主要用于进一步扩展技术视野或者夯实基础,便于进阶学习,作者会尽可能的在拓展篇持续扩充更多知识点。源码分析版块:主要满足高阶用户深入探索 Redis 内部实现的强烈渴望,这类读者坚信读懂源码才是技术实力的真正体现。 MySQL 是怎样运行的:从根儿上理解 MySQL授人以鱼不如授人以渔,从根儿上理解 MySQL,让 MySQL 不再是一个黑盒。你会学到什么? MySQL 的一些基本概念;如何处理使用 MySQL 过程中的乱码问题;从根儿上理解 InnoDB 存储引擎是如何存储记录、数据页,以及由页作为节点组成的B+树索引的原理;理解 InnoDB 存储引擎的表空间概念,知道 InnoDB 是如何管理段、区、页这些玩意儿以及 InnoDB 的数据字典;理解 MySQL 是如何执行单表查询、如何执行连接查询;理解 MySQL 基于代价的优化和基于规则的优化到底是啥意思;知道如何查看自己写的查询语句是好是坏,学会使用optimizer tracer;理解为什么需要事务以及它的基本概念;redo 和 undo 日志的作用以及在 MySQL 中这些日志的细节;理解并发带来的各种问题以及 MySQL 中使用锁的各种细节;理解学习的快乐,希望各位看完本小册就像是读完一本小说一样畅快淋漓。 OpenResty从入门到实战pphh 开源书籍《OpenResty 最佳实践》的作者之一,温铭大佬又推出了实战课《OpenResty 从入门到实战》,推荐入手! 专栏目录: (未完待续)

June 4, 2019 · 1 min · jiezi

PHP技术栈

本文旨在给要学习 PHP 的新手一个大概的认知轮廓,在心里有个学习的结构,有的放矢,避免走太多弯路。大神请忽略。 入门阶段预备知识1、掌握基本HTML、JS、CSS语法;熟悉 Bootstrap。 参考: https://www.runoob.com/html/h... https://www.liaoxuefeng.com/w... https://www.runoob.com/css/cs... 验收最低标准:模仿写出jd.com或者vip.com首页第一屏内容。2、熟悉Linux命令行 熟悉常用发行版系统(CentOS、Ubuntu)安装 熟悉常用命令行操作,包括文件管理、用户管理、权限管理、防火墙管理等 熟悉VIM使用 验收最低标准:掌握lnmp环境搭建。PHP基础掌握PHP基础语法、文件上传、cookie、Session、JSON。 掌握MySQL数据库连接:pdo使用。 掌握redis连接及简单应用。 掌握命名空间。 掌握面向对象编程思想。 参考:https://www.runoob.com/php/php-tutorial.html 学习框架学会使用ThinkPHP框架。主要是该框架在国内使用普及率太高了。不建议使用Laravel入门,因为该框架使用了较多的语法糖、第三方库,对新手可能有难度。 验收最低标准:可以使用ThinkPHP最新版作为入手框架,写出一个简单的博客。页面简单写就行。数据之间使用TP的 display 渲染到页面。学习写接口学会 Charles 抓包,看豆瓣的接口返回的数据。 学会写接口(GET、POST)的就行。 学会使用 POSTMAN。 验收标最低准:把上面的博客项目改成前后端分离的,先写完接口(最好有文档),再在页面里使用ajax调用接口数据。至此,你已经入门了。如果需要继续往下,还要学习。 第二阶段PHP使用 composer 安装PHP第三方库 对于PHP断点调试非常熟悉 学习常用PHP扩展 使用 SPL 掌握 PSR 规范 掌握反射的使用 掌握设计模式 熟练使用常用框架。 了解php和php-fpm的大部分配置选项和含义。 熟悉HTTP协议。 熟悉正则表达式。 MYSQL熟悉MYSQL优化的一些技巧,例如MySQL的性能追查,包括slow_log/explain等;对于order by、limit、like等一些坑能避开;能够熟练使用常用的索引;对于表结构创建选用哪种数据类型做到胸有成竹等等。 熟悉常用的配置,知道如何调优。 熟练配置主从。 NOSQL掌握Redis使用:对于常用数据结构的经典使用场景非常熟悉;了解Redis的事务、RDB、AOF等机制。 掌握memcache的使用,知道与redis的区别。 了解一下MongoDB。 Linux熟悉常用文本命令:例如wc、awk、split、diff、grep、sed等。 熟悉sort、uniq的使用。 熟练掌握ps、netstat、top等命令使用。 熟练使用Supervisor。 熟悉如何编写shell脚本。 能够理解Nginx的配置的含义。 第三阶段PHP该阶段PHP已经非常熟悉了,拥有快速开发项目、快速解决BUG的能力。代码遵循psr规范、稳定性很高。 熟悉消息队列使用,在很多场景合适的选择消息队列进行异步解耦。 熟悉如何使用 Elasticsearch 代替MYSQL的全文搜索功能。 熟悉多进程编程。 熟悉socket编程,对于网络IO模型有一定的认知,熟悉多路复用(select/poll/epoll)技术。 熟悉swoole框架,能应用于项目上。 不限制于框架本身,任何框架一天内快速入手。 对php的工作机制熟悉,熟悉php-fpm生命周期。 能够知道PHP相对于c等强类型语言性能为什么会慢。 对于PHP内部的实现原理有一定的认知,例如变量的实现、zend引擎的了解。 对于PHP的扩展有一定的认知,可以编写简单的扩展。 ...

June 4, 2019 · 1 min · jiezi

PHPMySQL导出大量数据Iterator-yield

开发中经常遇到这样的场景产品汪:我要在后台做一个功能,可以导出自定义时间范围的订单信息。开发小哥二话不说,半天就把功能做完并上线了。结果,第二天一上班产品汪过来就是拍桌子:MD,我想把去年一整年的订单都导出来,结果后台直接就挂了! 开发小哥一查,原来是内存溢出了,一年下来的的订单量足足有1000W条。于是,开发小哥跟产品汪吵了起来:你TM色不色傻,1000W的数据你导出来干diao,你是不是想把服务器给搞挂掉? 于是,产品汪与程序狗就这么结下梁子了。 但是。产品的需求你敢这样怼回去,那如果是老板提的这个需求呢,就是硬要把1000W条记录导出来,你还不得乖乖回去码代码? 那么,这个如果真要导出这大量数据,该怎么做呢?开发中我们经常会使用框架来提高我们的开发效率,但也意味着框架会对一些数据进行封装。 比如Yii2,当我们想获取去年一年的订单时,我们的代码会这样写: Order::find()->where("create_time between '2016-01-01' AND '2016-12-31'")->all(); 当我们将上面代码得到的结果集再拿去遍历时,数据量一大,就会内存溢出。原因是:Yii2中,对all方法进行了封将,将大量的数据存入了数组中,而遍历大数据,必然会导致内存迅速上升。那如何取出大量数据,而又不存到数组中呢?这就要用到了PHP中的迭代器:Iterator。如果有看过PDO::query的返回值类型的话,我们会发现,这个方法返回的PDOStatement,正是对Iterator的实现。关于Iterator,请自行脑补。 即然框架帮我们做了多余的封装,那么我们就改用原生API来实现。以下是完整代码 $sql = 'select * from user';$pdo = new\PDO( 'mysql:host=127.0.0.1;dbname=test', 'root', 'root' );$pdo->setAttribute( \PDO::MYSQL_ATTR_USE_BUFFERED_QUERY, false);$rows = $pdo->query($sql);$filename = date('Ymd').'.csv';//设置文件名header('Content-Type:text/csv');header("Content-Disposition:attachment;filename={$filename}");$out = fopen('php://output','w');fputcsv( $out, [ 'id', 'username', 'password', 'create_time' ]);foreach( $rows as $row ){$line=[ $row['id'], $row['username'], $row['password'], $row['create_time']];fputcsv($out,$line);}fclose($out);$memory=round((memory_get_usage()-$startMemory)/1024/1024,3).'M'.PHP_EOL;file_put_contents('/tmp/test.txt',$memory,FILE_APPEND);在表中生成7位数量级的记录,执行上面的代码,通过查看内存使用,发现整个过程只占用了0.XM的内存,完全没有任何内存溢出的现象。

June 3, 2019 · 1 min · jiezi

Spider引擎解决分库分表的尴尬

场景假设场景1:有两个分布在不通实例上的多张不通的表,想要通过某个字段关联,做一个统计,或者想将分布在不同实例的表,合并到一个实例中来做一些查询。 场景2:由于数据库容量的瓶颈或者是由于数据库访问性能的瓶颈,将一某一个大库、大表或者访问量非常大的表进行拆分,然后分布到不通的实例中。 简单来说就是水平、垂直拆分的场景 一、Spider引擎简介1、什么是Spider引擎Spider引擎是一个内置的支持数据分片特性的存储引擎,支持分区和XA事务,该引擎可以在服务器上建立和远程数据库表之间的链接,操作起来就像操作本地的表一样。并且对后台数据库的引擎没有任何限制。目前spider引擎已经集成到了MariaDB中。2、Spider架构图 3、Spider的优劣对比优势分析1.对业务完全透明,业务层不需要做任何的修改;对于分库和分表的操作业务层不需要关系,只需要通过spider作为代理入口,真实数据存储在哪台设备上,spider代理会自动进行路由。2.方便横向扩展,能解决单台mysql的性能和存储瓶颈33.对后端的数据库引擎没有限制4.实现垂直拆分和水平拆分功能,针对分表支持此哈希,范围,列表等算法5.完全兼容mysql协议劣势分析1.Spider本身不支持缓存和全文搜索,只能在后端数据库实现全文搜索2.Spider无法备份数据,只能对后端数据库做物理备份3.Spider本身是单点的,无法做灾备,只能通过VIP方式自己实现啊4.由于业务与数据库之间多了一层spider,在性能上多少会有些损耗二、Spider的使用场景解析1、垂直分表的场景和解析 从上图可以看出,spider后面接4台DB server,可以将不通功能的表分布到后端不通的DB server中,比如user_info的表专门存放在HostA中,user_msg表存放在了HostB中,user_detail表存放在了HostC中,user_log表存放在了HostD中。在图中的红色部分,当我们执行红色部分的SQL的时候,spider会通过user_info表的映射关系以及HostA的IP映射关系,将查询user_info表的请求都转发到HostA上,HostA查询完成后再将结果发给spider服务器,spider再转发给客户端2、水平分表的场景和解析 spider支持多种水平分表的模式,目前支持hash分表(hash)、范围分表(range)、列表分表(list),我这里用range来说明水平分表的工作原理。从上图中可以看出spider对user_info表针对id进行了分区,将0~100000的记录存储在了HostA,100000~200000的记录存储在了HostB,200000~300000的记录存储在了HostC,300000~400000的记录存储在了HostD。当用户访问user_info的某条或者多条记录的时候,spider会根据分区的情况,对相关的记录落在某台或者多台DB server上,再进行转发。比如select * from user_info where id=1这个SQL,spider在收到这个请求后,会跟进分区情况选择对应的DB server进行转发。这里会将该请求转发到HostA中。HostA处理完成后,再将结果返回给spider server,spider再将结果转发给发起请求的客户端。三、Spider引擎实战1、安装从spider 10.0.0.4版本开始,spider引擎就集成到了MariaDB中,集成后安装就非常的简单,安装步骤如下:1、安装mariaDB到spider server以及后端多台DB server上; 安装方法非常简单,请参考:https://mariadb.com/kb/en/mariadb/getting-installing-and-upgrading-mariadb/2、安装spider引擎到spider server上(后端的DB server不需要安装spider引擎) mysql -uroot -p < install_spider.sql 或者登录mysql后执行 source /path/install_spider.sql 备注:install_spider.sql在share目录下面 这个命令所做的事情如下: 创建spider相关的系统表 spider_link_failed_log spider_link_mon_servers spider_tables spider_xa spider_xa_failed_log spider_xa_member 创建spider相关的表结构 加载spider引擎2、使用未完待续~~~

June 3, 2019 · 1 min · jiezi

MySQL-主从复制原理

引言 MySQL 主从复制原理是相当基础的知识,很久没有接触过 MySQL 主从复制了,因为我这边负责的业务暂时没用使用 MySQL 主从复制。既然有些忘记了,现在我重新复习记录下。 MySQL 主从复制介绍 MySQL 的主从复制是一个异步的复制过程(但一般情况下感觉是实时同步的),数据库数据从一个 MySQL 数据库(我们称之为 Master)复制到另一个 MySQL 数据库(我们称之为 Slave)。在 Master 与 Slave 之间实现整个主从复制的过程是由三个线程参与完成的。其中有两个线程(SQL 线程和 IO 线程)在 Slave 端,另外一个线程(IO 线程)在 Master 端。(来自 MySQL 帮助文档) MySQL Replication 复制过程 Slave 服务器上执行start slave,开启主从复制开关。此时,Slave 服务器上的 IO 线程会通过 Master 服务器上授权的有复制权限的用户请求连接 Master 服务器, 并请求从指定 binlog 日志文件的指定位置之后发送 binlog 日志内容。 (日志文件名和位置就是在配置主从复制任务时执行change master命令时指定的)Master 服务器接收到来自 Slave 服务器的 IO 线程的请求后, Master 服务器上的 IO 线程根据 Slave 服务器的 IO 线程请求的信息, 读取指定 binlog 日志文件指定位置之后的 binlog 日志信息,然后返回给 Slave 端的 IO 线程。 返回的信息中除了 binlog 日志内容外, 还有本次返回日志内容后在 Master 服务器端的新的 binlog 文件名以及在 binlog 中的下一个指定更新位置。当 Slave 服务器的 IO 线程获取来自 Master 服务器上 IO 线程发送的日志内容及日志文件和位置点后, 将 binlog 日志内容依次写入到 Slave 端自身的 relay log(即中继日志)文件(mysql-relay-bin.xxxxxx)的最末端, 并将新的 binlog 文件名和位置记录到 master-info 文件中, 以便下一次读取 Master 端新 binlog 日志时, 能告诉 Master 服务器需要从新 binlog 日志的哪个文件哪个位置开始请求新的 binlog 日志内容。Slave 服务器端的 SQL 线程会实时检测本地 relay log 中新增加的日志内容, 然后及时的把 relay log 文件中的内容解析成在 Master 端曾经执行的 SQL 语句的内容, 并在自身 Slave 服务器上按语句的顺序执行应用这些 SQL 语句,应用完毕后清理应用过的日志。经过了上面的过程,就可以确保在 Master 端和 Slave 端执行了同样的 SQL 语句。 当复制状态正常的情况下,Master 端和 Slave 端的数据是完全一样的。 ...

June 3, 2019 · 1 min · jiezi

MySQL分页优化实验与总结

前言分页的sql优化是日常开发中经常遇到的问题,笔者在此做一个经验总结,并附上相应的实验过程。 实验准备若不想亲自实验的,可以直接跳过这一节。但还是建议大家做一下实验,眼见为实。 1.安装测试数据库本次实验使用的数据是mysql官方提供的employee数据库,mysql官方提供了一些测试数据库,可以在这里找到https://dev.mysql.com/doc/ind...。 2.修改测试数据库安装好employee数据库后,笔者出于测试修改了一下salaries表的结构,方便测试,修改操作如下: //修改原表的主键为idCREATE TABLE `test_salaries` ( `id` int(11) NOT NULL AUTO_INCREMENT, `emp_no` int(11) NOT NULL, `salary` int(11) NOT NULL, `from_date` date NOT NULL, `to_date` date NOT NULL, PRIMARY KEY (`id`), CONSTRAINT `test_salaries_ibfk_1` FOREIGN KEY (`emp_no`) REFERENCES `employees` (`emp_no`) ON DELETE CASCADE) ENGINE=InnoDB DEFAULT CHARSET=latin1; //导入原表数据INSERT INTO test_salaries (id,emp_no,salary,from_date,to_date) SELECT NULL,emp_no,salary,from_date,to_date FROM salaries;3.完成测试环境至此,实验的准备工作完成。可先查看一下test_salaries表中有多少数据(以下测试基于该表) SELECT count(*)FROM test_salaries; 优化分页SQL查询优化分页SQL查询的思路: 尽可能使用索引覆盖扫描,而不是查询所有的列。然后根据需要做一次关联操作再返回所需的列(延迟关联)将limit查询转换为已知位置的查询,让mysql通过范围扫描获得对应的结果(范围扫描)延迟关联原始sql查询语句: SELECT * FROM test_salaries WHERE salary <= 94000 LIMIT 2677500,10;原始sql查询语句执行效果: ...

June 3, 2019 · 1 min · jiezi

基于springsecurityoauth2实现单点登录持续更新

基于spring-security-实现数据库版文章代码地址:链接描述可以下载直接运行,基于springboot2.1.5,springcloud Greenwich版本实现。前面两篇写了认证oauth2通过内存 还有jdbc实现认证中心。接下来我们采用oauth2实现管理系统的单点登录。 说到这里,需要介绍几个注解: @EnableAuthorizationServer 该注解用来开启认证服务,使用该注解表明自己是一个认证服务。 @EnableResourceServer 该注解要用来开启资源保护,表明自己是资源服务器受认证服务保护。 @EnableOAuth2Sso 该注解表示自己是oauth2客户端,也即单点登录客户端 @EnableGlobalMethodSecurity(prePostEnabled = true, securedEnabled = true, jsr250Enabled = true) spring-security默 认禁用注解,使用该注解来判断用户对某个控制层的方法是否具有访问权限 好来,注解介绍完了,闲话少说。我们开始今天的主题“单点登录”。 (1)创建sso-client项目,修改maven依赖: 因为,是web项目需要添加maven依赖。 (2)在启动类加上@EnableOAuth2Sso注解,表明自己是客户端 (3)下面进行最重要的,设置配置文件 因为,前面几个配置在之前章节介绍过,这里只介绍server.servlet.session.cookie.name=OAUTH2SESSION这个配置。 这是个坑,我在没加这个配置之前,授权成功后,还是跳转授权登录页码。认证服务器和浏览器控制台也没有报错信息。只好debug一点点差错。 这里简单介绍下如何查阅源码,首先全局搜索自己的配置 security.oauth2.client.user-authorization-uri=http://localhost:9001/oauth/authorize因为这个地址是认证服务器请求授权的,所以,请求认证的过滤器肯定包含他。搜索的结果如下: 两个结果,一个是我们自己配置的忽略,点开另外一个: ok我们在源码中找到这个类,一直向上找,可以找到OAuth2RestTemplate 同样的,我们可以搜索这个地址,查找在认证服务器中是如何认证的。 跑偏了,还是介绍下这个配置吧,通过这个配置session和认证服务器不一样结局。也可以设置上下文路径 server.servlet.context-path=/sso-client (4)调回来,下来我们创建一个controller文件,用来获取授权用户信息: 在template下创建index.html欢迎页面: (5)启动客户端服务: (6)因为,我们需要请求认证服务器,校验token,因此认证服务器需要开启/oauth/token路径,修改WebSecurityConfig文件添加: (7)启动认证服务,访问客户端首页: http://localhost:9005 如下: 自动跳转到认证服务器登录地址,输入用户名: admin 密码: 123456 登录 你可以把项目修改端口启动试试,登录一个另一个不在需要登录。 未完待续,下一篇介绍资源服务器和认证服务器的集成。 有问题,请留言。

June 2, 2019 · 1 min · jiezi

Halo-v10-正式版发布一款惊艳的动态博客系统

前言Halo 从去年 5 月开源以来,广受小伙伴们的喜爱,在此非常感谢使用 Halo 发表博客的小伙伴们。今年,在 @JohnNiang 的帮助下,我们几乎完全重写了 Halo,然后 1.0 正式版就发布了。在此,非常感谢 @JohnNiang 的加入以及他做出的贡献。再到后面,我们公开了 admin api 之后,@雨季不再来 使用了 Flutter 为 Halo 开发了管理端的 APP。相信以后越来越多人加入之后,Halo 会变得更好。希望大家会喜欢。 主要特性拥有使用 Vue 开发的后台管理,体验升级,但是并不需要独立部署,启动 Halo 即可。拥有 Restful 风格的 Content api,你可以用于开发单页面主题,微信小程序等。拥有 Restful 风格的 Admin api,你可以用于开发桌面管理客户端,管理 App(已有) 等。拥有使用 Flutter 开发的管理端 App,支持 Android 和 iOS,随时随地发表你的想法!感谢@雨季不再来。拥有独立的评论插件,使用 Vue 开发,只需在页面引入构建好的 JS 文件即可,完美地和主题相结合。支持多主题。另外,还支持在线下载主题以及更新主题。支持在线修改主题文件内容,无需在本地修改然后上传。十分友好的主题开发体验,支持自定义配置。(主题开发文档正在开发中)。功能强大的附件管理,同时支持本地上传,又拍云/七牛云/阿里云等云存储,另外,还支持 SM.MS 图床(非常感谢 SM.MS,请大家善用该服务哦)。自带友情链接管理,图库管理(给爱摄影的小伙伴们)。支持自定义页面。支持 Markdown 文档导入,顺带解析 FrontMatter。支持日志功能,类似于 QQ 空间的说说,亦或者微博。同时支持微信发布日志(后续计划)。还有…相关链接Halo 开源地址:https://github.com/halo-dev/haloWeb 管理端:https://github.com/halo-dev/h...管理端 APP:https://github.com/halo-dev/h...独立评论插件:https://github.com/halo-dev/h...主题仓库:https://halo.run/theme交流论坛:https://bbs.halo.run有喜欢的同学可以点个 star 哦。有任何问题可以去 Github issues 或者 https://bbs.halo.run 。预览图 ...

June 2, 2019 · 1 min · jiezi

Docker快速搭建一套PHPNginxMySQLRedisXdebugMemcached-开发环境并演进

痛点笔者在尝试起一个新web项目时,往往会陷入重新建立一套Docker环境的繁琐事当中。我想大家在开始做一个新项目时,或者快速为了和以前的项目做完全的隔离,也会起一套新docker环境。 从这篇文章你会得到采用docker-compose容器编排技术,一步启动全部服务。php容器在官方的基础上还打包了一些常用拓展(附带build源码,动手能力强可以自己打包),php,nginx,mysql都附带有自定义配置文件(便于开发测试的配置调整),都供下载。 架构 本片文章搭建出来的环境如上图。 环境说明运行环境Mac OS 10.13.6Virtual Box 5.2.14Ubuntu 16.04.4Docker 17.07.0-ce容器Nginx 1.12.1-alpinePHP-fpm 5.6MySQL 5.7Redis 3.2Memcached 1.4.27这里说明一下笔者运行环境,采用了在Mac机上安装vbox虚拟机,在虚拟机里面的debian环境安装了Docker环境,文件放在Mac环境,通过文件挂载方式,达到Mac环境编辑,Docker环境实时更新效果。你要问为啥不在Mac下直接装Docker,历史原因~运行材料.├── build ## docker 镜像build 材料│   ├── php5.6 ## php 5.6│   │   ├── Dockerfile│   │   ├── imagick-3.4.3.tgz│   │   ├── memcached-2.2.0.tgz│   │   ├── redis-4.0.2.tgz│   │   ├── sources.list│   │   └── xdebug-XDEBUG_2_5_5.tar.gz│   └── php-cli ## php cli 的自建镜像│   ├── amqp-1.9.3.tgz│   ├── Dockerfile│   ├── Dockerfile-php-swoole│   ├── memcached-3.0.4.tgz│   ├── redis-4.1.1.tgz│   ├── sources.list.jessie│   ├── swoole-4.0.4.tgz│   ├── swoole-4.2.6.tgz│   ├── xdebug-2.6.1.tgz│   └── yaf-3.0.7.tgz├── config ## 配置文件│ ├── apt ## 由于使用的debian系列,所以命名apt│ │ └── sources.list ## 更新为国内源│ ├── memcached ## memchached的配置│ │ └── memcached.conf│ ├── mysql ## mysql 的配置│   │   ├── conf.d│   │   │   └── mysqld_safe_syslog.cnf│   │   └── my.cnf│ ├── nginx ## nginx 的配置│   │   ├── conf.d│   │   │   ├── default│   │   │   └── xiuno│   │   ├── mime.types│   │   ├── nginx.conf│   │   └── sites-enabled│ ├── php ## php的配置,分cli,和fpm配置│   │   ├── cli│   │   │   ├── conf.d│   │   │   │   ├── 05-opcache.ini│   │   │   │   ├── 10-pdo.ini│   │   │   │   ├── 20-curl.ini│   │   │   │   ├── 20-gd.ini│   │   │   │   ├── 20-imagick.ini│   │   │   │   ├── 20-json.ini│   │   │   │   ├── 20-memcache.ini│   │   │   │   ├── 20-mysqli.ini│   │   │   │   ├── 20-mysql.ini│   │   │   │   ├── 20-pdo_mysql.ini│   │   │   │   ├── 20-readline.ini│   │   │   │   ├── 20-redis.ini│   │   │   │   ├── 20-xdebug.ini│   │   │   │   └── swoole.ini│   │   │   └── php.ini│   │   ├── fpm│   │   │   ├── conf.d│   │   │   │   ├── docker.conf│   │   │   │   ├── www.conf│   │   │   │   └── zz-docker.conf│   │   │   ├── docker-php-fpm.conf│   │   │   ├── php-fpm.conf│   │   │   ├── php.ini│   │   │   └── pool.d│   │   │   └── www.conf│   │   └── mods-available│   │   ├── curl.ini│   │   ├── gd.ini│   │   ├── imagick.ini│   │   ├── json.ini│   │   ├── memcache.ini│   │   ├── mysqli.ini│   │   ├── mysql.ini│   │   ├── opcache.ini│   │   ├── pdo.ini│   │   ├── pdo_mysql.ini│   │   ├── readline.ini│   │   ├── redis.ini│   │   └── xdebug.ini│ └── redis ## redis 配置│   ├── redis.conf│   ├── redis-server.sh│   └── sentinel.conf├── data ## 为了数据持久化│ ├── mysql ## mysql 文件挂载│ └── redis ## redis 持久化数据文件夹├── docker-compose.yaml ## 容器编排 !!!├── log ## 各个容器产生的日志│ ├── mysql ## mysql日志│ │ ├── error.log│ │ └── mysql.log│ ├── nginx ## nginx 日志│   │   ├── access.log│   │   ├── access_xiuno.log│   │   ├── error.log│   │   └── error_xiuno.log│   └── php├── php ## php代码存放目录│ └── xiunobbs ## php项目└── tool ## php 一些工具 ├── composer.phar └── phpunit-4.8.36.phar配置文件下载git clone https://gitee.com/xupaul/docker_fast_init配置说明目前笔者还没有写相关自动化脚本自动适配用户的使用环境,所以这里需要先调整一下下载后的配置文件。docker-compose.yml 文件调整这个文件有大量的文件挂载配置,这块就需要调整,拿一个举例。 ...

June 2, 2019 · 3 min · jiezi

mysql高级知识总结

这篇文章的知识点来自于极客时间专栏<<MySQL实战45讲>>,本文持续更新。 索引索引的目的:提高查询效率。 常见索引模型:哈希表、有序数组、搜索树哈希表:键 - 值(key - value)对。哈希思路:把值放在数组里,用一个哈希函数把key换算成一个确定的位置,然后把value放在数组的这个位置哈希冲突(多个 key 值经过哈希函数的换算,会出现同一个值的情况)的处理办法:链表哈希表适用场景:只有等值查询的场景,比如 Memcached 及其他一些 NoSQL 引擎。 有序数组:按顺序存储。查询用二分法就可以快速查询,时间复杂度是:O(log(N))有序数组查询效率高,更新效率低,往中间插入一个记录就必须得挪动后面所有的记录,成本太高。有序数组的适用场景:静态存储引擎。 二叉搜索树:每个节点的左儿子小于父节点,父节点又小于右儿子二叉搜索树:查询时间复杂度O(log(N)),更新时间复杂度O(log(N))数据库存储大多不适用二叉树,因为树高过高,会适用N叉树 MySQL表引擎InnoDB中的索引模型:B+Tree索引类型:主键索引、非主键索引主键索引的叶子节点存的是整行的数据(聚簇索引),非主键索引的叶子节点内容是主键的值(二级索引) 主键索引和普通索引的区别:主键索引只要搜索ID这个B+Tree即可拿到数据。普通索引先搜索索引拿到主键值,再到主键索引树搜索一次(回表),所以在应用中尽量使用主键查询。 一个数据页满了,按照B+Tree算法,新增加一个数据页,叫做页分裂,会导致性能下降。空间利用率降低大概50%。当相邻的两个数据页利用率很低的时候会做数据页合并,合并的过程是分裂过程的逆过程。 自增主键使用自增主键的好处: 自增主键一般用整型做主键,则二级索引叶子节点只要 4 个字节;而如果使用业务字段做主键,比如字符串类型的身份证号,每个二级索引的叶子节点得占用约 20 个字节。插入数据时,自增主键能保证有序插入,避免了页分裂。从性能和存储空间方面考量,自增主键往往是更合理的选择。 使用业务字段做主键的使用场景: 只有一个索引该索引必须是唯一索引这就是典型的 KV 场景。由于没有其他索引,所以不用考虑其他索引的叶子节点大小的问题. 重建索引重建索引的目的:节省空间重建索引的办法:alter table T engine=InnoDB 联合索引覆盖索引:如果查询条件使用的是普通索引(或是联合索引的最左原则字段),查询结果是联合索引的字段或是主键,不用回表操作,直接返回结果,减少IO磁盘读写读取正行数据最左前缀:联合索引的最左 N 个字段,也可以是字符串索引的最左 M 个字符联合索引:根据创建联合索引的顺序,以最左原则进行where检索,比如(age,name)以age=1 或 age= 1 and name=‘张三’可以使用索引,单以name=‘张三’ 不会使用索引,考虑到存储空间的问题,还请根据业务需求,将查找频繁的数据进行靠左创建索引。索引下推:like 'hello%’and age >10 检索,MySQL5.6版本之前,会对匹配的数据进行回表查询。5.6版本后,会先过滤掉age<10的数据,再进行回表查询,减少回表率,提升检索速度。 参考资料极客时间MySQL实战45讲

June 1, 2019 · 1 min · jiezi

mysql基础知识总结

mysql知识体系庞大,很多知识可能刚学过就忘了,我希望可以在这篇文章记下一些有用的知识点,方便以后查找使用 表相关改表在修改表操作之前,最好先创建一份表的副本,然后在它的基础上修改。在test数据库创建表的副本: CREATE TABLE test.student_new LIKE student;上面的语句只是复制了表结构,新表还没有数据。要复制表数据,可用INSERT加SELECT。 UES test #切好到test数据库INSERT INTO test.student_new SELECT * FROM school.student;现在就可以改表了。

May 31, 2019 · 1 min · jiezi

1节课搞懂MySQL数据类型

腾讯云大学数据库直播课程系列第二讲《揭秘MySQL的数据类型》开讲!如果你是:数据库开发人员,数据库从业者,云数据技术爱好者,DBA对数据库知识感兴趣的小伙伴可以花点时间来听听鹅厂专家的分享,1小时搞懂云数据库MySQL数据类型! 讲师:腾讯云数据库产品经理summerdliu 课程内容:1、MySQL数据类型的基础知识2、MySQL数据类型的选择3、MySQL数据类型的选择与性能优化 如何参加?长按识别海报二维码即可马上预约,不要错过哦! 关注微信领课程福利扫码添加官方学习君账号,我们将邀请您提前加入学习互动群,您可以在群内结识共同兴趣的小伙伴,更多课程福利领取都在群内分享给你哟!

May 31, 2019 · 1 min · jiezi

干货-MySQL数据库安全之审计

每家公司都希望业务高速增长,最好能出几个爆款产品或者爆款业务,从而带动公司营收高速攀升。但站在数据库管理员的角度,这却是实实在在的压力,业务高速增长必然带来数据量的暴增。数据库系统的选型和设计是支撑整个业务系统的重要因素。MySQL数据库是基于云原生的数据库产品之一,云原生为云数据库提供了重要动力,相比于传统自建数据库,云数据库比单个数据库具有更大的弹性和可扩展性。 数据库审计主要用于监视并记录对数据库服务器的各类操作行为,并记入审计日志或数据库中以便日后进行跟踪、查询、分析,以实现对用户操作的监控和审计。审计是一项非常重要的工作,也是企业数据安全体系的重要组成部分。 MySQL企业版自带审计功能,但是需要付费。MySQL社区版没有审计功能,基于成本的考虑,很多用户采用社区版MySQL作为业务系统数据库。采用社区版MySQL如何实现重要的审计功能,本文从自建和云服务两种情况来解答这个问题。 自建MySQL数据库的场景 本文自建数据库所有实验环境是基于window10下MySQL5.7这个版本。 方法一 Genreal Log 默认情况下,MySQL不开启General log; 开启General log后,MySQL将所有到达MySQL Server的SQL语句记录下来。 开启General log步骤: 1、查看General Log开启情况:执行SQL命令show variables like '%general_log%’ ;可以看到默认general_log是OFF的: 2、开启General Log: 执行SQL命令set global general_log=on 而后查看general_log打开了: 3、验证:general_log打开后,所有SQL的访问都会记录在general_log_file指向的日志文件。我们执行几个SQL语句测试: 而后查看ZB-PF11H2E3.log日志文件里面的内容,我们看到刚才做的操作都已经记录在日志里了: 开启General Log只要用户执行了操作,无论对错,MySQL就会记录日志,这样的话日志量会非常庞大,对数据库效率有影响。所以我们一般不建议开启开功能,个别情况下可能会临时的开一段时间以供排查故障等使用。 方法二 BinLog+Init_connect BinLog是MySQL操作时留下的日志,BinLog一方面可以用在数据库的恢复与主从复制上,另外一方面可以用来做数据库的审计。 由于BinLog日志里面无法查询是谁在哪个时间段登录的等信息,缺少审计必要的信息。在MySQL中,每个连接都会先执行init_connect进行连接的初始化,我们可以在这里获取用户的登录名称和thread ID值。然后配合BinLog,就可以追踪到每个操作语句的操作时间,操作人等信息,再加上BinLog的日志信息实现审计。 配置和验证过程如下: 1、创建审计用的数据库和表: 2、创建具有操作auditdb数据权限的用户: 有用户添加操作auditdb的权限: 1 MySQL> insert into mysql.db (Host,Db,User1,Insert_priv) values ('%','auditdb','','Y'); 2 Query OK, 1 row affected (0.03 sec) 3 MySQL> flush privileges; 4 Query OK, 0 rows affected (0.00 sec)3、设置init_connect,并重启MySQL数据库在初始化参数文件[mysql]部分添加如下内容: ...

May 31, 2019 · 1 min · jiezi

基于springsecurityoauth2实现oauth2数据库版持续更新

基于spring-security-oauth2实现oauth2数据库版文章代码地址:链接描述可以下载直接运行,基于springboot2.1.5,springcloud Greenwich版本实现 该系列分为两个部分:分为内存实现,数据库实现。其中数据库实现采用RBAC权限角色管理。 上一篇,介绍了oauth2的内存实现,也就是认证服务把客户端和用户信息都存储在内存中,这样不利于拓展,不适合于生产环境。下面,我们开始基于mysql数据库的oauth2实现。 首先,我们创建oauth2数据库,注意编码选择utf-8mb4格式,utf-8是不规范的,mysql也没有进行更改。 好了,现在我们初始化表,sql如下: Drop table if exists oauth_client_details;create table oauth_client_details ( client_id VARCHAR(255) PRIMARY KEY, resource_ids VARCHAR(255), client_secret VARCHAR(255), scope VARCHAR(255), authorized_grant_types VARCHAR(255), web_server_redirect_uri VARCHAR(255), authorities VARCHAR(255), access_token_validity INTEGER, refresh_token_validity INTEGER, additional_information TEXT, autoapprove VARCHAR (255) default 'false') ENGINE=InnoDB DEFAULT CHARSET=utf8; Drop table if exists oauth_access_token;create table oauth_access_token ( token_id VARCHAR(255), token BLOB, authentication_id VARCHAR(255), user_name VARCHAR(255), client_id VARCHAR(255), authentication BLOB, refresh_token VARCHAR(255)) ENGINE=InnoDB DEFAULT CHARSET=utf8; ...

May 31, 2019 · 4 min · jiezi

工作过程遇到数据库相关的知识点汇总

工作过程遇到的,或者平时学习的数据库相关的知识点汇总。 Home Oracle1 大数据量加载方法汇总2 大数据量更新方法3 去掉回车换行空格的方法4 系统参数详解5 dbms_application_info包6 FORALL与BULK COLLECT语句8 With As 的用法9 like运算符和转义操作符10 抛出自定义错误SQLServer1 SqlServer列与逗号分隔字符串互相转换2 查看sqlserver被锁的表以及如何解锁Mysql1 centos 7.2 mysql5.7 不区分表名大小写2 mysql5.7.x:this is incompatible with DISTINCT

May 30, 2019 · 1 min · jiezi

MySQL-80-技术详解

MySQL 8.0 简介MySQL 5.7 到 8.0,Oracle 官方跳跃了 Major Version 版本号,随之而来的就是在 MySQL 8.0 上做了许多重大更新,在往企业级数据库的路上大步前行,全新 Data Dictionary 设计,支持 Atomic DDL,全新的版本升级策略,安全和账号管理加强,InnoDB 功能增强等,目前小版本已经 release 到 8.0.16,新的功能仍然在持续推出。RDS MySQL 8.0 产品是阿里云推出的 MySQL 系列云产品之一,使用完全兼容 MySQL 8.0 的阿 里云 AliSQL 8.0 分支,除了官方在 MySQL 8.0 推出的全新功能外,AliSQL 沉淀了许多在 Alibaba 集团电商业务和云上几十万客户在使用 MySQL 过程中遇到的问题和需求,以此来加固AliSQL, 提升 AliSQL 的性能和稳定性。下面分别对 MySQL 8.0 和 AliSQL 8.0 相关的版本和功能做简短的介绍: MySQL 8.0 版本更新1. 数据字典 MySQL 8.0 摒弃了 Server Layer 定义的 FRM 文件和其它非事务表,使用了一组 InnoDB 表来 保存数据字典,支持事务特性。 ...

May 30, 2019 · 2 min · jiezi

一文读懂MySQL复制机制

背景介绍复制,就是对数据的完整拷贝,说到为什么要复制,首先能想到的是怕数据意外丢失,使得用户蒙受损失。 当完成了数据复制之后,会发现它的优势不止这一点,假如一台机器宕机了,可以启用备份在另一台机器的数据。毕竟宕机的概率很小,闲暇时间还可以让备份机器分担主机器的流量压力。除此之外,当要升级数据库版本时,可以在不停止用户服务的情况下优先升级备用机器,待观测其可用稳定时再将主数据库升级。 但是,也不能总让DBA手动拷贝来完成复制,万一在DBA蹲坑的时候宕机了,在蹲坑期间产生的数据由于没有及时备份,会导致备用数据库的数据缺失,所以还是要设计一套可以自动复制的机制。 设计复制机制我们暂定被复制的数据库为主库,粘贴出来的为从库,要实现主库到从库的复制,看起来非常简单,只需一个计划任务,定时将主库数据文件复制一份,并传输到从库所在服务器。 但毕竟定时任务不是实时的,万一主库在上次复制的十分钟后发生了故障,被激活的从库用的是最近一次复制的数据,所以会缺失十分钟的数据,后果不堪设想。 还是要实时复制,那可以这样,主库将每次执行完的语句实时发给从库,让从库马上执行,就能保证两边数据一致了。 不太好的是,主库是实时发送数据给从库的,需要等从库执行完毕才能处理下一条语句,严重占用了主库的执行时间,如果从库过多,主库就废了。 还得改成异步才能节省主库的时间,可以将主库执行完的语句存到文件里,让从库来取,这样主库就不用等待从库了。既然是写到文件,速度是很快的,主库完全可以在执行前就将语句写到文件中,达到更高的同步效率。 上述有些问题,从库无法做到跑去主库取数据,只能起一个线程先与主库建立连接,并向主库索要数据,然后主库也起一个线程读取文件内容,并推给从库线程,从库收到语句后就可以马上执行了。 这样效率还是很低,主库的线程要等从库收到语句并执行完毕才能推下一条,如果有多个从库,主库就要开启多个线程长期与各个从库保持通信,占用主库服务器资源,不如从库也创建个文件临时保存主库发来的语句,先存起来再慢慢执行,主库压力小了,从库也放心。 现在从库有了自己的文件做中继,就不用着急了,从库可以再起一个线程,慢慢执行中继文件中的语句,执行完毕之后原文件没有价值了,就可以清理掉,免得占用服务器资源。 到目前为止,最基本的复制机制就设计完了,这种由主库到从库的复制方式就是典型的主从架构,在此基础上可以进行演化,比如从库有很多,主库要为每个从库推送数据,主库的压力会随之增大,又因为主库的职责不仅仅是同步数据,还要忙着读写数据,所以同步数据的事可以找人代替,比如在主库与从库之间再建立一个主库,新建立的主库唯一的职责就是同步数据给从库,这样真正的主库就只需要推送一次数据给新建的主库,其余时间就可以安心读写数据了。 这种演化而来的复制模式叫做多级复制架构,本文到此结束,上述就是三种复制架构中的其中两种,除此之外还有一个“主主”架构,在这里就不再多说了,感兴趣的可以自行了解或关注我们后续的文章。 如果你愿意,让我来帮你关注不知道又想知道却想不到的知识。

May 30, 2019 · 1 min · jiezi

mysql笔记

1. 显示mysql中所有数据库的名称 SHOW databases; SHOW schemas;2. 显示当前数据库中所有表的名称SHOW tables;//显示当前数据库的所有的表 SHOW tables from database_name;//显示某个数据库的所有的表3. 显示表的所有列SHOW columns from table_name from database_name;SHOW columns from database_name.table_name;4. 其它相关SHOW grants; // 查看权限 SHOW index from table; //查看索引SHOW engines; // 显示安装以后可用的存储引擎和默认引擎。5 显示创建数据库的结构 表的结构SHOW create database test;SHOW create table student;6. 检索数据SELECT name from student; //显示学生表的所有姓名SELECT name,age from student; //显示学生表的所有姓名,年龄SELECT * from student; // 显示学生表的所有表级别的增删改查/**@列操作*/ALTER table cup add column age int not null; //增列ALTER table cup drop column name; //删列 ALTER table cup modify column name varchar(40) not null //改列ALTER table cup change age age int(2) not null; //change可以替换列的名字 ALTER table cup modify id int(10) default 0 first; //把id移动到开头 ALTER table cup modify id int(10) default 0 last; //把id移动到最后ALTER table cup modify name varchar(20) after id; //移动位置 SHOW columns from cup; //查看列 /**@约束操作 primary key 主键 not null 非空 unique 唯一约束 */ALTER table cup add primary key(id); // 增主键ALTER table cup drop primary key; //删主键 数据的增删改查// 字段如果是一一对应,可以删掉,如果顺序不对或者数量不对要加上insert into cup (id,name,counts,age) values (1,"lili",22,22)// 条件删除delete from cup where id = 1;// 删除表的全部数据,表还有,但是数据是空的delete from cup;// 改数据update from cup set name="huahua" where id = 1;//查询数据SELECT name from cup;SELECT具体用法/***@简单查询*/SELECT name from cup; //查1行SELECT name,age from cup; //查2行SELECT * from cup; //查所有行/***@限制查询返回的数量*/SELECT * from cup limit 2; //只要前两条 SELECT * from cup limit 2 offset 1 ; //从第1条开始取2条/***@where 条件判断*/SELECT * from cup where id = 1;SELECT * from cup where id > 1;SELECT * from cup where id >= 1;SELECT * from cup where id < 1;//// 范围筛选 // id 1,2,3都可以SELECT * from cup where id in (1,2,3);// id 不是1,2,3都可以 SELECT * from cup where id not in (1,2,3);// id 大于1,2,3 的所有,就是大于全部才可以 SELECT * from cup where id > all (1,2,3);SELECT * from cup where id >= all (SELECT id from cup); // id 大于1,2,3中的1个就可以和下边一句是一样的 some和any一样用 SELECT * from cup where id > some (1,2,3);SELECT * from cup where id > 1 or id > 2 or id > 3;/***@合并查询结果*union会删除重复的数据,union all不会删除重复的 */// cup1和cup2的字段必须一样,如果不一样就合并一样的SELECT * from cup1 union SELECT * from cup2;/***@模糊查询*/SELECT name from cup where name LIKE "hua%"; // hua开头的SELECT name from cup where name LIKE "%hua%"; // 中间有hua的

May 30, 2019 · 2 min · jiezi

JavaWeb学生选课ServletJSPJDBC

运行结果: 数据库的2个表:course表 student表 ps:一定要build path导入数据库用的jar包,以及在在lib文件夹中导入数据库jar包 文件目录结构: 具体代码:index.jsp 首页 <%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%><!DOCTYPE html><html><head><meta charset="UTF-8"><title>欢迎进入选课系统</title></head><body><center><h2>欢迎进入选课 系统</h2><a href="login.jsp">学生登录</a><a href="regist.jsp">学生注册</a><a href="admin.jsp">管理员登录</a></center></body></html>login.jsp 学生登录 <%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%><!DOCTYPE html><html><head><meta charset="UTF-8"><title>学生登录</title></head> <body style="text-align: center;"> <br><br> <h3>学生登录</h3> <form action="LoginServlet" method="post"> 学号:<input type="text" name="stuno"> <br><br> 密码:<input type="password" name="stupassowrd"> <br><br> <input type="submit" value="登录" name="submit"> <a href="regist.jsp" role="button">注册</a> <a href="index.jsp">返回</a> </form> </body></html>regist.jsp 学生注册 <%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%><!DOCTYPE html><html><head><meta charset="UTF-8"><title>注册</title> <!-- Bootstrap CSS --> <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" integrity="sha384-ggOyR0iXCbMQv3Xipma34MD+dH/1fQ784/j6cY/iJTQUOhcWr7x9JvoRxT2MZw1T" crossorigin="anonymous"></head><body><h2 align=center>注册页面</h2> <center> <form action="RegisterServlet" method="post" > <table border="1"> <tr> <td>学号:</td> <td><input name="userNo"></td> </tr> <tr> <td>姓名:</td> <td><input name="userName"></td> </tr> <tr> <td>密码:</td> <td><input name="password" type="password"></td> </tr> <tr> <td>院系:</td> <td><input name="major"></td> </tr> <tr> <td>年级:</td> <td><input name="grade"></td> </tr> <tr> <td>班级:</td> <td><input name="sclass"></td> </tr> <tr align="center"> <td colspan="2"><input type="submit" value="提交注册"><input type = "reset" value = "重置"></td> </tr> </table> </form> 您有账号?<a href="login.jsp"><front color="GREEN" >点击直接登录</front></a> </center> </body></html>studentIndex.jsp 学生选课主页 ...

May 30, 2019 · 17 min · jiezi

全栈开发入门实战后台管理系统

本文首发于 GitChat 平台,免费 Chat,链接:全栈开发入门实战:后台管理系统 感谢你打开了这篇 Chat,在阅读之前,需要让你了解一些事情。 第一,本 Chat 虽然免费,不代表没有价值,我会将个人全栈开发的经历叙述给你,希望对你有一些帮助;第二,文中所使用的技术栈并非最新,也并非最优。后台管理系统更多是 2B 端的产品,通常是业务优先。本 Chat 的目的是为了让你能够快速上手全栈开发。第三,本 Chat 虽然名为全栈开发,但是不会带你做完一个完整的后台管理系统项目。一是由于篇幅有限,二是由于时间关系,个人精力也有限。 正文本 Chat 的内容,正如 Chat 简介中所描述,将分为以下 5 大块: 开发准备前台样式数据库连接前后台交互线上部署你可能会发现,好像不知道要做什么,没错,后台管理系统一般都是企业内部定制开发,通常是对业务的数据管理,具体做什么功能由业务决定,但多数功能都是围绕着表格或者表单。 上面列举的仅仅是全栈开发的大致流程。首先,要做一些准备工作,例如:开发环境、编辑器环境以及依赖包配置等等工作;其次,我们要选定一个后台模版样式,快速套用,实现业务功能。(当然,你要自己开发也行,但不建议这么做,除非为了学习);然后,根据业务做数据库的设计,编写后台数据处理逻辑,以及前后台数据交互等功能;最后,测试并部署上线。 这里的示例,将实现一个学生数据的在线管理需求,其实就是一个在线表格,包括添加,删除功能,系统层面包括登录退出功能。麻雀虽小,五脏俱全,整体架子搭好了,再在上面添加功能就简单多了。好了,现在就开始全栈之旅吧。 开发准备启动项目首先要做的是,开发环境的安装,这里就不多说了,关于 Node 环境的安装,默认你已经搞定了。 既然采用 Express 作为 Web 框架,Express 也是要安装的,有了 Node 环境,安装 Express 就简单多了。我们直接上手 Express 的脚手架,全栈开发关键要速度。 npm install express-generator -g一定记得是全局安装。安装完成之后,输入 express -h 可以查看帮助。这里选用 ejs 模版引擎,为什么?因为我顺手而已,这个不重要。找个合适的目录,运行下面命令: express -e node-web-fullstack-demo生成项目目录之后,首先要安装依赖,如下命令: cd example-node-web-fullstacknpm install等待安装完成,我们就可以启动项目了,使用命令 npm start ,去浏览器中,打开网址:http://localhost:3000,看到写着 Express 的首页,代表你的项目启动成功了。 编辑器环境配置一个好的编码环境,可以让你项目开发效率加倍。 首先介绍一个编辑器配置 EditorConfig,这是一个编辑器的小工具。它有什么作用呢?简而言之,就是让你可以在不同的编辑器上,获得相同的编码风格,例如:空格缩进还是 Tab 缩进?缩进几个空格? 你可能觉得诧异,这个不是在编辑器上设置就可以了吗?没错,假设你从始至终都是在同一个电脑同一个编辑器上编码,那么可以忽略它。如果存在多电脑配合,亦或是多个编辑器配合,那么它就是神器。它几乎支持所有的主流编辑器,不用单独去编辑器中设置,配置文件就在项目中,用那个编辑器打开项目,都能获得一致的编码风格。 ...

May 30, 2019 · 5 min · jiezi

Windows安装MySQL57教程

导读:我们日常学习可能会需要在本地安装MySQL服务,也遇到过小伙伴探讨关于Windows系统安装MySQL的问题。在这里建议大家安装MySQL5.7版本,当然想尝试8.0版本的同学也可以参考安装。本篇文章以MySQL5.7.23版本为例,一步步的为大家总结出安装步骤,希望对大家有所帮助! 1.检查及卸载原版本我们可以检查下我们的系统服务确定下有没有安装过MySQL,打开Windows系统服务有以下两种方式: 右击我的电脑/计算机,点击管理,打开计算机管理,依次选择服务和应用程序——服务。使用快捷命令:同时按下win+r键,在运行窗口中输入services.msc,即可打开服务。打开系统服务后页面如下,可以看到我的电脑中已经安装有MySQL,下面我将其卸载,若你的电脑没有MySQL服务则不需要操作此步。 现在我们打开cmd命令行来卸载MySQL: 停止MySQL服务   卸载MySQL   2.下载MySQL安装包下载地址:https://downloads.mysql.com/archives/community/选择5.7.23 Windows版本进行下载 3.解压安装包并配置环境变量将压缩包放在一个合适的盘进行解压,我这里放在了E盘,解压后建议将文件夹重命名为mysql5.7.23。建议安装前先配置下环境变量:右击我的电脑/计算机,点击属性,打开高级系统设置,点击环境变量。变量名:MYSQL_HOME变量值:E:mysql5.7.23path里添加:%MYSQL_HOME%bin 4.创建数据目录及配置文件此版本MySQL并没有创建data目录及my.ini。在MYSQL_HOME目录下创建data目录,建议将data目录设为E:mysql5.7.23data。另外,创建Uploads目录作为MySQL导入导出的目录。my.ini建议放在MYSQL_HOME目录下,简单配置可参考: [mysqld]port=3306character_set_server=utf8basedir=E:\mysql5.7.23datadir=E:\mysql5.7.23\dataserver-id=1sql_mode=NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTIONlower_case_table_names=1innodb_file_per_table = 1log_timestamps=SYSTEMlog-error = error.logslow_query_log = 1slow_query_log_file = slow.loglong_query_time = 5log-bin = binlogbinlog_format = rowexpire_logs_days = 15log_bin_trust_function_creators = 1secure-file-priv=E:\mysql5.7.23\Uploads[client] default-character-set=utf8完成之后我们的目录结构变成这样了 5.初始化数据库cmd命令行进入E:mysql5.7.23bin目录,执行mysqld --initialize-insecure执行完毕之后,在data目录下会生成很多文件。 6.注册并启动MySQL服务执行mysqld –install MySQL57安装服务(install后面是服务的名字,我们这里以MySQL57作为mysql5.7的服务名)net start MySQL57启动MySQL服务。 7.登录并修改密码提醒大家,由于初始化设置或版本差异,有些版本安装完成后root是空密码,有些是临时密码,我们需要查看error log日志提示。打开error日志,发现我这里是空密码。下面我们命令行登录 修改下密码:若需要配置root用户可以远程访问,则可以执行以下语句:接下来我们就可以用Navicat等工具登录了! 8.附送备份脚本额外赠送大家逻辑备份脚本哦,如果你想每天备份,可以将脚本加入计划任务中,每天定时执行。我们可以在E盘下创建一个MySQLdata_Bak目录,此目录下创建mysql_backup目录存放备份文件,mysql_bak.bat是备份脚本,脚本内容如下(自动删除7天前的备份文件): rem auther:wangrem date:20190526rem ******MySQL backup start********@echo offforfiles /p "E:\MySQLdata_Bak\mysql_backup" /m backup_*.sql -d -7 /c "cmd /c del /f @path"set "Ymd=%date:~0,4%%date:~5,2%%date:~8,2%0%time:~1,1%%time:~3,2%%time:~6,2%""E:\mysql5.7.23\bin\mysqldump" -uroot -p123456 -P3306 --default-character-set=utf8 -R -E --single-transaction --all-databases > "E:\MySQLdata_Bak\mysql_backup\backup_%Ymd%.sql"@echo onrem ******MySQL backup end********整体目录结构如下,双击运行下mysql_bak.bat脚本即可备份我们所有的数据库。 ...

May 29, 2019 · 1 min · jiezi

MySQL复制表结构和数据

mysql复制表有两种方式,create table as和create table like,这两者还是有差别,需要根据不同的使用场景去选择1、create table as,可以复制表结构,但不能复制索引;可以在复制表结构的同时复制数据复制表结构 create TABLE new_table as select * from old_table where 1=0;复制表结构和数据 create table new_table as select * from old_table;2、create table like,可以复制表结构和索引复制表结构create table new_table like old_table; 欢迎订阅「K叔区块链」 - 专注于区块链技术学习 博客地址:http://www.jouypub.com简书主页:https://www.jianshu.com/u/756c9c8ae984segmentfault主页:https://segmentfault.com/blog/jouypub腾讯云主页:https://cloud.tencent.com/developer/column/72548

May 29, 2019 · 1 min · jiezi

TiDB-在平安核心系统的引入及应用

作者:何志勇本文转载自公众号「平安科技数据库产品团队」。 2019 年 5 月 9 日,平安科技数据库产品资深工程师何志勇在第十届数据库技术大会 DTCC 上分享了《TiDB 在平安核心系统的引入及应用》,通过对 TiDB 进行 POC 测试,详细解析如何选择适用于金融行业级别的开源分布式数据库,以及平安“财神节”活动中引入 TiDB 的全流程应用实践案例分享。本文根据演讲内容整理。 <center>何志勇 平安科技数据库产品团队 资深工程师</center> 一、TiDB 引入的 POC 测试作为一名运维人员,引入一个新的数据库产品前必须要明确几点: 从业务的角度,引入的产品能否满足业务基本需求和使用场景。从运维管理角度看,这产品必须是可运维、可管理的,并且我们需要对其相应的功能与特性,要有一个很好的了解。产品性能稳定。所以在我们引入前从以下六个方面分别对 TiDB 进行测试验证,其中功能与架构、配置与管理、备份与恢复都是针对我们运维管理,SQL 特性、基准测试、应用场景测试则是应对业务需求和业务场景的。 1. 功能与架构TiDB 事务隔级别为 SI,支持 Spark 生态,支持动态扩容,跨数据中心部署。 这是 TiDB 官网最新的架构图: 从左至右看,可以通过 MySQL 或 MySQL 客户端接入 TiDB,TiDB 有 TiDB、PD、TiKV 三个组件,组件之间功能相互独立,需独立部署,分别负责计算、调度、存储功能;同时又相互协作,共同完成用户请求处理。在 TiKV 层各节点是使用 Raft 协议保证节点间数据的一致性,同时它还提供 Spark 接口供大数据分析。 从上往下看,可通过 Data Miaration 工具从 MySQL 迁移到 TiDB,同时提供备份恢复功能、内部性能监控监测及诊断、支持容器化部署。 TiDB 从架构及生态上基本上具备了传统数据库应有的功能。 2. SQL 特性兼容 mysql 语法,2.0 版本不支持窗口函数、分区表、视图、trigger 等。 ...

May 29, 2019 · 2 min · jiezi

mysql学习InnoDB数据结构

原来知道有一些索引失效的条件,最近看了看mysql底层数据结构,明白了为什么会失效 ,记录之。众所周知,常用的mysql数据引擎有两种,今天全是以InnoDB为基础开启探索之旅的,另一种有时间再说吧。 数据页与数据行我们都知道,数据库数据是存在磁盘中的,不过真正处理数据是在内存中进行的。这就需要从硬盘上不断地把数据读到内存中,由于内存和磁盘速度差了好几个数量级,所以为了避免频繁交互带来的性能问题,mysql一次会多读取一些,是多少呢?读一页。一页有16KB,也就是说一次读取一般都是16KB的倍数。页是硬盘内存交互的基本单位。 我们平时所说的一条记录叫数据行,InnoDB有四种不同类型的数据行,Compact、Redundant、Dynamic和Compressed。主要介绍下Compact 为了方便后面说明,建个表: CREATE TABLE `user` ( `id` int(11) NOT NULL AUTO_INCREMENT, `name` varchar(20) DEFAULT NULL, `age` smallint(3) DEFAULT NULL, PRIMARY KEY (`id`)) ENGINE=InnoDB AUTO_INCREMENT=111 DEFAULT CHARSET=utf8; 变长字段长度列表:类似于varchar() 这种可变长度,记录某个属性的长度,方便快速读取某属性的值。长度值是倒叙存放的。Null值列表:记录可为空的那些值,是否为空。为了方便说明举例: id name age99 haha (null)1 表示 这个属性为null,0表示这个属性不为null。所以name对应着0,age对应着1。由于是倒叙存放的,所以 Null值列表 这个地方存放的是 10(age,name); 记录头信息:数据有很多,关键的:delete_mask:标记该记录是否被删除record_type:表示当前记录的类型,0表示普通记录,1表示B+树非叶子节点记录,2表示最小记录,3表示最大记录。 接下来就是真实数据了,值得一提的是,还有三个隐藏项: row_id:如果没有主键ID,数据库会自动生成一个行的标识ID。所以这个值是可选的。transaction_id:事务IDroll_pointer:回滚指针。页行关系如上图所示,是一张数据页内部结构。一个16KB的页,内部存放着很多行,比如说那3条记录,除此之外,内部存放着两个特殊的记录,最小记录和最大记录。数据页内部记录之间是以单链表的形式存放的,头尾分别是那两个特殊的记录。在内存中有很多页,页和页之间是用双链表连接的。这样方便快速定位到数据在哪一页上。 B+ 索引聚簇索引ok,现在知道了数据页、数据行,和它们之间的数据结构之后,就可以看看我们所谓的索引了。正如开头所说的,这边只介绍InnoDB的聚簇索引,另一种搜索引擎,先不提它(嗯,现在甚至连名字都不提)。 聚簇索引,就是说有一颗树,叶子节点就是真实数据行所构成的数据页。 一般为了搜索快一点,我们主键都是自动生成的(例如咱们的User表),所以最下面那层是根据id排序生成的。最底下那层的叶子节点是真实的数据,有4页,每页里面有一个单链表,就是我们的真实数据行。第二行有两页,每页中也是有个数据行构成的单链表,这是的数据行只包含了页码(最底下那层某页)、某页最大id,由此可见,第二行比最底下那行页数少了很多很多。就这样,一层一层的抽取,一定会有一个所谓的跟页。我们搜索数据就是从跟页开始的,一层一层往下找的。由于一个数据页可以存放16KB数据,所以三四层的树状图就已经能存放很多很多数据了,所以不要担心树会很深。再强调一下,页内是单链表,同层的页和页之间是双链表。 二级索引上面那是以主键为搜索条件的索引,一般这棵树是自动生成的。 我们往往还会自己建立索引,比如给age添加索引。与聚簇索引类似,只不过叶子节点存的不是所有数据(并且根据age大小排序),而是存的该age属性和主键id,非叶子节点寸的是页码和下面那层某页最大的age值。这样,你确定了要搜的是哪些主键,还要回表(拿着这些主键回去聚簇索引找)去查询真实的数据。这边脑洞一下,即使你给age创建了索引,真正执行的时候,也不一定是通过查看二级索引,再回表的方式查数据(比如说通过二级索引搜索出来的是所有的id,再回表查询,得不偿失啊,还不如直接从聚簇索引直接去搜呢)。也可能根据聚簇索引直接搜索。具体采用哪种方式mysql自己会评估。 联合索引还有种特殊的二级索引,联合索引,比如说给(name、age)添加联合索引,底层数据结构和普通二级索引没什么区别,只不过叶子节点存的不是所有数据(并且先根据name大小排序,name相同的情况下再根据age排序),而是存的该name、age属性和主键id,非叶子节点寸的是页码和下面那层某页最大的name值。所以如果搜索条件只有age,没有name的话,联合索引会失效,所以要遵循最左原则。

May 28, 2019 · 1 min · jiezi

Tshare校园资源分享平台网站开发四之功能模块设计

上一篇博客地址:Tshare校园资源分享平台(网站开发三之数据库连接) 功能设计虽然我们能访问web站点,能连接数据库了,但是并不意味着我们马上就要开始写代码,我们得先分析一下我们的网站都需要实现哪些功能,这样我们才能针对如何实现这些功能进行编码。 宣传页由于网站的主要目的是校园内部提供服务,所以不是每一个人都能享受网站的服务,所以制作一个宣传首页用于吸引用户,也在此首页中实现用户的注册、登录功能。 资料分享平台当用户注册完之后登录网站,应该能够互相分享自己手中的资源(主要指学习资源,试卷、课件等等)。所以要提供文件的上传、搜索、预览、下载功能。 后续扩展功能闲置交易、表白墙、失物招领等等。 详细设计用户的注册用户注册必须使用校内教育邮箱进行注册,所以我们需要给邮箱发送一个验证码,只有邮箱验证吗验证成功才能进行注册。所以需要有发送邮件的功能 用户的登录用户登录只需要验证用户名和密码。为了让用户有良好的体验,可以设置7天内自动登陆,所以在用户登录的时候将用户名和密码进行加密后写入浏览器cookie。所以需要有加密功能和cookie设置读取功能。 文件上传通过收集身边的同学的学习资料信息,设计文件上传时需要填写的表单信息。同时只能上传单个文件,如果要上传文件夹需要压缩为zip后才能上传。而上传的zip压缩包在服务器端需要解压缩成一个文件夹保存。所以需要提供zip压缩包解压缩功能。 文件搜索通过关键字搜索文件,搜索时采用模糊搜索,可以对整个关键字进行模糊搜索,还可以将关键字进行中文分词后再依次模糊搜索。所以需要提供中文分词的功能。 文件预览我们决定将最终的预览文件定为png图片,也就是说所有可以预览的文件类型我们都以png格式显示。对于word类型的文件,需要先转为pdf,然后选取pdf前10页进行拆分,然后将拆分得到的pdf转为png,最后将所有的png进行合并为一张长图。所以需要提供有word转pdf的功能、pdf拆分的功能、pdf转png的功能以及png合并功能。 文件下载如果下载的是文件夹,需要将文件夹压缩为zip再下载。所以需要提供有zip压缩功能 总结以上所有的功能都是从后端的角度分析的(毕竟我在小组中负责的是后端控制),那么根据正常的流程图,我们可以开始编写代码了。应该先实现宣传页中的注册登录功能,在实现资料分享的上传、搜索、预览和下载功能。由于我们的工程已经结束了,而且我也不可能一行代码一行代码的写在博客中,所以我会按板块来写后面的博客。

May 28, 2019 · 1 min · jiezi

Tshare校园资源共享平台网站开发二之主机浏览器访问虚拟机apache

上一篇博客地址:Tshare校园资源分享平台(网站开发一之环境搭建) 回顾上一篇博客我们已经在一个虚拟机上搭建好了apache+mysql+php的环境,并且在虚拟机的浏览器中成功的访问到了web站点中的index.php。 新内容本篇博客将会讲解如何在主机的浏览器中访问到虚拟机的apache服务,毕竟虚拟机流畅性不如主机,而且主机是Windows系统或mac os系统,可以方便地下载安装自己喜欢地浏览器(这里建议使用Chrome浏览器)。 让虚拟机和主机能够互ping前面说过,我选择的是VMware虚拟机,在VMware上实现虚拟机和主机通讯并不需要繁琐的步骤。 1.将虚拟机的网络连接模式设置为NAT模式(网络地址转换) 2.点击编辑,选择虚拟网络编辑器,点击右下角的更改设置,然后修改子网ip和子网掩码 3.将多余的网络移除,只剩下VMnet8 4.选择NAT模式(与虚拟机共享主机IP),在点击NAT设置,设置网管IP为192.168.10.2 5.将两个钩选中,然后点击DHCP设置 6.设置动态IP范围 7.打开网络适配器中的VMnet8属性 8.设置其ip地址和子网掩码 9.重启虚拟机,打开终端输入ifconfig查看虚拟机ip地址,并尝试在主机的命令行下ping这个ip 主机通过虚拟机ip访问虚拟机的apache服务centos系统的防火墙会禁止外网访问某些端口,除非让防火墙开放端口。当然seLinux也是一个让人非常头疼的东西,很多时候即使防火墙开发端口,仍然不能访问,原因就是selinux在搞鬼。所以首先我们就把selinux关闭了。 vim /etc/selinux/config#将SELINUX=enforcing改为SELINUX=disable#保存退出,重启虚拟机,开启apache服务,在主机浏览器中访问虚拟机ip 访问成功!(如果访问失败,可能是防火墙没有开启80端口,可以百度如何让防火墙开放端口的指令) 主机上连接mysql如果你的主机上下载mysql的图形操作界面(navicat for mysql),还可以在主机上远程连接虚拟机的mysql(当然前提是虚拟机开启了mysql服务) 此时连接会报错,告诉我们192.168.10.1这个ip地址无法远程连接到虚拟机数据库,需要对虚拟机数据库做一些更改 #登录mysql/var/mysql/bin/mysql -uroot -ppassword:此处输入密码mysql> use mysql;mysql> update user set host = '%' where user ='root';mysql> flush privileges;#重启mysql服务再次远程连接,即可连接到虚拟机的数据库。当然我这里直接使用了root用户登录,你可以创建一个新用户 总结虚拟机和主机能够通讯是关键,然后是绕过防火墙,就能达到我们的目的了。下一篇博客地址:Tshare校园资源分享平台(网站开发三之数据库连接)

May 28, 2019 · 1 min · jiezi

Tshare校园资源分享平台网站开发三之数据库连接

上一篇博客:Tshare校园资源分享平台(网站开发二之主机浏览器访问虚拟机apache) 新内容环境搭建、web站点访问和数据库连接是本次开发的三个最基础的前提,这篇博客之后我们将开始真正的开发之旅 php连接数据库在虚拟机上安装sublime text 3下载地址:http://www.sublimetext.com/3#复制到/mnt目录下,直接解压缩tar -jxvf sublime_text_3.tar.bz2#配置桌面快捷方式#1. 将解压缩后目录中的sublime_text.desktop复制到/usr/share/applications下#2. 修改/usr/share/applications/sublime_text.desktop#3. 将快捷方式复制到桌面,双击即可打开sublime编辑器cp /mnt/sublime_text_3/sublime_text.desktop /usr/share/applicationsvim /usr/share/applications/sublime_text.desktop#将Exec修改为/mnt/sublime_text_3/sublime_text#将icom修改为/mnt/sublime_text_3/Icon/48x48/sublime-text.png#保存退出 主机连接上虚拟机的数据库,并创建一个新的测试数据库test 编写Db.php连接数据库,编写test.php操作数据库Db.php<?php/** * 专门用来操作数据库的类,继承mysqli类 */class Db extends mysqli{ public function __construct() { $host = "192.168.10.31"; // 数据库的主机名称,此处也就是我们虚拟机的ip地址 $user = "root"; // 数据库用户名,我们使用root用户连接 $password = "fuhao520999"; // root用户的密码,在安装mysql时我们修改过 $dbname = "test"; // 连接的目标数据库名,为我们刚才创建的test数据库 parent::__construct($host, $user, $password, $dbname); }}?>test.php<?phpinclude_once("Db.php");$db = new Db();var_dump($db);?>主机浏览器访问 此时我们成功的在php中连接上数据库了。有一个我没想到的是,竟然不需要我配置mysqli的扩展,可能是之前编译安装php的时候已经把mysqli扩展安装了。 总结本次博客内容虽然不多,但是却很重要,如果有的朋友遇到了缺少mysqli扩展的错误,可以参考以下链接:http://www.jquerycn.cn/blog/p...当然我们不需要重新下载php的源代码,因为之前我们已经下载过了,直接到指定的目录找到扩展文件,编译安装即可。

May 28, 2019 · 1 min · jiezi

MySQL

MySQL服务器逻辑架构图 它是由C和C++编写的,对于数据库连接还得明确以下两个概念: ODBC(Open Database Connectivity):是用于连接数据库管理系统的接口协议,与操作系统、编程语言、数据库系统无关,只需要使用该数据库提供的OBJC driver。JDBC(Java DatabBase Connectivity):是由JAVA语言提供的数据库接口API,可以用于连接实现了JDBC driver的数据库,比如:MySQL提供的mysql-connector-java.jar

May 27, 2019 · 1 min · jiezi

必看的数据库使用规范

导读: 关于MySQL数据库规范,相信大家多少看过一些文档。本篇文章给大家详细分类总结了数据库相关规范,从库表命名设计规范讲起,到索引设计规范,后面又给出SQL编写方面的建议。相信这些规范适用于大多数公司,也希望大家都能按照规范来使用我们的数据库,这样我们的数据库才能发挥出更高的性能。 关于库:【强制】库的名称必须控制在32个字符以内,英文一律小写。【强制】库的名称格式:业务系统名称_子系统名。【强制】库名只能使用英文字母,数字,下划线,并以英文字母开头。【强制】创建数据库时必须显式指定字符集,并且字符集只能是utf8或者utf8mb4。创建数据库SQL举例:Create database db1 default character set utf8;【建议】临时库、表名以tmp_ 为前缀,并以日期为后缀,备份库、表以 bak_ 为前缀,并以日期为后缀。关于表【强制】表和列的名称必须控制在32个字符以内,表名只能使用字母、数字和下划线,一律小写。【强制】表名要求模块名强相关,同一模块使用的表名尽量使用统一前缀。【强制】创建表时必须显式指定字符集为utf8或utf8mb4。【强制】列名尽量不用关键字(如type,order等)。【强制】创建表时必须显式指定表存储引擎类型,如无特殊需求,一律为InnoDB。【强制】建表必须有comment。【强制】对于超过100W行的大表进行alter table,必须经过DBA审核,并在业务低峰期执行,多个alter需整合在一起。因为alter table会产生表锁,期间阻塞对于该表的所有写入,对于业务可能会产生极大影响。【建议】建表时关于主键:表必须有主键(1)强制要求主键为id,类型为int或bigint,且为auto_increment 建议使用unsigned无符号型。(2)标识表里每一行主体的字段不要设为主键,建议设为其他字段如user_id,order_id等,并建立unique key索引。因为如果设为主键且主键值为随机插入,则会导致innodb内部page分裂和大量随机I/O,性能下降。 【建议】核心表(如用户表)必须有行数据的创建时间字段create_time和最后更新时间字段update_time,便于查问题。【建议】表中所有字段尽量都是NOT NULL属性,业务可以根据需要定义DEFAULT值。 因为使用NULL值会存在每一行都会占用额外存储空间、数据迁移容易出错、聚合函数计算结果偏差等问题。【建议】中间表用于保留中间结果集,名称必须以tmp_ 开头。备份表用于备份或抓取源表快照,名称必须以bak_开头。中间表和备份表定期清理。【示范】一个较为规范的建表语句: CREATE TABLE user_info ( `id` int unsigned NOT NULL AUTO_INCREMENT COMMENT '自增主键', `user_id` bigint(11) NOT NULL COMMENT '用户id', `username` varchar(45) NOT NULL COMMENT '真实姓名', `email` varchar(30) NOT NULL COMMENT '用户邮箱', `nickname` varchar(45) NOT NULL COMMENT '昵称', `birthday` date NOT NULL COMMENT '生日', `sex` tinyint(4) DEFAULT '0' COMMENT '性别', `short_introduce` varchar(150) DEFAULT NULL COMMENT '一句话介绍自己,最多50个汉字', `user_resume` varchar(300) NOT NULL COMMENT '用户提交的简历存放地址', `user_register_ip` int NOT NULL COMMENT '用户注册时的源ip', `create_time` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '创建时间', `update_time` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '修改时间', `user_review_status` tinyint NOT NULL COMMENT '用户资料审核状态,1为通过,2为审核中,3为未通过,4为还未提交审核', PRIMARY KEY (`id`), UNIQUE KEY `uniq_user_id` (`user_id`), KEY `idx_username`(`username`), KEY `idx_create_time_status`(`create_time`,`user_review_status`)) ENGINE=InnoDB DEFAULT CHARSET=utf8 COMMENT='网站用户基本信息'关于索引【强制】InnoDB表必须主键为id int/bigint auto_increment,且主键值禁止被更新。【强制】InnoDB和MyISAM存储引擎表,索引类型必须为BTREE。【建议】主键的名称以 pk_ 开头,唯一键以 uniq_ 或 uk_ 开头,普通索引以 idx_ 开头,一律使用小写格式,以字段的名称或缩写作为后缀。【建议】单个表上的索引个数不能超过8个。【建议】在建立索引时,多考虑建立联合索引,并把区分度最高的字段放在最前面。如列userid的区分度可由select count(distinct userid)计算出来。【建议】在多表join的SQL里,保证被驱动表的连接列上有索引,这样join执行效率最高。【建议】建表或加索引时,保证表里互相不存在冗余索引。对于MySQL来说,如果表里已经存在key(a,b),则key(a)为冗余索引,需要删除。SQL编写【强制】程序端SELECT语句必须指定具体字段名称,禁止写成 *。【强制】程序端insert语句指定具体字段名称,不要写成insert into t1 values(…)。【强制】除静态表或小表(100行以内),DML语句必须有where条件,且使用索引查找。【强制】where条件里等号左右字段类型必须一致,否则无法利用索引。【强制】WHERE 子句中禁止只使用全模糊的LIKE条件进行查找,必须有其他等值或范围查询条件,否则无法利用索引。【强制】索引列不要使用函数或表达式,否则无法利用索引。如where length(name)='Admin'或where user_id+2=10023。【建议】insert into…values(XX),(XX),(XX).. 这里XX的值不要超过5000个。值过多虽然上线很很快,但会引起主从同步延迟。【建议】SELECT语句不要使用UNION,推荐使用UNION ALL,并且UNION子句个数限制在5个以内。因为union all不需要去重,节省数据库资源,提高性能。【强制】禁止跨db的join语句。【建议】不建议使用子查询,建议将子查询SQL拆开结合程序多次查询,或使用join来代替子查询。【建议】线上环境,多表join不要超过5个表。【建议】在多表join中,尽量选取结果集较小的表作为驱动表,来join其他表。【建议】批量操作数据时,需要控制事务处理间隔时间,进行必要的sleep。建议】事务里包含SQL不超过5个 因为过长的事务会导致锁数据较久,MySQL内部缓存、连接消耗过多等问题。【建议】事务里更新语句尽量基于主键或unique key,如update … where id=XX; 否则会产生间隙锁,内部扩大锁定范围,导致系统性能下降,产生死锁。【建议】减少使用order by,和业务沟通能不排序就不排序,或将排序放到程序端去做。Order by、group by、distinct这些语句较为耗费CPU,数据库的CPU资源是极其宝贵的。【建议】order by、group by、distinct这些SQL尽量利用索引直接检索出排序好的数据。如where a=1 order by b可以利用key(a,b)。【建议】包含了order by、group by、distinct这些查询的语句,where条件过滤出来的结果集请保持在1000行以内,否则SQL会很慢。 ...

May 27, 2019 · 1 min · jiezi

MySQL数据表合并去重

场景:爬取的数据生成数据表,结构与另一个主表相同,需要进行合并+去重 解决:(直接举例)首先创建两个表pep,pep2,其中pep是主表 CREATE TABLE IF NOT EXISTS `pep/pep2`(`id` INT UNSIGNED AUTO_INCREMENT,`no` VARCHAR(100) NOT NULL,PRIMARY KEY ( `id` ))ENGINE=InnoDB DEFAULT CHARSET=utf8;然后向pep中插入两条数据,pep2中插入一条与pep中相同的一条数据 insert into pep(no) values('abc');insert into pep(no) values('caa');insert into pep2(no) values('abc');将pep2的数据插入pep中 insert into pep (no) select no from pep2;分组去重创建新的临时表tmp create table temp111 select id,no from pep group by id,no;注意:创建完这个表的id字段类型已经不是主键自增 删除pep表,并将tmp表重命名为pep drop table pep;alter table tmp rename to pep;查看desc结构和select * from pep发现id的字段类型变了,这里需要改回原来的类型; alter table `pep` add primary key (`id`);alter table `pep` modify id int auto_increment;还有可以使用join来做去重,更快的还可以添加一个字段(可以是几个字段+起来的的md5值),给这个字段创建一个唯一索引unique,以后插入数据的时候,自动回过滤掉重复的数据。

May 27, 2019 · 1 min · jiezi

Linux运维mysql数据库的备份与恢复

运维工程师的日常工作需要对各种数据进行备份,其中数据库数据的备份当属重点之一,为了方便管理,选择哪种备份方案是很重要的。数据备份种类全量备份全量备份就是指对某一个时间点上的所有数据或应用进行的一个完全拷贝。实际应用中就是用一盘磁带对整个系统进行全量备份,包括其中的系统和所有数据。 特点 备份的数据全面而且最为完整数据量大的时候备份时间长备份数据会存在大量重复信息增量备份增量备份是指在一次全备份或上一次增量备份后,以后每次的备份只需备份与前一次相比增加或者被修改的文件。这就意味着,第一次增量备份的对象是进行全备后所产生的增加和修改的文件;第二次增量备份的对象是进行第一次增量备份后所产生的增加和修改的文件,如此类推。 特点 与全量备份相比,没有重复的备份数据备份数据量不大,备份恢复的时间短数据恢复麻烦,必须具有上一次全备份和所有增量备份磁带,并且需要按照全量备份到增量备份的顺序反推进行恢复差异备份差异备份是指在一次全备份后到进行差异备份的这段时间内,对那些增加或者修改文件的备份。 特点 备份时间短,节省磁盘空间恢复所需的磁带少,恢复时间短比较数据备份的数据量(大>>小):全量备份>差异备份>增量备份 数据的恢复时间(快>>慢):全量备份->差异备份->增量备份 mysql数据库备份工具mysqldump工具mysqldump是一款mysql逻辑备份的工具,它将数据库里面的对象(表)导出作为SQL脚本文件。它是mysql备份常用的备份方法,适合于不同版本mysql之间的升级、迁移等,不过在数据库比较大的时候,效率不高。 下面是mysqldump命令的常见用法: # 备份单个的数据库,如备份db1这个数据库mysqldump -uroot -p123456 db1 > /backup/db1_`date +%F`.sql# 备份所有数据库,-A参数mysqldump -uroot -p123456 -A > /backup/all_db.sql# 备份远程主机的数据库,-h指定IP地址,-P(大写P)指定端口mysqldump -uroot -p123456 -h192.168.30.4 -P3306 db1 > /backup/db1.sql# 只备份表结构,不备份数据,使用-d参数mysqldump -uroot -p123456 -d db1 > /backup/db1.sql# 只备份数据,不备份表结构,使用-t参数mysqldump -uroot -p123456 -t db1 > /backup/db1.sql # 备份指定的多个库,-B参数mysqldump -uroot -p123456 -B db1 db2 db3 > /backup/db123.sql# 备份指定的表,如备份db1库里面的stu表mysqldump -uroot -p123456 db1 stu > /backup/db1_stu.sql# 备份多个表mysqldump -uroot -p123456 库1 表1 表2 表3... > db_tables.sql# 恢复数据mysqldump -uroot -p123456 dbname < xxx.sql#或者mysqldump -uroot -p123456 < xxx.sql其他参数: ...

May 27, 2019 · 1 min · jiezi

数据库优化第一步数据类型

阅读原文:数据库优化第一步:数据类型 为什么选择合适的数据类型很重要?因为数据类型会影响存储空间的开销,也会影响数据的查询效率,可以说这是你优化数据库的第一步要做的事情。 疑问本文的前提环境是:MySQL 5.7 , UTF-8 Unicode char与varchar的区别和选择?CHAR是固定长度,长度范围为0-255字符,存储时,如果字符数没有达到定义的位数,会在后面用空格补全存入数据库中,比指定长度大的值将被截短。VARCHAR是变长长度,长度范围为0-21845(utf8)或16383(utf8mb4)字符,存储时,如果字符没有达到定义的位数,也不会在后面补空格,当然还有一或两个字节来描述该字节长度varchar(10) 括号中的数字代表 字节 还是 字符 ?代表的是字符,无论英文或中文 都可以存储10个字符。 int(5) 括号中的数字代表 什么 ?数字5并不是代表存储的长度,int型的长度是4字节固定的,括号里的数字仅仅代表最小显示的宽度。 那我们设置它的意义何在呢? 其实当我们长度超过5的时候它是没用的,和没有设置一样,当长度没有超过5时,并且设置了zerofill(填充零),它会在不足的从左侧填充零,假如插入了数字 22 ,那么显示的是 00022 (navicat不显示,可在cmd中查看)。 所以你指定的数字和它的大小及存储的空间没有关系。 int 括号中的数字为什么默认11或10 ?int有符号数最小值: -2 1 4 7 4 8 3 6 4 8 总共11位 2 1 4 7 4 8 3 6 4 7 总共10位 所以你懂得…… 其它的整数类型以此类推。 现在为什么很少使用CHAR ?因为我们使用的是 InnoDB存储引擎,内部的行存储格式没有区分固定长度和可变长度列(所有数据行都使用指向数据列值的头指针),因此在本质上,使用固定长度的CHAR列不一定比使用可变长度VARCHAR列简单。 Value CHAR(4) 实际存储VARCHAR(4) 实际存储''' '4 bytes''1 bytes'ab''ab '4 bytes'ab'3 bytes'abcd''abcd'4 bytes'abcd'5 bytes'abcdef''abcd'4 bytes'abcd'5 bytes可以用上表来表示,当定义char时,不管你存入多少字符,都会占用到你定义的字符数,而用varchar时,则和你输入的字符数有关,会多一到两个字节来记录字节长度,当数据位占用的字节数小于255时,用1个字节来记录长度,数据位占用字节数大于255时,用2个字节来记录长度,还有一位来记录是否为nul值 ...

May 27, 2019 · 1 min · jiezi

mysql利用表对象数据文件恢复数据

数据库文件基础.frm文件: 只存储表的结构信息,frm文件跟数据库存储引擎无关,这也就是说,它和表的索引、数据都无关。MyISAM引擎.myd文件: 数据文件.myi文件:索引文件Innodb引擎ib_logfile0和ib_logfile1:重做日志文件,两个文件一模一样,之所以存在两个是,为了避免一个文件损坏后,而且MySQL crash之后,innodb无法恢复数据。ibdata1:数据文件根据《MySQL技术内幕》一书的介绍,innodb存在表空间的概念,是以共享表空间的格式,将数据都存入到一个文件中。介绍ibdata1,ibdata1是与存储引擎相关的,只在innodb存储引擎下出现,而且是mysql-server中所有innodb存储引擎的表,不分数据库都存储到ibdata1中,当然这个文件中还会存储其他信息,如索引等。当在MySQL中开启innodb_file_per_table后,那么将会在每个数据库对应的文件夹下,每张表将有存在两个对应文件,一个是.frm,另外一个是.ibd文件。这种情况成为私有表空间。但是这个时候共享表空间ibdata1,仍然是存在的。使用数据库文件恢复数据yum安装的mysql,数据目录是/var/lib/mysql,可以通过/etc/my.cnf查看。 MyISAM引擎表恢复数据直接备份.frm,.myd,.myi文件,然后再复制粘贴到目标数据库文件夹即可。 Innodb引擎表恢复数据如果是系统表空间的情况,一个笨办法就是建立一个新的mysql环境,将旧环境中的ibdata1文件和需要恢复的aa,bb等数据库文件夹复制到新mysql数据目录。然后重启mysqld守护进程就行。 systemctl restart mysqld下面是恢复的rbac数据库user表的数据 如果是私有表空间的话,虽然没实验过,但我猜想,直接复制.frm文件和.ibd文件到目标数据库即可。 参考文章利用数据库文件恢复MySQL数据

May 26, 2019 · 1 min · jiezi

Tshare校园分享平台网站开发一之环境搭建

       这学期开了一门称为软件工程的课,老师给我们布置了一个大作业。我们一个小组共有四个人,决定做一个校园资料分享平台。现在工作快要结束了,我决定将整个项目移植到Linux上,从创建虚拟机->环境搭建->php扩展等等,将这个过程写成连载的博客,供自己以后查阅,也让新手们少走一些弯路。环境搭建 第一步,下载一个linux镜像,我选择了centos7的镜像,这个在百度里面一搜就能搜到下载地址,一般选择DVD镜像;第二步,在VMware workstation上创建一个Linux的虚拟机。之所以选择VMware而不选择virtual box,是因为我通过血和泪的实践,觉得VMware更好用(ps:当初我用virtual box安centos7后花了好几天调分辨率都没有成功,centos7只支持4:3的分辨率,让我这个19201080的显示器看起来很难受,当然这个问题是可以解决的,不过用VMware就方便多了,其自带的tools会让我们的虚拟机能够使用19201080的分辨率)。由于虚拟机创建过程不是本次开发的重点,所以不会的朋友可以百度如何在VMware上安装Centos7。第三步,在虚拟机创建好之后,我们需要检测网络的连接:主机与虚拟机之间可以互ping,而且虚拟机可以访问外网,因为我们需要安装运行环境,如何让虚拟机连接到网络以及如何让主机与虚拟机之间可以互ping,百度以下你就知道了。第四步,我们选择使用Apache+php+mysql进行开发,但是我们租了一台服务器,所以开发的时候使用服务器上的数据库,不需要在本地下载mysql。所以我们只需要安装apache和php即可,可以使用yum源直接安装,安装教程百度即可。最后,当所有的环境都建好之后,我们需要知道如下几个文件: /etc/php.ini:这个文件是php的配置文件,php的扩展配置都在这个文件中进行配置; /usr/lib64/php/modules:这是php扩展文件的保存路径,这个路径可以使用phpinfo()看到,并不是每个人都在这个目录下; /etc/httpd/conf/httpd.conf:这是apache的配置文件; /var/log/httpd/error_log:这是apache的错误日志。环境测试 测试apache。首先开启apache服务(终端输入service httpd start)。centos虚拟机中自带一个Firefox可以使用这个浏览器,但是不建议,我在虚拟机中用这个浏览器感觉很难受。建议使用主机上的浏览器来访问虚拟机中的apache服务,这要求主机和虚拟机之间能够互通(能互ping),还要求linux虚拟机的防火墙开启80端口。如果这两样都满足了,还不能在主机的浏览器上访问虚拟机的apache,那么很有可能是SELinux这个东西在捣乱,反正虚拟机上也没有什么东西需要保护,可以直接把SELinux关闭。然后进行访问,在主机浏览器中输入虚拟机的ip地址,将会看到apache的测试页面。测试php。apache默认配置的web站点在/var/www/html目录下,在这个目录中编写一个测试代码index.php,写上几行测试代码,然后在主机浏览器中访问index.php,看能不能输出正确的结果。配置php基础环境 此处的配置环境并不是下载php也不是下载php扩展,而是修改httpd.conf来完成php的一些基础配置。首先我们需要将php代码和html代码都作为php代码进行解析,也就是说能在html文件中解析php代码,这个需要在<ifmodule mine_module>中加入两行代码: AddType application/x-httpd-php .html .htm .php AddType application/x-httpd-php-source .phps测试在html文件中编写php代码能否被解析。总结 由于有一些知识并不是本项目的重点,所以我一直在说“自己百度”,其实有些东西有些挫折很多人都遇到过并且都记录了下载,只要自己勤于查找,就会发现自己犯的错误,能够借助前人已经为铺好的路来解决。这一篇博客主要讲的是如何搭建环境,别看我只用了短短几句话描述,实际上如果对这些过程不熟练可能会花费你几天时间才能完成。下一篇博客开始引入已经写好的代码,配置所需要的php扩展,不会将每一句代码都拿出来解释,实际上这些东西只要会编程就都能写出来,不一样的是从Windows平台来到linux平台后,应该怎么解决一些问题。

May 26, 2019 · 1 min · jiezi

Java四种引用简介

引语:    我们知道java相比C,C++中没有令人头痛的指针,但是却有和指针作用相似的引用对象(Reference),就是常说的引用,比如,Object obj = new Object();这个obj就是引用,它指向的是真正的对象Object的地址,不过今天要说的是java中的四种引用。有人可能比较懵逼,四种引用?是的,从JDK1.2之后,java对引用这块的概念进行了扩充,按照引用的强度分为了四种引用:强引用,软引用,弱引用,虚引用。下面就让我们来看看这四种引用都具体的情况吧。 1.强引用1.1介绍:我们平时代码中使用得最多的引用,对象的类是:StrongReference。就比如上面说的Object obj = new Object();我们再熟悉不过了,作为最强的引用,只要引用还存在着,垃圾收集器就不会将该引用给回收,即使会出现OOM(内存溢出)。就是说这种引用只要引用还一直指向的对象,垃圾收集器是不会去管它的,所以它被称为强引用。不过如果 Object obj = new Object();obj = null;obj被赋值为了null,该引用就断了,垃圾收集器会在合适的时候回收改引用的内存。还有一种情况就是obj是成员变量,方法执行完了,obj随着被栈帧被回收了,obj引用也是一起被回收了。强引用的使用就不介绍了,地球人都知道。 2.软引用2.1介绍:软引用是用来描述一些有用但是非必须的对象。对应的类是SoftReference,它被回收的时机是系统内存不足的时候,如果内存足够,它不会被回收,内存不足了,可能会发生OOM了,软引用的对象就会被回收。这样的特性是不是就像缓存?是的,软引用可以用来存放缓存的数据,内存足够的时候一直可以访问,内存不足的时候,需要重新创建或者访问原对象。 2.2使用:其实不管是软引用,弱引用,还是虚引用,代码中使用方式都是像下面这样,使用对应的Reference将对象放入到构造函数当中,然后使用的地方reference.get()来调用具体对象。 Object obj = new Object();SoftReference<Object> softReference = new SoftReference<>(obj);softReference.get();同时可以使用ReferenceQueue来把引用和引用队列给关联起来: Object obj = new Object();ReferenceQueue<Object> refQueue = new ReferenceQueue<>();SoftReference<Object> softReference = new SoftReference<>(obj, refQueue);__所谓关联起来,其实就是当引用被回收的时候,会被添加到ReferenceQueue中,使用ReferenceQueue.poll()方法可以返回当前可用的引用,并从队列冲删除__。简单来说就是引用和引用队列关联起来(引用的构造函数传入队列),然后引用被回收的时候会被添加到队列中,然后使用poll()方法可以返回引用。 3.弱引用3.1介绍:虚引用比上面两个引用就更菜了,只要垃圾收集器扫描到了它,被弱引用关联的对象就会被回收。被弱引用关联对象的生命周期其实就是从对象创建到下一次垃圾回收。对应的类是WeakReference。 3.2使用:public static void main(String[] args) throws InterruptedException { Object obj = new Object(); ReferenceQueue<Object> refQueue = new ReferenceQueue<>(); WeakReference<Object> weakRef = new WeakReference<>(obj, refQueue); System.out.println("引用:" + weakRef.get()); System.out.println("队列中的东西:" + refQueue.poll()); // 清除强引用, 触发GC obj = null; System.gc(); Thread.sleep(200); System.out.println("引用:" + weakRef.get()); System.out.println("引用加入队列了吗? " + weakRef.isEnqueued()); System.out.println("队列中的东西:" + refQueue.poll()); /** * 输出结果 * 引用:java.lang.Object@7bb11784 * 队列中的东西:null * 引用:null * 引用加入队列了吗? true * 队列中的东西:java.lang.ref.WeakReference@33a10788 */ }可以看到当强引用被清除,手动触发GC后,弱引用回收,被加入到队列中了。 ...

May 26, 2019 · 1 min · jiezi

尝试用binlog恢复mysql数据

Binlog介绍:Binlog又称归档日志是专门用来记录逻辑的 (监控并记录你在干啥,比如有没有偷偷删表删库??)Binlog位于server层,因此所有的存储引擎都可以使用Binlog没有固定大小,会追加写入且不会覆盖旧的BinlogBinlog开启和配置:首先我们要检查下我们是否开启了Binlog输入命令: show variables like '%bin%'; 1,变量log_bin 为 on表示已开启 (如何开启? 直接my.cnf添加log_bin="log_bin_basername"即可) 2,变量log_bin_basename 为 binlog日志的文件名,还会自动接后缀.00000xx,每次重启mysql服务或者使用flush logs命令都会生成一个新的binlog文件 3,变量bin_format则表示日志记录的格式,共有三种格式,分别是statement,rows,mixed, statement 记录的是sql语句rows 记录的是对数据操作的上下文mixed 则兼容statement和rows,会自动根据场景来选择使用前两者的哪一种一般我们推荐使用mixed,因为statement存在隔离限制,如果再"rc/ru" 即 读未提交/读提交的隔离级别下,会产生不可重复读,配置主从后使用statement格式(因为只是记录sql)进行复制会导致主从数据不一致 接着我们先查看一下当前的isolation 输入命令:show variables like '%isolation%'; ps:5.7+变量名变为`tracsaction_isolation`,我这边是5.6版本的所以还是`tx_isolation`通过图可以看到,我这边隔离级别为rc,也就是读提交 对照上面讲的,rc 不支持 statement 格式,所以我们要切换格式为rows或者mixed 可以直接通过global 变量更改,或者直接修改my.cnf,我这里直接修改my.cnf 保存,重启服务,然后重新查看变量binlog_format,ok,已变更为mixed 建立测试数据并备份:建立一个test库,然后在test库中建立一个简单的t1表用以测试 CREATE TABLE `t1` ( `id` int(3) NOT NULL AUTO_INCREMENT, `num` int(4) DEFAULT NULL, PRIMARY KEY (`id`)) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8然后往t1表插入三条数据 insert into t1 (num) values(1),(2),(3); 这样我们测试表和备份数据就完成了,然后用mysqldump进行备份 mysqldump -u -h -p database > /dirs/xxx.sql ...

May 25, 2019 · 1 min · jiezi

去-BAT-面试总结了这-55-道-MySQL-面试题

1、一张表,里面有ID自增主键,当insert了17条记录之后,删除了第15,16,17条记录,再把Mysql重启,再insert一条记录,这条记录的ID是18还是15?(1)如果表的类型是MyISAM,那么是18.因为MyISAM表会吧自增主键的最大ID记录到数据文件里,重启MysQL自增主键的最大ID也不会丢失。(2)如果表的类型是InnoDB,那么是15.InnoDB表只是把自增主键的最大ID记录到内存中,所以重启数据库或者是对表进行OPTIMIZE操作,都会导致最大ID丢失。 2、Mysql的技术特点是什么?Mysql数据库软件是一个客户端或服务器系统,其中包括:支持各种客户端程序和库的多线程SQL服务器、不同的后端、广泛的应用程序编程接口和管理工具。 3、Heap表是什么?HEAP表存在于内存中,用于临时高速存储。 BLOB或TEXT字段是不允许的只能使用比较运算符=,<,>,=>,= <HEAP表不支持AUTO_INCREMENT索引不可为NULL 4、Mysql服务器默认端口是什么?Mysql服务器的默认端口是3306。 5、与Oracle相比,Mysql有什么优势?Mysql是开源软件,随时可用,无需付费。Mysql是便携式的带有命令提示符的GUI。使用Mysql查询浏览器支持管理 6、如何区分FLOAT和DOUBLE?以下是FLOAT和DOUBLE的区别: 浮点数以8位精度存储在FLOAT中,并且有四个字节。浮点数存储在DOUBLE中,精度为18位,有八个字节。 7、区分CHAR_LENGTH和LENGTH?CHAR_LENGTH是字符数,而LENGTH是字节数。Latin字符的这两个数据是相同的,但是对于Unicode和其他编码,它们是不同的。 8、请简洁描述Mysql中InnoDB支持的四种事务隔离级别名称,以及逐级之间的区别?SQL标准定义的四个隔离级别为: read uncommited :读到未提交数据read committed:脏读,不可重复读repeatable read:可重读serializable :串行事物 9、在Mysql中ENUM的用法是什么?ENUM是一个字符串对象,用于指定一组预定义的值,并可在创建表时使用。 Create table size(name ENUM('Smail,'Medium','Large'); 10、如何定义REGEXP?REGEXP是模式匹配,其中匹配模式在搜索值的任何位置。 11、CHAR和VARCHAR的区别?以下是CHAR和VARCHAR的区别: CHAR和VARCHAR类型在存储和检索方面有所不同CHAR列长度固定为创建表时声明的长度,长度值范围是1到255当CHAR值被存储时,它们被用空格填充到特定长度,检索CHAR值时需删除尾随空格。 12、列的字符串类型可以是什么?字符串类型是: SETBLOBENUMCHARTEXTVARCHAR 13、如何获取当前的Mysql版本?SELECT VERSION();用于获取当前Mysql的版本。 14、Mysql中使用什么存储引擎?存储引擎称为表类型,数据使用各种技术存储在文件中。 技术涉及: Storage mechanismLocking levelsIndexingCapabilities and functions. 15、Mysql驱动程序是什么?以下是Mysql中可用的驱动程序: PHP驱动程序JDBC驱动程序ODBC驱动程序CWRAPPERPYTHON驱动程序PERL驱动程序RUBY驱动程序CAP11PHP驱动程序Ado.net5.mxj 16、TIMESTAMP在UPDATE CURRENT_TIMESTAMP数据类型上做什么?创建表时TIMESTAMP列用Zero更新。只要表中的其他字段发生更改,UPDATE CURRENT_TIMESTAMP修饰符就将时间戳字段更新为当前时间。 17、主键和候选键有什么区别?表格的每一行都由主键唯一标识,一个表只有一个主键。 主键也是候选键。按照惯例,候选键可以被指定为主键,并且可以用于任何外键引用。 18、如何使用Unix shell登录Mysql?我们可以通过以下命令登录: #[mysql dir]/bin/mysql -h hostname -u <UserName> -p <password> 19、 myisamchk是用来做什么的?它用来压缩MyISAM表,这减少了磁盘或内存使用。 21、如何控制HEAP表的最大尺寸?Heal表的大小可通过称为max_heap_table_size的Mysql配置变量来控制。 22、MyISAM Static和MyISAM Dynamic有什么区别?在MyISAM Static上的所有字段有固定宽度。动态MyISAM表将具有像TEXT,BLOB等字段,以适应不同长度的数据类型。点击这里有一套最全阿里面试题总结。 MyISAM Static在受损情况下更容易恢复。 23、federated表是什么?federated表,允许访问位于其他服务器数据库上的表。 24、如果一个表有一列定义为TIMESTAMP,将发生什么?每当行被更改时,时间戳字段将获取当前时间戳。 25、列设置为AUTO INCREMENT时,如果在表中达到最大值,会发生什么情况?它会停止递增,任何进一步的插入都将产生错误,因为密钥已被使用。 ...

May 24, 2019 · 2 min · jiezi

mysql高效索引之覆盖索引

什么叫做覆盖索引? 解释一: 就是select的数据列只用从索引中就能够取得,不必从数据表中读取,换句话说查询列要被所使用的索引覆盖。 解释二: 索引是高效找到行的一个方法,当能通过检索索引就可以读取想要的数据,那就不需要再到数据表中读取行了。如果一个索引包含了(或覆盖了)满足查询语句中字段与条件的数据就叫做覆盖索引。 解释三:是非聚集组合索引的一种形式,它包括在查询里的Select、Join和Where子句用到的所有列(即建立索引的字段正好是覆盖查询语句[select子句]与查询条件[Where子句]中所涉及的字段,也即,索引包含了查询正在查找的所有数据)。 不是所有类型的索引都可以成为覆盖索引。覆盖索引必须要存储索引的列,而哈希索引、空间索引和全文索引等都不存储索引列的值,所以MySQL只能使用B-Tree索引做覆盖索引当发起一个被索引覆盖的查询(也叫作索引覆盖查询)时,在EXPLAIN的Extra列可以看到“Using index”的信息。 注:遇到以下情况,执行计划不会选择覆盖查询。 select选择的字段中含有不在 索引 中的字段 ,即索引没有覆盖全部的列。where条件中不能含有对索引进行like的操作。mysql聚集索引,辅助索引,联合索引,覆盖索引 聚集索引:一个表中只能有一个,聚集索引的顺序与数据真实的物理存储顺序一致。查询速度贼快,聚集索引的叶子节点上是该行的所有数据 ,数据索引能加快范围查询(聚集索引的顺序和数据存放的逻辑顺序一致)。主键!=聚集索引。 辅助索引(非聚集索引):一个表中可以有多个,叶子节点存放的不是一整行数据,而是键值,叶子节点的索引行中还包含了一个'书签',这个书签就是指向聚簇索引的一个指针,从而在聚簇索引树中找到一整行数据。 联合索引:就是由多列组成的的索引。遵循最左前缀规则。对where,order by,group by 都生效。 覆盖索引:指从辅助索引中就能获取到需要的记录,而不需要查找聚簇索引中的记录。使用覆盖索引的一个好处是因为辅助索引不包括一条记录的整行信息,所以数据量较聚集索引要少,可以减少大量io操作。 聚集索引与辅助索引的区别:叶子节点是否存放的为一整行数据 最左前缀规则:假设联合索引由列(a,b,c)组成,则一下顺序满足最左前缀规则:a、ab、abc;selece、where、order by 、group by都可以匹配最左前缀。其它情况都不满足最左前缀规则就不会用到联合索引。

May 24, 2019 · 1 min · jiezi

Linux下定时备份数据库

Linux下定时备份数据库linux下使用crontab定时备份MYSQL数据库的方法只需按照下面3步做,一切都在你的掌控之下: 第一步:在服务器上配置备份目录代码:1 mkdir /var/lib/mysqlbackup 2 cd /var/lib/mysqlbackup第二步:编写备份脚本代码:1 vi dbbackup.sh 2 粘帖以下代码,务必更改其中的username,password和dbname。 3 #!/bin/sh4 mysqldump -uuser -ppassword dbname | gzip > /var/lib/mysqlbackup/dbnamedate +%Y-%m-%d_%H%M%S.sql.gz5 cd /var/lib/mysqlbackup6 rm -rf find . -name '*.sql.gz' -mtime 10 #删除10天前的备份文件第三步:更改备份脚本权限1 chmod +x dbbackup.sh 第四步:用crontab定时执行备份脚本代码:crontab -e 若每天晚上21点00备份,添加如下代码00 21 * /var/lib/mysqlbackup/dbbackup.sh会遇到的问题:1.mysqldump 是备份数据库的命令,不懂直接百度就好。2.Crontab 是定时任务的命令,如果不懂可以访问http://www.thinkphp.cn/code/1...3.备份数据首先要确定已经给root设置了密码,否则会报mysqldump执行时Got error: 1045: Access denied for user ‘root’@’localhost’ (using password: YES) when trying to connect解决办法:登录mysql客户端 1 mysql -hserverip -uroot -p2 mysql> use mysql; Database changed3 mysql> update user set password=password('new password') where user='root'; Query OK, 4 rows affected (0.00 sec) Rows matched: 4 Changed: 4 Warnings: 04 mysql> flush privileges; Query OK, 0 rows affected (0.00 sec) //这个命令是给用户赋予了新的权限或者密码,直接读到内存中不需要重启数据库防止出错5 mysql> quit ...

May 24, 2019 · 1 min · jiezi

由导出CSV文件格式错误的小结

问题描述:目前、一般情况下,在web开发过程中,使用导入导出报表的情形很多。我们先说导出。项目数据量多导出行数较多,50万行左右,选择的是csv方式导出。针对以下应用场景,导出过程有几点需要注意的的地方。(测试使用环境、php7.1,mysql5.7.22,mysql5.5.53,mac自带numbers 6.0版本,Windows系统 Excel2007版) 应用场景:1、用户只习惯用Excel处理数据,csv导出但是用excel打开。2、无论导入导出,用户均对数据表格格式没有要求(边框、底纹、对齐等),仅对数据格式有基本要求(数字、文本、浮点数等)。3、后端对xls/xlsx大文件的导入性能较差。(目前php导出excel方式占用内存较大。大数据导出很可能就是内存溢出) 导出注意点:1、导出数据庞大,尽可能少用汉字。比如有些状态字段,数据库存的就是数字或只占一个字节,完全换成中文状态的话,可能达6个字节甚至更多。效率受影响。若是必须要用中文形式。尽可能精简。 2、其他常见问题。先看一组图:这是初始要导出的数据这是csv格式展示,这是我们想要的结果。这是windows系统excel2007版本打开的样子。仔细观察,我们发现了几个问题:zifunumebr字段前导0都没了。number字段有个长整型变成了科学计数法。zifu字段中文汉字变成了乱码。最后一行zifu、fudian字段在excel中显示的时候合并了。这里解决方法其实也很简单。就是在插入字段后面加一个制表符 “t”,注意,不能使用单引号。这样一来除了中文乱码不能解决,其他类型字段都能解决。中文乱码解决的话,其实也很简单,iconv函数,将urf-8转为GBK编码,在Excel中打开就不会错了

May 23, 2019 · 1 min · jiezi

报名中云开发者大会武汉站漫谈数据平台与智能应用

| 导语 6月2日,武汉世茂希尔顿酒店,腾讯云邀您参加云+开发者大会(武汉站),与技术大咖们漫谈数据平台与智能应用,洞察数据,启迪智能。 大数据与人工智能时代,新的数据智能平台技术及其发展能为我们带来什么惊喜呢? 本次大会将邀请腾讯以及业界技术专家现场分享关于新的数据智能平台技术以及应用新趋势。 大会主要围绕新的数据洞察技术、新的数据价值驱动、新的数据与智能联通方式、数据智能落地的新场景与新问题等热点话题,带来丰富的技术干货与实战内容。 活动信息 活动指南 时间 2019-06-02 周日 13:30-18:00 地点 武汉世贸希尔顿酒店 汉阳厅 公共交通: 1,乘坐地铁4/6号线,拦江路地铁站或马鹦路地铁站下车,步行约1公里 2,乘坐524路/554/24/532路等,在鹦鹉大道腰路堤站下车,步行约1公里 报名渠道 点此报名 现场奖品 活动现场设置了抽奖环节大奖将在活动结束后抽出腾讯定制礼品等你来拿! 一等奖:1名 听听音箱 二等奖:2名 腾讯云定制移动电源 三等奖: 5名 腾讯云定制旅行套装 鼓励奖:5名 腾讯定制笔记本套装 此外,凡到场的嘉宾都有精美礼品相送哦~ 技术交流**关注武汉开发者大会,参与精彩大会互动可扫面上方二维码添加云小助微信号:yunjiadahui**

May 23, 2019 · 1 min · jiezi

记一次MySql的数据拆分

前言早上上班的时候,查询数据突然发现比较慢,于是去查看数据库,结果发现表数据已经达到了千万级别,于是就准备拆分一下数据表. 思路由于数据表 table_one 数据非常庞大,并且线上业务也在不定时的往表里写入数据,所以这里不会考虑数据迁移.这里采用的方式为数据分类: 历史冷数据 和 近期热数据 .通过一定的业务条件将 table_one 中的数据进行分类 ,最终形成的分类比例为 10(历史) : 1(近期) ,或者历史冷数据更大. 步骤改表名: 修改原数据表名 table_one 改为 table_old ,即使 table_one 中的数据非常庞大,但是改表也是毫秒级的.创建新表: 重新创建一张新表 table_one , 如果线上业务有数据处理,它也会进入到新表中.这里的 AUTO_INCREMENT 设置为 10005000 预留了 5000 容错数据 .批量新增: 根据数据分类的条件 (这里是 type = 1) ,将 近期热数据 写入到 table_one 中 .这里值得注意的是,查询新增的数据不能大于 MySQL 的最大内存值.(数据大约为 500万条),否则会出现 Out of memory .检测 table_old 中符合条件的最大ID,是否在 table_one 中如果没有数据,则根据 table_old 和 table_one 中的 id 差集 ,新增没有的数据实现-- 1.改表名ALTER TABLE `table_one` RENAME TO `table_old`;-- 2.创建新表 table_one , AUTO_INCREMENT 扩大一定的范围CREATE TABLE `table_one` (`id` int(11) unsigned NOT NULL AUTO_INCREMENT,`name` varchar(50) NOT NULL DEFAULT '' COMMENT '名称',`type` tinyint(2) unsigned NOT NULL DEFAULT '0' COMMENT '类型',PRIMARY KEY (`id`),KEY `type` (`type`) USING BTREE) ENGINE=InnoDB AUTO_INCREMENT=10005000 DEFAULT CHARSET=utf8 COMMENT='原始表';-- 3.批量新增INSERT INTO `talbe_one` (`id`,`name`,`type`)SELECT * FROM `table_old` WHERE type = 1 ;-- 4.检测 table_old 中符合条件的最大ID,是否在 table_one 中SELECT * FROM `table_one` WHERE id = (SELECT MAX(id) FROM `table_old` WHERE type = 1)-- 5.如果没有数据,则根据 table_old 和 table_one 中的 id 差集 ,新增没有的数据Tips : 数据拆分的方式有很多,具体还是要看自己的业务数据和业务场景 ! ...

May 23, 2019 · 1 min · jiezi

MyISAM和InnoDB的比较

MyISAM:不支持事务,而且也不支持外键,但是每次查询都是原子的支持表级锁,即每次操作是对整个表加锁一个MYISAM表有三个文件:索引文件、表结构文件(.frm文件)、数据文件(.MYD文件)采用非聚集索引,索引文件的数据域存储指向数据文件的指针。辅索引与主索引基本一致,但是辅索引不用保证唯一性优点:查询数据相对较快,适合大量的select,可以全文索引。缺点:不支持事务,不支持外键,并发量较小,不适合大量update InnoDb:支持ACID的事务,支持事务的四种隔离级别;支持行级锁及外键约束:因此可以支持写并发;不存储总行数;一个InnoDb引擎存储在一个文件空间(共享表空间,表大小不受操作系统控制,一个表可能分布在多个文件里),也有可能为多个(设置为独立表空,表大小受操作系统文件大小限制,一般为2G),受操作系统文件大小的限制;主键索引采用聚集索引(索引的数据域存储数据文件本身),辅索引的数据域存储主键的值;因此从辅索引查找数据,需要先通过辅索引找到主键值,再访问辅索引;最好使用自增主键,防止插入数据时,为维持B+树结构,文件的大调整。优点:支持事务,支持外键,并发量较大,适合大量update缺点:查询数据相对较快,不适合大量的select MyISAM与InnoDB的比较基本的差别为:MyISAM类型不支持事务处理等高级处理,而InnoDB类型支持。MyISAM类型的表强调的是性能,其执行数度比InnoDB类型更快,但是不提供事务支持,而InnoDB提供事务支持已经外部键等高级数据库功能。 两种存储引擎的大致区别表现在: 1)InnoDB支持事务,MyISAM不支持。2)InnoDB支持外键,MyISAM不支持.3)从MySQL5.5.5以后,InnoDB是默认引擎.4)InnoDB不支持FULLTEXT类型的索引.5)InnoDB中不保存表的行数,如select count(0) from table时,InnoDB需要扫描一遍整个表来计算有多少行,但是MyISAM只要简单的读出保存好的行数即可。注意的是,当count(0)语句包含where条件时MyISAM也需要扫描整个表.6)对于自增长的字段,InnoDB中必须包含只有该字段的索引,但是在MyISAM表中可以和其他字段一起建立联合索引.7)清空整个表时,InnoDB是一行一行的删除,效率非常慢。MyISAM则会重建表8)InnoDB支持行锁(某些情况下还是锁整表,如 update table set a=1 where user like '%lee%'.9)MyISAM的索引和数据是分开的,并且索引是有压缩的,内存使用率就对应提高了不少。能加载更多索引,而Innodb是索引和数据是紧密捆绑的,没有使用压缩从而会造成Innodb比MyISAM体积庞大不小.10)MyISAM缓存在内存的是索引,不是数据。而InnoDB缓存在内存的是数据,相对来说,服务器内存越大,InnoDB发挥的优势越大。关于MyISAM与InnoDB选择:MYISAM和INNODB是Mysql数据库提供的两种存储引擎。两者的优劣可谓是各有千秋。INNODB会支持一些关系数据库的高级功能,如事务功能和行级锁,MYISAM不支持。MYISAM的性能更优,占用的存储空间少。所以,选择何种存储引擎,视具体应用而定: 1)如果你的应用程序一定要使用事务,毫无疑问你要选择INNODB引擎。但要注意,INNODB的行级锁是有条件的。在where条件没有使用主键时,照样会锁全表。比如DELETE FROM mytable这样的删除语句。2)如果你的应用程序对查询性能要求较高,就要使用MYISAM了。MYISAM索引和数据是分开的,而且其索引是压缩的,可以更好地利用内存。所以它的查询性能明显优于INNODB。压缩后的索引也能节约一些磁盘空间。MYISAM拥有全文索引的功能,这可以极大地优化LIKE查询的效率。3)MyISAM适合查询以及插入为主的应用,InnoDB适合频繁修改以及涉及到安全性较高的应用。

May 22, 2019 · 1 min · jiezi

数据库索引

数据库索引为什么使用索引一般数据量少的情况下,数据加载到内存后进行全表扫描。数据量一大必须加索引(字典)。什么样的信息能成为索引能把该记录限定在一定查找范围内的字段。主键、唯一键。索引的数据结构生成索引,建立二叉查找树进行二分查找,生成索引,建立B-Tree,B+-Tree,Hash结构进行查找。密集索引和稀疏索引的区别索引模块如何定位并优化慢查询Sql- 根据慢日志定位慢查询sql show VARIABLES like '%query%'; -- 查询慢查询记录 show status like '%slow_queries%'; set global slow_query_log = on; -- 开启慢查询日志 set global long_query_time = 1; -- 设置慢查询指定的时间为1s explain select ..... -- 执行计划查看sql 如果explain执行计划中`type字段`是index、all的时候就需要优化了, 如果`extra字段`是Useing_filesort(文件排序)、Useing_temporary(临时表)也需要使用索引优化。 - 使用explain执行计划分析sql- 修改sql或者尽量让sql走索引联合索引的最左匹配原则的成因索引是建立的越多越好么

May 22, 2019 · 1 min · jiezi

关于springboot里面的事务回滚的简单记录

最近自己在写一个小的项目,写的时候才发现自己会的东西太少了,总是遇到各种各样的坑。今天主要记录一下自己在写数据库存储的时候想到要是出现错误,是不是要回滚数据库的操作呀!然后就百度并实践了一下,得出下面的结论: 第一、需要在service方法上添加注解: @Transactional(rollbackFor = Exception.class)第二、如果你没有用try catch去捕获异常的话,那么只需要加上这个注解就可以了,如果你捕获异常了但catch里面只是打印或者返回了异常信息,没有手动抛出RuntimeException异常。那么这个时候你就需要在catch里面添加一个手动回滚的机制了。 TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();这样就OK了,当然也可以通过AOP去批量实现这种效果,只是暂时我还没有研究明白,所以就先记录这个最简单的了。后期补上。。。

May 22, 2019 · 1 min · jiezi

Java保存日期到mysql中datetime类型字段的问题

Java保存日期数据时遇到保存日期不正确的问题处理首先确认保存的是日期类型,并且保存完之后数据库保存的时间和实际插入的日期不一致确认使用的是mysql解决办法确认mysql的设置show variables like '%time_zone%'system_time_zone CSTtime_zone SYSTEM如果是上述的则是正确的 如果修正mysql的时间配置set GLOBAL time_zone='+8:00';set time_zone='+8:00';flush PRIVILEGES;确认配置的数据库连接中有&serverTimezone=GMT%2b8配置

May 22, 2019 · 1 min · jiezi

服务器部署

什么是服务器?1.组成部分2.分类3.特点业务场景 部署什么?如何选择安全防御措施步骤创建主机创建用户安装运行环境把项目同步到服务器安装进程管理程序使用ip和端口调试,没问题,使用nginx作为反向代理使用域名访问(先申请再绑定)

May 21, 2019 · 1 min · jiezi

Centos7安装jdk18tomcat8mysql8

安装前准备JDK依赖包:yum install glibc.i686MYSQL依赖包:yum -y install libaio.so.1 libgcc_s.so.1 libstdc++.so.6 yum update libstdc++-4.4.7-4.el6.x86_64yum -y install libncurses.so.5 libtinfo.so.5安装java JDK1.下载下载jDK1.8到本地 安装mysql安装tomcat

May 21, 2019 · 1 min · jiezi

阿里云数据库MySQL版快速上手

MySQL是全球最受欢迎的开源数据库,其在各Web应用中均有广泛部署。阿里云数据库MySQL版基于Alibaba的MySQL源码分支,经过双11高并发、大数据量的考验,拥有优良的性能和吞吐量。除此之外,阿里云数据库MySQL版还拥有经过优化的读写分离、数据压缩、智能调优等高级功能。 阿里云数据库MySQL版优势: 最高安全等级,保证数据库安全性。已通过ISO 20000、SOCPCI-DSS等保三级等十项安全合规认证。 多种部署架构,满足各类可用性要求。通过多种部署架构,您可以自由选择,满足各种可用性要求。 灵活的产品形态,满足系统可扩展性。多维度,分钟级的扩展能力,尽情享受云计算所带来的按需购买、按量付费的便利。 丰富运维功能,免去运维麻烦。阿里云数据库专家多年数据库运维经验产品化,免去90%运维烦恼。 阿里云数据库MySQL版使用场景:网站——高性价比场景:开箱即用,高性价比数据库产品。基于飞天大规模分布式计算和存储能力,提供超高性价比的单机版实例,同时利用读写分离横向扩展读能力,满足网站类的业务需求。 金融——安全容灾场景:数据强一致性保证,满足金融级可靠性要求。搭建事前、事中、事后三层数据安全防护网,提供双热机热备、同城、异地三中心部署架构,充分满足金融级合规可靠性需求。 电商——高并发、高性能场景:提供稳定、高性能、安全可靠的数据库服务。针对电商秒杀场景进行专项优化,解决热点数据的高并发更新性能瓶颈,100倍性能提升。通过高安全模式,内置SQL注入检测模块,实时拦截风险SQL,保护数据安全。 游戏——行业高可用场景:高稳定性,随时闪回任意时间点。对计算资源的弹性伸缩能力,赋予您更高的生产力,分钟级部署游戏分区数据库;主备双节点架构搭配高安全链路,实现全自动无感知容灾切换,业务稳定性先人一步。 通用——大数据计算:链接大数据存储、计算和可视化引擎。MySQL作为在线关系型数据存储服务,搭配E-MapReduce、HybridDB、DataV等,可满足如日志分析、数据库存、商业智能、机器学习、科学模拟等业务。 阿里云数据库MySQL版快速入门课程:阿里云大学—开发者课堂

May 21, 2019 · 1 min · jiezi

一个mysql死锁场景分析

最近遇到一个mysql在RR级别下的死锁问题,感觉有点意思,研究了一下,做个记录。涉及知识点:共享锁、排他锁、意向锁、间隙锁、插入意向锁、锁等待队列 场景隔离级别:Repeatable-Read表结构如下 create table t ( id int not null primary key AUTO_INCREMENT, a int not null default 0, b varchar(10) not null default '', c varchar(10) not null default '', unique key uniq_a_b(a,b), unique key uniq_c(c));初始化数据 insert into t(a,b,c) values(1,'1','1');有A/B两个session,按如下顺序执行两个事务 结果是 B执行完4之后还是一切正常A执行5的时候,被blockB接着执行6,B报死锁,B回滚,A插入数据show engine innodb status中可以看到死锁信息,这里先不贴,先解释几种锁的概念,再来理解死锁过程 共享(S)锁/互斥(X)锁共享锁允许事务读取记录互斥锁允许事务读写记录这两种其实是锁的模式可以和行锁、间隙锁混搭,多个事务可以同时持有S锁,但是只有一个事务能持有X锁 意向锁一种表锁(也是一种锁模式),表明有事务即将给对应表的记录加S或者X锁。SELECT ... LOCK IN SHARE MODE会在给记录加S锁之前先给表加IS锁,SELECT ... FOR UPDATE会在给记录加X锁之前给表加IX锁。这是一种mysql的锁优化策略,并不是很清楚意向锁的优化点在哪里,求大佬指教 两种锁的兼容情况如下 行锁很简单,给对应行加锁。比如update、select for update、delete等都会给涉及到的行加上行锁,防止其他事务的操作 间隙锁在RR隔离级别下,为了防止幻读现象,除了给记录本身,还需要为记录两边的间隙加上间隙锁。比如列a上有一个普通索引,已经有了1、5、10三条记录,select * from t where a=5 for update除了会给5这条记录加行锁,还会给间隙(1,5)和(5,10)加上间隙锁,防止其他事务插入值为5的数据造成幻读。当a上的普通索引变成唯一索引时,不需要间隙锁,因为值唯一,select * from t where a=5 for update不可能读出两条记录来。 ...

May 18, 2019 · 4 min · jiezi

SQL-行转列列转行

SQL 行转列,列转行行列转换在做报表分析时还是经常会遇到的,今天就说一下如何实现行列转换吧。 行列转换就是如下图所示两种展示形式的互相转换 行转列假如我们有下表: SELECT *FROM studentPIVOT ( SUM(score) FOR subject IN (语文, 数学, 英语))通过上面 SQL 语句即可得到下面的结果 PIVOT 后跟一个聚合函数来拿到结果,FOR 后面跟的科目是我们要转换的列,这样的话科目中的语文、数学、英语就就被转换为列。IN 后面跟的就是具体的科目值。 当然我们也可以用 CASE WHEN 得到同样的结果,就是写起来麻烦一点。 SELECT name, MAX( CASE WHEN subject='语文' THEN score ELSE 0 END) AS "语文", MAX( CASE WHEN subject='数学' THEN score ELSE 0 END) AS "数学", MAX( CASE WHEN subject='英语' THEN score ELSE 0 END) AS "英语"FROM studentGROUP BY name使用 CASE WHEN 可以得到和 PIVOT 同样的结果,没有 PIVOT 简单直观。 ...

May 18, 2019 · 1 min · jiezi

项目笔记1通过在线制图工具绘制阿里云部署图

title: 通过在线制图工具绘制阿里云部署图最近做一个项目是关于采集指纹的系统,先给大家简单介绍一下项目的主要功能: 该项目主要是做一个采集婴幼儿的手掌指纹和掌纹的客户端,并且通过服务端接口保存手掌指纹到阿里云oss存储中。同时后台提供管理功能,对采集人员,系统角色权限管理,同时提供婴幼儿的手指指纹图片的查看和分析功能。 系统分为三个子系统: 指纹采集客户端程序(client)指纹采集接口应用服务(通过springboot 框架开发的Restful Api方式 (client restful api)指纹采集后台管理应用前端页面 (Ant Design Vue Admin )指纹采集后台应用接口服务器 (通过Spring Boot框架开发,用到Redis, JWT,mybatis等技术)由于客户要求使用阿里云服务作为应用部署的基本设施,按照客户的要求绘制阿里云系统部署架构图。 最后讨论后的部署建议方案: 为了保证数据传输的安全建议采用https SSL证书方式。用户请求通过负载均衡SLB分发到阿里云的ESC上。后端web服务器采用多台ECS(至少2台)负载用户请求。数据库采用阿里云的Mysql版本,通过设置好数据库的备份和安全OSS存在被采集人指纹信息。使用redis作为数据缓存中心。短信接口建议采用阿里云平台短信网关服务。在此使用了一个网上在线制图网站Freedgo Design 其访问地址为: https://www.freedgo.com. freedgo Design 是一个多种类型图表的在线绘制软件,让您创建 阿里云架构图 腾讯云架构图 Oracle云架构图 AWS系统部署图 软件架构图, UML,BPMN,ERD,流程图,UX设计图,ANT DESIGN,思维导图,图表。可以做到注册用户免费使用。 具体绘制步骤如下:打开https://www.freedgo.com,先点...,Freedgo Design提供邮箱、微信、QQ、微博等多种注册方式。注册成功后,点击 开始制作 按钮,然后就进入制图工具页面进行绘制。选择菜单文件-> 从类型中新建 -> 云架构 -> 阿里云左侧图标库中选择所需要的web服务器,数据库,redis等等图标安装业务逻辑绘制在线架构图。最终的绘制效果如下图:

May 16, 2019 · 1 min · jiezi

MariaDB-开启慢查询-Log找出到底慢在哪个-Query-语句上-Slow-query-logHigh-CPU

本教学使用环境介绍伺服器端:Ubuntu 18.04 LTS资料库:Mariadb 10.1.34(Mysql)语言版本:php 7.3本机端:MacOS High Sierra 网路上写的设定档是 /etc/mysql/my.cnf但我实际去找是在 mariadb.conf.d 底下的 50-server.cnf 才是(可能是 Mysql 跟 MariaDB 的差别?) $ cd /etc/mysql/mariadb.conf.d使用 nano 开启 $ nano 50-server.cnf进入后会看到 [mysqld] ,直接在下面加上 slow_query 变成: [mysqld]# 开启慢日志功能slow_query_log = 1# 查询时间超过 2 秒则定义为慢查询(可自行改秒数)long_query_time = 2# 将产生的 slow query log 放到你指定的地方slow_query_log_file = /var/www/slow_query.log保存后别忘了重启资料库 systemctl restart mariadb.service验证是否成功开启先透过 CLI 进入 Mysql (Mariadb) $ mysql -u root -p进入后输入指令以下 MariaDB [(none)]> 简称为 > > show variables like '%quer%';会出现以下表格 ...

May 16, 2019 · 1 min · jiezi

造轮子-EGGJS的MySQL操作库

最近学习eggjs,学习过程中使用官方推荐的MySQL库,感觉官方库不太好用,基础的CURD没问题。但是复杂点的操作就不行了,虽然官方还有一个egg-sequelize,但是这个这并不妨碍我造轮子。下面介绍一下我的这个轮子。 介绍这个轮子其实是很早以前就造好的,主要参考THINKPHP的数据库操作方式。将设置表名(table)、设置查询字段(field)、联表(join)等操作进行链式操作,给人一种语义化操作数据库的感觉。 比如从用户表查找id为1的用户的名字,则只需要这样操作: mysql.table('user').field('name').where({ id: 1 }).find();// SELECT name FROM user where id=1 limit 1是不是很简单呢? 造的轮子名字叫@hyoga/egg-mysql,所以只需要: 安装npm i @hyoga/egg-mysql --save配置// {app_root}/config/config.default.jsexports.mysql = { mysql: { client: { host: '127.0.0.1', port: '3306', user: 'root', password: '', database: 'db', }, // 是否加载到 app 上,默认开启 app: true, // 是否加载到 agent 上,默认关闭 agent: false, },};使用// {app_root}/config/plugin.jsexports.mysql = { enable: true, package: '@hyoga/egg-mysql',};// {app_root}/app/service/user.jsexport default class User extends Service { private table = 'user'; public async list() { // sql = SELECT * FROM user WHERE status = 1 return this.app.mysql.table(this.table).where({ status: 1 }).select(); }} 这时候mysql就挂载到egg的app对象了,接下来就可以到处链式操作了。 ...

May 15, 2019 · 1 min · jiezi

19051501记录一次日常犯的错

Parameter 'array' not found. Available parameters are [collection, list]莫名其妙,今天写代码遇到个低级错误,困扰了好久,测试突然给提了个缺陷,说业务逻辑有问题于是,就启动了缺陷排查的流程1.问题复现   根据问题复现步骤,确实发现业务逻辑不对2.代码排查   根据代码排查,业务逻辑确实写了,对表的更新3.日志排查   根据日志排查,发现新增的代码并没有执行,而且,也没有报错。随后就进行了纠结(现在都想敲死自己,应该不用纠结,在编辑器debug跑一遍,问题就暴露出来了)。4.解决问题   先使用单测,跑了一遍对应的方法,发现确实没有问题,所以怀疑,是因为MOCK掉的DAO方法,抛了一个异常,然后没有显式的抛出来,所以就手动debug启动了下应用,就是POSTMAN测试,果然,报错如下: nested exception is org.apache.ibatis.binding.BindingException: Parameter 'array' not found. Available parameters are [collection, list]这里是因为,在mybaits传集合参数,进行循环时,一定要指定集合类型,目前mybaits对List集合和Array集合,是不同,需要在循环时指定对应的集合,如果使用类似于Long[] 等进行传参时,一定要指定collection="array",如果使用List进行传参时,需要指定collection="list",否则就会抛异常。至于为什么在服务器上没有抛异常出来,很可能是被框架给吃掉了,需要进一步排查。

May 15, 2019 · 1 min · jiezi

如何用大数据在5分钟内完成一份行业报告以果酒行业为例

果酒发展到今天,已经逐渐形成了其市场氛围,除葡萄酒仍旧占据主要市场外,其它类果酒,也占有一定的市场份额,大有异军突起之势。 尤其夏天到了,不如来杯美味的果酒。你喜欢什么口味的果酒呢? 现根据某电商网站数据,从销量、品牌、产品等角度,对除葡萄酒外其它类别果酒,做出以下分析。 一销量分析 果酒类别与销量分析果酒行业品类众多,果酒市场差距明显。 大数据显示,苹果酒以超过75万+的销量独占鳌头,占总额20%; 石榴酒、杨梅酒均以超过33万+的销量分居二三位; 桃子酒、蓝莓酒、青梅酒、荔枝酒、哈密瓜酒、梅子酒、草莓梅子酒分居4~10位。 此外,其它各类别果酒总占比达24%。(数据来源于网络,仅供参考) (数据来源于网络,仅供参考) 注:其它果酒各类别销量请联系客服处理。 果酒的各品牌销量分析从销量来看,各大品牌都占据着一定市场份额,其中SUNTORY/三得利居于榜首; 二三名分别由aller wine/萄乐 和 CHOYA/俏雅占据,二者相差无几,大有追赶之势。 此外雪姬、千古盛等品牌也占据一定市场。 (数据来源于网络,仅供参考) (数据来源于网络,仅供参考) 二品牌分析 各品牌产品数量排行据下图可知,各大品牌产品数量参差不齐,俏雅以微弱优势领先SUNTORY/三得利居于第一位。 然而,相较于其后各大品牌仍有明显优势。 (数据仅供参考) (数据仅供参考) 各品牌产品类别分析各大品牌对自己旗下产品注重多有不同,其中荔枝酒、桃子酒、青梅酒、梅子酒最为各大品牌的所青睐。 以且听风吟和俏雅为例: 品牌:且听风吟 (数据仅供参考) (数据仅供参考) 品牌:俏雅 (数据仅供参考) (数据仅供参考) 三产品分析各种类果酒产品依次分布,其中以草莓梅子酒类产品数量最多,已接近3500种,柠檬酒也以超过3000+数量,紧随其后。 (数据仅供参考)(数据仅供参考) 大数据运用到果酒行业,可以更为精准、直观、科学的掌握果酒市场及行业发展态势,同时辅助企业进行品牌传播经营、公关指导工作。 图源:网络 .end. 果酒全类别销量如何?价格如何? 各类别下品牌如何?产品细节如何?以上表格均为部分数据,更多独家数据分析,尽在完整报告。

May 15, 2019 · 1 min · jiezi

Mysqlvarchar类型

1.varchar类型(1)varchar (N):中的N指的是字符的长度,即:该字段最多能存储多少个字符(characters),不是字节数。不管是一个中英文字符或者数字、或者一个汉字,都当做一个字符。【 a,我,1 都是一个字符,但是a和1是一个字节,‘我’(utf8下)是3个字节。 utf8mb4下:汉字也是3个字节,表情符号是4个字节 】(2)varchar 最多能存储 65535 个字节的数据。65535 = 所有字段的长度 + 变长字符的长度标识 + NULL标识位变长字符的长度标识:用1到2个字节表示实际长度(长度 >255 时,需要2个字节; <255 时,需要1个字节)NULL标识位:varchar字段定义中带有 default null 允许列空,则需要 1 bit 来标识,每 8 个bits的标识组成一个字段。一张表中存在N个varchar字段,那么需要(N+7)/8 (取整)bytes存储所有的NULL标识位。 (3)虽然InnoDB内部支持 varchar 65535 字节的行大小,但是MySQL本身对所有列的合并大小施加了 65535 字节的行大小限制。详情见例子 2.varchar 长度的编编限制:字符类型若为gbk,每个字符最多占2个字节,最大长度不能超过32766;字符类型若为utf8,每个字符最多占3个字节,最大长度不能超过21845。字符类型若为utf8mb4,每个字符最多占4个字节,最大长度不能超过16283。若定义的时候超过上述限制,则varchar字段会被强行转为text类型,并产生warning。 3.例子若一个表定义为create table t4(c int, c2 char(30), c3 varchar(N)) charset=utf8;则此处N的最大值为 (65535-1-2-4-30*3)/3=21812减 1:实际行存储从第二个字节开始;减 2:varchar 头部的2个字节表示长度减 4:原因是int类型的c占4个字节;减 30*3:原因是char(30)占用90个字节,编码是utf8。如果被varchar超过上述的b规则,被强转成text类型,则每个字段占用定义长度为11字节,当然这已经不是“varchar”了。 mysql> alter table t4 modify column c3 varchar(21813);ERROR 1118 (42000): Row size too large. The maximum row size for the used table type, not counting BLOBs, is 65535. This includes storage overhead, check the manual. You have to change some columns to TEXT or BLOBs

May 14, 2019 · 1 min · jiezi

Please-read-Security-to-find-out-how-to-run-mysqld-as-root

错误信息:[ERROR] Fatal error: Please read "Security" section of the manual to find out how to run mysqld as root! 错误原因是mysql处于安全考虑,默认拒绝以root账号启动服务 解决方法有以下几种: 1、通过在命令后面加上--user=root进行强制使用root账号启动。 mysqld --user=root2、使用一个普通用户进行启动mysqld 。这个用户必须是属于mysqld用户组,编辑/etc/my.cnf文件,在[mysqld]下新增启动用户mysql [mysqld]user=mysql启动时加上--user=mysql mysqld --user=mysql 欢迎订阅「K叔区块链」 - 专注于区块链技术学习 博客地址:http://www.jouypub.com简书主页:https://www.jianshu.com/u/756c9c8ae984segmentfault主页:https://segmentfault.com/blog/jouypub腾讯云主页:https://cloud.tencent.com/developer/column/72548

May 14, 2019 · 1 min · jiezi

SpringBoot整合MybatisPlus的简单教程简单整合

最近在研究springboot,顺便就会看看数据库连接这一块的知识 ,所以当我发现有通用Mapper和MybatisPlus这两款网络上比较火的简化mybatis开发的优秀软件之后。就都想试一下,看看哪一款比较适合自己。先创建一个springboot的项目,可以参考我之前的文章Spring Boot 的简单教程(一) Spring Boot 项目的创建。创建好springboot之后就需要整合mybatis和mybatis-plus了。 打开pom.xml文件,将最新的mybatis相关的包都引用进来。 <!-- 这是mysql的依赖 --> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <scope>runtime</scope> </dependency> <!-- 这是lombok的依赖 --> <dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> <optional>true</optional> </dependency> <!-- 这是mybatis-plus依赖 --> <dependency> <groupId>com.baomidou</groupId> <artifactId>mybatis-plus-boot-starter</artifactId> <version>3.1.1</version> </dependency> <!-- 这是mybatis-plus的代码自动生成器 --> <dependency> <groupId>com.baomidou</groupId> <artifactId>mybatis-plus-generator</artifactId> <version>3.1.1</version> </dependency> <!-- 这是模板引擎依赖 --> <dependency> <groupId>org.freemarker</groupId> <artifactId>freemarker</artifactId> <version>2.3.28</version> </dependency>需要对application.yml进行相关的配置。 #端口号 server: port: 8088 #数据库的配置信息 spring: datasource: url: jdbc:mysql://localhost:3306/*** #自己的数据库名称 username: root password: 123456 mybatis: #开启驼峰命名法 configuration: map-underscore-to-camel-case: true mybatis-plus: # xml地址 mapper-locations: classpath:mapper/*Mapper.xml # 实体扫描,多个package用逗号或者分号分隔 type-aliases-package: *** #自己的实体类地址 configuration: # 这个配置会将执行的sql打印出来,在开发或测试的时候可以用 log-impl: org.apache.ibatis.logging.stdout.StdOutImpl自动生成模块的方法,在相应的位置上添加上自己的一些包名就可以运行生成相应的Entity、Mapper、Mapper XML、Service、Controller 等各个模块的代码。public class CodeGenerator { /** * <p> * 读取控制台内容 * </p> */ public static String scanner(String tip) { Scanner scanner = new Scanner(System.in); StringBuilder help = new StringBuilder(); help.append("请输入" + tip + ":"); System.out.println(help.toString()); if (scanner.hasNext()) { String ipt = scanner.next(); if (StringUtils.isNotEmpty(ipt)) { return ipt; } } throw new MybatisPlusException("请输入正确的" + tip + "!"); } public static void main(String[] args) { // 代码生成器 AutoGenerator mpg = new AutoGenerator(); // 全局配置 GlobalConfig gc = new GlobalConfig(); String projectPath = System.getProperty("user.dir"); gc.setOutputDir(projectPath + "/src/main/java"); gc.setAuthor("jobob"); gc.setOpen(false); // gc.setSwagger2(true); 实体属性 Swagger2 注解 mpg.setGlobalConfig(gc); // 数据源配置 DataSourceConfig dsc = new DataSourceConfig(); dsc.setUrl("jdbc:mysql://localhost:3306/***?useUnicode=true&useSSL=false&characterEncoding=utf8"); // dsc.setSchemaName("public"); dsc.setDriverName("com.mysql.cj.jdbc.Driver"); dsc.setUsername("root"); dsc.setPassword("***"); mpg.setDataSource(dsc); // 包配置 PackageConfig pc = new PackageConfig(); //这里有个模块名的配置,可以注释掉不用。// pc.setModuleName(scanner("模块名")); pc.setParent("com.zhouxiaoxi.www"); mpg.setPackageInfo(pc); // 自定义配置 InjectionConfig cfg = new InjectionConfig() { @Override public void initMap() { // to do nothing } }; // 如果模板引擎是 freemarker String templatePath = "/templates/mapper.xml.ftl"; // 如果模板引擎是 velocity// String templatePath = "/templates/mapper.xml.vm"; // 自定义输出配置 List<FileOutConfig> focList = new ArrayList<>(); // 自定义配置会被优先输出 focList.add(new FileOutConfig(templatePath) { @Override public String outputFile(TableInfo tableInfo) { // 自定义输出文件名 , 如果你 Entity 设置了前后缀、此处注意 xml 的名称会跟着发生变化!! return projectPath + "/src/main/resources/mapper/"// + + pc.getModuleName() + 如果放开上面的模块名,这里就有一个模块名了 + "/" + tableInfo.getEntityName() + "Mapper" + StringPool.DOT_XML; } }); /* cfg.setFileCreate(new IFileCreate() { @Override public boolean isCreate(ConfigBuilder configBuilder, FileType fileType, String filePath) { // 判断自定义文件夹是否需要创建 checkDir("调用默认方法创建的目录"); return false; } }); */ cfg.setFileOutConfigList(focList); mpg.setCfg(cfg); // 配置模板 TemplateConfig templateConfig = new TemplateConfig(); // 配置自定义输出模板 //指定自定义模板路径,注意不要带上.ftl/.vm, 会根据使用的模板引擎自动识别 // templateConfig.setEntity("templates/entity2.java"); // templateConfig.setService(); // templateConfig.setController(); templateConfig.setXml(null); mpg.setTemplate(templateConfig); // 策略配置 StrategyConfig strategy = new StrategyConfig(); //数据库表映射到实体的明明策略 strategy.setNaming(NamingStrategy.underline_to_camel); //数据库表字段映射到实体的命名策略, 未指定按照 naming 执行 strategy.setColumnNaming(NamingStrategy.underline_to_camel); //自定义继承的Entity类全称,带包名// strategy.setSuperEntityClass("***"); strategy.setEntityLombokModel(true); strategy.setRestControllerStyle(true); //自定义继承的Controller类全称,带包名// strategy.setSuperControllerClass("***"); strategy.setInclude(scanner("表名,多个英文逗号分割").split(",")); //自定义基础的Entity类,公共字段(可添加更多)// strategy.setSuperEntityColumns("id"); //驼峰转连字符 strategy.setControllerMappingHyphenStyle(true); //表前缀// strategy.setTablePrefix(pc.getModuleName() + "_"); mpg.setStrategy(strategy); mpg.setTemplateEngine(new FreemarkerTemplateEngine()); mpg.execute(); }}在生成的controller里面添加对应的方法启动就可以正常进行访问了。 ...

May 14, 2019 · 2 min · jiezi

InnoDB引擎B树索引使用和新特性

我们已经讲过了MySQL InnoDB索引原理和算法,这里来说下如何管理和使用B+树索引以及一些新的特性。 B+ 树索引的管理我们在InnoDB引擎中常用的索引基本都是B+ 树索引。 创建和删除索引它的创建和删除有两种方法: # 方式一:alter table, 此时index和key均可以,如果要求所有值均不重复,加上uniquealter table tbl_name add [unique] index|key index_name (index_col_name,...);alter table tbl_name drop index|key index_name;# 方式二:create/drop index, 此时只能用indexcreate index index_name on tbl_name (index_col_name,...);drop index index_name on tbl_name;修改索引MySQL没有提供修改索引的命令,我们一般先删掉索引,再重建同名索引达到修改的目标。 查看索引我们在查看数据表描述时可以看到都有哪些索引,有三种方法: # 方法一:查看创建表的语句mysql> show create table serviceHost;| Table | Create Table | t | CREATE TABLE `t` ( `id` int(11) NOT NULL AUTO_INCREMENT, `a` varchar(20) DEFAULT NULL, `b` varchar(20) DEFAULT NULL, `c` varchar(20) DEFAULT NULL, `d` varchar(20) DEFAULT NULL, `e` varchar(20) DEFAULT NULL, `f` varchar(20) DEFAULT NULL, PRIMARY KEY (`id`), UNIQUE KEY `a` (`a`), KEY `idx_b` (`b`), KEY `idex_cde` (`c`,`d`,`e`)) ENGINE=InnoDB DEFAULT CHARSET=utf8 |1 row in set (0.00 sec)可以看到该表中有4个索引,主键集合索引(id),唯一辅助索引(a),单列辅助索引(b),组合辅助索引(c,d,e)。 ...

May 14, 2019 · 8 min · jiezi

Mysql56-安装

Centos 安装 MySQL Repository: rpm -Uvh http://dev.mysql.com/get/mysql-community-release-el7-5.noarch.rpm安装 MySQL Server, MySQL client 已經包括在 server 套件內: yum install mysql-community-server开机启动 MySQL /usr/bin/systemctl enable mysqld启动 MySQL /usr/bin/systemctl start mysqldMySQL 预设密码为空, 执行以下命令修改密码: /usr/bin/mysql_secure_installation

May 13, 2019 · 1 min · jiezi

mysql数据库设计规范

数据库设计规范数据库命名规范规范备注数据库对象名称统一使用小写字母并用下划线分割eg:mkt_tool数据库对象名称禁止使用MySQL保留关键字eg:password,from等数据库对象名称做到见名思义,最长不超过32个字符尽可能的精简、明确临时表以tmp为前缀,日期为后缀eg:mp_user_20180921备份表以bak为前缀,日期为后缀eg:bak_user_20180921所有存储相同数据的列名和列类型必须一致eg:a表的uid与b表的uid数据类型与列类型一致数据库基本设计规范规范备注所有数据表使用innodb作为存储引擎5.6以后作为默认引擎,支持事务、行级锁、更好的恢复性,高并发下性能更好数据库和表的字符集统一使用UTF8主要是因为避免由于字符集转换产生的乱码,其次utf8包含的字符更多,一个汉字占3个字节数据表和字段需要添加注释后续维护方便单表数据量控制在500万以内单表存储的数据量大小限制取决于存储设置和文件系统尽量做到冷热数据分离,减小表的宽度避免查询无用的数据禁止在表中预留字段,禁止在数据库中存储图片及文件等二进制数据按需增加,避免表数据快速增长禁止在线上做数据库压力测试 禁止开发环境直接连接生产环境数据库避免数据脏乱数据库索引规范规范备注限制每张表索引的数量,单表索引不超过5个索引不是越多越好,增加查询效率的同时,会降低更新的效率每个innodb表必须有一个主键不使用频繁更新的键,不使用hash,字符串,MD5作为主键,优先选取自动增长的列作为主键如何选择联合索引的顺序区分度最高的放在索引的最左侧;字段长度最小的放在最左侧;使用度最频繁的列放在最左侧避免建立冗余度和重复列索引增加了优化器生成查询计划的时间对于冗余索引并不会提高索引的性能,反而影响查询计划的生成对于频繁的查询优先考虑使用覆盖索引避免Innodb进行索引的二次查找尽量避免使用外键外键用于保证参照完整性,建议在业务端实现外键的约束,因为每次写操作都需要检测外键约束从而降低性能。数据库字段规范规范备注优先选择存储需要的最小的数据类型int类型相比字符串类型存储空间更小,优先使用无符号的整型存储避免使用text、bolb、enum类型使用text类型的时候注意只能使用前缀索引,不能有默认值尽可能的定义为NOT NULL索引NULL需要额外的空间来保存,进行比较和计算时需要对NULL进行特殊处理避免使用字符串存储日期型的数据,使用TIMESTAMP或DATETIME存储1、无法使用日期函数进行比较和计算;2、用字符串存储需要占用更多的空间使用decimal类型存储金额类数据1、decimal在计算时不丢失精度,占用的空间由定义的宽度决定;2、可用于存储比bigint更大的数据数据库SQL开发规范规范备注使用预编译进行数据库操作1、一次解析,多次使用重复使用执行计划;2、避免动态SQL带来的SQL注入;避免数据类型的隐式转换隐式转换、会导致索引失效 eg:select * from test where id = '1' 充分利用已经存在的索引1、避免使用双%的查询,使用后%进行替换;2、一个SQL只能利用到复合索引中的一列进行范围查询;3、使用left join或not exists来优化not in操作禁止使用select * 查询1、消耗更多的CPU和io资源;2、无法使用到覆盖索引;禁止使用不含字段列表的INSERT语句明确指定insert的字段避免使用子查询,可以把子查询优化为join操作1、子查询的结果集无法使用到索引;2、子查询产生临时表操作,数据量大会影响效率;3、产生的临时表消耗过多的CPU和IO避免使用JOIN关联太多的表1、每join一个表会占用一部分内存(join_buffer_size);2、会产生临时表操作,影响查询效率;3、MySQL允许关联61个表,最多不超过5个减少同数据库交互的次数1、数据库适合批量处理,避免多次请求数据库;2、合并多个相同的操作到一起,如一次修改多个字段使用in代替onin的值不超过500个,in可以有效的利用索引的禁止使用order by rand()排序order by rand()会把所有符合条件的数据装到内存中排序获取where从句中禁止对列进行函数转换和计算对列进行函数转换会导致无法使用到索引 eg:where date(time) = '20180123' 明显不会有重复值的情况下使用UNION ALLUNION会把数据放到临时表进行去重拆分复杂的大SQL为多个小SQLMySQL一个SQL只能使用一个CPU计算,SQL拆分后可以通过并行执行提高效率数据库操作行为规范规范备注超过100万行的数据批量写操作,需要分批多次操作1、大批量的写操作,容易造成主从延迟 2、产生大量的日志 3、避免产生大事务操作大表结构修改直接修改大表容易进行锁表,使用pt-online-schema-change修改表结构禁止为程序使用的账户授予root权限,遵循权限最小原则程序使用的账户不准有drop权限,程序使用的账户只能连接到一个数据库

May 13, 2019 · 1 min · jiezi

提高性能MySQL-读写分离环境搭建二

title: 提高性能,MySQL 读写分离环境搭建(二)tags: MySQLcategories: MySQLabbrlink: 60ae3a4d date: 2019-05-13 10:12:36上篇文章和大家聊了 CentOS7 安装 MySQL5.7 ,这个大家一般装在虚拟机里边,装好了,把虚拟拷贝一份,这样我们就有两个 MySQL ,就可以开始今天的主从搭建了。 准备工作我这里有一张简单的图向大伙展示 MySQL 主从的工作方式: 这里,我们准备两台机器: 主机:192.168.248.128从机:192.168.248.139主机配置主机的配置就三个步骤,比较容易: 1.授权给从机服务器 GRANT REPLICATION SLAVE ON *.* to 'rep1'@'192.168.248.139' identified by '123';FLUSH PRIVILEGES;这里表示配置从机登录用户名为 rep1,密码为 123,并且必须从 192.168.248.139这个地址登录,登录成功之后可以操作任意库中的任意表。其中,如果不需要限制登录地址,可以将 IP 地址更换为一个 %。 2.修改主库配置文件,开启 binlog ,并设置 server-id ,每次修改配置文件后都要重启 MySQL 服务才会生效 vi /etc/my.cnf修改的文件内容如下: [mysqld]log-bin=/var/lib/mysql/binlogserver-id=128binlog-do-db = cmdb如下图: log-bin:同步的日志路径及文件名,一定注意这个目录要是 MySQL 有权限写入的(我这里是偷懒了,直接放在了下面那个datadir下面)。binlog-do-db:要同步的数据库名,当从机连上主机后,只有这里配置的数据库才会被同步,其他的不会被同步。server-id: MySQL 在主从环境下的唯一标志符,给个任意数字,注意不能和从机重复。配置完成后重启 MySQL 服务端: systemctl restart mysqld3.查看主服务器当前二进制日志名和偏移量,这个操作的目的是为了在从数据库启动后,从这个点开始进行数据的恢复: show master status; 至此,主机配置完成。 ...

May 13, 2019 · 1 min · jiezi

springboot整合quarzt实现动态定时任务

实现定时任务的几种方式:1.使用linux的crontab 优点: 1.使用方式很简单,只要在crontab中写好 2.随时可以修改,不需要重启服务器 缺点: 1.分布式的系统中不好使用,只能一台台机器去修改 2.分是最小的时间单位,秒级的不能使用2.使用spring自带的ScheduledExecutor 优点: cronExpression比crontab的更强大一些支持到秒,性能更好 缺点: 修改了cronExpression的重启服务器,否则不生效3. 使用JDK自带的Timer优点: 轻量级,执行速度快缺点:分布式系统不好使用.而且不能指定时间执行,只能按某个频次来执行4.使用quarzt优点:1.可适用于分布式系统,quartz可支持集群模式2.修改了定时任务无须重启服务器(这只是我个人想到的一些优缺点,网友有其他看法可以留言说下)你好! 这是你第一次使用 Markdown编辑器 所展示的欢迎页。如果你想学习如何使用Markdown编辑器, 可以仔细阅读这篇文章,了解一下Markdown的基本语法知识。 整合步骤:我们现在知道了quartz有这么优秀,该怎么整合到项目中呢?笔者接下来将实现一个通过http接口调用来触发动态定时任务的一个小功能.笔者使用的环境:jdk:1.8.0_162;springboot:1.5.10.RELEASE1.引入需要的jar包,在pom文件中加入quartz的jar包和spring支持quartz的jar <dependency> <groupId>org.quartz-scheduler</groupId> <artifactId>quartz</artifactId> <version>2.3.1</version> </dependency> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-context-support</artifactId> </dependency>2.配置调度器的bean,这里spring实现了三个工厂类,SchedulerFactoryBean,CronTriggerBean,JobDetailBean,使用注解的方式将这三个类交给spring管理.一般看网上的资料都是这三个类,都交给spring管理,可以参考这篇文章[这篇文章]。(https://blog.csdn.net/liuchua...。而我这里定时任务的触发是要通过接口的方式来触发,所以只用实现以下SchedulerFactoryBean的调度器即可。如果读者不是很明白这几个类是干嘛的,可以看下quartz使用的文章。我这里简单说下:scheduler:任务的调度器,job:具体的任务类,trigger:触发器,任务什么时候执行是由它决定的。就是说时间人物做什么,scheduler就是主语的人物,trigger是时间,job是做什么事。 @Configurationpublic class SchedulerConfig { /** * attention: * Details:定义quartz调度工厂 */ @Bean(name = "scheduler") public SchedulerFactoryBean schedulerFactory() { SchedulerFactoryBean bean = new SchedulerFactoryBean(); // 用于quartz集群,QuartzScheduler 启动时更新己存在的Job bean.setOverwriteExistingJobs(true); // 延时启动,应用启动1秒后 bean.setStartupDelay(1); return bean; }}3.具体任务类job,必须实现quartz的job类,这个也可以去实现spring的QuartJobBean(spring对job类的实现)是一样的,或者还有一种方式就是MethodInvokingJobDetailFactoryBean,这个类里面可以设置什么类的什么方法来执行这个任务,会更灵活一些: @Slf4jpublic class ScheduleTaskJob implements Job { @Override public void execute(JobExecutionContext context) throws JobExecutionException { log.info("任务执行了......"); }}4.http的接口来触发该调度程序: ...

May 12, 2019 · 1 min · jiezi

MySQL-Online-DDL导致全局锁表案例分析

MySQL Online DDL导致全局锁表案例分析我这边遇到了什么问题?线上给某个表执行新增索引SQL, 然后整个数据CPU打到100%, 连接数暴增到极限, 最后导致所有访问数据库的应用都奔溃. SQL如下: ALTER TABLE `book` ADD INDEX `idx_sub_title` (`sub_title` ASC);能看到什么? '10063293', 'root', '10.0.0.1:35252', 'novel', 'Query', '50', 'Waiting for table metadata lock', 'ALTER TABLE `lemon_novel`.`book` \nADD INDEX `idx_sub_title` (`sub_title` ASC)''10094494', 'root', '172.16.2.112:42808', 'novel', 'Query', '31', 'Waiting for table metadata lock', 'SELECT \n book_trend.book_id AS book_id, 很奇怪, 这两边都在等"Waiting for table metadata lock" 反手查一下"Waiting for table metadata lock"是什么MySQL出现Waiting for table metadata lock的原因以及解决方法mysql: Waiting for table metadata lockHow do I find which transaction is causing a “Waiting for table metadata lock” state?MySQL:8.11.4 Metadata LockingMySQL:14.13.1 Online DDL Operations初步的一些结论看下来下面的一些结论: ...

May 12, 2019 · 1 min · jiezi

mysql版本详细介绍及安装部署mysql56

运维DBA工作内容初级DBA: 安装配置,基本使用,基本故障处理中级DBA: 体系结构、备份策略涉及,故障恢复,基础高可用的运维(搭建、监控、故障处理、架构演变)、基础优化(索引、执行计划、慢日志)高级DBA: 高可用架构(设计、实施、运维)、高性能架构(读写分离,分库、分表,分布式)、整体数据库优化(基于业务的SQL优化)MySQL学习框架MySQL简介及部署MySQL体系结构MySQL基础管理SQL应用Information_schema获取元数据索引及执行计划MySQL存储引擎MySQL日志管理MySQL备份与恢复MySQL主从复制及架构演变MySQL高可用架构MySQL高性能架构MySQL优化MySQL5.7及8.0高可用新特性数据库管理系统什么是数据数据(data)是事实或观察的结果,是对客观事物的逻辑归纳,是用于表示客观事物的未经加工的的原始素材。数据可以是连续的值,比如声音、图像,称为模拟数据。也可以是离散的,如符号、文字,称为数字数据。 在计算机系统中,数据以二进制信息单元0,1的形式表示。 数据的定义:数据是指对客观事件进行记录并可以鉴别的符号,是对客观事物的性质、状态以及相互关系等进行记载的物理符号或这些物理符号的组合。它是可识别的、抽象的符号。数据库管理系统(Database Management System) (需要了解)特点: 高效/安全种类: RDBMS:关系型数据库NoSQL:非关系型数据库RDBMS与NOSQL (需要熟悉)RDBMS和NoSQL基本特点产品介绍(熟悉) RDBMS:种类: Oracle、mysql、mssql(SQL Server)、PG(postgresql)特点: 以多张二维表的方式来存储,又给多张表建立了一定关系. 数据安全性要求较高的应用场景NoSQL:种类: redis、mongodb、memcache、Hbase、neo4j特点: 简单,快,适合做缓存数据库 针对性能要求较高,数据安全性要求不是太高的场景,一般是配合RDBMS使用的产品关系型与非关系型数据库的对比 Oracle产品介绍Oracle: 10g 11g 12c 18c (需要了解)MySQL: 5.6 5.7 8.0 (需要熟悉)补充: 5.6 ----->5.6.38 5.6.38 ,GA6个月以上的版本5.7 ----->5.7.17版本以上:5.7.18,5.7.20 , GA6个月以上的版本GA=稳定版本MySQL获取与安装方式介绍MySQL官方下载链接 RPM、Yum:安装方便、安装速度快,无法定制 (需要了解) 二进制:不需要安装,解压即可使用,不能定制功能 (需要熟悉) 编译安装:可定制,安装慢。(需要熟悉)4个步骤: 1.解压(tar)2.生成(./configure) 3.编译(make)4.安装(make install) 5.5之前:./configure make make install5.5之后:cmake gmake先编译,然后制作rpm,制作yum库,然后yum安装.(需要熟悉)简单、速度快、可定制,比较复杂 制作时间长 企业选择安装方式中小企业:以上方式都可以,运维偏向编译,dba偏向选择大型企业:可以选择第4种安装方式源码编译安装MySQL安装前准备下载好5.6.38百度云提取:5.6.38版本提取码: ht2b 上传到服务器上安装依赖包yum install -y ncurses-devel libaio-devel安装cmake代替了之前的./config yum install cmake -y创建用户useradd -s /sbin/nologin -M mysqlid mysql创建目录 ...

May 11, 2019 · 1 min · jiezi

Nodejs

本demo是使用express+mySql制作一个简单的链接sql项目前准备安装node.js http://nodejs.cn/安装express http://www.expressjs.com.cn/安装Mysql https://www.mysql.com/项目结构初始化第一步:首先新建express站点,这些我们新建的项目名称是expres sql,如果小伙伴们不知道express的这些指令,可以通过express –help查看(插一句,在这之前确保已经安装了 express)第二步:进入到这个项目目录 cd sql第三步:安装依赖 npm install第四步:启动这个项目* & npm start,这里如果你安装了pm2,也可以使用pm2启动第五步:命令行会提示在哪个端口监听,如果想改默认端口号,在bin文件夹下面的www文件进行修改第六步:打开浏览器进行查看 localhost:3000(默认) 至于文件夹里面的目是用express 生成的 http://www.expressjs.com.cn/首页页面+功能实现关于系统中和用户的相关路由配置都写的routes文件夹下面的item.js中 注意: app.js文件中引入了routes中的item.js,var item = require('./routes/item');并且使用app.use()将应用挂载到app应用上app.use(‘/item’, itemRouter);所以在访问item这个路径时就要变成/users/item新建html页面 <!DOCTYPE html><html><head> <title></title></head><body></body></html><script src="https://cdn.bootcss.com/jquer...;></script> <script> $(function(){ $.ajax({ url:"http://localhost:3000/item/list", type:'post', dataType:'json', success:function(e){ for(var i in e){ $('body').append("<h1>"+"<a href='id.html?id="+e[i].id+"'>"+e[i].name+"</a>"+"</h1>"+"<p>"+e[i].content+"</p>") } } }) })</script>现在通过在自己电脑输入http://localhost:3000/routes文件夹下item.js下面输入注册的路由var express=require('express');//引入express 模块var router=express.Router(); //路由var mysql= require('mysql');//引入mysql模块var connection=mysql.createConnection({ //链接数据库池 host:'localhost', user:'root',//用户名 password:'123456'//密码 在配置mysql 的时候设置}); router.post('/list',function(req,res,next){ res.header('Access-Control-Allow-Origin','*') ;connection.query('SELECT * FROM baobei.list_table', function(err, rows, fields) {res.send(rows)});}) ...

May 11, 2019 · 1 min · jiezi

mysql-sql语句大全MySQL语句-整理

mysql sql语句大全(MySQL语句 整理) 整理加入DESC 降序ASC 升序 复制代码 1、说明:创建数据库CREATE DATABASE database-name2、说明:删除数据库drop database dbname3、说明:备份sql server--- 创建 备份数据的 deviceUSE masterEXEC sp_addumpdevice 'disk', 'testBack', 'c:mssql7backupMyNwind_1.dat'--- 开始 备份BACKUP DATABASE pubs TO testBack4、说明:创建新表create table tabname(col1 type1 [not null] [primary key],col2 type2 [not null],..)根据已有的表创建新表:A:create table tab_new like tab_old (使用旧表创建新表)B:create table tab_new as select col1,col2… from tab_old definition only5、说明:删除新表drop table tabname6、说明:增加一个列Alter table tabname add column col type注:列增加后将不能删除。DB2中列加上后数据类型也不能改变,唯一能改变的是增加varchar类型的长度。7、说明:添加主键: Alter table tabname add primary key(col)说明:删除主键: Alter table tabname drop primary key(col)8、说明:创建索引:create [unique] index idxname on tabname(col….)删除索引:drop index idxname注:索引是不可更改的,想更改必须删除重新建。9、说明:创建视图:create view viewname as select statement删除视图:drop view viewname10、说明:几个简单的基本的sql语句选择:select * from table1 where 范围插入:insert into table1(field1,field2) values(value1,value2)删除:delete from table1 where 范围更新:update table1 set field1=value1 where 范围查找:select * from table1 where field1 like ’%value1%’ ---like的语法很精妙,查资料!排序:select * from table1 order by field1,field2 [desc]总数:select count as totalcount from table1求和:select sum(field1) as sumvalue from table1平均:select avg(field1) as avgvalue from table1最大:select max(field1) as maxvalue from table1最小:select min(field1) as minvalue from table111、说明:几个高级查询运算词A: UNION 运算符UNION 运算符通过组合其他两个结果表(例如 TABLE1 和 TABLE2)并消去表中任何重复行而派生出一个结果表。当 ALL 随 UNION 一起使用时(即 UNION ALL),不消除重复行。两种情况下,派生表的每一行不是来自 TABLE1 就是来自 TABLE2。B: EXCEPT 运算符EXCEPT 运算符通过包括所有在 TABLE1 中但不在 TABLE2 中的行并消除所有重复行而派生出一个结果表。当 ALL 随 EXCEPT 一起使用时 (EXCEPT ALL),不消除重复行。C: INTERSECT 运算符INTERSECT 运算符通过只包括 TABLE1 和 TABLE2 中都有的行并消除所有重复行而派生出一个结果表。当 ALL 随 INTERSECT 一起使用时 (INTERSECT ALL),不消除重复行。注:使用运算词的几个查询结果行必须是一致的。12、说明:使用外连接A、left (outer) join:左外连接(左连接):结果集几包括连接表的匹配行,也包括左连接表的所有行。SQL: select a.a, a.b, a.c, b.c, b.d, b.f from a LEFT OUT JOIN b ON a.a = b.cB:right (outer) join:右外连接(右连接):结果集既包括连接表的匹配连接行,也包括右连接表的所有行。C:full/cross (outer) join:全外连接:不仅包括符号连接表的匹配行,还包括两个连接表中的所有记录。12、分组:Group by: 一张表,一旦分组完成后,查询后只能得到组相关的信息。 组相关的信息:(统计信息) count,sum,max,min,avg 分组的标准) ...

May 10, 2019 · 8 min · jiezi

云社区技术沙龙深圳站与大咖聊聊互联网架构

5月25日,在深圳腾讯滨海大厦,云+社区邀您参加《互联网架构》沙龙活动,一起探讨技术架构发展趋势,畅想未来。 技术不断演变的过程中,技术架构对于企业来说起到什么作用? 本期沙龙将邀请腾讯的技术专家分享关于技术架构、落地实践案例、无服务器云函数架构、海量存储系统架构等话题,从技术角度看架构发展,带来丰富的实践经验内容,让你对技术架构有更深入的了解和认识 活动信息 点此报名

May 10, 2019 · 1 min · jiezi

根据不同需求选择使用不同mysql存储引擎

根据不同需求选择使用不同mysql存储引擎 1、InnoDB引擎(默认) 事务安全(ACID),并发,类似银行交易数据,需要具有提交、回滚、崩溃恢复能力。2、MyISAM引擎 若数据表主要是写入与查询操作,则此引擎效率较高。类似一些固定配置数据。3、Memory引擎 存放临时数据、中间结果。多表联合查询结果存入临时表,后再取临时表数据进行分组、重排序等。4、Archive引擎 只需要写入与查询、持续高并发写入,类似记录日志。5、CSV引擎 导入csv文件。个人想法,请大神们指教

May 10, 2019 · 1 min · jiezi

MySQL-InnoDB索引原理和算法

也许你经常用MySQL,也会经常用索引,但是对索引的原理和高级功能却并不知道,我们在这里一起学习下。 InnoDB存储索引在数据库中,如果索引太多,应用程序的性能可能会受到影响;如果索引太少,又会对查询性能产生影响。所以,我们要追求两者的一个平衡点,足够多的索引带来查询性能提高,又不因为索引过多导致修改数据等操作时负载过高。 InnoDB支持3种常见索引: 哈希索引B+ 树索引全文索引我们接下来要详细讲解的就是B+ 树索引和全文索引。 哈希索引InnoDB存储引擎支持的哈希索引是自适应的,会根据表的使用情况自动为表生成哈希索引,不能人为干预是否在一张表中生成哈希索引。这块内容我们先不展开说,后续补充。 B+ 树索引B+ 树索引是目前关系型数据库系统中查找最为常用和有效的索引,其构造类似于二叉树,根据键值对快速找到数据。B+ 树(balance+ tree)由B树(banlance tree 平衡二叉树)和索引顺序访问方法(ISAM: Index Sequence Access Method)演化而来,这几个都是经典的数据结构。而MyISAM引擎最初也是参考ISAM数据结构设计的。 基础数据结构想要了解B+ 树数据结构,我们先了解一些基础的知识。 二分查找法又称为折半查找法,指的是将数据顺序排列,通过每次和中间值比较,跳跃式查找,每次缩减一半的范围,快速找到目标的算法。其算法复杂度为log2(n),比顺序查找要快上一些。 如图所示,从有序列表中查找48,只需要3步: 详细的算法可以参考二分查找算法。 二叉查找树二叉查找树的定义是在一个二叉树中,左子树的值总是小于根键值,根键值总是小于右子树的值。在我们查找时,每次都从根开始查找,根据比较的结果来判断继续查找左子树还是右子树。其查找的方法非常类似于二分查找法。 平衡二叉树二叉查找树的定义非常宽泛,可以任意构造,但是在极端情况下查询的效率和顺序查找一样,如只有左子树的二叉查找树。 若想构造一个性能最大的二叉查找树,就需要该树是平衡的,即平衡二叉树(由于其发明者为G. M. Adelson-Velsky 和 Evgenii Landis,又被称为AVL树)。其定义为必须满足任何节点的两个子树的高度最大差为1的二叉查找树。平衡二叉树相对结构较优,而最好的性能需要建立一个最优二叉树,但由于维护该树代价高,因此一般平衡二叉树即可。 平衡二叉树查询速度很快,但在树发生变更时,需要通过一次或多次左旋和右旋来达到树新的平衡。这里不发散讲。 B+ 树了解了基础的数据结构后,我们来看下B+ 树的实现,其定义十分复杂,目标是为磁盘或其他直接存取辅助设备设计的一种平衡查找树。在该树中,所有的记录都按键值的大小放在同一层的叶子节点上,各叶子节点之间有指针进行连接(非连续存储),形成一个双向链表。索引节点按照平衡树的方式构造,并存在指针指向具体的叶子节点,进行快速查找。 下面的B+ 树为数据较少时,此时高度为2,每页固定存放4条记录,扇出固定为5(图上灰色部分)。叶子节点存放多条数据,是为了降低树的高度,进行快速查找。 当我们插入28、70、95 3条数据后,B+ 树由于数据满了,需要进行页的拆分。此时高度变为3,每页依然是4条记录,双向链表未画出但是依然是存在的,现在可以看出来是一个平衡二叉树的雏形了。 InnoDB的B+ 树索引InnoDB的B+ 树索引的特点是高扇出性,因此一般树的高度为2~4层,这样我们在查找一条记录时只用I/O 2~4次。当前机械硬盘每秒至少100次I/O/s,因此查询时间只需0.02~0.04s。 数据库中的B+ 树索引分为聚集索引(clustered index)和辅助索引(secondary index)。它们的区别是叶子节点存放的是否为一整行的完整数据。 聚集索引聚集索引就是按照每张表的主键(唯一)构造一棵B+ 树,同时叶子节点存放整行的完整数据,因此将叶子节点称为数据页。由于定义了数据的逻辑顺序,聚集索引也能快速的进行范围类型的查询。 聚集索引的叶子节点按照逻辑顺序连续存储,叶子节点内部物理上连续存储,作为最小单元,叶子节点间通过双向指针连接,物理存储上不连续,逻辑存储上连续。 聚集索引能够针对主键进行快速的排序查找和范围查找,由于是双向链表,因此在逆序查找时也非常快。 我们可以通过explain命令来分析MySQL数据库的执行计划: # 查看表的定义,可以看到id为主键,name为普通列mysql> show create table dimensionsConf;| Table | Create Table | dimensionsConf | CREATE TABLE `dimensionsConf` ( `id` int(11) NOT NULL AUTO_INCREMENT, `name` varchar(20) DEFAULT NULL, `remark` varchar(1024) NOT NULL, PRIMARY KEY (`id`), FULLTEXT KEY `fullindex_remark` (`remark`)) ENGINE=InnoDB AUTO_INCREMENT=178 DEFAULT CHARSET=utf8 |1 row in set (0.00 sec)# 先测试一个非主键的name属性排序并查找,可以看到没有使用到任何索引,且需要filesort(文件排序),这里的rows为输出行数的预估值mysql> explain select * from dimensionsConf order by name limit 10\G;*************************** 1. row *************************** id: 1 select_type: SIMPLE table: dimensionsConf type: ALLpossible_keys: NULL key: NULL key_len: NULL ref: NULL rows: 57 Extra: Using filesort1 row in set (0.00 sec)# 再测试主键id的排序并查找,此时使用主键索引,在执行计划中没有了filesort操作,这就是聚集索引带来的优化mysql> explain select * from dimensionsConf order by id limit 10\G;*************************** 1. row *************************** id: 1 select_type: SIMPLE table: dimensionsConf type: indexpossible_keys: NULL key: PRIMARY key_len: 4 ref: NULL rows: 10 Extra: NULL1 row in set (0.00 sec)# 再查找根据主键id的范围查找,此时直接根据叶子节点的上层节点就可以快速得到范围,然后读取数据mysql> explain select * from dimensionsConf where id>10 and id<10000\G;*************************** 1. row *************************** id: 1 select_type: SIMPLE table: dimensionsConf type: rangepossible_keys: PRIMARY key: PRIMARY key_len: 4 ref: NULL rows: 56 Extra: Using where1 row in set (0.00 sec)辅助索引辅助索引又称非聚集索引,其叶子节点不包含行记录的全部数据,而是包含一个书签(bookmark),该书签指向对应行数据的聚集索引,告诉InnoDB存储引擎去哪里查找具体的行数据。辅助索引与聚集索引的关系就是结构相似、独立存在,但辅助索引查找非索引数据需要依赖于聚集索引来查找。 ...

May 10, 2019 · 3 min · jiezi

Mysql梳理

DCLData Control Language(数据库的系统管理员)控制用户的访问权限。使用语句包括grant[授权]、revoke[回收权限] eg1:创建一个数据库用户 z1,具有对 zz 数据库中所有表的 SELECT/INSERT 权限: grant select, insert on zz.* to 'z1'@'localhost' identified by 'z123';eg2:将 z1 的权限变更,收回 INSERT,只能对数据进行 SELECT 操作: revoke insert on zz.* from 'z1'@'localhost';这又是什么? GRANT update ON inventory TO joe WITH GRANT OPTION;一个对象权限被授予用户 JOE。with admin option 只能在赋予 system privilege 的时使用;with grant option 只能在赋予 object privilege 的时使用。 系统权限对象权限DDLData Definition Language定义数据库、表、视图、索引和触发器等。create[创建]、alter[修改表定义]、drop[删除]truncate。 创建数据库CREATE DATABASE 数据库名;如果创建的数据表中有值为中文的字段,在创建数据库时需要指定一个支持中文字符的字符集编码。推荐使用UTF-8编码。 CREATE DATABASE db_1 CHARACTER SET UTF-8 COLLATE utf_general_ci;ps:1.数据库名可以由任意字母、数字、下画线(_)和美元符号($)组成,但不能由单独的数字组成,也不能为MySQL关键字,而且长度还不能超过64个字符。2.在windows系统下,数据库名不区分大小写,在UNIX、Linux系统下,数据库名、表名是区分大小写的,但MySQL语句不区分大小写。3.完整的MySQL语句必须以‘;’结尾的语句。或者用g代替;(仅限命令行,有的版本可能不支持了)。 ...

May 9, 2019 · 4 min · jiezi

mysql基础5月

1、登录mysql mysql -uroot -p --prompt=\h~\\cdelimiter //修改默认结束符\T //输出到日志\t

May 9, 2019 · 1 min · jiezi

一次非常有意思的SQL优化经历从30248271s到0001s

本文来源 | toutiao.com/i6668275333034148356 作者 | Java技术架构 背景介绍 我用的数据库是mysql5.6,下面简单的介绍下场景: 课程表: 数据100条 学生表: 数据70000条 学生成绩表SC: 数据70w条 查询目的: 查找语文考100分的考生 查询语句: 执行时间:30248.271s 为什么这么慢?先来查看下查询计划: 发现没有用到索引,type全是ALL,那么首先想到的就是建立一个索引,建立索引的字段当然是在where条件的字段。 先给sc表的c_id和score建个索引 再次执行上述查询语句,时间为: 1.054s 快了3w多倍,大大缩短了查询时间,看来索引能极大程度的提高查询效率,看来建索引很有必要,很多时候都忘记建索引了,数据量小的的时候压根没感觉,这优化感觉挺爽。 但是1s的时间还是太长了,还能进行优化吗,仔细看执行计划: 查看优化后的sql: 补充:这里有网友问怎么查看优化后的语句 方法如下: 在命令窗口执行 有type=all 按照我之前的想法,该sql的执行的顺序应该是先执行子查询 耗时:0.001s 得到如下结果: 然后再执行 耗时:0.001s 这样就是相当快了啊,Mysql竟然不是先执行里层的查询,而是将sql优化成了exists子句,并出现了EPENDENT SUBQUERY, mysql是先执行外层查询,再执行里层的查询,这样就要循环70007*11=770077次。 那么改用连接查询呢? 这里为了重新分析连接查询的情况,先暂时删除索引sc_c_id_index,sc_score_index 执行时间是:0.057s 效率有所提高,看看执行计划: 这里有连表的情况出现,我猜想是不是要给sc表的s_id建立个索引 CREATE index sc_s_id_index on SC(s_id); show index from SC ...

May 9, 2019 · 1 min · jiezi

提高性能MySQL-读写分离环境搭建一

这是松哥之前一个零散的笔记,整理出来分享给大伙! MySQL 读写分离在互联网项目中应该算是一个非常常见的需求了。受困于 Linux 和 MySQL 版本问题,很多人经常会搭建失败,今天松哥就给大伙举一个成功的例子,后面有时间再和大家分享下使用 Docker 搭建环境,那样就 100% 成功了。 CentOS 安装 MySQL自己玩 Linux 松哥一般首选 Ubuntu,不过公司里边使用一般还是 CentOS 为主,因此这里松哥就以 CentOS 为例来向大家演示整个过程,今天这篇文章主要来看看 MySQL 的安装。 环境: CentOS7MySQL5.7具体的安装步骤如下: 检查是否安装了 mariadb,如果已经安装了则卸载:yum list installed | grep mariadb如果执行结果如下,表示已经安装了 mariadb,将之卸载: mariadb-libs.x86_64 1:5.5.52-1.el7 @anaconda卸载命令如下: yum -y remove mariadb* 接下来下载官方提供的 rpm 包如果 CentOS 上没有 wget 命令,首先通过如下命令安装 wget: yum install wget然后执行如下操作下载 rpm 包: wget https://dev.mysql.com/get/mysql57-community-release-el7-11.noarch.rpm下载完成后,安装rpm包:rpm -ivh mysql57-community-release-el7-11.noarch.rpm检查 MySQL 的 yum 源是否安装成功:yum repolist enabled | grep "mysql.*-community.*"执行结果如下表示安装成功: ...

May 9, 2019 · 1 min · jiezi

软件与服务对比分析对象存储的发展历程下

导语在《从“软件”到“服务”——【对象存储】的发展历程(上)》中,我们和大家在对象存储大规模普及之前,大量的数据存储和处理是怎么实现的。但这些方案大都专注于解决其中一类问题,缺少足够的普适性。那么对象存储出现后,究竟解决了什么问题?优势又为何呢?1.软件 V.S 服务跟上一篇提到的各个软件相比,对象存储与之最大的区别不在于实现的机制,而在于形态从软件到服务的一个大飞跃。在这儿我想用一个可能不太恰当的比喻来说这事——传统的体重计。 不管是电子的还是机械的,他只是一个工具,我们评价的标准更多是价格、准确度、易用性、量程。而互联网的体重计,能帮你记录你的体重变化曲线,你关心的可能更多是数据联动、可视化、以及根据你的体重给出的建议。当然,如果你真的对减肥有强烈的需求,那么找一个合适的教练,由教练来指导你的减肥流程才合适,而互联网体重计只是教练手中的一个工具而已。 服务跟软件相比,有几个大的不同点: 首先是自由演化——对象存储的客户可以只关心SLA,并不关心你实现SLA的手段,所以演化更自由;其次是使用服务完全不用关心运维问题——运维问题完全交给服务提供商来解决;最后是采用服务形态后,业务的架构方式更灵活——比如控制面和数据面分离更轻松等。作为一个部署在云端的服务,它的接口和实现是分离的,也就是说我可以在保持接口不变的情况下持续演化实现。我们可以想象一下第一次在 AWS S3 上传的数据还有一些直到今天也没有删除,但这些数据可能已经经历了很多代的硬盘(毕竟硬盘的寿命一般也就3-5年),以及很多代的存储引擎了。这也是与传统存储软件不同的地方,传统存储软件如果大幅度更改了架构,那么通常是以一个新的存储软件的形式来出现。 背后的原因至少有两点: 不同存储引擎之间的平滑过渡和数据迁移难度很高,耗时很长,风险也很大,对于软件的使用者来讲根本不愿承受这些风险;每个存储引擎都有自己的优缺点,如果是服务的提供方,还能接受新引擎的缺点,也能通过硬件或者使用其他方式来弥补,但作为软件来使用的话,部分喜欢老版本优点的用户会长期停留在老版本,这经常会导致社区的分裂。2.传统存储 V.S 对象存储存储类的软件运维永远是一个问题,磁盘的寿命一般是3~5年,在3副本的情况下,1PB存储需要300块10TB硬盘,5年总共260周,也就是说,平均每周都要进行一次以上的硬盘更换操作。而采用对象存储,对应的麻烦一般交给服务供应商来解决。服务供应商一般会选择将坏盘留在机架上,等服务器到期后一次性销毁,来降低运维成本。此外,为了避免单机架、单AZ(Available Zone,可用区,一般一个AZ对应一个机房,两个AZ之间间距不低于20km,且不高于100km)故障导致数据不可用,一般还会采用一些反亲和策略,比如同一数据的多个副本,放在3个机架上,并且至少两个不同的AZ来存储。 跟运维相关的采购负担也是使用存储软件的一个大难题,在很多业务刚开始推广时,并不知道需要多少存储和上传带宽。如果按照上限准备,势必造成大量的浪费。如果准备不足,一旦存储用满,客户无法上传,就是影响运营的超大事故。而使用对象存储,这些问题都不再存在。 采用对象存储后,我们可以更方便地引入控制流和数据流分离。以一个UGC(User-generated content,用户生成内容,比如抖音、快手)类型的图片或者短视频网站为例,如果控制流和数据流不分离,那么为了提供用户访问网站的体验,我们需要租赁优质的多线BGP机房,这类机房的带宽成本非常昂贵,而图片和短视频的带宽需求巨大(主要是上传所需的带宽和CDN回源所需的带宽),造成总成本过高。如果把图片/短视频相关的上传和CDN都挪到对象存储服务商,只把控制相关的部分保留在昂贵的多线BGP机房。首先是上传基本免费,如果租赁同一个服务商的CDN,CDN回源费用也可以打折,而上传、下载的质量保证则由服务商去做保证,在获得足够质量的同时能大幅度节省费用。由于对象存储一般提供各类回调功能和转码功能,所以你原有的功能需求一般也能通过架构微调来满足。 除此之外,对象存储服务还能提供完全无缝的迁移方案,利用镜像存储等功能,可以做到在迁移时,终端用户完全无感知。比如从原始存储站点A迁移到对象存储B,一般步骤如下: 当然实际情况可能会更复杂,比如还涉及到图片转码等功能的迁移。 3.对象存储在中国的特色扩展图片和音视频处理算是很有中国特色的一个对象存储的扩展了,这也跟中国的对象存储发展跟富媒体网站的兴起时间重叠有一定的关系。基于对象存储的富媒体处理的好处不仅仅在于简化了使用流程,免除了客户自己维护图片转码集群负担,还大幅度降低了图片相关的安全风险。众所周知,图片相关的 libjpeg, libpng 等库是安全漏洞的重灾区,UGC类的业务很难避免黑客上传恶意图片来攻击。对象存储的供应商能使用的手段也不仅仅是紧盯CVE及时升级,还包括了使用容器来加固转码引擎,定期清理容器来避免APT攻击等手段。 综上所述,采用对象存储,跟采用存储软件相比,最主要的收益来自于运维负担、采购风险转移给了对象存储供应商,其次的收益还包括更灵活的架构于使用方式。其实对象存储的功能还有很多,如果对象存储兼容常用的S3 协议的话,对应的生态也很强大,不仅有大量的工具,常见的框架一般也有S3的支持。推荐阅读从“软件”到“服务”——【对象存储】的发展历程(上) 免费试用*点击“免费试用”免费领取京东云10GB对象存储额度

May 7, 2019 · 1 min · jiezi

jpa-数据库id自增-数据库别名

id自增 @GeneratedValue(strategy= GenerationType.IDENTITY) @Id private Integer id;数据库别名 @Column(name = "department_name") private String name;

May 7, 2019 · 1 min · jiezi

Windows平台后端开发环境神器Laragon裂墙推荐

Laragon is a portable, isolated, fast & powerful universal development environment for PHP, Node.js, Python, Java, Go, Ruby. It is fast, lightweight, easy-to-use and easy-to-extend.Laragon是一个可移植,隔离,快速且功能强大的通用开发环境,适用于PHP,Node.js,Python,Java,Go,Ruby。它快速,轻便,易于使用且易于扩展。Laragon仓库从github下载 前言从事web开发已经两年多了, 在Windows平台的服务后端开发环境搭建方面最早使用的是XAMPP, 到后来用了很长一段时间的WampServer, 再后来因为nginx的关系用上了功能看似很多的phpstudy, 而这phpstudy的使用体验真是太糟心了, 界面操作逻辑不方便那还没什么, 可运行的nginx服务不稳定会莫名终止就太气人了。每每这样都绝望地将项目放到Laravel推荐的标准开发环境HomeStead上面跑,杀鸡也用牛刀着实不痛快。直到我在Alternativeto(一个推荐同类软件的网站)上发现了Laragon,这款工具真是太棒了,简直将我从麻烦的环境问题中将我解救了出来。对于一款免费还帮了我这么多的工具,我觉得我得为它做点什么才不负于它,于是我想把它推荐给所有需要在Windows平台搭建后台开发环境的开发者,让更多的人知道它的威名~ 一些简单介绍Laragon这是一个可一键开启Apache、Nginx、MySQL、Redis、Memcached等服务的开发环境神器,适用于PHP,Node.js,Python,Java,Go和Ruby的开发。 安装目录 开箱可用的程序下图是程序的存入目录 主界面 选择要开启的服务 常规设置 Laragon最打动我的地方1.项目目录可以放在硬盘任意位置,而不必是软件的安装目录下 选好代码根目录后,会为每个文件夹自动生成相应nginx配置文件auto.开头的文件就是自动生成的配置文件,这类文件会在每次更换代码根目录时被删除再新建,因此建议按自己项目情况配置好后,另起文件名。 同时会根据目录更新host文件 根目录选择了一个php的Laravel项目,public/是入口目录 在设置好代码根目录时Laragon就已经设置好默认的nginx配置了,因此可以直接打开 如果是ThinkPHP项目,nginx的url重写配置要重新定义,如 2.不止有让你的项目跑起来的服务程序,还携带了一系列让你高效开发的配套工具数据库查看有HeidiSQL命令行终端有Cmder专业的日志查看工具[Logs Viewer]成为Laragon默认文本打开工具且加入到Windows右键菜单编辑器[Notepad++]FTP工具WinSCPComposerGit... 还有很多就不一一赘述了总之就是贴心~ 在Cmder中使用composer 3.扩展版本和服务非常简单比如Laragon自带的php版本是7.2的,我要扩展到7.3的话就是从官网上下载windows平台php二进制包,放到Laragon安装目录的bin/php/目录下,然后选择用这个包运行即可。就是这么简单。 放置包 选择使用该包 4.免费一键开启ngrok内网穿透,让本地项目可通过外网查看菜单>代码根目录项>分享>选择要分享出去的目录 ngrok 外网访问这个功能估计是免费且服务器在海外,因此速度和稳定性不是七分理想,偶尔一用还是很不错的,也省了很多功夫。 后记如果我上面说的也是你想要的,那请立即下载体验吧。

May 7, 2019 · 1 min · jiezi

MySql-事物及隔离级别

一、事务的基本要素(ACID) 1、原子性(Atomicity):事务开始后所有操作,要么全部做完,要么全部不做,不可能停滞在中间环节。事务执行过程中出错,会回滚到事务开始前的状态,所有的操作就像没有发生一样。也就是说事务是一个不可分割的整体,就像化学中学过的原子,是物质构成的基本单位。 2、一致性(Consistency):事务开始前和结束后,数据库的完整性约束没有被破坏 。比如A向B转账,不可能A扣了钱,B却没收到。 3、隔离性(Isolation):同一时间,只允许一个事务请求同一数据,不同的事务之间彼此没有任何干扰。比如A正在从一张银行卡中取钱,在A取钱的过程结束前,B不能向这张卡转账。 4、持久性(Durability):事务完成后,事务对数据库的所有更新将被保存到数据库,不能回滚。 二、事务的四种隔离级别在数据库操作中,为了有效保证并发读取数据的正确性,提出的事务隔离级别。我们的数据库锁,也是为了构建这些隔离级别存在的。隔离级别脏读(Dirty Read)不可重复读(NonRepeatable Read)幻读(Phantom Read)未提交读(Read uncommitted)可能可能可能已提交读(Read committed)不可能可能可能可重复读(Repeatable read)不可能不可能可能可串行化(Serializable )不可能不可能不可能未提交读(Read Uncommitted):允许脏读,也就是可能读取到其他会话中未提交事务修改的数据提交读(Read Committed):只能读取到已经提交的数据。Oracle等多数数据库默认都是该级别 (不重复读)可重复读(RepeatedRead):可重复读。在同一个事务内的查询都是事务开始时刻一致的,InnoDB默认级别。在SQL标准中,该隔离级别消除了不可重复读,但是还存在幻象读。mysql默认级别:可重复读串行读(Serializable):完全串行化的读,每次读都需要获得表级共享锁,读写相互都会阻塞三、事务的并发问题 1、脏读:事务A读取了事务B更新的数据,然后B回滚操作,那么A读取到的数据是脏数据 2、不可重复读:事务 A 多次读取同一数据,事务 B 在事务A多次读取的过程中,对数据作了更新并提交,导致事务A多次读取同一数据时,结果 不一致。 3、幻读:系统管理员A将数据库中所有学生的成绩从具体分数改为ABCDE等级,但是系统管理员B就在这个时候插入了一条具体分数的记录,当系统管理员A改结束后发现还有一条记录没有改过来,就好像发生了幻觉一样,这就叫幻读。 小结:不可重复读的和幻读很容易混淆,不可重复读侧重于修改,幻读侧重于新增或删除。解决不可重复读的问题只需锁住满足条件的行,解决幻读需要锁表。 四、MVCC在MySQL的InnoDB中的实现在InnoDB中,会在每行数据后添加两个额外的隐藏的值来实现MVCC,这两个值一个记录这行数据何时被创建,另外一个记录这行数据何时过期(或者被删除)。 在实际操作中,存储的并不是时间,而是事务的版本号,每开启一个新事务,事务的版本号就会递增。 在可重读Repeatable reads事务隔离级别下: SELECT时,读取创建版本号<=当前事务版本号,删除版本号为空或>当前事务版本号。INSERT时,保存当前事务版本号为行的创建版本号。DELETE时,保存当前事务版本号为行的删除版本号。UPDATE时,插入一条新纪录,保存当前事务版本号为行创建版本号,同时保存当前事务版本号到原来删除的行。通过MVCC,虽然每行记录都需要额外的存储空间,更多的行检查工作以及一些额外的维护工作,但可以减少锁的使用,大多数读操作都不用加锁,读数据操作很简单,性能很好,并且也能保证只会读取到符合标准的行,也只锁住必要行。 我们不管从数据库方面的教课书中学到,还是从网络上看到,大都是上文中事务的四种隔离级别这一模块列出的意思。 MVCC 总结:为了实现快照读(读写不冲突)五 MySQL死锁死锁是只两个或者多个事务在同一个资源上相互占用,并请求锁定对方占用的资源。从而导致循环的现象。当多个事务试图以不同的顺序锁定资源时,就可能产生死锁。多个事务同事锁定同一个资源时,也会产生死锁。例如,两个事务同事处理stockprice表。 事务1: start transaction; update stockprice set close = 45.50 where stock_id = 4 and date = '2019-05-05'; update stockprice set close = 36.66 where stock_id = 3 and date = '2019-05-06'; commit事务2: start transaction; update stockprice set high = 33.33 where stock_id = 3 and date = '2019-05-06'; update stockprice set high = 35.66 where stock_id = 4 and date = '2019-05-05'; commit 如果连个都执行了第一条update 语句,跟新了一行数据,同事也锁定了该行数据,接着每个事务都尝试去执行第二条update语句,发现该行已经被对方锁定,然后两个事务都等待对方释放锁,同事又持有对方需要的锁,则陷入死循环。除非有外部因素介入才能解除死锁。 ...

May 6, 2019 · 1 min · jiezi

04-MySQL数据库索引

面试官:当一条查询执行较慢时通常可以如何进行优化我:加索引!面试官:那么到底什么是索引,其底层又是如何实现的呢我:懵逼! 索引的常见模型 索引的出现是为了提高查询效率,就像书的目录一样 常见的实现索引的模型有:哈希表、有序数组和搜索树哈希表:键 - 值(key - value)。哈希思路:把值放在数组里,用一个哈希函数把key换算成一个确定的位置,然后把value放在数组的这个位置哈希冲突的处理办法:链表哈希表适用场景:只有等值查询的场景有序数组:按顺序存储。查询用二分法就可以快速查询,时间复杂度是:O(log(N))有序数组查询效率高,更新效率低有序数组的适用场景:静态存储引擎。二叉搜索树:每个节点的左儿子小于父节点,父节点又小于右儿子二叉搜索树:查询时间复杂度O(log(N)),更新时间复杂度O(log(N))数据库存储大多不适用二叉树,因为树高过高,会适用N叉树 哈希表 是一种以键-值(key-value)存储数据的结构,我们只要输入待查找的值即key,就可以找到其对应的值即Value。哈希的思路很简单,把值放在数组里,用一个哈希函数把key换算成一个确定的位置,然后把value放在数组的这个位置。(与HashMap类似)优点:效率高缺点:因为不是有序的,所以哈希索引做区间查询的速度是很慢的。 你可以设想下,如果你现在要找某字段在[a, b]这个区间的数据,就必须全部扫描一遍了。 所以,哈希表这种结构适用于只有等值查询的场景,不适用于区间查询 有序数组 等值查询和范围查询场景中的性能就都非常优秀 搜索树模型又可以细分为二叉树红黑树B+树 索引的实现由存储引擎来决定,InnoDB索引的实现使用B+树模型二叉树和红黑树的搜索效率很高,但是应用在数据库中时因为数据量较大,二叉树和红黑树每次只分裂出两个分支,导致分裂层数很大,空间占用率高而B+树选择增加分支树,把整颗树的高度维持在很小的范围内,同时在内存里缓存前面若干层的节点,可以极大地降低访问磁盘的次数,提高读的效率。同时要注意的一点是:二叉树类数据结构效率高的前提是数据有序,这也是数据库常存在一个自增主键的原因 扩展:什么是B+树 B-树 即Balance-tree即B树 B+树 B+树索引并不能找到一个给定键值的具体行。B+树索引能找到的只是被查找数据行所在的页。然后数据库通过把页读入到内存,再在内存中进行查找,最后得到要在找的数据。因为页目录中的槽是按照主键顺序排列的,所以在每一个页目录中,通过二分查找,定位到数据行所在的页,然后将整个页读入内存 B*树 是B+树的变体,在B+树的非根和非叶子结点再增加指向兄弟的指针 B树模型小结: B(B-)树:多路搜索树,每个结点存储M/2到M个关键字,非叶子结点存储指向关键字范围的子结点;所有关键字在整颗树中出现,且只出现一次,非叶子结点可以命中;B+树:在B-树基础上,为叶子结点增加链表指针,所有关键字都在叶子结点中出现,非叶子结点作为叶子结点的索引;B+树总是到叶子结点才命中;B*树:在B+树基础上,为非叶子结点也增加链表指针,将结点的最低利用率从1/2提高到2/3;索引失效 1、如果条件中有or,即使其中有部分条件带索引也不会使用,除非条件中的列全部有索引。2、like查询是以%开头(但是以%结尾却不会失效)3、如果列类型是字符串,那一定要在条件中将数据使用引号引用起来,否则不使用索引。(例如where ID = 3 和 where ID = "3")4、如果mysql估计使用全表扫描要比使用索引快,则不使用索引。(因为server层有优化器)

May 6, 2019 · 1 min · jiezi

03MySQL数据库事务的隔离级别

事务 就是要保证一组数据库操作,要么全部成功,要么全部失败。 在MySQL中,事务支持是在引擎层实现的 MySQL是一个支持多引擎的系统,但并不是所有的引擎都支持事务。比如MySQL原生的MyISAM引擎就不支持事务,这也是MyISAM被InnoDB取代的重要原因之一。事务的四大特性:ACID(Atomicity、Consistency、Isolation、Durability,即原子性、一致性、隔离性、持久性),今天我们就来说说其中I,也就是“隔离性”。 当数据库上有多个事务同时执行的时候,就可能出现脏读(dirty read)、不可重复读(non-repeatable read)、幻读(phantom read)的问题,为了解决这些问题,就有了“隔离级别”的概念。 在谈隔离级别之前,你首先要知道,你隔离得越严实,效率就会越低。因此很多时候,我们都要在二者之间寻找一个平衡点。 SQL标准的事务隔离级别包括:(从上到下越来越严实) 读未提交(read uncommitted)读提交(read committed)可重复读(repeatable read)串行化(serializable )逐一解释: 读未提交是指,一个事务还没提交时,它做的变更就能被别的事务看到。这会带来脏读、幻读、不可重复读问题。(基本没用)读提交是指,一个事务提交之后,它做的变更才会被其他事务看到。避免了脏读,但仍然存在不可重复读和幻读问题。可重复读是指,一个事务执行过程中看到的数据,这个事务自己看到的数据始终不变(当然他可能已经被其他事务改变了)在可重复读隔离级别下,未提交变更对其他事务也是不可见的。 避免了脏读和不可重复读问题,但幻读依然存在。串行化,顾名思义是对于同一行记录,“写”会加“写锁”,“读”会加“读锁”。当出现读写锁冲突的时候,后访问的事务必须等前一个事务执行完成,才能继续执行,避免了以上所有问题。直接看文字描述可能不太好理解,那我们来看图吧 我们来看看在不同的隔离级别下,事务A会有哪些不同的返回结果,也就是图里面V1、V2、V3的返回值分别是什么。 若隔离级别是“读未提交”, 则V1的值就是2。这时候事务B虽然还没有提交,但是结果已经被A看到了。因此,V2、V3也都是2。若隔离级别是“读提交”,则V1是1,V2的值是2。事务B的更新在提交后才能被A看到。所以, V3的值也是2。若隔离级别是“可重复读”,则V1、V2是1,V3是2。之所以V2还是1,遵循的就是这个要求:事务在执行期间看到的数据前后必须是一致的。若隔离级别是“串行化”,则在事务B执行“将1改成2”的时候,会被锁住。直到事务A提交后,事务B才可以继续执行。所以从A的角度看, V1、V2值是1,V3的值是2。在实现上,数据库里面会创建一个视图,访问的时候以视图的逻辑结果为准。在“可重复读”隔离级别下,这个视图是在事务启动时创建的,整个事务存在期间都用这个视图。在“读提交”隔离级别下,这个视图是在每个SQL语句开始执行的时候创建的。这里需要注意的是,“读未提交”隔离级别下直接返回记录上的最新值,没有视图概念;而“串行化”隔离级别下直接用加锁的方式来避免并行访问。 我们可以看到在不同的隔离级别下,数据库行为是有所不同的。Oracle数据库的默认隔离级别其实就是“读提交”,因此对于一些从Oracle迁移到MySQL的应用,为保证数据库隔离级别的一致,你一定要记得将MySQL的隔离级别设置为“读提交”。 总结来说,存在即合理,哪个隔离级别都有它自己的使用场景,你要根据自己的业务情况来定。我想你可能会问那什么时候需要“可重复读”的场景呢?我们来看一个数据校对逻辑的案例。 假设你在管理一个个人银行账户表。一个表存了每个月月底的余额,一个表存了账单明细。这时候你要做数据校对,也就是判断上个月的余额和当前余额的差额,是否与本月的账单明细一致。你一定希望在校对过程中,即使有用户发生了一笔新的交易,也不影响你的校对结果。 这时候使用“可重复读”隔离级别就很方便。事务启动时的视图可以认为是静态的,不受其他事务更新的影响。 悲观锁与乐观锁 悲观锁,正如它的名字那样,数据库总是认为别人会去修改它所要操作的数据,因此在数据库处理过程中将数据加锁。其实现依靠数据库底层。 乐观锁,如它的名字那样,总是认为别人不会去修改,只有在提交更新的时候去检查数据的状态。通常是给数据增加一个字段来标识数据的版本。 MySQL的MVCC(多版本并发控制) 我们知道,MySQL的innodb采用的是行锁,而且采用了多版本并发控制来提高读操作的性能。 什么是多版本并发控制呢 ?其实就是在每一行记录的后面增加两个隐藏列,记录创建版本号和删除版本号, 而每一个事务在启动的时候,都有一个唯一的递增的版本号。 1、在插入操作时 : 记录的创建版本号就是事务版本号。 比如我插入一条记录, 事务id 假设是1 ,那么记录如下:也就是说,创建版本号就是事务版本号。 2、在更新操作的时候,采用的是先标记旧的那行记录为已删除,并且删除版本号是事务版本号,然后插入一行新的记录的方式。 比如,针对上面那行记录,事务Id为2 要把name字段更新 update table set name= 'new_value' where id=1; 3、删除操作的时候,就把事务版本号作为删除版本号。比如 delete from table where id=1; 4、查询操作: 从上面的描述可以看到,在查询时要符合以下两个条件的记录才能被事务查询出来: 1) 删除版本号 大于 当前事务版本号,就是说删除操作是在当前事务启动之后做的。 2) 创建版本号 小于或者等于 当前事务版本号 ,就是说记录创建是在事务中(等于的情况)或者事务启动之前。 ...

May 5, 2019 · 1 min · jiezi

MySQL在win10以及linux下数据库的备份以及还原

MySQL在win环境或者linux下的命令都是一样的,只是路径不一致而已 MySQL的备份 (非必须)命令行进入MySQL的bin目录输入命令:mysqldump -u userName -p dataBaseName > filePath and fileName输入密码MySQL的还原 (非必须)命令行进入MySQL的bin目录登录MySQL:mysql -u 用户名 -p 密码新建/使用数据库 新建数据库:create database dataBaseName;使用现成数据库:use dataBaseName;还原数据库:source filePath and fileName;

May 5, 2019 · 1 min · jiezi

MySQL在Win10与Ubuntu下的安装与配置

    近段时间把自己电脑(win)、虚拟机(Ubuntu)以及阿里云(ubuntu)都重置了一遍,其中本机以及阿里云都有用到MySQL,不想之后找教程找的那么麻烦。所以就自己总结一遍,一次性把轮子造好。     环境 Win10 1803 HomeUbuntu 16.04.3Windows环境下安装下载MySQL压缩包https://dev.mysql.com/downloads/mysql/解压到本地目录,并添加一个配置文件,命名为my.ini,内容如下:[mysqld] # 设置为自己MYSQL的安装目录 # 注意是双斜杆,我就入过坑basedir=D:\\MySQL# 设置为MYSQL的数据目录 # 文件夹需手动创建datadir=D:\\MySQL\\datadefault-storage-engine=INNODBcharacter-set-server=utf8[mysql]# 设置mysql客户端默认字符集default-character-set=utf8[client]# 设置mysql客户端连接服务端时默认使用的端口port=3306default-character-set=utf8以管理员权限进入MySQL的bin目录d: //MySQL的安装目录盘符cd MySQL/bin安装MySQL服务mysqld --install//出现Service successfully installed即安装成功初始化日志文件mysqld --initialize --console    记住mysql反馈语句中最后一条:a temporary password is....为第八步出现的问题作铺垫。 配置环境变量;D:\MySQL\bin;//分号分隔前属性,bin目录的路径换成自己电脑的路径启动服务net start mysql登录服务器mysql -uroot -p    输入密码提示Access denied for user 'root'@'localhost' (using password: YES)<br/>    解决方法及后续步骤:解决MySQL 8.0登录Access denied for user 'root'@'localhost' (using password: YES) ubuntu环境下安装打开终端输入命令sudo apt-get install mysql-serversudo apt-get isntall mysql-clientsudo apt-get install libmysqlclient-dev    在安装过程中会让你输入密码以及确认密码,不要忘掉,那是mysql的root用户密码 检查是否安装成功sudo netstat -tap | grep mysql    若出现截图内的语句即说明安装成功     存在的一点点问题     原本我是想在ubuntu下像在win一样通过配置文件进行安装的,但是试了很久都不行最后再次重置了服务器。     如果你们有什么方法是可以的可以在评论告诉我。

May 5, 2019 · 1 min · jiezi

02-MySQL数据库的日志系统

要了解数据库的日志系统首先得知道其存在的必要性:数据库事务的ACID中的Durability-持久性就是依靠日志系统来实现的 日志模块:redo-log(InnoDB特有)当数据库引擎InnoDB从服务层接收到一条更新语句,InnoDB 引擎就会先把记录写到 redo log中并更新到内存中(效率非常高),并在空闲的时候将数据写入到磁盘中(此时才是实际更新) 值得注意的是 InnoDB 的 redo-log 记录的数据有限,当超过大小之后会先等日志写入到磁盘释放出一部分空间后才能继续写入到redo-log日志文件中 虽然redo-log 记录的数据有限但依旧可以保留大量数据,当数据库发生异常重启时,依旧可以通过redo-log恢复数据而不用担心数据写入磁盘过程中发生异常而产生的数据丢失 日志模块:bin-log(存在于server层 MySQL自带)最开始 MySQL 里并没有 InnoDB 引擎。MySQL自带的引擎是 MyISAM。bin-log是记录着mysql所有事件的操作,可以通过bin-log做完整恢复,因此当你不小心删库了也可以通过bin-log日志系统恢复数据,可以基于时间点恢复也可以基于位置恢复。你也可以利用二进制日期进行远程复制,通过主机上的二进制日志文件,将数据更改同步到备机。值得注意的是 MyISAM 的bin-log日志系统并没有 crash-safe 能力,这也是 InnoDB 引入redo-log日志系统的原因。bin-log日志文件没有大小限制,是可以线性增长的。当一个文件满了,会重新创建一个日志文件。一般情况下我们安装mysql之后binary log二进制日志并没有开启,需要我们自行开启。 (具体开启语句以及恢复数据语句可以自行百度查到) 日志的两阶段提交上面我们讲了数据库存在的两种日志而其中一种日志不具有crash-safe 能力,那么问题来了:当发生数据库异常重启时,redo-log记录的数据比bin-log记录的数据多怎么办?为了保证日志一致性需要引入事务控制,即日志的两阶段提交 可以看到 在最后三步 写入redo-log先prepare,然后写bin-log,最后提交事务。 当然MySQL还有很多其他的日志,这里只讲解了常用的两种,其余日志可以自行查阅学习

May 5, 2019 · 1 min · jiezi

01一条SQL语句在执行时其底层经历了哪些过程

一条SQL语句在执行时,其底层经历了哪些过程?大体来讲,MySQL 可以分为 Server 层和存储引擎层两部分(当然,首先还得经过客户端)多个存储引擎共用一个server层 因此所有跨存储引擎的功能都在这一层实现,比如存储过程、触发器、视图等 建表时如果不指定存储引擎则默认使用的是InnoDB存储引擎 连接器一条SQL语句从客户端传过来首先会创建一个连接,用username和password认证身份连接完成后如果没有其他操作便处于空闲状态 默认8h自动断开空闲连接连接还分为长连接和短连接长连接:持续使用同一个连接处理请求短连接:一个连接仅执行几次后便断开,然后重新建立连接因为创建连接的过程比较复杂,所以建议尽量使用长连接但是长连接太多有时候MySQL占用内存涨的特别快,此时可以考虑以下两种方案:1.定期断开长连接或者执行一个占用内存大的查询后断开连接重新连接后继续下面的查询2.MySQL5.7以上版本可以使用mysql_reset_connection命令来初始化连接资源,此操作不需要重连以及权限验证,就可以将连接恢复到刚刚创建完的状态 查询缓存建立连接后先去查询缓存但是大家基本不用mysql的缓存功能因为只要有对该表数据更新,表上的所有缓存都会清空然后重新创建缓存所以一般默认不查缓存 但可以使用select SQL_CACHE * from T where ID = 1按需查询PS.MySQL8.0直接将查询缓存功能删掉了 分析器经过缓存器后来到分析器先做词法分析 分析出sql语句中的关键字然后做语法分析 判断是否有语法错误 优化器经过分析后MySQL知道你要做什么了,但是在实际执行之前还得经过优化器优化一下在表中有多个索引的时候,由优化器来决定使用哪个索引或者有多表关联(join)的时候决定连接顺序 选择效率高的方案TODO:MySQL根据什么选择索引呢?后续解答 执行器执行器开始执行之前会验证是否有读/写权限 没有则返回权限错误有的话就打开表调用指定的存储引擎接口获取执行结果集 返回给客户端TODO:存储引擎内部机制后续讲解

May 5, 2019 · 1 min · jiezi

解决MySQL-80-输入无误仍然提示Access-denied问题

    近些时间在开始学MySQL,安装挺顺利的,按照网上现成的教程就能安装成功。    但是,在输入 mysql -uroot -p    再输入密码时,遇到了这个情况 Access denied for user 'root'@'localhost' (using password: YES)    在网上找了很多解决办法,但是基本只有一个,在.ini文件中的mysqld条目添加 skip-grant-tables    然后重启服务器,再按照刚刚的步骤再来一遍(最后不输入密码),但是还是一条语句把我拦了下来 Access denied for user 'root'@'localhost' (using password: NO)    综合了网上很多方法,自己一个一个拼接着去试,最后成功了    总体上的思想还是修改.ini配置文件的内容,不过是通过命令行的形式修改,不知道是不是因为版本迭代了把以前那个直接修改文件的方法屏蔽了,无论如何,通过命令行修改在MySQL 8.0上是可以的。     下面开始吧。 以管理员身份打开cmd,切换到MySQL的bin目录关闭MySQL服务器net stop mysql跳过输入密码的步骤(注意:文件名字与路径要与自己的吻合)mysqld --defaults-file="D:\MySQL\my.ini" --console --skip-grant-tables如果出现类似截图圈起来的语句则说明成功 重启服务器net start mysql登录MySQL服务器mysql -uroot -p    输入密码之后就能登录成功了。(数字1跟字母l很像很像) 到这一步差不多就能完成了,但是当我输入show databases;    MySQL给我的反馈是: You must reset your password using ALTER USER statement before executing this statement.    我的猜测应该是MySQL认为安装时提供的随机密码不安全,让用户重置密码。    网上找了一下,然后找到的现成办法    参考文章:https://dev.mysql.com/doc/ref... 密码永不过期的ALTER USER 'root'@'localhost' IDENTIFIED BY '新密码' PASSWORD EXPIRE NEVER;密码有限期的ALTER USER 'root'@'localhost' IDENTIFIED BY '新密码' PASSWORD EXPIRE;    然后重新登录一下服务器就能正常的操作了。

May 5, 2019 · 1 min · jiezi

mysql中的rowid

前言在Oracle数据库的表中的每一行数据都有一个唯一的标识符,称为rowid,在Oracle内部通常就是使用它来访问数据的。 而在MySQL中也有一个类似的隐藏列_rowid来标记唯一的标识。但是需要注意_rowid并不是一个真实存在的列,其本质是一个非空唯一列的别名。 PS:本文是基于MySQL 5.7进行研究的 _rowid到底是什么在前文提到了_rowid并不是一个真实存在的列,其本质是一个非空唯一列的别名。为什么会这么说呢? 因为在某些情况下_rowid是不存在的,其只存在于以下情况: 当表中存在一个数字类型的单列主键时,_rowid其实就是指的是这个主键列当表中不存在主键但存在一个数字类型的非空唯一列时,_rowid其实就是指的是对应非空唯一列。需要注意以下情况是不存在_rowid的 主键列或者非空唯一列的类型不是数字类型主键是联合主键唯一列不是非空的。详情可以参考MySQL官方文档内容: If a table has a PRIMARY KEY or UNIQUE NOT NULL index that consists of a single column that has an integer type, you can use _rowid to refer to the indexed column in SELECT statements, as follows: _rowid refers to the PRIMARY KEY column if there is a PRIMARY KEY consisting of a single integer column. If there is a PRIMARY KEY but it does not consist of a single integer column, _rowid cannot be used.Otherwise, _rowid refers to the column in the first UNIQUE NOT NULL index if that index consists of a single integer column. If the first UNIQUE NOT NULL index does not consist of a single integer column, _rowid cannot be used.参考资料13.1.14 CREATE INDEX SyntaxRe: Oracle ROWID equivalent in MySQL

May 4, 2019 · 1 min · jiezi

增量同步mysql-数据到elasticsearch-canal-adapter方式binlog实现从零到一超级详细全面

下面是我在单机上面从零到一实现增量同步mysql 数据到elasticsearch canal adapter方式(binlog)实现实现步骤(1)安装mysql(2)开启mysql binlog row模式,并启动mysql(3)安装jdk(4)安装Elasticsearch并启动(我安装的是6.4.0,主要目前canal adapter1.1.3还不支持7.0.0的版本)(5)安装kibana并启动(6)安装并启动canal-server(7)安装并启动canal-adapter 我使用的操作系统是centos71、通过yum安装mysql(1)去官网查看最新的安装包https://dev.mysql.com/downloa... (2)下载mysql源安装包wget http://dev.mysql.com/get/mysql57-community-release-el7-11.noarch.rpm目前版本已经很高了,但是我使用的是57安装mysql源 yum -y install mysql57-community-release-el7-11.noarch.rpm查看效果: yum repolist enabled | grep mysql.* (3)安装mysql服务器yum install mysql-community-server(4)启动mysql服务systemctl start mysqld.service查看mysql服务的状态: systemctl status mysqld.service (5)查看初始化密码grep "password" /var/log/mysqld.log登录: mysql -u root -p (6)数据库授权(切记这一步一定要做,我为了方便后面使用的都是root账号,没有说新建一个canal账号)数据库没有授权,只支持localhost本地访问 GRANT ALL PRIVILEGES ON *.* TO 'root'@'%' IDENTIFIED BY '123456' WITH GRANT OPTION;FLUSH PRIVILEGES;用户名:root密码:123456指向ip:%代表所有Ip,此处也可以输入Ip来指定Ip 2、开启mysql binlog模式找到my.cnf文件,我本地目录是/etc/my.cnf添加即可 log-bin=mysql-binbinlog-format=ROWserver-id=1然后重启mysql,检查一下binlog是否正确启动 show variables like '%log_bin%'; 3、安装jdk我装的是jdk版本是1.8.0_202下载网址:https://www.oracle.com/techne...(1)将jdk-8u202-linux-x64.tar.gz放入/usr/local目录(2)解压缩等一系列处理 tar -xzvf jdk-8u202-linux-x64.tar.gzmv jdk-8u202-linux-x64 jdkrm -rf jdk-8u202-linux-x64.tar.gz命令执行完成之后在/usr/local目录下就会生成一个jdk目录(3)配置环境变量 vi /etc/profile增加:export JAVA_HOME=/usr/local/jdkexport CLASSPATH=.:$JAVA_HOME/lib/tools.jar:$JAVA_HOME/lib/dt.jarexport PATH=$JAVA_HOME/bin:$PATH(4)检查JDK是否安装成功 ...

May 4, 2019 · 9 min · jiezi

一千行-MySQL-学习笔记

点击上方“程序员江湖”,选择“置顶或者星标” 你关注的就是我关心的! 做者:格物 原文地址:https://shockerli.net/post/10... 非常不错的总结,强烈建议保存下来,需要的时候看一看。基本操作/* Windows服务 */-- 启动MySQL   net start mysql-- 创建Windows服务   sc create mysql binPath= mysqld_bin_path(注意:等号与值之间有空格)/* 连接与断开服务器 */mysql -h 地址 -P 端口 -u 用户名 -p 密码SHOW PROCESSLIST -- 显示哪些线程正在运行SHOW VARIABLES -- 显示系统变量信息数据库操作/* 数据库操作 */ -------------------- 查看当前数据库   SELECT DATABASE();-- 显示当前时间、用户名、数据库版本   SELECT now(), user(), version();-- 创建库   CREATE DATABASE[ IF NOT EXISTS] 数据库名 数据库选项   数据库选项:       CHARACTER SET charset_name       COLLATE collation_name-- 查看已有库   SHOW DATABASES[ LIKE 'PATTERN']-- 查看当前库信息   SHOW CREATE DATABASE 数据库名-- 修改库的选项信息   ALTER DATABASE 库名 选项信息-- 删除库   DROP DATABASE[ IF EXISTS] 数据库名       同时删除该数据库相关的目录及其目录内容表的操作-- 创建表   CREATE [TEMPORARY] TABLE[ IF NOT EXISTS] [库名.]表名 ( 表的结构定义 )[ 表选项]       每个字段必须有数据类型       最后一个字段后不能有逗号       TEMPORARY 临时表,会话结束时表自动消失       对于字段的定义:           字段名 数据类型 [NOT NULL | NULL] [DEFAULT default_value] [AUTO_INCREMENT] [UNIQUE [KEY] | [PRIMARY] KEY] [COMMENT 'string']-- 表选项   -- 字符集       CHARSET = charset_name       如果表没有设定,则使用数据库字符集   -- 存储引擎       ENGINE = engine_name       表在管理数据时采用的不同的数据结构,结构不同会导致处理方式、提供的特性操作等不同       常见的引擎:InnoDB MyISAM Memory/Heap BDB Merge Example CSV MaxDB Archive       不同的引擎在保存表的结构和数据时采用不同的方式       MyISAM表文件含义:.frm表定义,.MYD表数据,.MYI表索引       InnoDB表文件含义:.frm表定义,表空间数据和日志文件       SHOW ENGINES -- 显示存储引擎的状态信息       SHOW ENGINE 引擎名 {LOGS|STATUS} -- 显示存储引擎的日志或状态信息   -- 自增起始数       AUTO_INCREMENT = 行数   -- 数据文件目录       DATA DIRECTORY = '目录'   -- 索引文件目录       INDEX DIRECTORY = '目录'   -- 表注释       COMMENT = 'string'   -- 分区选项       PARTITION BY ... (详细见手册)-- 查看所有表   SHOW TABLES[ LIKE 'pattern']   SHOW TABLES FROM 表名-- 查看表机构   SHOW CREATE TABLE 表名 (信息更详细)   DESC 表名 / DESCRIBE 表名 / EXPLAIN 表名 / SHOW COLUMNS FROM 表名 [LIKE 'PATTERN']   SHOW TABLE STATUS [FROM db_name] [LIKE 'pattern']-- 修改表   -- 修改表本身的选项       ALTER TABLE 表名 表的选项       eg: ALTER TABLE 表名 ENGINE=MYISAM;   -- 对表进行重命名       RENAME TABLE 原表名 TO 新表名       RENAME TABLE 原表名 TO 库名.表名 (可将表移动到另一个数据库)       -- RENAME可以交换两个表名   -- 修改表的字段机构(13.1.2\. ALTER TABLE语法)       ALTER TABLE 表名 操作名       -- 操作名           ADD[ COLUMN] 字段定义       -- 增加字段               AFTER 字段名          -- 表示增加在该字段名后面               FIRST               -- 表示增加在第一个           ADD PRIMARY KEY(字段名)   -- 创建主键           ADD UNIQUE [索引名] (字段名)-- 创建唯一索引           ADD INDEX [索引名] (字段名) -- 创建普通索引           DROP[ COLUMN] 字段名      -- 删除字段           MODIFY[ COLUMN] 字段名 字段属性     -- 支持对字段属性进行修改,不能修改字段名(所有原有属性也需写上)           CHANGE[ COLUMN] 原字段名 新字段名 字段属性      -- 支持对字段名修改           DROP PRIMARY KEY    -- 删除主键(删除主键前需删除其AUTO_INCREMENT属性)           DROP INDEX 索引名 -- 删除索引           DROP FOREIGN KEY 外键    -- 删除外键-- 删除表   DROP TABLE[ IF EXISTS] 表名 ...-- 清空表数据   TRUNCATE [TABLE] 表名-- 复制表结构   CREATE TABLE 表名 LIKE 要复制的表名-- 复制表结构和数据   CREATE TABLE 表名 [AS] SELECT * FROM 要复制的表名-- 检查表是否有错误   CHECK TABLE tbl_name [, tbl_name] ... [option] ...-- 优化表   OPTIMIZE [LOCAL | NO_WRITE_TO_BINLOG] TABLE tbl_name [, tbl_name] ...-- 修复表   REPAIR [LOCAL | NO_WRITE_TO_BINLOG] TABLE tbl_name [, tbl_name] ... [QUICK] [EXTENDED] [USE_FRM]-- 分析表   ANALYZE [LOCAL | NO_WRITE_TO_BINLOG] TABLE tbl_name [, tbl_name] ...数据操作/* 数据操作 */ -------------------- 增   INSERT [INTO] 表名 [(字段列表)] VALUES (值列表)[, (值列表), ...]       -- 如果要插入的值列表包含所有字段并且顺序一致,则可以省略字段列表。       -- 可同时插入多条数据记录!       REPLACE 与 INSERT 完全一样,可互换。   INSERT [INTO] 表名 SET 字段名=值[, 字段名=值, ...]-- 查   SELECT 字段列表 FROM 表名[ 其他子句]       -- 可来自多个表的多个字段       -- 其他子句可以不使用       -- 字段列表可以用*代替,表示所有字段-- 删   DELETE FROM 表名[ 删除条件子句]       没有条件子句,则会删除全部-- 改   UPDATE 表名 SET 字段名=新值[, 字段名=新值] [更新条件]字符集编码/* 字符集编码 */ -------------------- MySQL、数据库、表、字段均可设置编码-- 数据编码与客户端编码不需一致SHOW VARIABLES LIKE 'character_set_%'   -- 查看所有字符集编码项   character_set_client        客户端向服务器发送数据时使用的编码   character_set_results       服务器端将结果返回给客户端所使用的编码   character_set_connection    连接层编码SET 变量名 = 变量值   SET character_set_client = gbk;   SET character_set_results = gbk;   SET character_set_connection = gbk;SET NAMES GBK;  -- 相当于完成以上三个设置-- 校对集   校对集用以排序   SHOW CHARACTER SET [LIKE 'pattern']/SHOW CHARSET [LIKE 'pattern']   查看所有字符集   SHOW COLLATION [LIKE 'pattern']     查看所有校对集   CHARSET 字符集编码     设置字符集编码   COLLATE 校对集编码     设置校对集编码数据类型(列类型)/* 数据类型(列类型) */ ------------------1\. 数值类型-- a. 整型 ----------   类型         字节     范围(有符号位)   tinyint     1字节    -128 ~ 127      无符号位:0 ~ 255   smallint    2字节    -32768 ~ 32767   mediumint   3字节    -8388608 ~ 8388607   int         4字节   bigint      8字节   int(M)  M表示总位数   - 默认存在符号位,unsigned 属性修改   - 显示宽度,如果某个数不够定义字段时设置的位数,则前面以0补填,zerofill 属性修改       例:int(5)   插入一个数'123',补填后为'00123'   - 在满足要求的情况下,越小越好。   - 1表示bool值真,0表示bool值假。MySQL没有布尔类型,通过整型0和1表示。常用tinyint(1)表示布尔型。-- b. 浮点型 ----------   类型             字节     范围   float(单精度)     4字节   double(双精度)    8字节   浮点型既支持符号位 unsigned 属性,也支持显示宽度 zerofill 属性。       不同于整型,前后均会补填0.   定义浮点型时,需指定总位数和小数位数。       float(M, D)     double(M, D)       M表示总位数,D表示小数位数。       M和D的大小会决定浮点数的范围。不同于整型的固定范围。       M既表示总位数(不包括小数点和正负号),也表示显示宽度(所有显示符号均包括)。       支持科学计数法表示。       浮点数表示近似值。-- c. 定点数 ----------   decimal -- 可变长度   decimal(M, D)   M也表示总位数,D表示小数位数。   保存一个精确的数值,不会发生数据的改变,不同于浮点数的四舍五入。   将浮点数转换为字符串来保存,每9位数字保存为4个字节。2\. 字符串类型-- a. char, varchar ----------   char    定长字符串,速度快,但浪费空间   varchar 变长字符串,速度慢,但节省空间   M表示能存储的最大长度,此长度是字符数,非字节数。   不同的编码,所占用的空间不同。   char,最多255个字符,与编码无关。   varchar,最多65535字符,与编码有关。   一条有效记录最大不能超过65535个字节。       utf8 最大为21844个字符,gbk 最大为32766个字符,latin1 最大为65532个字符   varchar 是变长的,需要利用存储空间保存 varchar 的长度,如果数据小于255个字节,则采用一个字节来保存长度,反之需要两个字节来保存。   varchar 的最大有效长度由最大行大小和使用的字符集确定。   最大有效长度是65532字节,因为在varchar存字符串时,第一个字节是空的,不存在任何数据,然后还需两个字节来存放字符串的长度,所以有效长度是64432-1-2=65532字节。   例:若一个表定义为 CREATE TABLE tb(c1 int, c2 char(30), c3 varchar(N)) charset=utf8; 问N的最大值是多少? 答:(65535-1-2-4-30*3)/3-- b. blob, text ----------   blob 二进制字符串(字节字符串)       tinyblob, blob, mediumblob, longblob   text 非二进制字符串(字符字符串)       tinytext, text, mediumtext, longtext   text 在定义时,不需要定义长度,也不会计算总长度。   text 类型在定义时,不可给default值-- c. binary, varbinary ----------   类似于char和varchar,用于保存二进制字符串,也就是保存字节字符串而非字符字符串。   char, varchar, text 对应 binary, varbinary, blob.3\. 日期时间类型   一般用整型保存时间戳,因为PHP可以很方便的将时间戳进行格式化。   datetime    8字节    日期及时间     1000-01-01 00:00:00 到 9999-12-31 23:59:59   date        3字节    日期         1000-01-01 到 9999-12-31   timestamp   4字节    时间戳        19700101000000 到 2038-01-19 03:14:07   time        3字节    时间         -838:59:59 到 838:59:59   year        1字节    年份         1901 - 2155datetime    YYYY-MM-DD hh:mm:sstimestamp   YY-MM-DD hh:mm:ss           YYYYMMDDhhmmss           YYMMDDhhmmss           YYYYMMDDhhmmss           YYMMDDhhmmssdate        YYYY-MM-DD           YY-MM-DD           YYYYMMDD           YYMMDD           YYYYMMDD           YYMMDDtime        hh:mm:ss           hhmmss           hhmmssyear        YYYY           YY           YYYY           YY4\. 枚举和集合-- 枚举(enum) ----------enum(val1, val2, val3...)   在已知的值中进行单选。最大数量为65535.   枚举值在保存时,以2个字节的整型(smallint)保存。每个枚举值,按保存的位置顺序,从1开始逐一递增。   表现为字符串类型,存储却是整型。   NULL值的索引是NULL。   空字符串错误值的索引值是0。-- 集合(set) ----------set(val1, val2, val3...)   create table tab ( gender set('男', '女', '无') );   insert into tab values ('男, 女');   最多可以有64个不同的成员。以bigint存储,共8个字节。采取位运算的形式。   当创建表时,SET成员值的尾部空格将自动被删除。列属性(列约束)/* 列属性(列约束) */ ------------------1\. PRIMARY 主键   - 能唯一标识记录的字段,可以作为主键。   - 一个表只能有一个主键。   - 主键具有唯一性。   - 声明字段时,用 primary key 标识。       也可以在字段列表之后声明           例:create table tab ( id int, stu varchar(10), primary key (id));   - 主键字段的值不能为null。   - 主键可以由多个字段共同组成。此时需要在字段列表后声明的方法。       例:create table tab ( id int, stu varchar(10), age int, primary key (stu, age));2\. UNIQUE 唯一索引(唯一约束)   使得某字段的值也不能重复。3\. NULL 约束   null不是数据类型,是列的一个属性。   表示当前列是否可以为null,表示什么都没有。   null, 允许为空。默认。   not null, 不允许为空。   insert into tab values (null, 'val');       -- 此时表示将第一个字段的值设为null, 取决于该字段是否允许为null4\. DEFAULT 默认值属性   当前字段的默认值。   insert into tab values (default, 'val');    -- 此时表示强制使用默认值。   create table tab ( add_time timestamp default current_timestamp );       -- 表示将当前时间的时间戳设为默认值。       current_date, current_time5\. AUTO_INCREMENT 自动增长约束   自动增长必须为索引(主键或unique)   只能存在一个字段为自动增长。   默认为1开始自动增长。可以通过表属性 auto_increment = x进行设置,或 alter table tbl auto_increment = x;6\. COMMENT 注释   例:create table tab ( id int ) comment '注释内容';7\. FOREIGN KEY 外键约束   用于限制主表与从表数据完整性。   alter table t1 add constraint t1_t2_fk foreign key (t1_id) references t2(id);       -- 将表t1的t1_id外键关联到表t2的id字段。       -- 每个外键都有一个名字,可以通过 constraint 指定   存在外键的表,称之为从表(子表),外键指向的表,称之为主表(父表)。   作用:保持数据一致性,完整性,主要目的是控制存储在外键表(从表)中的数据。   MySQL中,可以对InnoDB引擎使用外键约束:   语法:   foreign key (外键字段) references 主表名 (关联字段) [主表记录删除时的动作] [主表记录更新时的动作]   此时需要检测一个从表的外键需要约束为主表的已存在的值。外键在没有关联的情况下,可以设置为null.前提是该外键列,没有not null。   可以不指定主表记录更改或更新时的动作,那么此时主表的操作被拒绝。   如果指定了 on update 或 on delete:在删除或更新时,有如下几个操作可以选择:   1\. cascade,级联操作。主表数据被更新(主键值更新),从表也被更新(外键值更新)。主表记录被删除,从表相关记录也被删除。   2\. set null,设置为null。主表数据被更新(主键值更新),从表的外键被设置为null。主表记录被删除,从表相关记录外键被设置成null。但注意,要求该外键列,没有not null属性约束。   3\. restrict,拒绝父表删除和更新。   注意,外键只被InnoDB存储引擎所支持。其他引擎是不支持的。建表规范/* 建表规范 */ ------------------   -- Normal Format, NF       - 每个表保存一个实体信息       - 每个具有一个ID字段作为主键       - ID主键 + 原子表   -- 1NF, 第一范式       字段不能再分,就满足第一范式。   -- 2NF, 第二范式       满足第一范式的前提下,不能出现部分依赖。       消除符合主键就可以避免部分依赖。增加单列关键字。   -- 3NF, 第三范式       满足第二范式的前提下,不能出现传递依赖。       某个字段依赖于主键,而有其他字段依赖于该字段。这就是传递依赖。       将一个实体信息的数据放在一个表内实现。SELECT/* SELECT */ ------------------SELECT [ALL|DISTINCT] select_expr FROM -> WHERE -> GROUP BY [合计函数] -> HAVING -> ORDER BY -> LIMITa. select_expr   -- 可以用 * 表示所有字段。       select * from tb;   -- 可以使用表达式(计算公式、函数调用、字段也是个表达式)       select stu, 29+25, now() from tb;   -- 可以为每个列使用别名。适用于简化列标识,避免多个列标识符重复。       - 使用 as 关键字,也可省略 as.       select stu+10 as add10 from tb;b. FROM 子句   用于标识查询来源。   -- 可以为表起别名。使用as关键字。       SELECT * FROM tb1 AS tt, tb2 AS bb;   -- from子句后,可以同时出现多个表。       -- 多个表会横向叠加到一起,而数据会形成一个笛卡尔积。       SELECT * FROM tb1, tb2;   -- 向优化符提示如何选择索引       USE INDEX、IGNORE INDEX、FORCE INDEX       SELECT * FROM table1 USE INDEX (key1,key2) WHERE key1=1 AND key2=2 AND key3=3;       SELECT * FROM table1 IGNORE INDEX (key3) WHERE key1=1 AND key2=2 AND key3=3;c. WHERE 子句   -- 从from获得的数据源中进行筛选。   -- 整型1表示真,0表示假。   -- 表达式由运算符和运算数组成。       -- 运算数:变量(字段)、值、函数返回值       -- 运算符:           =, <=>, <>, !=, <=, <, >=, >, !, &&, ||,           in (not) null, (not) like, (not) in, (not) between and, is (not), and, or, not, xor           is/is not 加上ture/false/unknown,检验某个值的真假           <=>与<>功能相同,<=>可用于null比较d. GROUP BY 子句, 分组子句   GROUP BY 字段/别名 [排序方式]   分组后会进行排序。升序:ASC,降序:DESC   以下[合计函数]需配合 GROUP BY 使用:   count 返回不同的非NULL值数目  count(*)、count(字段)   sum 求和   max 求最大值   min 求最小值   avg 求平均值   group_concat 返回带有来自一个组的连接的非NULL值的字符串结果。组内字符串连接。e. HAVING 子句,条件子句   与 where 功能、用法相同,执行时机不同。   where 在开始时执行检测数据,对原数据进行过滤。   having 对筛选出的结果再次进行过滤。   having 字段必须是查询出来的,where 字段必须是数据表存在的。   where 不可以使用字段的别名,having 可以。因为执行WHERE代码时,可能尚未确定列值。   where 不可以使用合计函数。一般需用合计函数才会用 having   SQL标准要求HAVING必须引用GROUP BY子句中的列或用于合计函数中的列。f. ORDER BY 子句,排序子句   order by 排序字段/别名 排序方式 [,排序字段/别名 排序方式]...   升序:ASC,降序:DESC   支持多个字段的排序。g. LIMIT 子句,限制结果数量子句   仅对处理好的结果进行数量限制。将处理好的结果的看作是一个集合,按照记录出现的顺序,索引从0开始。   limit 起始位置, 获取条数   省略第一个参数,表示从索引0开始。limit 获取条数h. DISTINCT, ALL 选项   distinct 去除重复记录   默认为 all, 全部记录UNION/* UNION */ ------------------   将多个select查询的结果组合成一个结果集合。   SELECT ... UNION [ALL|DISTINCT] SELECT ...   默认 DISTINCT 方式,即所有返回的行都是唯一的   建议,对每个SELECT查询加上小括号包裹。   ORDER BY 排序时,需加上 LIMIT 进行结合。   需要各select查询的字段数量一样。   每个select查询的字段列表(数量、类型)应一致,因为结果中的字段名以第一条select语句为准。子查询/* 子查询 */ ------------------   - 子查询需用括号包裹。-- from型   from后要求是一个表,必须给子查询结果取个别名。   - 简化每个查询内的条件。   - from型需将结果生成一个临时表格,可用以原表的锁定的释放。   - 子查询返回一个表,表型子查询。   select * from (select * from tb where id>0) as subfrom where id>1;-- where型   - 子查询返回一个值,标量子查询。   - 不需要给子查询取别名。   - where子查询内的表,不能直接用以更新。   select * from tb where money = (select max(money) from tb);   -- 列子查询       如果子查询结果返回的是一列。       使用 in 或 not in 完成查询       exists 和 not exists 条件           如果子查询返回数据,则返回1或0。常用于判断条件。           select column1 from t1 where exists (select * from t2);   -- 行子查询       查询条件是一个行。       select * from t1 where (id, gender) in (select id, gender from t2);       行构造符:(col1, col2, ...) 或 ROW(col1, col2, ...)       行构造符通常用于与对能返回两个或两个以上列的子查询进行比较。   -- 特殊运算符   != all()    相当于 not in   = some()    相当于 in。any 是 some 的别名   != some()   不等同于 not in,不等于其中某一个。   all, some 可以配合其他运算符一起使用。连接查询(join)/* 连接查询(join) */ ------------------   将多个表的字段进行连接,可以指定连接条件。-- 内连接(inner join)   - 默认就是内连接,可省略inner。   - 只有数据存在时才能发送连接。即连接结果不能出现空行。   on 表示连接条件。其条件表达式与where类似。也可以省略条件(表示条件永远为真)   也可用where表示连接条件。   还有 using, 但需字段名相同。 using(字段名)   -- 交叉连接 cross join       即,没有条件的内连接。       select * from tb1 cross join tb2;-- 外连接(outer join)   - 如果数据不存在,也会出现在连接结果中。   -- 左外连接 left join       如果数据不存在,左表记录会出现,而右表为null填充   -- 右外连接 right join       如果数据不存在,右表记录会出现,而左表为null填充-- 自然连接(natural join)   自动判断连接条件完成连接。   相当于省略了using,会自动查找相同字段名。   natural join   natural left join   natural right joinselect info.id, info.name, info.stu_num, extra_info.hobby, extra_info.sex from info, extra_info where info.stu_num = extra_info.stu_id;TRUNCATE/* TRUNCATE */ ------------------TRUNCATE [TABLE] tbl_name清空数据删除重建表区别:1,truncate 是删除表再创建,delete 是逐条删除2,truncate 重置auto_increment的值。而delete不会3,truncate 不知道删除了几条,而delete知道。4,当被用于带分区的表时,truncate 会保留分区备份与还原/* 备份与还原 */ ------------------备份,将数据的结构与表内数据保存起来。利用 mysqldump 指令完成。-- 导出mysqldump [options] db_name [tables]mysqldump [options] ---database DB1 [DB2 DB3...]mysqldump [options] --all--database1\. 导出一张表 mysqldump -u用户名 -p密码 库名 表名 > 文件名(D:/a.sql)2\. 导出多张表 mysqldump -u用户名 -p密码 库名 表1 表2 表3 > 文件名(D:/a.sql)3\. 导出所有表 mysqldump -u用户名 -p密码 库名 > 文件名(D:/a.sql)4\. 导出一个库 mysqldump -u用户名 -p密码 --lock-all-tables --database 库名 > 文件名(D:/a.sql)可以-w携带WHERE条件-- 导入1\. 在登录mysql的情况下: source  备份文件2\. 在不登录的情况下 mysql -u用户名 -p密码 库名 < 备份文件视图什么是视图:   视图是一个虚拟表,其内容由查询定义。同真实的表一样,视图包含一系列带有名称的列和行数据。但是,视图并不在数据库中以存储的数据值集形式存在。行和列数据来自由定义视图的查询所引用的表,并且在引用视图时动态生成。   视图具有表结构文件,但不存在数据文件。   对其中所引用的基础表来说,视图的作用类似于筛选。定义视图的筛选可以来自当前或其它数据库的一个或多个表,或者其它视图。通过视图进行查询没有任何限制,通过它们进行数据修改时的限制也很少。   视图是存储在数据库中的查询的sql语句,它主要出于两种原因:安全原因,视图可以隐藏一些数据,如:社会保险基金表,可以用视图只显示姓名,地址,而不显示社会保险号和工资数等,另一原因是可使复杂的查询易于理解和使用。-- 创建视图CREATE [OR REPLACE] [ALGORITHM = {UNDEFINED | MERGE | TEMPTABLE}] VIEW view_name [(column_list)] AS select_statement   - 视图名必须唯一,同时不能与表重名。   - 视图可以使用select语句查询到的列名,也可以自己指定相应的列名。   - 可以指定视图执行的算法,通过ALGORITHM指定。   - column_list如果存在,则数目必须等于SELECT语句检索的列数-- 查看结构   SHOW CREATE VIEW view_name-- 删除视图   - 删除视图后,数据依然存在。   - 可同时删除多个视图。   DROP VIEW [IF EXISTS] view_name ...-- 修改视图结构   - 一般不修改视图,因为不是所有的更新视图都会映射到表上。   ALTER VIEW view_name [(column_list)] AS select_statement-- 视图作用   1\. 简化业务逻辑   2\. 对客户端隐藏真实的表结构-- 视图算法(ALGORITHM)   MERGE       合并       将视图的查询语句,与外部查询需要先合并再执行!   TEMPTABLE   临时表       将视图执行完毕后,形成临时表,再做外层查询!   UNDEFINED   未定义(默认),指的是MySQL自主去选择相应的算法。事务(transaction)事务是指逻辑上的一组操作,组成这组操作的各个单元,要不全成功要不全失败。   - 支持连续SQL的集体成功或集体撤销。   - 事务是数据库在数据晚自习方面的一个功能。   - 需要利用 InnoDB 或 BDB 存储引擎,对自动提交的特性支持完成。   - InnoDB被称为事务安全型引擎。-- 事务开启   START TRANSACTION; 或者 BEGIN;   开启事务后,所有被执行的SQL语句均被认作当前事务内的SQL语句。-- 事务提交   COMMIT;-- 事务回滚   ROLLBACK;   如果部分操作发生问题,映射到事务开启前。-- 事务的特性   1\. 原子性(Atomicity)       事务是一个不可分割的工作单位,事务中的操作要么都发生,要么都不发生。   2\. 一致性(Consistency)       事务前后数据的完整性必须保持一致。       - 事务开始和结束时,外部数据一致       - 在整个事务过程中,操作是连续的   3\. 隔离性(Isolation)       多个用户并发访问数据库时,一个用户的事务不能被其它用户的事物所干扰,多个并发事务之间的数据要相互隔离。   4\. 持久性(Durability)       一个事务一旦被提交,它对数据库中的数据改变就是永久性的。-- 事务的实现   1\. 要求是事务支持的表类型   2\. 执行一组相关的操作前开启事务   3\. 整组操作完成后,都成功,则提交;如果存在失败,选择回滚,则会回到事务开始的备份点。-- 事务的原理   利用InnoDB的自动提交(autocommit)特性完成。   普通的MySQL执行语句后,当前的数据提交操作均可被其他客户端可见。   而事务是暂时关闭“自动提交”机制,需要commit提交持久化数据操作。-- 注意   1\. 数据定义语言(DDL)语句不能被回滚,比如创建或取消数据库的语句,和创建、取消或更改表或存储的子程序的语句。   2\. 事务不能被嵌套-- 保存点   SAVEPOINT 保存点名称 -- 设置一个事务保存点   ROLLBACK TO SAVEPOINT 保存点名称 -- 回滚到保存点   RELEASE SAVEPOINT 保存点名称 -- 删除保存点-- InnoDB自动提交特性设置   SET autocommit = 0|1;   0表示关闭自动提交,1表示开启自动提交。   - 如果关闭了,那普通操作的结果对其他客户端也不可见,需要commit提交后才能持久化数据操作。   - 也可以关闭自动提交来开启事务。但与START TRANSACTION不同的是,       SET autocommit是永久改变服务器的设置,直到下次再次修改该设置。(针对当前连接)       而START TRANSACTION记录开启前的状态,而一旦事务提交或回滚后就需要再次开启事务。(针对当前事务)锁表/* 锁表 */表锁定只用于防止其它客户端进行不正当地读取和写入MyISAM 支持表锁,InnoDB 支持行锁-- 锁定   LOCK TABLES tbl_name [AS alias]-- 解锁   UNLOCK TABLES触发器/* 触发器 */ ------------------   触发程序是与表有关的命名数据库对象,当该表出现特定事件时,将激活该对象   监听:记录的增加、修改、删除。-- 创建触发器CREATE TRIGGER trigger_name trigger_time trigger_event ON tbl_name FOR EACH ROW trigger_stmt   参数:   trigger_time是触发程序的动作时间。它可以是 before 或 after,以指明触发程序是在激活它的语句之前或之后触发。   trigger_event指明了激活触发程序的语句的类型       INSERT:将新行插入表时激活触发程序       UPDATE:更改某一行时激活触发程序       DELETE:从表中删除某一行时激活触发程序   tbl_name:监听的表,必须是永久性的表,不能将触发程序与TEMPORARY表或视图关联起来。   trigger_stmt:当触发程序激活时执行的语句。执行多个语句,可使用BEGIN...END复合语句结构-- 删除DROP TRIGGER [schema_name.]trigger_name可以使用old和new代替旧的和新的数据   更新操作,更新前是old,更新后是new.   删除操作,只有old.   增加操作,只有new.-- 注意   1\. 对于具有相同触发程序动作时间和事件的给定表,不能有两个触发程序。-- 字符连接函数concat(str1,str2,...])concat_ws(separator,str1,str2,...)-- 分支语句if 条件 then   执行语句elseif 条件 then   执行语句else   执行语句end if;-- 修改最外层语句结束符delimiter 自定义结束符号   SQL语句自定义结束符号delimiter ;     -- 修改回原来的分号-- 语句块包裹begin   语句块end-- 特殊的执行1\. 只要添加记录,就会触发程序。2\. Insert into on duplicate key update 语法会触发:   如果没有重复记录,会触发 before insert, after insert;   如果有重复记录并更新,会触发 before insert, before update, after update;   如果有重复记录但是没有发生更新,则触发 before insert, before update3\. Replace 语法 如果有记录,则执行 before insert, before delete, after delete, after insertSQL编程/* SQL编程 */ --------------------// 局部变量 ------------ 变量声明   declare var_name[,...] type [default value]   这个语句被用来声明局部变量。要给变量提供一个默认值,请包含一个default子句。值可以被指定为一个表达式,不需要为一个常数。如果没有default子句,初始值为null。-- 赋值   使用 set 和 select into 语句为变量赋值。   - 注意:在函数内是可以使用全局变量(用户自定义的变量)--// 全局变量 ------------ 定义、赋值set 语句可以定义并为变量赋值。set @var = value;也可以使用select into语句为变量初始化并赋值。这样要求select语句只能返回一行,但是可以是多个字段,就意味着同时为多个变量进行赋值,变量的数量需要与查询的列数一致。还可以把赋值语句看作一个表达式,通过select执行完成。此时为了避免=被当作关系运算符看待,使用:=代替。(set语句可以使用= 和 :=)。select @var:=20;select @v1:=id, @v2=name from t1 limit 1;select * from tbl_name where @var:=30;select into 可以将表中查询获得的数据赋给变量。   -| select max(height) into @max_height from tb;-- 自定义变量名为了避免select语句中,用户自定义的变量与系统标识符(通常是字段名)冲突,用户自定义变量在变量名前使用@作为开始符号。@var=10;   - 变量被定义后,在整个会话周期都有效(登录到退出)--// 控制结构 ------------ if语句if search_condition then   statement_list  [elseif search_condition then   statement_list]...[else   statement_list]end if;-- case语句CASE value WHEN [compare-value] THEN result[WHEN [compare-value] THEN result ...][ELSE result]END-- while循环[begin_label:] while search_condition do   statement_listend while [end_label];- 如果需要在循环内提前终止 while循环,则需要使用标签;标签需要成对出现。   -- 退出循环       退出整个循环 leave       退出当前循环 iterate       通过退出的标签决定退出哪个循环--// 内置函数 ------------ 数值函数abs(x)          -- 绝对值 abs(-10.9) = 10format(x, d)    -- 格式化千分位数值 format(1234567.456, 2) = 1,234,567.46ceil(x)         -- 向上取整 ceil(10.1) = 11floor(x)        -- 向下取整 floor (10.1) = 10round(x)        -- 四舍五入去整mod(m, n)       -- m%n m mod n 求余 10%3=1pi()            -- 获得圆周率pow(m, n)       -- m^nsqrt(x)         -- 算术平方根rand()          -- 随机数truncate(x, d)  -- 截取d位小数-- 时间日期函数now(), current_timestamp();     -- 当前日期时间current_date();                 -- 当前日期current_time();                 -- 当前时间date('yyyy-mm-dd hh:ii:ss');    -- 获取日期部分time('yyyy-mm-dd hh:ii:ss');    -- 获取时间部分date_format('yyyy-mm-dd hh:ii:ss', '%d %y %a %d %m %b %j'); -- 格式化时间unix_timestamp();               -- 获得unix时间戳from_unixtime();                -- 从时间戳获得时间-- 字符串函数length(string)          -- string长度,字节char_length(string)     -- string的字符个数substring(str, position [,length])      -- 从str的position开始,取length个字符replace(str ,search_str ,replace_str)   -- 在str中用replace_str替换search_strinstr(string ,substring)    -- 返回substring首次在string中出现的位置concat(string [,...])   -- 连接字串charset(str)            -- 返回字串字符集lcase(string)           -- 转换成小写left(string, length)    -- 从string2中的左边起取length个字符load_file(file_name)    -- 从文件读取内容locate(substring, string [,start_position]) -- 同instr,但可指定开始位置lpad(string, length, pad)   -- 重复用pad加在string开头,直到字串长度为lengthltrim(string)           -- 去除前端空格repeat(string, count)   -- 重复count次rpad(string, length, pad)   --在str后用pad补充,直到长度为lengthrtrim(string)           -- 去除后端空格strcmp(string1 ,string2)    -- 逐字符比较两字串大小-- 流程函数case when [condition] then result [when [condition] then result ...] [else result] end   多分支if(expr1,expr2,expr3)  双分支。-- 聚合函数count()sum();max();min();avg();group_concat()-- 其他常用函数md5();default();--// 存储函数,自定义函数 ------------ 新建   CREATE FUNCTION function_name (参数列表) RETURNS 返回值类型       函数体   - 函数名,应该合法的标识符,并且不应该与已有的关键字冲突。   - 一个函数应该属于某个数据库,可以使用db_name.funciton_name的形式执行当前函数所属数据库,否则为当前数据库。   - 参数部分,由"参数名"和"参数类型"组成。多个参数用逗号隔开。   - 函数体由多条可用的mysql语句,流程控制,变量声明等语句构成。   - 多条语句应该使用 begin...end 语句块包含。   - 一定要有 return 返回值语句。-- 删除   DROP FUNCTION [IF EXISTS] function_name;-- 查看   SHOW FUNCTION STATUS LIKE 'partten'   SHOW CREATE FUNCTION function_name;-- 修改   ALTER FUNCTION function_name 函数选项--// 存储过程,自定义功能 ------------ 定义存储存储过程 是一段代码(过程),存储在数据库中的sql组成。一个存储过程通常用于完成一段业务逻辑,例如报名,交班费,订单入库等。而一个函数通常专注与某个功能,视为其他程序服务的,需要在其他语句中调用函数才可以,而存储过程不能被其他调用,是自己执行 通过call执行。-- 创建CREATE PROCEDURE sp_name (参数列表)   过程体参数列表:不同于函数的参数列表,需要指明参数类型IN,表示输入型OUT,表示输出型INOUT,表示混合型注意,没有返回值。存储过程/* 存储过程 */ ------------------存储过程是一段可执行性代码的集合。相比函数,更偏向于业务逻辑。调用:CALL 过程名-- 注意- 没有返回值。- 只能单独调用,不可夹杂在其他语句中-- 参数IN|OUT|INOUT 参数名 数据类型IN      输入:在调用过程中,将数据输入到过程体内部的参数OUT     输出:在调用过程中,将过程体处理完的结果返回到客户端INOUT   输入输出:既可输入,也可输出-- 语法CREATE PROCEDURE 过程名 (参数列表)BEGIN   过程体END用户和权限管理/* 用户和权限管理 */ -------------------- root密码重置1\. 停止MySQL服务2\.  [Linux] /usr/local/mysql/bin/safe_mysqld --skip-grant-tables &   [Windows] mysqld --skip-grant-tables3\. use mysql;4\. UPDATE user SET PASSWORD=PASSWORD("密码") WHERE user = "root";5\. FLUSH PRIVILEGES;用户信息表:mysql.user-- 刷新权限FLUSH PRIVILEGES;-- 增加用户CREATE USER 用户名 IDENTIFIED BY [PASSWORD] 密码(字符串)   - 必须拥有mysql数据库的全局CREATE USER权限,或拥有INSERT权限。   - 只能创建用户,不能赋予权限。   - 用户名,注意引号:如 'user_name'@'192.168.1.1'   - 密码也需引号,纯数字密码也要加引号   - 要在纯文本中指定密码,需忽略PASSWORD关键词。要把密码指定为由PASSWORD()函数返回的混编值,需包含关键字PASSWORD-- 重命名用户RENAME USER old_user TO new_user-- 设置密码SET PASSWORD = PASSWORD('密码')  -- 为当前用户设置密码SET PASSWORD FOR 用户名 = PASSWORD('密码') -- 为指定用户设置密码-- 删除用户DROP USER 用户名-- 分配权限/添加用户GRANT 权限列表 ON 表名 TO 用户名 [IDENTIFIED BY [PASSWORD] 'password']   - all privileges 表示所有权限   - *.* 表示所有库的所有表   - 库名.表名 表示某库下面的某表   GRANT ALL PRIVILEGES ON pms.* TO 'pms'@'%' IDENTIFIED BY 'pms0817';-- 查看权限SHOW GRANTS FOR 用户名   -- 查看当前用户权限   SHOW GRANTS; 或 SHOW GRANTS FOR CURRENT_USER; 或 SHOW GRANTS FOR CURRENT_USER();-- 撤消权限REVOKE 权限列表 ON 表名 FROM 用户名REVOKE ALL PRIVILEGES, GRANT OPTION FROM 用户名   -- 撤销所有权限-- 权限层级-- 要使用GRANT或REVOKE,您必须拥有GRANT OPTION权限,并且您必须用于您正在授予或撤销的权限。全局层级:全局权限适用于一个给定服务器中的所有数据库,mysql.user   GRANT ALL ON *.*和 REVOKE ALL ON *.*只授予和撤销全局权限。数据库层级:数据库权限适用于一个给定数据库中的所有目标,mysql.db, mysql.host   GRANT ALL ON db_name.*和REVOKE ALL ON db_name.*只授予和撤销数据库权限。表层级:表权限适用于一个给定表中的所有列,mysql.talbes_priv   GRANT ALL ON db_name.tbl_name和REVOKE ALL ON db_name.tbl_name只授予和撤销表权限。列层级:列权限适用于一个给定表中的单一列,mysql.columns_priv   当使用REVOKE时,您必须指定与被授权列相同的列。-- 权限列表ALL [PRIVILEGES]    -- 设置除GRANT OPTION之外的所有简单权限ALTER   -- 允许使用ALTER TABLEALTER ROUTINE   -- 更改或取消已存储的子程序CREATE  -- 允许使用CREATE TABLECREATE ROUTINE  -- 创建已存储的子程序CREATE TEMPORARY TABLES     -- 允许使用CREATE TEMPORARY TABLECREATE USER     -- 允许使用CREATE USER, DROP USER, RENAME USER和REVOKE ALL PRIVILEGES。CREATE VIEW     -- 允许使用CREATE VIEWDELETE  -- 允许使用DELETEDROP    -- 允许使用DROP TABLEEXECUTE     -- 允许用户运行已存储的子程序FILE    -- 允许使用SELECT...INTO OUTFILE和LOAD DATA INFILEINDEX   -- 允许使用CREATE INDEX和DROP INDEXINSERT  -- 允许使用INSERTLOCK TABLES     -- 允许对您拥有SELECT权限的表使用LOCK TABLESPROCESS     -- 允许使用SHOW FULL PROCESSLISTREFERENCES  -- 未被实施RELOAD  -- 允许使用FLUSHREPLICATION CLIENT  -- 允许用户询问从属服务器或主服务器的地址REPLICATION SLAVE   -- 用于复制型从属服务器(从主服务器中读取二进制日志事件)SELECT  -- 允许使用SELECTSHOW DATABASES  -- 显示所有数据库SHOW VIEW   -- 允许使用SHOW CREATE VIEWSHUTDOWN    -- 允许使用mysqladmin shutdownSUPER   -- 允许使用CHANGE MASTER, KILL, PURGE MASTER LOGS和SET GLOBAL语句,mysqladmin debug命令;允许您连接(一次),即使已达到max_connections。UPDATE  -- 允许使用UPDATEUSAGE   -- “无权限”的同义词GRANT OPTION    -- 允许授予权限表维护/* 表维护 */-- 分析和存储表的关键字分布ANALYZE [LOCAL | NO_WRITE_TO_BINLOG] TABLE 表名 ...-- 检查一个或多个表是否有错误CHECK TABLE tbl_name [, tbl_name] ... [option] ...option = {QUICK | FAST | MEDIUM | EXTENDED | CHANGED}-- 整理数据文件的碎片OPTIMIZE [LOCAL | NO_WRITE_TO_BINLOG] TABLE tbl_name [, tbl_name] ...杂项/* 杂项 */ ------------------1\. 可用反引号()为标识符(库名、表名、字段名、索引、别名)包裹,以避免与关键字重名!中文也可以作为标识符!`2\. 每个库目录存在一个保存当前数据库的选项文件db.opt。3\. 注释:   单行注释 # 注释内容   多行注释 /* 注释内容 */   单行注释 -- 注释内容     (标准SQL注释风格,要求双破折号后加一空格符(空格、TAB、换行等))4\. 模式通配符:   _   任意单个字符   %   任意多个字符,甚至包括零字符   单引号需要进行转义 '5\. CMD命令行内的语句结束符可以为 ";", "G", "g",仅影响显示结果。其他地方还是用分号结束。delimiter 可修改当前对话的语句结束符。6\. SQL对大小写不敏感7\. 清除已有语句:c ...

May 4, 2019 · 14 min · jiezi

在线数据库关系图设计工具-dbdiagramio

前段时间,笔者在设计某个系统模块的时候,需要增加十几张表。 为了简单快速地把这十几张表设计并定义出来,我找到了一个可以在线设计数据库关系图(database relationship diagram)且可以导出DDL SQL的工具——dbdiagram.io。 dbdiagram.io是holistics.io这款商业产品的社区版。 dbdiagram.io使用DSL语言,可以简单快速地创建数据库关系图。 这款工具的操作界面也非常简约并具有设计感: 有时候我们需要在关系型数据库中设计一些表,以便实现我们的业务功能。或者我们对某个系统的表结构不是很熟悉,希望画个图表示一下这些实体之间的关系。又或者我们希望把设计好的数据库关系图直接转化为DDL SQL。而且我们不想使用复杂的工具,付出高昂的学习成本。也不想用太重的工具,占用内存。这个时候这个在线的数据库关系图工具就排上用场了。 语法下面介绍一下它的语法。 定义表的语法如下: Table users { id integer [pk] username varchar [not null, unique] full_name type [not null] .....}如果表名太长还支持取别名: Table longtablename as t_alias { .....}定义外键支持如下三种关系: < : One-to-many> : Many-to-one- : One-to-one并且提供了3种定义外键的方式: Ref name-optional { table1.field1 < table2.field2}Ref name-optional: t1.f1 < t2.f2Table posts { id integer [pk, ref: < comments.post_id] user_id integer [ref: > users.id]}例子下面以电商系统常用的几张表作为例子演示一下它的用法。 当你登录自己的Google账号以后,可以把你设计好的图形保存到线上,这样就可以通过一个唯一的链接访问 : https://dbdiagram.io/d/5cc910...。 ...

May 1, 2019 · 1 min · jiezi

关于ubuntu安装wordpress的步骤

开始搭建博客啦!!!安装Apacheapt-get install apache2查看状态service apache2 restart/status/start/stop 关闭防火墙80端口限制ufw allow 80安装MySQLapt-get install mysql-server mysql-client 查看状态service mysql retart/status/start/stop关闭防火墙3306端口限制ufw allow 3306安装PHPapt-get install php7.0 apt-get install libapache2-mod-php7.0 apt-get install php7.0-mysql重启服务service apache2 restart service mysql restart安装phpMyAdminsudo apt-get install phpmyadmin 安装时:空格选择apache2,enter确定,下一步配置数据库,输入密码。创建phpMyAdmin快捷方式sudo ln -s /usr/share/phpmyadmin /var/www/html 启用Apache mod_rewrite模块,后面修改wordpress链接时会用sudo a2enmod rewrite 重启服务service php7.0-fpm restart 提示服务没找到?不去管它service apache2 restart配置Apachevim /etc/apache2/apache2.conf添加以下信息:AddType application/x-httpd-php .php .htm .html AddDefaultCharset UTF-8重启Apache服务service apache2 restart安装ufw 防火墙sudo apt-get install ufw 初始化数据库sudo mysql -u root -p Enter Password:…mysql> CREATE DATABASE wordpressdb; mysql>exit重启服务sudo service apache2 restart sudo service mysql restart浏览器访问:http:// ubuntu 地址/phpmyadmin用Xftp连接虚拟机,然后将wordpress里面的所有文件全部都安装到放到/var/www/html里面。打开浏览器访问http://ip地址进行安装就可以了。安装完之后更新会出现问题,所以需要设置权限:首先进入 apache下的wordpress 的目录下 (这是apache服务器默认安装的路径)cd /var/www/html 接着,给wordpress整个文件夹进行赋值权限,如果不赋予权限 更新的时候会报权限不足的错误 (root 权限下进行)chmod -R 777 ./wordpress/如果是将wordpress里面的所有文件直接放到html下面的话就需要:chmod -R 777 ./然后: 进入wordpress 文件夹里面。修改wp-config.php 文件:vim wp-config.php 添加代码define("FS_METHOD", "direct"); define("FS_CHMOD_DIR", 0777); define("FS_CHMOD_FILE", 0777); 按下ESC后输入:wq回车保存文件,重启apache服务sudo service apache2 restart

April 30, 2019 · 1 min · jiezi

mapper4与springboot的简单整合

最近自己在网上搜索一些关于mapper4的教程,一直都没有找到简单明了的,所以就只能自己写一篇初级入门的mapper4与当下最火的springboot的整合。1.首先我们需要用IDEA工具新建一个springboot的项目。 Group和Artfact需要自己进行填写,否则就是默认的。 选择Web和MySQL 然后点击下一步完成就好了。 项目建好之后的结构如下所示,需要将application.properties改名为application.yml。 2.需要在maven里面添加相关的依赖。<!-- 添加通用 Mapper 提供的 starter --><dependency> <groupId>tk.mybatis</groupId> <artifactId>mapper-spring-boot-starter</artifactId> <version>2.1.5</version></dependency><!-- 添加lombok插件 --><dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> <version>1.18.6</version> <scope>provided</scope></dependency>3.application配置文件进行相关设置。#端口号server: port: 8088spring: #数据库连接数据配置 datasource: url: jdbc:mysql://localhost:3306/mapper-test username: root password: 123456mybatis: #驼峰命名法 configuration: map-underscore-to-camel-case: true #配置mybatis的全局配置文件 mapper-locations: classpath:mapping/*.xml#sql语句的打印logging: level: com: mapper4: www: debug4.需要在Spring Boot 的启动类上用@MapperScan 注解进行配置。@tk.mybatis.spring.annotation.MapperScan(basePackages = "扫描包") 5.新建一个Girl的实体类,并将其放到entity包中。 用lombok的@Data注解,这样就可以省略掉get/set等方法。 6.新建一个GirlMapper接口类,并将其放入到mapper包中。 继承BaseMapper<实体类>类。 7.新建一个GirlController类,将其放到controller中。 写一个根据id查询数据的方法。 8.用postman进行接口的调用你就会发现可以成功的查询出相关的数据了。拓展如果你想要自己写一些sql语句进行查询,不想使用mapper4自带的方法的话,那你就需要自己写一个*mapper.xml。这里我们简单的写一个*mapper.xml进行查询。其实我们在application.yml里面已经进行了相关的配置了。 这样程序就会自动的去这个目录下面去扫描相关的xml进行关联了。 我们需要在resources里面新建一个mapping文件夹,里面来存放我们写的*mapper.xml文件 需要在GirlMapper.xml里面添加一个新的查询SQL。 在GirlMapper类中添加这个方法,然后就可以在GirlController里面进行调用了。 在GirlController里面添加相关的方法。 进行测试就可以了,发现也是可以的,至此我们就完成了springboot与mapper4的简单集成。

April 30, 2019 · 1 min · jiezi

Sequel-pro

1、连接mysql数据库(ssh连接) 2、查询 1、记得写;;;重要的事情说3遍附参考链接Mac 上的 MySQL 管理工具 -- Sequel Pro--作者ingood

April 30, 2019 · 1 min · jiezi

阿里开发者招聘节-面试题0607-MySQL的数据如何恢复到任意时间点

摘要: 阿里巴巴资深技术专家们结合多年的工作、面试经验总结提炼而成的笔试真题这一次将陆续放出(面试题答案将在专辑分享结束后统一汇总分享)。并通过这些笔试真题开放阿里巴巴工作机会,让更多的开发者加入到阿里这个大平台。为帮助开发者们提升面试技能、有机会入职阿里,云栖社区特别制作了这个专辑——阿里巴巴资深技术专家们结合多年的工作、面试经验总结提炼而成的面试真题这一次将陆续放出(面试题官方参考答案将在专辑结束后统一汇总分享,点此进入答题并围观他人答案)。并通过这些笔试真题开放阿里巴巴工作机会,让更多的开发者加入到阿里这个大平台。 这一次,不仅是知识的收获,还将间接地与技术大牛们做了直观的沟通,了解他们的出题思路与考察要点,并加以消化吸收,这对自己技术能力本身就是一种极大的提升。走上编程之路,不断丰富自己方能与世接轨,努力做最优秀的自己。 4月28日,我们给开发者的第6~7道面试题。 06. 从innodb的索引结构分析,为什么索引的key长度不能太长07. MySQL的数据如何恢复到任意时间点阿里巴巴出题专家:近秋 阿里云数据库产品技术部技术专家,有6年的行业从业经验。2016年加入阿里云,目前负责最流行的开源数据库MySQL在阿里云的商业化的工作。 招聘职位:阿里云数据库技术专家点击进入聚能聊答题,并围观大家的回答! 本文作者:山哥在这里阅读原文 本文为云栖社区原创内容,未经允许不得转载。

April 30, 2019 · 1 min · jiezi

Centos65安装MySQL56备忘记录

Centos6.5安装MySQL5.61. 查看系统状态[root@itzhouq32 tools]# cat /etc/issueCentOS release 6.5 (Final)Kernel \r on an \m[root@itzhouq32 tools]# uname -aLinux itzhouq32 2.6.32-431.el6.x86_64 #1 SMP Fri Nov 22 03:15:09 UTC 2013 x86_64 x86_64 x86_64 GNU/Linux2.创建需要下载rpm软件包的目录[root@itzhouq32 /]# mkdir soft[root@itzhouq32 /]# cd soft[root@itzhouq32 soft]# ls[root@itzhouq32 soft]#3. 查看系统中是否有已经存在的MySQL如果有需要卸载用这个查找 # rpm -qa | grep mysql用这个卸载 yum -y remove mysql-libs-5.1*4. 下载MySQL-5.6安装包分别执行下面的三条命令 # wget http://dev.mysql.com/Downloads/MySQL-5.6/MySQL-server-5.6.21-1.rhel5.x86_64.rpm# wget http://dev.mysql.com/Downloads/MySQL-5.6/MySQL-devel-5.6.21-1.rhel5.x86_64.rpm# wget http://dev.mysql.com/Downloads/MySQL-5.6/MySQL-client-5.6.21-1.rhel5.x86_64.rpm如果下载的速度太慢,也可以使用window下载后传输到虚拟机的这个目录,然后安装。 5. 安装# rpm -ivh MySQL-server-5.6.21-1.rhel5.x86_64.rpm如果有以下报错信息,需要安装依赖包。 error: Failed dependencies: libaio.so.1()(64bit) is needed by MySQL-server-5.6.21-1.rhel5.x86_64 libaio.so.1(LIBAIO_0.1)(64bit) is needed by MySQL-server-5.6.21-1.rhel5.x86_64 libaio.so.1(LIBAIO_0.4)(64bit) is needed by MySQL-server-5.6.21-1.rhel5.x86_64执行: ...

April 30, 2019 · 2 min · jiezi

MySQL-InnoDB特性-Buffer-Pool漫谈

缓存管理是DBMS的核心系统,用于管理数据页的访问、刷脏和驱逐;虽然操作系统本身有page cache,但那不是专门为数据库设计的,所以大多数数据库系统都是自己来管理缓存。由于几乎所有的数据页访问都涉及到Buffer Pool,因此buffer pool的并发访问控制尤为重要,可能会影响到吞吐量和响应时间,本文主要回顾一下MySQL的buffer Pool最近几个版本的发展(若有遗漏,欢迎评论补充), 感受下最近几年这一块的进步 MySQL5.5之前只能设置一个buffer pool, 通过innodb_buffer_pool_size来控制, 刷脏由master线程承担,扩展性差。 MySQL 5.5引入参数innodb_buffer_pool_instances,将buffer pool拆分成多个instance,从而减少对buffer pool的访问控制,这时候的刷脏还是由Master线程来承担。 MySQL 5.6引入了buffer Pool page Id转储和导入特性,也就是说可以随时把内存中的page no存下来到文件里,在重启时会自动把这些Page加载到内存中,使内存保持warm状态. 此外该版本第一次引入了page cleaner,将flush list/lru上的刷脏驱逐工作转移到单独线程,减少了master线程的负担 MySQL 5.7这个版本发布了一个重要特性:online buffer pool resize. 当然是否是online需要打一个问号,因为在resize的过程中需要拿很多全局大锁,在高负载场景下很容易导致实例Hang住(81615)。 和之前不同,buffer pool被分成多个instance,每个instance又由多个chunk组成,每个chunk的大小受到参数innodb_buffer_pool_chunk_size控制,默认128MB, buffer pool resize都是以chunk为单位增加或减少的。另外一个需要注意的点是:你配置的Buffer Pool Size可能比你实际使用的内存要大,尤其对于大Bp而言,这是因为内部做了对齐处理, buffer pool size必须以 innodb_buffer_pool_chunk_size * innodb_buffer_pool_instances来做向上对齐(80350) 我们知道通常数据文件的IO都被设置成O_DIRECT, 但每次修改后依然需要去做fsync,来持久化元数据信息,而对于某些文件系统而言是没必要做fsync的,因此加入了新选项O_DIRECT_NO_FSYNC,这个需求来自于facebook. 他们也对此做了特殊处理:除非文件size变化,否则不做fsync。(最近在buglist上对这个参数是否安全的讨论也很有意思,官方文档做了新的说明,感兴趣的可以看看 [94912:O_DIRECT_NO_FSYNC possible write hole](https://bugs.mysql.com/bug.php?id=94912))) 再一个重要功能是终于引入了multiple page cleaner, 可以多个后台线程并发刷脏页,提供了更好的刷脏性能,有效避免用户线程进入single page flush。当然这还不够完美,主要有四点: 用户线程依然会进入single page flush,而一旦大量线程进入,就会导致严重性能下降:超频繁的fsync,激烈的dblwr竞争,线程切换等等当redo空间不足时,用户线程也会进入page flush,这在高负载场景下是很常见的,你会发现系统运行一段时间后,性能急剧下降。这是因为redo产生太快,而page flush又跟不上,导致checkpoint无法推进。那么用户线程可能就要过来做fuzzy checkpoint了。那时候性能基本上没法看了。dblwr成为重要的单点瓶颈。 如果你的服务器不支持原子写的话,必须打开double write buffer。写入Ibdata一段固定区域,这里是有锁包含的,区分为两部分:single page flush和batch flush, 但无论如何,即使拆分了多个page cleaner,最终扩展性还是受限于dblwr没有专用的lru evict线程,都是Page cleaner键值的。举个简单的例子,当buffer pool占满,同时又有很多脏页时,Page cleaner可能忙于刷脏,而用户线程则得不到free page,从而陷入single page flush如果你对上述几个问题极不满意,可以尝试percona server, 他们向来擅长优化Io bound场景的性能,并且上述几个问题都解决了,尤其是dblwr,他们做了多分区的改进。 ...

April 29, 2019 · 1 min · jiezi

MySQL-高可用性少宕机即高可用

我们之前了解了复制、扩展性,接下来就让我们来了解可用性。归根到底,高可用性就意味着 "更少的宕机时间"。 老规矩,讨论一个名词,首先要给它下个定义,那么什么是可用性? 1 什么是可用性我们常见的可用性通常以百分比表示,这本身就有其隐藏的意味:高可用性不是绝对的。换句话说,100% 的可用性是不可能达到的。没错,这里可以这么肯定的说。 我们一般用 “9” 的个数来描述可用性。X个9表示在数据中心运行1年时间的使用过程中,各系统可以正常使用时间与总时间(1年)之比。例如:“5 个 9” 表示 99.999%,那么应用宕机时间 t: (1-99.999%) 3600 24 * 365 = 315.36s = 5.256m因此,我们可以说,“5 个 9” 表示应用每年只允许 5.256 分钟的宕机时间。同样的计算,我们可以得出 3 个 9 每年宕机时间为 8.76 小时,4 个 9 的是 52.6 分钟。 实际上,5 个 9 对于大多数应用来说已经是很难做到的,但是对于一些大型公司,肯定还会去尝试获得更多的 "9",已尽量减少应用的宕机时间,降低宕机成本。 每个应用对可用性的需求各不相同。在设定一个目标值之前,一定要考虑清楚是不是确实需要达到这个目标。可用性的效果和开销对应的比例并不是线性增长的,每提高一点可用性,所花费的成本都会远超之前。 因此,对于可用性,我们可以遵循这样一个原则: 能够承担多少宕机成本,就保证相应的可用时间。说起来可能有点绕,简单来说:对于有 10W 用户的应用,假设实现 5 个 9 需要 100W,每年应用即使宕机 9 小时,总损失也才 50W,你说这个应用有必要去实现 5 个 9 的可用性吗? 另外,我们上面给可用性定义成了 “宕机时间”,但实际上可用性还应该包括应用是否能以足够好的性能处理请求。对于一个大型服务器而言,重启 MySQL 后,可能需要几个小时才能预热数据以保证请求的响应时间。这里的几个小时也应该包括在宕机时间内。 到此为止,我们应该有个大致的印象,可用性与应用宕机有关系。接下来,让我们再深入一步,了解下应用宕机的原因。 ...

April 29, 2019 · 1 min · jiezi

2018MySQL面试知识点整理

mysql 查询子句: group by 多个字段,group by 前可使用聚合函数,having: 对查询后结果的筛选 和where后面的语法类似字段别名 表别名 as子查询 子查询结果作为父查询的表 select xxx from (子查询) as 子查询结果命名子查询作为字段使用: select xxx from table where id in(select id ...)子查询可以跨多个表隔离级别: 未提交读(Read uncommitted),可能产生:脏读,不可重复读,幻读读已提交(Read committed),可能产生:不可重复读,幻读可重复读(Repeatable read):可能产生:幻读串行化(Serializable):可能产生:无mysql默认级别:可重复读 1. select @@global.tx_isolation;2. select @@session.tx_isolation;3. set global transaction isolation level read committed; //全局的4. set session transaction isolation level read committed; //当前会话mvcc(Multi Version Concurrency Control):为了实现快照读(读写不冲突) redo log: mysql将事务操作过程中产生redo log,事务提交时flush到硬盘(顺序的) 1. 当主机崩溃重启,可以从redo log获取日志恢复undo log: 事务操作过程中,记录修改的回滚操作,事务回滚可以用上 1. mysql根据 undo log 可以回溯到某个版本,实现mvccinnodb是以聚集索引组织数据的。数据行中包含rowid(主键id),还包括: ...

April 28, 2019 · 2 min · jiezi