软件生命周期指一个计算机软件从功能确定,设计,到开发成功投入使用,并在使用中不断修改增补完善,直到停止该软件使用的全过程(酝酿到废弃的过程);
初始构思、需求分析、功能设计、内部设计、文档计划、测试计划、文档准备、集成、测 试、维护、升级、再测试、逐步淘汰 (phase-out)、等等
瀑布模型,迭代式模型,快速原型模型,螺旋模型
版本控制(Revision control)是一种软体工程技巧,开发过程,确保由不同人所编辑的同一档案都得到更新。
Git(读音为/gɪt/。)是一个开源的分布式版本控制系统,可以有效、高速的处理从很小到非常大的项目版本管理。
Git 是 Linus Torvalds 为 了 帮 助 管 理 Linux 内 核 开 发 而 开 发 的 一 个 开 放 源 码 的 版 本 控 制 软 件 。
https://git-scm.com/doc
SVN 是 Subversion 的简称,是一个开放源代码的版本控制系统,相较于 RCS、CVS,它采用了分支管理系统,
它 的 设 计 目 标 就 是 取 代 CVS 。 互 联 网 上 很 多 版 本 控 制 服 务 已 从 CVS 迁 移 到 Subversion 。
https://tortoisesvn.net/support.html
(1)项目规划阶段:负责从单元测试到系统测试的整个测试阶段的监控。
(2)需求分析阶段:确定测试需求分析、系统测试计划的制定,评审后成为管理项目。测试需求分析是对产品
生命周期中测试所需求的资源、配置、每阶段评判通过的规约;系统测试计划则是依据软件的需求规格说明书,制
定测试计划和设计相应的测试用例。
(3)详细设计和概要设计阶段:确保集成测试计划和单元测试计划完成。
(4)编码阶段:由开发人员进行自己负责部分的代码的测试。在项目较大时,由专人进行编码阶段的测试任务。
(5)测试阶段(单元、集成、系统测试):依据测试代码进行测试,并提交相应测试状态报告和测试结束报告。
开发和测试是一个有机的整体!在产品的发布之前,开发和测试是循环进行的, 测出的缺陷要经开发人员修改
后继续测试。在开发的同时测试经理开始编写测试用例,测 试文档要参考开发文档,所以开发和测试是不可分割的,少了任何一个都不能开发出产品。
角色方面, 像理论和实验的关系,开发人员通过自己的想象创造出一套思想,之 后测试人员再对它进行检验、证伪,开发人员再修改的过程从而不断丰富产品;
方法方面, 演绎和归纳的关系,一个要掌握大量的技术,一个要不断的从实例中学习;
需求定义阶段:根据项目需求提取测试需求 并形成测试需求文档,根据提取的测试需求和项目计划进行测试计
划的拟定,测试计划文档
设计阶段:根据测试需求拟订测试方案并形成测试方案文档;根据测试方案制定测试用例,并形成测试用例文档
编码阶段:执行测试并完善测试用例文档
系统集成阶段:测试总结报告,阶段问题统计报告,测试问题报告
目的 : 使测试工作顺利进行;使项目参与人员沟通更舒畅;使测试工作更加系统化。
任务 : 寻找 Bug;避免软件开发缺陷;衡量软件的品质;关注用户的需求。总的目标是:确保软件的质量。
计划六要素 :
why——为什么要进行这些测试
what—测试哪些方面,不同阶段的工作内容
when—测试不同阶段的起止时间
where—相应文档,缺陷的存放位置,测试环境等
who—项目有关人员组成,安排哪些测试人员进行测试
how—如何去做,使用哪些测试工具以及测试方法进行测试。
黑盒测试:把测试对象当成一个黑盒子,测试人员完全不考虑逻辑结构和内部特性, 只依据程式的需求说明书
来检查程式的功能是否满足它的功能说明。
白盒测试:把测试对象当成一个透明的盒子,允许测试人员利用程序内部逻辑结构及 相关信息,设计或选择测
试用例,对程式所有逻辑路径进行测试。
单元测试:白盒测试的一种,对软件设计中的单元模块进行测试。
集成测试:在单元测试的基础上,对单元模块之间的连接和组装进行测试。
系统测试:在所有都考虑的情况下,对系统进行测试。
验收测试:第三方进行的确认软件满足需求的测试。
黑盒有等价类划分法,边界分析法,因果图法和错误猜测法。
优点有 :
- 比较简单,不需要了解程序内部的代码及实现;
- 与软件的内部实现无关;
- 从用户角度出发,能很容易的知道用户会用到哪些功能,会遇到哪些问题;
- 基于软件开发文档,所以也能知道软件实现了文档中的哪些功能;
- 在做软件自动化测试时较为方便。
缺点有 :- 不可能覆盖所有的代码,覆盖率较低,大概只能达到总代码量的 30%;
- 自动化测试的复用性较低。
白盒有逻辑覆盖法,循环测试路径选择,基本路径测试。
优点是 帮助软件测试人员增大代码的覆盖率,提高代码的质量,发现代码中隐藏的问题。
缺点是 程序运行会有很多不同的路径,不可能测试所有的运行路径;测试基于代码,只能测试开发人员做的对不
对,而不能知道设计的正确与否,可能会漏掉一些功能需求;系统庞大时,测试开销会非常大。
Alpha 测试是由一个用户在开发环境下进行的测试,也可以是公司内部的用户在模拟实际操作环境下进行的受控测试,Alpha 测试不能由程序员或测试员完成。Alpha 测试发现的错误,可以在测试现场立刻反馈给开发人员,由开发人员及时分析和处理。目的是评价软件产品的功能、可使用性、可靠性、性能和支持。尤其注重产品的界面和特色。Alpha 测试可以从软件产品编码结束之后开始,或在模块(子系统)测试完成后开始,也可以在确认测试过程中产品达到一定的稳定和可靠程度之后再开始。有关的手册(草稿)等应该在 Alpha 测试前准备好。
Beta 测试是软件的多个用户在一个或多个用户的实际使用环境下进行的测试。开发者通常不在测试现场,Beta测试不能由程序员或测试员完成。因而,Beta 测试是在开发者无法控制的环境下进行的软件现场应用。在 Beta 测试中,由用户记下遇到的所有问题,包括真实的以及主管认定的,定期向开发者报告,开发者在综合用户的报告后,做出修改,最后将软件产品交付给全体用户使用。Beta 测试着重于产品的支持性,包括文档、客户培训和支持产品的生产能力。只有当 Alpha 测试达到一定的可靠程度后,才能开始 Beta 测试。由于 Beta 测试的主要目标是测试可支持性,所以 Beta 测试应该尽可能由主持产品发行的人员来管理。
第一类标准:测试超过了预定时间,则停止测试。
第二类标准:执行了所有的测试用例,但并没有发现故障,则停止测试。
第三类标准:使用特定的测试用例设计方案作为判断测试停止的基础
第四类标准:正面指出停止测试的具体要求,即停止测试的标准可定义为查出某一预订 数目的故障。
第五类标准:根据单位时间内查出故障的数量决定是否停止测试。
测试用例是为某个特殊目标而编制的一组测试输入、执行条件以及预期结果,以便测试某个程序路径或核实是
否满足某个特定需求。
测试用例的基本元素: 测试索引,测试环境,测试输入,测试操作,预期结果,评价标准。
首先根据需求文档、概要设计、测试计划、测试方案细分出各功能模块的测试项
再根据各测试项,按照概要设计、详细设计以及测试方案中测试的覆盖率细分出测试子项
最后按照测试子项、根据测试用例的设计方法(因果图、边界值、等价类等的设计方法)书写测试用例。
:::info
tip
选用适合的用例管理工具(如 word,excel)
用例一定要及时更新(补充新的想法,删除过时的需求)
做好用例分级
做好用例评审,可征询相关人员意见,如评审通过可参考其执行测试,如未通过,需修改直到通过为止。
可以考虑结对编写,这个是不错的主意
要全面,包括功能、性能、兼容性、安全性、易用性、容错性等等
注意把握适当的颗粒度
:::
/proc/meminfo
tail -n 50 /etc/profile
前10行 head -n 10 /etc/profile
grep "ERROR" file_name
cat file_name | grep "ERROR"
netstat -anp | grep port_number
ps -ef | grep ps_name
ifconfig
mkdir -p ./a/b
rm -rf ./a
find ~/ -name xx.txt
ps -ef | grep tomcat
kill -9 tomcat_port
tail -f log_file
netstat -tlnp
tar zcvf xx.tar.gz file tar zxvf xx.tar.gz
cat /etc/passwd | head -n 5 | cut -d : -f 1
Linux 系统中 grep 命令是一种强大的文本搜索工具,它能使用正则表达式搜索文本,并把匹配的行打印出来。
grep 全称是 Global Regular Expression Print,表示全局正则表达式版本,它的使用权限是所有用户。
linux 下的 find:
简单点说说,grep 是查找匹配条件的行,find 是搜索匹配条件的文件。
数据库(Database)是按照数据结构来组织、存储和管理数据的仓库
关系型数据库(RDBMS) 是由多张能互相联接的二维行列表格组成的数据库
主关键字(primary key) 是表中的一个或多个字段,它的值用于唯一地标识表中的某一条记录
外键表示了两个关系之间的相关联系。以另一个关系的外键作主关键字的表被称为主表,具有此外键的表被称为主表的从表。外键又称作外关键字
在关系数据库中,索引是一种单独的、物理的对数据库表中一列或多列的值进行排序的一种存储结构,它是某个表中一列或若干列值的集合和相应的指向表中物理标识这些值的数据页的逻辑指针清单
1、from 子句组装来自不同数据源的数据;
2、where 子句基于指定的条件对记录行进行筛选;
3、group by 子句将数据划分为多个分组;
4、使用聚集函数进行计算;
5、使用 having 子句筛选分组;
6、计算所有的表达式;
7、select 的字段;
8、使用 order by 对结果集进行排序。
储存过程是一个可编程的函数,它在数据库中创建并保存。它可以有 SQL 语句和一些特殊的控制结构组成。
当希望在不同的应用程序或平台上执行相同的函数,或者封装特定功能时,存储过程是非常有用的。数据库中的存
储过程可以看做是对编程中面向对象方法的模拟。它允许控制数据的访问方式。存储过程通常有以下优点:
1、存储过程能实现较快的执行速度
2、存储过程允许标准组件是编程。
3、存储过程可以用流程控制语句编写,有很强的灵活性,可以完成复杂的判断和较复杂的运算。
4、存储过程可被作为一种安全机制来充分利用。
5、存储过程能够减少网络流量
1、原子性(Atomicity):事务中的全部操作在数据库中是不可分割的,要么全部完成,要么均不执行。
2、一致性(Consistency):几个并行执行的事务,其执行结果必须与按某一顺序串行执行的结果相一致。
3、隔离性(Isolation):事务的执行不受其他事务的干扰,事务执行的中间结果对其他事务必须是透明的。
4、持久性(Durability):对于任意已提交事务,系统必须保证该事务对数据库改变不被丢失,即使数据库出现故障
数据库索引,是数据库管理系统中一个排序的数据结构,以协助快速查询、更新数据库表中数据。索引的实现
通常使用 B_TREE。B_TREE 索引加速了数据访问,因为存储引擎不会再去扫描整张表得到需要的数据;相反,它
从根节点开始,根节点保存了子节点的指针,存储引擎会根据指针快速寻找数据。
PS : MySQL 5.5版本之后,默认使用的 InnoDB 搜索引擎, 底层使用的 B+ 树 索引结构;
1、储存引擎选择:如果数据表需要事务处理,应该考虑使用 InnoDB,因为它完全符合 ACID 特性。如果不需要事务处理,使用默认存储引擎 MyISAM 是比较明智的 (5.5之前默认的是 MyISAM)
2、分表分库,主从。
3、对查询进行优化,要尽量避免全表扫描,首先应考虑在 where 及 order by 涉及的列上建立索引
4、应尽量避免在 where 子句中对字段进行 null 值判断,否则将导致引擎放弃使用索引而进行全表扫描
5、应尽量避免在 where 子句中使用!= 或<> 操作符,否则将引擎放弃使用索引而进行全表扫描
6、应尽量避免在 where 子句中使用 or 来连接条件,如果一个字段有索引,一个字段没有索引,将导致引擎放弃使用索引而进行全表扫描
7、Update 语句,如果只更改 1、2 个字段,不要 Update 全部字段,否则频繁调用会引起明显的性能消耗,同时带来大量日志
8、对于多张大数据量(这里几百条就算大了)的表 JOIN,要先分页再 JOIN,否则逻辑读会很高,性能很差。
项目 | MyISAM | ** InnoDB** |
---|---|---|
事务 | 不支持 | 支持事务, 可回滚还原 |
应用场景 | 适合查询以及插入为主 | 适合频繁修改以及涉及到安全性较高的 |
外键 | 不支持 | 支持 |
版本默认引擎 | 5.5之前默认 | 5.5及之后默认 |
不支持 FULLTEXT 类型的索引 | ||
保存行数(但是where条件也要扫全表) | 不保存表的行数,(扫描全表计算行) | |
锁粒度 | 仅仅支持表锁 | 支持行锁,表锁 |
联合索引 | 自增字段, 必须包含只有该字段的索引 |
a. 应尽量避免全表扫描,首先应考虑在 where 及 order by 涉及的列上建立索。
b. 应尽量避免在 where 子句中对字段进行 null 值判断,避免使用!=或<>操作符,避免使用 or连接条件,或在 where 子句中使用参数、对字段进行表达式或函数操作,否则会导致权标扫描
c. 不要在 where 子句中“=”左边进行函数、算术运算或其他表达式运算,否则系统将可能无法正确使用索引。
d. 使用索引字段作为条件时,如果该索引是复合索引,那么必须使用到该索引中的第一个字段作为条件时才能保证系统使用该索引,否则该索引将不会被使用。
e. 很多时候可考虑用 exists 代替 in。
f. 尽量使用数字型字段。
g. 尽可能的使用 varchar/nvarchar 代替 char/nchar。
h. 任何地方都不要使用 select from t ,用具体的字段列表代替“” ,不要返回用不到的任何字段。
i. 尽量使用表变量来代替临时表。
j. 避免频繁创建和删除临时表,以减少系统表资源的消耗。
k. 尽量避免使用游标,因为游标的效率较差。
l. 在所有的存储过程和触发器的开始处设置 SET NOCOUNT ON ,在结束时设置 SET NOCOUNT OFF。
m. 尽量避免大事务操作,提高系统并发能力。
n. 尽量避免向客户端返回大数据量,若数据量过大,应该考虑相应需求是否合理。
1.优化索引、SQL 语句、分析慢查询;
2.设计表的时候严格根据数据库的设计范式来设计数据库;
3.使用缓存,把经常访问到的数据而且不需要经常变化的数据放在缓存中,能节约磁盘 IO
4.优化硬件;采用 SSD,使用磁盘队列技术(RAID0,RAID1,RDID5)等
5.采用 MySQL 内部自带的表分区技术,把数据分层不同的文件,能够提高磁盘的读取效率;
6.垂直分表;把一些不经常读的数据放在一张表里,节约磁盘 I/O;
7.主从分离读写;采用主从复制把数据库的读操作和写入操作分离开来;
8.分库分表分机器(数据量特别大),主要的的原理就是数据路由;
9.选择合适的表引擎,参数上的优化
10.进行架构级别的缓存,静态化和分布式;
11.不采用全文索引;
12.采用更快的存储方式,例如 NoSQL 存储经常访问的数据。
程序开发过程中不注意规范书写sql 语句和对特殊字符进行过滤,导致客户端可以通过全局变量POST 和GET提交一些 sql 语句正常执行。产生 Sql 注入。下面是防止办法:
a. 过滤掉一些常见的数据库操作关键字,或者通过系统函数来进行过滤。
b. 在 PHP 配置文件中将 Register_globals=off;设置为关闭状态
c. SQL 语句书写的时候尽量不要省略小引号(tab 键上面那个)和单引号
d. 提高数据库命名技巧,对于一些重要的字段根据程序的特点命名,取不易被猜到的
e. 对于常用的方法加以封装,避免直接暴漏 SQL 语句
f. 开启 PHP 安全模式:Safe_mode=on;
g. 打开 magic_quotes_gpc 来防止 SQL 注入
h. 控制错误信息:关闭错误提示信息,将错误信息写到系统日志。
i. 使用 mysqli 或 pdo 预处理。
a. SQL 数据存在特定结构的表中;而 NoSQL 则更加灵活和可扩展,存储方式可以省是 JSON 文档、哈希表或者其他方式。
b. 在 SQL 中,必须定义好表和字段结构后才能添加数据,例如定义表的主键(primary key),索引(index),触发器(trigger),存储过程(stored procedure)等。表结构可以在被定义之后更新,但是如果有比较大的结构变更的话会变得比较复杂。在 NoSQL 中,数据可以在任何时候任何地方添加,不需要先定义表。
c. SQL 中如果需要增加外部关联数据的话,规范化做法是在原表中增加一个外键,关联外部数据表。而在NoSQL 中除了这种规范化的外部数据表做法以外,我们还能用如下的非规范化方式把外部数据直接放到原数据集中,以提高查询效率。缺点也比较明显,更新审核人数据的时候将会比较麻烦。
d. SQL 中可以使用 JOIN 表链接方式将多个关系数据表中的数据用一条简单的查询语句查询出来。NoSQL 暂未提供类似 JOIN 的查询方式对多个数据集中的数据做查询。所以大部分 NoSQL 使用非规范化的数据存储方式存储数据。
e. SQL 中不允许删除已经被使用的外部数据,而 NoSQL 中则没有这种强耦合的概念,可以随时删除任何数据。
f. SQL 中如果多张表数据需要同批次被更新,即如果其中一张表更新失败的话其他表也不能更新成功。这种场景可以通过事务来控制,可以在所有命令完成后再统一提交事务。而 NoSQL 中没有事务这个概念,每一个数据集的操作都是原子级的。
g. 在相同水平的系统设计的前提下,因为 NoSQL 中省略了 JOIN 查询的消耗,故理论上性能上是优于 SQL 的。
MongoDB 是由 C++语言编写的,是一个基于分布式文件存储的开源数据库系统。在高负载的情况下,添加更多的节点,可以保证服务器性能;
MongoDB 旨在为 WEB 应用提供可扩展的高性能数据存储解决方案。
MongoDB 将数据存储为一个文档,数据结构由键值(key=>value)对组成。MongoDB 文档类似于 JSON 对象。字段值可以包含其他文档,数组及文档数组。
MongoDB 是一个面向文档数据库,目前由 10gen 开发并维护,它功能丰富齐全,所以完全可以替代MySQL。
与 MySQL 等关系型数据库相比,MongoDB 的优点如下:
①弱一致性,更能保证用户的访问速度。
②文档结构的存储方式,能够更便捷的获取数据。
③内置 GridFS,支持大容量的存储。
④内置 Sharding。
⑤第三方支持丰富。(这是与其他的 NoSQL 相比,MongoDB 也具有的优势)
⑥性能优越:
MongoDB 本身它还算比较年轻的一个产品,所以它的问题,就是成熟度肯定没有传统 MySQL 那么成熟稳定。
所以在使用的时候:
尽量使用稳定版,不要在线上使用开发版,这是一个大原则;
**备份和索引; ** MongoDB 还有一个最大的缺点,就是它占用的空间很大,因为它属于典型空间换时间原则的类型。那么它的磁盘空间比普通数据库会浪费一些,而且到目前为止它还没有实现在线压缩功能,在 MongoDB 中频繁的进行数据增删改时,如果记录变了,例如数据大小发生了变化,这时候容易产生一些数据碎片,出现碎片引发的结果,一个是索引会出现性能问题。
select * from table** limit (start-1)limit,limit*; 其中 start 是页码,limit 是每页显示的条数。
select * from table limit (beg-1)*size,limit; 其中 beg 是页码,size 是每页显示的条数。
先要解析出 baidu.com 对应的 ip 地址:
要先使用 arp 获取默认网关的 mac 地址
组织数据发送给默认网关(ip 还是 dns 服务器的 ip,但是 mac 地址是默认网关的 mac 地址)
默认网关拥有转发数据的能力,把数据转发给路由器
路由器根据自己的路由协议,来选择一个合适的较快的路径转发数据给目的网关
目的网关(dns 服务器所在的网关),把数据转发给 dns 服务
dns 服务器查询解析出 baidu.com 对应的 ip 地址,并原路返回请求这个域名的 client
得到了 baidu.com 对应的 ip 地址之后,会发送 tcp 的 3 次握手,进行连接
使用 http 协议发送请求数据给 web 服务器
web 服务器收到数据请求之后,通过查询自己的服务器得到相应的结果,原路返回给浏览器
浏览器接收到数据之后通过浏览器自己的渲染功能来显示这个网页
浏览器关闭 tcp 连接,即 4 次挥手结束,完成整个访问过程
SQL 注入攻击是注入攻击最常见的形式(此外还有 OS 注入攻击(Struts 2 的高危漏洞就是通过 OGNL 实施OS 注入攻击导致的)),当服务器使用请求参数构造 SQL 语句时,恶意的 SQL 被嵌入到 SQL 中交给数据库执行。SQL 注入攻击需要攻击者对数据库结构有所了解才能进行,攻击者想要获得表结构有多种方式:
(1)如果使用开源系统搭建网站,数据库结构也是公开的(目前有很多现成的系统可以直接搭建论坛,电商网站,虽然方便快捷但是风险是必须要认真评估的);
(2)错误回显(如果将服务器的错误信息直接显示在页面上,攻击者可以通过非法参数引发页面错误从而通过错误信息了解数据库结构,Web 应用应当设置友好的错误页,一方面符合最小惊讶原则,一方面屏蔽掉可能给系统带来危险的错误回显信息);
(3)盲注。防范 SQL 注入攻击也可以采用消毒的方式,通过正则表达式对请求参数进行验证,此外,参数绑定也是很好的手段,这样恶意的 SQL 会被当做 SQL 的参数而不是命令被执行,JDBC 中的 PreparedStatement 就是支持参数绑定的语句对象,从性能和安全性上都明显优于 Statement。
**XSS(Cross Site Script,跨站脚本攻击)**是向网页中注入恶意脚本在用户浏览网页时在用户浏览器中执行恶意脚本的攻击方式。跨站脚本攻击分有两种形式:
反射型攻击(诱使用户点击一个嵌入恶意脚本的链接以达到攻击的目标,目前有很多攻击者利用论坛、微博发布含有恶意脚本的 URL 就属于这种方式)
持久型攻击(将恶意脚本提交到被攻击网站的数据库中,用户浏览网页时,恶意脚本从数据库中被加载到页面执行,QQ 邮箱的早期版本就曾经被利用作为持久型跨站脚本攻击的平台)。
**CSRF 攻击(Cross Site Request Forgery,跨站请求伪造)**是攻击者通过跨站请求,以合法的用户身份进行非法操作(如转账或发帖等)。CSRF 的原理是利用浏览器的 Cookie 或服务器的 Session,盗取用户身份,原理如下图所示。防范 CSRF 的主要手段是识别请求者的身份,主要有以下几种方式:
(1)在表单中添加令牌(token);
(2)验证码;
(3)检查请求头中的 Referer(前面提到防图片盗链接也是用的这种方式)。
令牌和验证都具有一次消费性的特征,因此在原理上一致的,但是验证码是一种糟糕的用户体验,不是必要的情况下不要轻易使用验证码,目前很多网站的做法是如果在短时间内多次提交一个表单未获得成功后才要求提供验证码,这样会获得较好的用户体验。
待补充部分:
#第五章 – API测试
第六章 – APP测试
第七章 – 管理工具
第八章 – 其它补充