LVS+KeepAlived+Nginx高可用实现方案 转自CSDN

文章目录

概念

LVS

KeepAlived

为什么要使用

准备

软件安装

KeepAlived 安装

源码安装

yum安装

服务启动、重启、关闭

安装ipvsadm

nginx安装

防火墙(iptables)

防火墙配置(方式一)

防火墙配置(方式二)

配置nginx服务器(>>这里很重要!很重要!很重要!!!<<)

最后关键一步,配置keepalived

配置MASTER

配置BACKUP

配置注意项

启动keepalived

LVS管理工具-ipvsadm

安装

查看统计

lvs超时配置

测试

正常代理转发

KeepAlived高可用测试

LVS监控真实服务测试

常见问题

这是一段血泪教程…

概念

LVS

什么是lvs

LVS是Linux Virtual Server的简写,意即Linux虚拟服务器,是一个虚拟的服务器集群系统。本项目在1998年5月由章文嵩博士成立,是中国国内最早出现的自由软件项目之一。

宗旨

使用集群技术和Linux操作系统实现一个高性能、高可用的服务器.

很好的可伸缩性(Scalability)

很好的可靠性(Reliability)

很好的可管理性(Manageability)。

特点

可伸缩网络服务的几种结构,它们都需要一个前端的负载调度器(或者多个进行主从备份)。我们先分析实现虚拟网络服务的主要技术,指出IP负载均衡技术是在负载调度器的实现技术中效率最高的。在已有的IP负载均衡技术中,主要有通过网络地址转换(Network Address Translation)将一组服务器构成一个高性能的、高可用的虚拟服务器,我们称之为VS/NAT技术(Virtual Server via Network Address Translation)。在分析VS/NAT的缺点和网络服务的非对称性的基础上,我们提出了通过IP隧道实现虚拟服务器的方法VS/TUN (Virtual Server via IP Tunneling),和通过直接路由实现虚拟服务器的方法VS/DR(Virtual Server via Direct Routing),它们可以极大地提高系统的伸缩性。VS/NAT、VS/TUN和VS/DR技术是LVS集群中实现的三种IP负载均衡技术。

其他

更多其他特点请参考百度百科-Lvs

KeepAlived

什么是keepAlived

keepalived是一个类似于layer3, 4 & 5交换机制的软件,也就是我们平时说的第3层、第4层和第5层交换。Keepalived是自动完成,不需人工干涉。

简介

Keepalived的作用是检测服务器的状态,如果有一台web服务器宕机,或工作出现故障,Keepalived将检测到,并将有故障的服务器从系统中剔除,同时使用其他服务器代替该服务器的工作,当服务器工作正常后Keepalived自动将服务器加入到服务器群中,这些工作全部自动完成,不需要人工干涉,需要人工做的只是修复故障的服务器。

工作原理

Layer3,4,5工作在IP/TCP协议栈的IP层,TCP层,及应用层,原理分别如下:

Layer3:Keepalived使用Layer3的方式工作式时,Keepalived会定期向服务器群中的服务器发送一个ICMP的数据包(既我们平时用的Ping程序),如果发现某台服务的IP地址没有激活,Keepalived便报告这台服务器失效,并将它从服务器群中剔除,这种情况的典型例子是某台服务器被非法关机。Layer3的方式是以服务器的IP地址是否有效作为服务器工作正常与否的标准。

Layer4:如果您理解了Layer3的方式,Layer4就容易了。Layer4主要以TCP端口的状态来决定服务器工作正常与否。如web server的服务端口一般是80,如果Keepalived检测到80端口没有启动,则Keepalived将把这台服务器从服务器群中剔除。

Layer5:Layer5对指定的URL执行HTTP GET。然后使用MD5算法对HTTP GET结果进行求和。如果这个总数与预期值不符,那么测试是错误的,服务器将从服务器池中移除。该模块对同一服务实施多URL获取检查。如果您使用承载多个应用程序服务器的服务器,则此功能很有用。此功能使您能够检查应用程序服务器是否正常工作。MD5摘要是使用genhash实用程序(包含在keepalived软件包中)生成的。

SSL_GET与HTTP_GET相同,但使用SSL连接到远程Web服务器。

MISC_CHECK:此检查允许用户定义的脚本作为运行状况检查程序运行。结果必须是0或1.该脚本在导演盒上运行,这是测试内部应用程序的理想方式。可以使用完整路径(即/path_to_script/script.sh)调用可以不带参数运行的脚本。那些需要参数的需要用双引号括起来(即“/path_to_script/script.sh arg 1 … arg n”)

作用

主要用作RealServer的健康状态检查以及LoadBalance主机和BackUP主机之间failover的实现。

高可用web架构: LVS+keepalived+nginx+apache+php+eaccelerator(+nfs可选 可不选)

为什么要使用

当我们的服务器意外挂了之后,我们要怎么做?

当然是找一台新的机器,替代现有的机器,然后做新的环境部署,端口映射,域名解析等等一系列的工作,再将服务重新启动;但是如果这一系列的操作都是手动完成的,那么等你把这些工作搞好,可能服务已经停止个把小时了,这会儿估计运营早就提着菜刀架在你脖子上了;

但是如果使用了KeepAlived之后,然后提前将备用机准备好,当主的机器挂掉之后,自动将VIP给你切换到备用机,并且以邮件的形式告诉你说主服务已经挂了,你得赶紧恢复起来;这时候你就可以慢慢的去找主服务的问题,这时候并不会影响到你的正常业务运行。

准备

虚拟机(CentOS 7)

准备了4台虚拟机,用于测试

IP 作用

192.168.1.128 keepalived master

192.168.1.129 keepalived backup

192.168.1.130 nginx1

192.168.1.131 nginx2

192.168.1.200 虚拟ip VIP

基本架设示意图

安装源文件

keepalived-2.0.10 下载

软件安装

在192.168.1.128及192.168.1.129上安装keepalived

在192.168.1.130及192.168.1.131上安装nginx

KeepAlived 安装

基础软件安装

yum install gcc

yum -y install openssl-devel

yum -y install libnl libnl-devel

yum install -y libnfnetlink-devel

yum -y install net-tools

yum install vim -y

1

2

3

4

5

6

源码安装

将以上下载的2.0.10的版本拷贝至/use/local/src下

安装

解压编译、安装

cd /use/local/src

tar -zxvf keepalived-2.0.10.tar.gz

mv keepalived-2.0.10 ../keepalived

cd /use/local/keepalived/

./configure

make && make install

1

2

3

4

5

6

常见错误1

!!! OpenSSL is not properly installed on your system. !!!

!!! Can not include OpenSSL headers files. !!!

解决方法:

yum -y install openssl-devel

常见错误2

this build will not support IPVS with IPv6. Please install libnl/libnl-3 dev libraries to support IPv6 with IPVS.(此版本不支持使用IPv6的IPVS。 请安装libnl / libnl-3 dev库以支持带IPVS的IPv6。)

解决方法:

yum -y install libnl libnl-devel

常见问题三

configure: error: libnfnetlink headers missing

解决方法:

yum install -y libnfnetlink-devel

keepalived配置

将keepalived配置文件拷贝到etc/keepalived下

mkdir /etc/keepalived

cp /usr/local/keepalived/keepalived/etc/keepalived/keepalived.conf /etc/keepalived/

1

2

开机启动项

把 keepalived的启动文件复制到init.d下,加入开机启动项

cp /usr/local/keepalived/keepalived/etc/init.d/keepalived /etc/rc.d/init.d/

1

将keepalived文件拷贝到etc下

cp /usr/local/keepalived/keepalived/etc/sysconfig/keepalived /etc/sysconfig/

1

把keepalived加入系统命令目录

cp /usr/local/sbin/keepalived /usr/sbin/

1

常见问题

error while loading shared libraries: libcrypto.so.1.1: cannot open shared object file: No such file or directory

解决方式:

ln -s /usr/local/lib64/libssl.so.1.1 /usr/lib64/libssl.so.1.1

ln -s /usr/local/lib64/libcrypto.so.1.1 /usr/lib64/libcrypto.so.1.1

yum安装

这里的教程使用的上面的源码安装

yum install -y keepalived

1

服务启动、重启、关闭

这里只是测试服务是否能正常启动,后续还需要更改keepalived的配置之后才能正常的使用

启动

/etc/init.d/keepalived start

1

重启

/etc/init.d/keepalived restart

1

启动

/etc/init.d/keepalived stop

1

安装ipvsadm

用于查看lvs转发及代理情况的工具

只需要在192.168.1.128及192.168.1.129上安装即可

yum install ipvsadm -y

1

nginx安装

只需要在192.168.1.130及192.168.1.131上安装nginx即可

请参考基于CentOS 7 web服务环境搭建(包含JDK+Nginx+Tomcat+Mysql+Redis)中nginx的安装部分

或者

请参考OpenResty(Nginx+Lua)高并发最佳实践直接安装OpenResty即可包含了nginx部分,这里选用的是这种方式

防火墙(iptables)

停用firewalld

systemctl stop firewalld.service

systemctl disable firewalld.service

systemctl mask firewalld.service

1

2

3

安装iptables防火墙

#查看iptables相关的安装包

yum list iptables*

#安装

yum install -y iptables-services

1

2

3

4

防火墙配置(方式一)

编辑防火墙,增加端口

keepalived服务器下的配置

192.168.1.128和192.168.1.129下的添加以下配置

vi /etc/sysconfig/iptables

#允许vrrp多播心跳(如果防火墙开启,这里不配置这个,就会出现裂脑)

-A INPUT -p vrrp -j ACCEPT

#开启80端口的访问(如果防火墙开启,不配置这个,vip的80端口将无法正常访问)

-I INPUT -p tcp --dport 80 -j ACCEPT

1

2

3

4

nginx服务器下配置

192.168.1.130和192.168.1.131下的添加以下配置

vi /etc/sysconfig/iptables

#nginx默认监听的80端口 这里直接开启80端口的外网访问(不开启外网将无法正常反问对应服务器的nginx)

-A INPUT -p tcp -m state --state NEW -m tcp --dport 80 -j ACCEPT

1

2

重启防火墙

systemctl restart iptables.service

1

防火墙配置(方式二)

直接关闭所有防火墙,这种方式仅仅用于测试;不推荐用于实际项目

systemctl stop iptables.service

1

配置nginx服务器(>>这里很重要!很重要!很重要!!!<<)

以下操作需要在角色为Web服务器的两台中进行

即192.168.1.130和192.168.1.131这两台服务器上配置即可

启动nginx服务

确保nginx已经正常运行了

ps -ef|grep nginx

1

编辑realserver脚本文件两台机器都要搞

进入init文件夹

cd /etc/init.d/

编辑脚本

vim realserver

添加以下脚本

#虚拟的vip 根据自己的实际情况定义

SNS_VIP=192.168.1.200

/etc/rc.d/init.d/functions

case "$1" in

start)

      ifconfig lo:0 $SNS_VIP netmask 255.255.255.255 broadcast $SNS_VIP

      /sbin/route add -host $SNS_VIP dev lo:0

      echo "1" >/proc/sys/net/ipv4/conf/lo/arp_ignore

      echo "2" >/proc/sys/net/ipv4/conf/lo/arp_announce

      echo "1" >/proc/sys/net/ipv4/conf/all/arp_ignore

      echo "2" >/proc/sys/net/ipv4/conf/all/arp_announce

      sysctl -p >/dev/null 2>&1

      echo "RealServer Start OK"

      ;;

stop)

      ifconfig lo:0 down

      route del $SNS_VIP >/dev/null 2>&1

      echo "0" >/proc/sys/net/ipv4/conf/lo/arp_ignore

      echo "0" >/proc/sys/net/ipv4/conf/lo/arp_announce

      echo "0" >/proc/sys/net/ipv4/conf/all/arp_ignore

      echo "0" >/proc/sys/net/ipv4/conf/all/arp_announce

      echo "RealServer Stoped"

      ;;

*)

      echo "Usage: $0 {start|stop}"

      exit 1

esac

exit 0

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

保存并设置脚本的执行权限

chmod 755 /etc/init.d/realserver

因为realserver脚本中用到了/etc/rc.d/init.d/functions,所以一并设置权限

chmod 755 /etc/rc.d/init.d/functions

执行脚本

service realserver start

查看执行结果

ip a

如果看到以下效果,说明脚本已经执行成功了

最后关键一步,配置keepalived

配置MASTER

进入192.168.1.128服务器

cd /etc/keepalived

#备份默认的keepalived配置

mv keepalived.conf keepalived-back.conf

vim keepalived.conf

添加以下配置:

global_defs {

  notification_email {

        edisonchou@hotmail.com

  }

  notification_email_from sns-lvs@gmail.com

  smtp_server 192.168.80.1

  smtp_connection_timeout 30

  router_id LVS_DEVEL  # 设置lvs的id,在一个网络内应该是唯一的

}

vrrp_instance VI_1 {

    state MASTER  #指定Keepalived的角色,MASTER为主,BACKUP为备 记得大写

    interface eno16777736  #网卡id 不同的电脑网卡id会有区别 可以使用:ip a查看

    virtual_router_id 51  #虚拟路由编号,主备要一致

    priority 100  #定义优先级,数字越大,优先级越高,主DR必须大于备用DR

    advert_int 1  #检查间隔,默认为1s

    authentication {  #这里配置的密码最多为8位,主备要一致,否则无法正常通讯

        auth_type PASS

        auth_pass 1111

    }

    virtual_ipaddress {

        192.168.1.200  #定义虚拟IP(VIP)为192.168.1.200,可多设,每行一个

    }

}

# 定义对外提供服务的LVS的VIP以及port

virtual_server 192.168.1.200 80 {

    delay_loop 6 # 设置健康检查时间,单位是秒

    lb_algo rr # 设置负载调度的算法为wlc

    lb_kind DR # 设置LVS实现负载的机制,有NAT、TUN、DR三个模式

    nat_mask 255.255.255.0

    persistence_timeout 0

    protocol TCP

    real_server 192.168.1.130 80 {  # 指定real server1的IP地址

        weight 3  # 配置节点权值,数字越大权重越高

        TCP_CHECK {

        connect_timeout 10

        nb_get_retry 3

        delay_before_retry 3

        connect_port 80

        }

    }

    real_server 192.168.1.131 80 {  # 指定real server2的IP地址

        weight 3  # 配置节点权值,数字越大权重越高

        TCP_CHECK {

        connect_timeout 10

        nb_get_retry 3

        delay_before_retry 3

        connect_port 80

        }

    }

}

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

配置BACKUP

进入192.168.1.129服务器

cd /etc/keepalived

#备份默认的keepalived配置

mv keepalived.conf keepalived-back.conf

vim keepalived.conf

添加以下配置:

global_defs {

  notification_email {

        edisonchou@hotmail.com

  }

  notification_email_from sns-lvs@gmail.com

  smtp_server 192.168.80.1

  smtp_connection_timeout 30

  router_id LVS_DEVEL  # 设置lvs的id,在一个网络内应该是唯一的

}

vrrp_instance VI_1 {

    state BACKUP #指定Keepalived的角色,MASTER为主,BACKUP为备 记得大写

    interface eno16777736  #网卡id 不同的电脑网卡id会有区别 可以使用:ip a查看

    virtual_router_id 51  #虚拟路由编号,主备要一致

    priority 50  #定义优先级,数字越大,优先级越高,主DR必须大于备用DR

    advert_int 1  #检查间隔,默认为1s

    authentication {  #这里配置的密码最多为8位,主备要一致,否则无法正常通讯

        auth_type PASS

        auth_pass 1111

    }

    virtual_ipaddress {

        192.168.1.200  #定义虚拟IP(VIP)为192.168.1.200,可多设,每行一个

    }

}

# 定义对外提供服务的LVS的VIP以及port

virtual_server 192.168.1.200 80 {

    delay_loop 6 # 设置健康检查时间,单位是秒

    lb_algo rr # 设置负载调度的算法为wlc

    lb_kind DR # 设置LVS实现负载的机制,有NAT、TUN、DR三个模式

    nat_mask 255.255.255.0

    persistence_timeout 0

    protocol TCP

    real_server 192.168.1.130 80 {  # 指定real server1的IP地址

        weight 3  # 配置节点权值,数字越大权重越高

        TCP_CHECK {

        connect_timeout 10

        nb_get_retry 3

        delay_before_retry 3

        connect_port 80

        }

    }

    real_server 192.168.1.131 80 {  # 指定real server2的IP地址

        weight 3  # 配置节点权值,数字越大权重越高

        TCP_CHECK {

        connect_timeout 10

        nb_get_retry 3

        delay_before_retry 3

        connect_port 80

        }

    }

}

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

配置注意项

router_id

后面跟的自定义的ID在同一个网络下是一致的

state

state后跟的MASTER和BACKUP必须是大写;否则会造成配置无法生效的问题

interface

网卡ID;这个值不能完全拷贝我的配置,要根据自己的实际情况来看,可以使用以下方式查询

ip a

priority

主备优先级

MASTER中配置的priority必须比BACKUP大;差值最好>=50

authentication

主备之间的认证方式

一般使用PASS即可;主备的配置必须一致;否则无法通讯,会导致裂脑;密码不能大于8位

virtual_ipaddress

配置的VIP;允许配置多个

启动keepalived

在192.168.1.128和192.168.1.129下分别执行以下指令启动keepalived

/etc/init.d/keepalived start

检查主keepalived 启动后的配置情况

ip a

如果网卡下出现192.168.1.200(VIP)说明主已经启动成功

检查备keepalived 启动后的配置情况

ip a

备服务器的网卡下没有出现192.168.1.200(VIP)的ip,说明备服务正常

注:如果这里也出现了VIP,那么说明裂脑了,需要检查防火墙是否配置正确;是否允许了vrrp的多播通讯

LVS管理工具-ipvsadm

安装

yum install ipvsadm -y

查看统计

查看当前配置的虚拟服务和各个RS的权重

  ipvsadm -Ln

查看当前ipvs模块中记录的连接(可用于观察转发情况)

  ipvsadm -lnc

查看ipvs模块的转发情况统计

  ipvsadm -Ln --stats | --rate

lvs超时配置

查看lvs的超时时间

ipvsadm -L --timeout

优化连接超时时间

ipvsadm --set 1 10 300

这里的TCP的连接超时时间最好和keepalived中的persistence_timeout超时时间保持一致;persistence_timeout的超时时间表示指定时间内,同ip的请求会转发到同一个服务;

更多ipvsadm的操作请参考以下文章

https://www.cnblogs.com/lipengxiang2009/p/7353373.html

测试

正常代理转发

使用我linux虚拟机的windows宿主机进行测试

测试vip

ping 192.168.1.200

测试vip监听的端口

telnet 192.168.1.200 80

请求虚拟IP查看转发的服务

KeepAlived高可用测试

停掉主keepalived

/etc/init.d/keepalived stop

vip漂移至备服务器

此时网页访问:192.168.1.200依然能够正常访问;却分发依然正常

重启主keepalived

主服务恢复之后;vip又会自动漂移回主服务

LVS监控真实服务测试

查看最新的虚拟ip对应的RealServer的情况

ipvsadm -l

可以看出192.168.1.130和192.168.1.131两台正式服务都还在

测试停掉192.168.1.130

再次查看虚拟ip对应的RealServer的情况

可以看出192.168.1.130这台已经挂掉的服务器已经被移除了

测试访问虚拟ip

所有的访问都只会转发到131的真实服务器

恢复192.168.1.130

lvs又会自动监控并加入192.168.1.130

常见问题

裂脑

主备keepalived服务器同时出现了VIP;导致vip无法正常使用

常见原因为防火墙配置所致导致多播心跳失败

vip能ping通,但是vip监听的端口不通

第一个原因:nginx1和nginx2两台服务器的服务没有正常启动

第二个原因:请参考上面Nginx服务器那一大项中所说的配置,可能没有配置好

vip ping不通

核对是否出现裂脑

核对keepalived的配置是否正确

感谢以下资料对我的帮助

【参考资料】

Keepalived源码安装

高可用解决方案–keepalived

Centos7.2下基于Nginx+Keepalived搭建高可用负载均衡(一.基于Keepalived搭建HA体系)

keepalived介绍和配置

【大型网站技术实践】初级篇:借助LVS+Keepalived实现负载均衡

【解决问题参考资料】

咨询个lvs的问题,有时访问VIP会出现SYN_RECV

怎么样让 LVS 和 realserver 工作在同一台机器上

两台服务器既做LVS主备又做realserver的配置方法

keepalived+lvs无法访问vip或访问超时

lvs中ipvsadm的ActiveConn和InActConn的深入理解

---------------------

作者:lupengfei1009

来源:CSDN

原文:https://blog.csdn.net/lupengfei1009/article/details/86514445

版权声明:本文为博主原创文章,转载请附上博文链接!

©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 212,332评论 6 493
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 90,508评论 3 385
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 157,812评论 0 348
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 56,607评论 1 284
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 65,728评论 6 386
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 49,919评论 1 290
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,071评论 3 410
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 37,802评论 0 268
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 44,256评论 1 303
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 36,576评论 2 327
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 38,712评论 1 341
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 34,389评论 4 332
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,032评论 3 316
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 30,798评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,026评论 1 266
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 46,473评论 2 360
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 43,606评论 2 350

推荐阅读更多精彩内容