1、概述
1.1 官方文档
Launch an instancehttps://docs.openstack.org/install-guide/launch-instance.html
《OpenStack Yoga版安装笔记(十四)启动一个实例》文档中,已经按照Option1: Provider networks创建网络。
本文按照Option2:Self-service networks创建网络,并在此网络创建虚机(Launch an instance)。
1.2 Self-service Networks
自服务网络(Self-Service Networks)可以理解为租户网络,由租户自行创建网络,租户通过认证(keystone)和授权(各服务模块进行授权),登录云平台(OpenStack),创建租户网络、租户子网、租户路由器。
租户路由器连接租户网络和Provider网络,并通过provider网络连接外部网络。
2、Create virtual networks(Self-service networks)
2.1 前提
注:You must create the provider network before the self-service network.
(因为在这里需要依赖provider网络和外部连接,provider在创建时使用--external参数)
root@osclient ~(myproject/myuser)# openstack network list
+--------------------------------------+-------------+--------------------------------------+
| ID | Name | Subnets |
+--------------------------------------+-------------+--------------------------------------+
| 48f2b88e-7740-4d94-a631-69e2abadf25b | provider | 8279842e-d7c5-4ba6-a037-831e0a72a938 |
+--------------------------------------+-------------+--------------------------------------+
2.2 Create the self-service network
2.2.1 加载用户凭证
Source the demo
credentials to gain access to user-only CLI commands:
(在安装openstack client的客户端执行即可,可以理解为租户登录云平台的场景)
root@osclient:~# cat demo-openrc
export OS_PROJECT_DOMAIN_NAME=Default
export OS_USER_DOMAIN_NAME=Default
export OS_PROJECT_NAME=myproject
export OS_USERNAME=myuser
export OS_PASSWORD=openstack
export OS_AUTH_URL=http://controller:5000/v3
export OS_IDENTITY_API_VERSION=3
export OS_IMAGE_API_VERSION=2
export PS1='\u@\h \W(myproject/myuser)\$ '
root@osclient:~# source demo-openrc
root@osclient ~(myproject/myuser)#
root@osclient ~(myproject/myuser)#
2.2.2 Create the network
(可以理解为租户登录云平台后,创建租户网络的场景)
root@osclient ~(myproject/myuser)# openstack network create selfservice
+---------------------------+--------------------------------------+
| Field | Value |
+---------------------------+--------------------------------------+
| admin_state_up | UP |
| availability_zone_hints | |
| availability_zones | |
| created_at | 2025-04-09T22:52:13Z |
| description | |
| dns_domain | None |
| id | 28d343c8-1cbb-4d3a-b69c-7d9afe5840fa |
| ipv4_address_scope | None |
| ipv6_address_scope | None |
| is_default | False |
| is_vlan_transparent | None |
| mtu | 1450 |
| name | selfservice |
| port_security_enabled | True |
| project_id | f5e75a3f7cc347ad89d20dcfe70dae01 |
| provider:network_type | None |
| provider:physical_network | None |
| provider:segmentation_id | None |
| qos_policy_id | None |
| revision_number | 1 |
| router:external | Internal |
| segments | None |
| shared | False |
| status | ACTIVE |
| subnets | |
| tags | |
| updated_at | 2025-04-09T22:52:13Z |
+---------------------------+--------------------------------------+
root@osclient ~(myproject/myuser)#
注:Non-privileged users typically cannot supply additional parameters to this command. The service automatically chooses parameters using information from the following files:
ml2_conf.ini
:[ml2] tenant_network_types = vxlan [ml2_type_vxlan] vni_ranges = 1:1000
2.2.3 Create a subnet on the network
(可以理解为租户登录云平台后,创建租户子网subnet的场景。为方便起见,直接使用安装文档的参数即可,也可以自行规划网段)
root@osclient ~(myproject/myuser)# openstack subnet create --network selfservice \
> --dns-nameserver 8.8.4.4 --gateway 172.16.1.1 \
> --subnet-range 172.16.1.0/24 selfservice
+----------------------+--------------------------------------+
| Field | Value |
+----------------------+--------------------------------------+
| allocation_pools | 172.16.1.2-172.16.1.254 |
| cidr | 172.16.1.0/24 |
| created_at | 2025-04-09T23:04:55Z |
| description | |
| dns_nameservers | 8.8.4.4 |
| dns_publish_fixed_ip | None |
| enable_dhcp | True |
| gateway_ip | 172.16.1.1 |
| host_routes | |
| id | 2825e2f9-b894-49ba-8cdb-399285223219 |
| ip_version | 4 |
| ipv6_address_mode | None |
| ipv6_ra_mode | None |
| name | selfservice |
| network_id | 28d343c8-1cbb-4d3a-b69c-7d9afe5840fa |
| project_id | f5e75a3f7cc347ad89d20dcfe70dae01 |
| revision_number | 0 |
| segment_id | None |
| service_types | |
| subnetpool_id | None |
| tags | |
| updated_at | 2025-04-09T23:04:55Z |
+----------------------+--------------------------------------+
root@osclient ~(myproject/myuser)#
创建一个network,会在每个节点按需创建一个linux bridge(本文设置的neutron驱动为Linux bridge)。
创建一个subnet,会在安装dhcp agent的节点创建一个qdhcp。
此时可以在controller node查看:
root@controller:~# brctl show
bridge name bridge id STP enabled interfaces
brq28d343c8-1c 8000.fa9e6d61701c no tap9c9c42d1-7c
vxlan-649
brq48f2b88e-77 8000.36f43ea8e0c3 no ens34
tapa51b2fe4-04
virbr0 8000.5254007be820 yes
root@controller:~#
brq28d343c8-1c,对应network selfservice。
brq48f2b88e-77,对应network provider。
controller node上的qdhcp信息查看:
root@controller:~# ip netns list
qdhcp-28d343c8-1cbb-4d3a-b69c-7d9afe5840fa (id: 0)
qdhcp-48f2b88e-7740-4d94-a631-69e2abadf25b (id: 1)
root@controller:~# ip netns exec qdhcp-28d343c8-1cbb-4d3a-b69c-7d9afe5840fa ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
2: ns-9c9c42d1-7c@if7: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1450 qdisc noqueue state UP group default qlen 1000
link/ether fa:16:3e:be:16:3b brd ff:ff:ff:ff:ff:ff link-netnsid 0
inet 172.16.1.2/24 brd 172.16.1.255 scope global ns-9c9c42d1-7c
valid_lft forever preferred_lft forever
inet 169.254.169.254/32 brd 169.254.169.254 scope global ns-9c9c42d1-7c
valid_lft forever preferred_lft forever
inet6 fe80::a9fe:a9fe/128 scope link
valid_lft forever preferred_lft forever
inet6 fe80::f816:3eff:febe:163b/64 scope link
valid_lft forever preferred_lft forever
root@controller:~#
qdhcp-28d343c8-1cbb-4d3a-b69c-7d9afe5840fa,给subnet selfservice使用;
qdhcp-48f2b88e-7740-4d94-a631-69e2abadf25b,给subnet provider使用。
* 查看qdhcp相关配置信息:
root@controller:~# ps -ef | grep dnsmasq
libvirt+ 1348 1 0 05:57 ? 00:00:00 /usr/sbin/dnsmasq --conf-file=/var/lib/libvirt/dnsmasq/default.conf --leasefile-ro --dhcp-script=/usr/lib/libvirt/libvirt_leaseshelper
root 1349 1348 0 05:57 ? 00:00:00 /usr/sbin/dnsmasq --conf-file=/var/lib/libvirt/dnsmasq/default.conf --leasefile-ro --dhcp-script=/usr/lib/libvirt/libvirt_leaseshelper
nobody 2770 1 0 06:06 ? 00:00:00 dnsmasq --no-hosts --no-resolv --pid-file=/var/lib/neutron/dhcp/28d343c8-1cbb-4d3a-b69c-7d9afe5840fa/pid --dhcp-hostsfile=/var/lib/neutron/dhcp/28d343c8-1cbb-4d3a-b69c-7d9afe5840fa/host --addn-hosts=/var/lib/neutron/dhcp/28d343c8-1cbb-4d3a-b69c-7d9afe5840fa/addn_hosts --dhcp-optsfile=/var/lib/neutron/dhcp/28d343c8-1cbb-4d3a-b69c-7d9afe5840fa/opts --dhcp-leasefile=/var/lib/neutron/dhcp/28d343c8-1cbb-4d3a-b69c-7d9afe5840fa/leases --dhcp-match=set:ipxe,175 --dhcp-userclass=set:ipxe6,iPXE --local-service --bind-dynamic --dhcp-range=set:subnet-2825e2f9-b894-49ba-8cdb-399285223219,172.16.1.0,static,255.255.255.0,86400s --dhcp-option-force=option:mtu,1450 --dhcp-lease-max=256 --conf-file=/dev/null --domain=openstacklocal
nobody 2775 1 0 06:06 ? 00:00:00 dnsmasq --no-hosts --no-resolv --pid-file=/var/lib/neutron/dhcp/48f2b88e-7740-4d94-a631-69e2abadf25b/pid --dhcp-hostsfile=/var/lib/neutron/dhcp/48f2b88e-7740-4d94-a631-69e2abadf25b/host --addn-hosts=/var/lib/neutron/dhcp/48f2b88e-7740-4d94-a631-69e2abadf25b/addn_hosts --dhcp-optsfile=/var/lib/neutron/dhcp/48f2b88e-7740-4d94-a631-69e2abadf25b/opts --dhcp-leasefile=/var/lib/neutron/dhcp/48f2b88e-7740-4d94-a631-69e2abadf25b/leases --dhcp-match=set:ipxe,175 --dhcp-userclass=set:ipxe6,iPXE --local-service --bind-dynamic --dhcp-range=set:subnet-8279842e-d7c5-4ba6-a037-831e0a72a938,203.0.113.0,static,255.255.255.0,86400s --dhcp-option-force=option:mtu,1500 --dhcp-lease-max=256 --conf-file=/dev/null --domain=openstacklocal
root 6182 3604 0 07:11 pts/0 00:00:00 grep --color=auto dnsmasq
root@controller:~#
nobody 2770 1 0 06:06 ? 00:00:00 dnsmasq --no-hosts......
Neutron 相关的
dnsmasq
实例:这行是由 Neutron 启动的
dnsmasq
实例,主要负责为一个子网(subnet-2825e2f9-b894-49ba-8cdb-399285223219
)提供 DHCP 服务。关键配置如下:
--dhcp-range
: 指定 DHCP 地址池为172.16.1.0
,子网掩码255.255.255.0
,租约时间为 86400 秒(即 24 小时)。
--dhcp-option-force
: 强制设置 MTU 为 1450。
--dhcp-lease-max
: 最大租约数为 256。
--dhcp-leasefile
: 设置 DHCP 租约文件路径,存储租约信息。
--domain=openstacklocal
: 配置 DHCP 域名。
可进一步查看相关信息:
root@controller:~# cat /var/lib/neutron/dhcp/28d343c8-1cbb-4d3a-b69c-7d9afe5840fa/opts
tag:subnet-2825e2f9-b894-49ba-8cdb-399285223219,option:dns-server,8.8.4.4
tag:subnet-2825e2f9-b894-49ba-8cdb-399285223219,option:classless-static-route,169.254.169.254/32,172.16.1.2,0.0.0.0/0,172.16.1.1
tag:subnet-2825e2f9-b894-49ba-8cdb-399285223219,249,169.254.169.254/32,172.16.1.2,0.0.0.0/0,172.16.1.1
tag:subnet-2825e2f9-b894-49ba-8cdb-399285223219,option:router,172.16.1.1root@controller:~#
2.3 Create a router
(可以理解为创建租户自己创建租户路由器的场景)
2.3.1 本节概述
Self-service networks connect to provider networks using a virtual router that typically performs bidirectional NAT. Each router contains an interface on at least one self-service network and a gateway on a provider network.
这段描述讲述的是 OpenStack 或类似云平台中 自服务网络(self-service networks)和 提供者网络(provider networks)如何通过 虚拟路由器 进行连接的过程。我们可以逐句分析和解读。
1. Self-service networks connect to provider networks using a virtual router that typically performs bidirectional NAT.
自服务网络(self-service networks)是用户或租户在云平台上创建的虚拟网络,通常用于虚拟机(VM)和容器的内部通信。用户可以根据自己的需求配置这些网络。
提供者网络(provider networks)是由云服务提供商管理的网络,通常是物理网络或物理基础设施上的虚拟化网络,负责为自服务网络提供外部连接。
虚拟路由器(virtual router)用于将自服务网络和提供者网络连接起来。它通常会执行 双向 NAT(bidirectional NAT),也就是将自服务网络和外部提供者网络之间的 IP 地址进行映射(即虚拟机内部使用的私有 IP 与外部网络使用的公共 IP 地址之间的转换)。
双向 NAT 的作用是:
从自服务网络到提供者网络:虚拟机(或其他自服务网络中的资源)使用私有 IP 地址访问外部资源时,虚拟路由器会将源 IP 地址转换成公共 IP 地址,从而进行通信。
从提供者网络到自服务网络:外部资源(例如,外部互联网或其他物理网络)访问虚拟机时,虚拟路由器会将目的 IP 地址转换为对应的私有 IP 地址。
2. Each router contains an interface on at least one self-service network and a gateway on a provider network.
每个虚拟路由器都有至少一个自服务网络接口 和一个提供者网络网关。
自服务网络接口:路由器上的接口连接到自服务网络,允许虚拟机通过该接口访问其他自服务网络中的资源。
提供者网络网关:路由器的网关连接到提供者网络,允许自服务网络中的资源访问外部网络(如互联网或外部物理网络)。
总结:
这段描述的核心意思是:
虚拟路由器 扮演了自服务网络和提供者网络之间的桥梁角色。
该路由器通过 双向 NAT 来实现私有 IP 和公共 IP 之间的映射。
每个路由器上至少有一个接口连接到自服务网络,并且通过网关与提供者网络连接,从而使自服务网络能够访问外部资源,并允许外部资源与自服务网络中的资源通信。
现实应用:
这种架构通常用于 私有云 或 虚拟化平台,例如 OpenStack,其中虚拟网络隔离(比如子网、VLAN)和网络地址转换(NAT)是实现虚拟机与外部通信的重要机制。通过这种方式,云平台的用户可以在隔离的网络中管理虚拟机,同时也能安全地连接到互联网或其他外部网络。
The provider network must include the router:external
option to enable self-service routers to use it for connectivity to external networks such as the Internet. The admin
or other privileged user must include this option during network creation or add it later. In this case, the router:external
option was set by using the --external
parameter when creating the provider
network.
“admin” role的“admin" user在"admin" 中已经创建“provider network”:
root@osclient ~(admin/amdin)# openstack network create --share --external --provider-physical-network provider --provider-network-type flat provider
root@osclient ~(admin/amdin)# openstack network list +--------------------------------------+-------------+--------------------------------------+ | ID | Name | Subnets | +--------------------------------------+-------------+--------------------------------------+ | 28d343c8-1cbb-4d3a-b69c-7d9afe5840fa | selfservice | 2825e2f9-b894-49ba-8cdb-399285223219 | | 48f2b88e-7740-4d94-a631-69e2abadf25b | provider | 8279842e-d7c5-4ba6-a037-831e0a72a938 | +--------------------------------------+-------------+--------------------------------------+ root@osclient ~(admin/amdin)# openstack network show provider +---------------------------+--------------------------------------+ | Field | Value | +---------------------------+--------------------------------------+ | admin_state_up | UP | | availability_zone_hints | | | availability_zones | nova | | created_at | 2024-09-21T09:06:01Z | | description | | | dns_domain | None | | id | 48f2b88e-7740-4d94-a631-69e2abadf25b | | ipv4_address_scope | None | | ipv6_address_scope | None | | is_default | False | | is_vlan_transparent | None | | mtu | 1500 | | name | provider | | port_security_enabled | True | | project_id | ee65b6c3961747b988ab8bd1cc19fb93 | | provider:network_type | flat | | provider:physical_network | provider | | provider:segmentation_id | None | | qos_policy_id | None | | revision_number | 2 | | router:external | External | | segments | None | | shared | True | | status | ACTIVE | | subnets | 8279842e-d7c5-4ba6-a037-831e0a72a938 | | tags | | | updated_at | 2024-09-26T00:19:21Z | +---------------------------+--------------------------------------+ root@osclient ~(admin/amdin)#
2.3.2 加载用户凭证
(可以理解为租户登录云平台的场景)
“myrole" role的“myuser" user登录”myproject" project:
root@osclient:~# cat demo-openrc
export OS_PROJECT_DOMAIN_NAME=Default
export OS_USER_DOMAIN_NAME=Default
export OS_PROJECT_NAME=myproject
export OS_USERNAME=myuser
export OS_PASSWORD=openstack
export OS_AUTH_URL=http://controller:5000/v3
export OS_IDENTITY_API_VERSION=3
export OS_IMAGE_API_VERSION=2
export PS1='\u@\h \W(myproject/myuser)\$ '
root@osclient:~# source demo-openrc
root@osclient ~(myproject/myuser)#
root@osclient ~(myproject/myuser)#
2.3.3 Create the router
(可以理解为租户登录云平台后,租户自己创建租户路由器的场景)
root@osclient ~(myproject/myuser)# openstack router create router
+-------------------------+--------------------------------------+
| Field | Value |
+-------------------------+--------------------------------------+
| admin_state_up | UP |
| availability_zone_hints | |
| availability_zones | |
| created_at | 2025-04-10T07:46:46Z |
| description | |
| external_gateway_info | null |
| flavor_id | None |
| id | 782e8b74-a13c-4e8c-83dd-066f49e55ac2 |
| name | router |
| project_id | f5e75a3f7cc347ad89d20dcfe70dae01 |
| revision_number | 1 |
| routes | |
| status | ACTIVE |
| tags | |
| updated_at | 2025-04-10T07:46:46Z |
+-------------------------+--------------------------------------+
此时,由于创建的router没有和任何network链接,所有在controller node没有下发任何命令。
root@controller:~# brctl show
bridge name bridge id STP enabled interfaces
brq28d343c8-1c 8000.fa9e6d61701c no tap9c9c42d1-7c
vxlan-649
brq48f2b88e-77 8000.36f43ea8e0c3 no ens34
tapa51b2fe4-04
virbr0 8000.5254007be820 yes
root@controller:~# ip netns
qdhcp-28d343c8-1cbb-4d3a-b69c-7d9afe5840fa (id: 0)
qdhcp-48f2b88e-7740-4d94-a631-69e2abadf25b (id: 1)
2.3.4 router和租户网络连接
Add the self-service network subnet as an interface on the router:
root@osclient ~(myproject/myuser)# openstack router add subnet router selfservice
root@osclient ~(myproject/myuser)#
在 OpenStack 中,
openstack router add subnet router selfservice
这个命令的作用是将一个子网(selfservice
)与一个路由器(router
)关联起来。这个操作通常发生在 Neutron 网络配置中,目的是让路由器能够为子网提供连接功能,使得子网内的实例可以访问外部网络,或让外部网络能够访问该子网中的实例。具体来说:
router
:是你在 OpenStack 中创建的路由器。它用于将不同子网之间的流量进行路由转发。
selfservice
:是你已经创建的子网。子网一般包含了一个范围内的 IP 地址段。
add subnet
:表示将一个子网添加到路由器上,允许路由器为这个子网提供路由功能。通过执行这条命令,你就把
selfservice
子网的流量通过路由器进行管理,通常是为了实现网络隔离、网络地址转换(NAT)或其他网络流量控制功能。总结来说,
openstack router add subnet
命令是用来配置路由器和子网之间的连接关系,使得子网内的设备可以通过路由器访问外部网络,或者外部网络能够访问子网内的设备。
此时,router在controller生成了qrouter,并和network selfservice对应的linux bridge连接。
root@controller:~# ip netns
qrouter-782e8b74-a13c-4e8c-83dd-066f49e55ac2 (id: 2)
qdhcp-28d343c8-1cbb-4d3a-b69c-7d9afe5840fa (id: 0)
qdhcp-48f2b88e-7740-4d94-a631-69e2abadf25b (id: 1)
root@controller:~# ip netns exec qrouter-782e8b74-a13c-4e8c-83dd-066f49e55ac2 ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
2: qr-fb68b947-33@if12: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1450 qdisc noqueue state UP group default qlen 1000
link/ether fa:16:3e:33:b2:f8 brd ff:ff:ff:ff:ff:ff link-netnsid 0
inet 172.16.1.1/24 brd 172.16.1.255 scope global qr-fb68b947-33
valid_lft forever preferred_lft forever
inet6 fe80::f816:3eff:fe33:b2f8/64 scope link
valid_lft forever preferred_lft forever
root@controller:~# brctl show
bridge name bridge id STP enabled interfaces
brq28d343c8-1c 8000.fa9e6d61701c no tap9c9c42d1-7c
tapfb68b947-33
vxlan-649
brq48f2b88e-77 8000.36f43ea8e0c3 no ens34
tapa51b2fe4-04
virbr0 8000.5254007be820 yes
查看qrouter路由信息:
root@controller:~# ip netns exec qrouter-782e8b74-a13c-4e8c-83dd-066f49e55ac2 ip route
172.16.1.0/24 dev qr-fb68b947-33 proto kernel scope link src 172.16.1.1
root@controller:~#
这条命令的输出显示了在名为
qrouter-782e8b74-a13c-4e8c-83dd-066f49e55ac2
的网络命名空间内的路由表。这个路由表条目表示,通过接口
qr-fb68b947-33
,路由器可以访问172.16.1.0/24
子网,并且路由器接口 IP 地址是172.16.1.1
。
dev qr-fb68b947-33
:该子网通过网络接口qr-fb68b947-33
连接。qr-
前缀通常表示 Neutron 创建的虚拟路由器接口。
proto kernel
:表示该路由是由内核自动添加的,通常是由 OpenStack 创建的路由。
2.3.5 router和provider网络连接
Set a gateway on the provider network on the router:
(在这里,router上连接provider network的端口叫gateway,这条命令会在router上添加一条通过该端口的缺省路由。从这里可以看出,租户可以自己创建网络,并通过云平台能力自动和外部网络连接,租户不需要关心实际如何连接的)
root@osclient ~(myproject/myuser)# openstack router set router --external-gateway provider
root@osclient ~(myproject/myuser)#
此时,controller node的qrouter增加了端口,并连接到network provider对应的linux bridge:
root@controller:~# ip netns
qrouter-782e8b74-a13c-4e8c-83dd-066f49e55ac2 (id: 2)
qdhcp-28d343c8-1cbb-4d3a-b69c-7d9afe5840fa (id: 0)
qdhcp-48f2b88e-7740-4d94-a631-69e2abadf25b (id: 1)
root@controller:~# ip netns exec qrouter-782e8b74-a13c-4e8c-83dd-066f49e55ac2 ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
2: qr-fb68b947-33@if12: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1450 qdisc noqueue state UP group default qlen 1000
link/ether fa:16:3e:33:b2:f8 brd ff:ff:ff:ff:ff:ff link-netnsid 0
inet 172.16.1.1/24 brd 172.16.1.255 scope global qr-fb68b947-33
valid_lft forever preferred_lft forever
inet6 fe80::f816:3eff:fe33:b2f8/64 scope link
valid_lft forever preferred_lft forever
3: qg-02f3fada-b8@if13: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
link/ether fa:16:3e:bd:68:5a brd ff:ff:ff:ff:ff:ff link-netnsid 0
inet 203.0.113.144/24 brd 203.0.113.255 scope global qg-02f3fada-b8
valid_lft forever preferred_lft forever
inet6 fe80::f816:3eff:febd:685a/64 scope link
valid_lft forever preferred_lft forever
root@controller:~# brctl show
bridge name bridge id STP enabled interfaces
brq28d343c8-1c 8000.fa9e6d61701c no tap9c9c42d1-7c
tapfb68b947-33
vxlan-649
brq48f2b88e-77 8000.36f43ea8e0c3 no ens34
tap02f3fada-b8
tapa51b2fe4-04
virbr0 8000.5254007be820 yes
root@controller:~#
查看qrouter路由信息,增加了subnet provider的子网路由和缺省路由,其中缺省路由下一跳地址203.0.113.1是OpenStack设定的。
root@controller:~# ip netns exec qrouter-782e8b74-a13c-4e8c-83dd-066f49e55ac2 ip route
default via 203.0.113.1 dev qg-02f3fada-b8 proto static
172.16.1.0/24 dev qr-fb68b947-33 proto kernel scope link src 172.16.1.1
203.0.113.0/24 dev qg-02f3fada-b8 proto kernel scope link src 203.0.113.144
* 查看这个qrouter由哪个L3 agent负责执行:
Once the gateway interface has been added, the router will be scheduled to an eligible L3 agent. Using the Neutron l3-agent-list-hosting-router command, you can determine which L3 agent the router was scheduled to, as shown in the following screenshot:
root@controller ~(admin/amdin)# neutron l3-agent-list-hosting-router router
neutron CLI is deprecated and will be removed in the Z cycle. Use openstack CLI instead.
+--------------------------------------+------------+----------------+-------+----------+
| id | host | admin_state_up | alive | ha_state |
+--------------------------------------+------------+----------------+-------+----------+
| 784c22ee-79e2-4bfa-84c5-4a2456a805e4 | controller | True | :-) | |
+--------------------------------------+------------+----------------+-------+----------+
root@controller ~(admin/amdin)# openstack network agent list
+--------------------------------------+--------------------+------------+-------------------+-------+-------+---------------------------+
| ID | Agent Type | Host | Availability Zone | Alive | State | Binary |
+--------------------------------------+--------------------+------------+-------------------+-------+-------+---------------------------+
| 4516d406-7b90-4029-93a9-6a7fbe964bc2 | DHCP agent | controller | nova | :-) | UP | neutron-dhcp-agent |
| 784c22ee-79e2-4bfa-84c5-4a2456a805e4 | L3 agent | controller | nova | :-) | UP | neutron-l3-agent |
| dd50147c-5a72-4386-9073-a4431c47a3b4 | Metadata agent | controller | None | :-) | UP | neutron-metadata-agent |
| f05c0a19-5657-4e12-8f4c-f5ea5dfc7043 | Linux bridge agent | compute1 | None | :-) | UP | neutron-linuxbridge-agent |
| fc147e91-1504-4a3c-8709-0665c97b4cb6 | Linux bridge agent | controller | None | :-) | UP | neutron-linuxbridge-agent |
+--------------------------------------+--------------------+------------+-------------------+-------+-------+---------------------------+
root@controller ~(admin/amdin)#
2.4 Verify operation
1、source the admin
credentials to gain access to admin-only CLI commands:
root@osclient ~(admin/amdin)# cat admin-openrc
export OS_PROJECT_DOMAIN_NAME=Default
export OS_USER_DOMAIN_NAME=Default
export OS_PROJECT_NAME=admin
export OS_USERNAME=admin
export OS_PASSWORD=openstack
export OS_AUTH_URL=http://controller:5000/v3
export OS_IDENTITY_API_VERSION=3
export OS_IMAGE_API_VERSION=2
export PS1='\u@\h \W(admin/amdin)\$ '
root@osclient ~(admin/amdin)#
2、List network namespaces. You should see one qrouter
namespace and two qdhcp
namespaces.
root@controller:~# ip netns
qrouter-782e8b74-a13c-4e8c-83dd-066f49e55ac2 (id: 2)
qdhcp-28d343c8-1cbb-4d3a-b69c-7d9afe5840fa (id: 0)
qdhcp-48f2b88e-7740-4d94-a631-69e2abadf25b (id: 1)
root@controller:~#
3、List ports on the router to determine the gateway IP address on the provider network:
root@osclient ~(admin/amdin)# openstack port list --router router
+--------------------------------------+------+-------------------+------------------------------------------------------------------------------+--------+
| ID | Name | MAC Address | Fixed IP Addresses | Status |
+--------------------------------------+------+-------------------+------------------------------------------------------------------------------+--------+
| 02f3fada-b837-405d-83c6-cd05d0e5dd3f | | fa:16:3e:bd:68:5a | ip_address='203.0.113.144', subnet_id='8279842e-d7c5-4ba6-a037-831e0a72a938' | ACTIVE |
| fb68b947-3324-441a-a58c-6a4a87f01517 | | fa:16:3e:33:b2:f8 | ip_address='172.16.1.1', subnet_id='2825e2f9-b894-49ba-8cdb-399285223219' | ACTIVE |
+--------------------------------------+------+-------------------+------------------------------------------------------------------------------+--------+
root@osclient ~(admin/amdin)#
4、Ping this IP address from the controller node or any host on the physical provider network:
C:\>ping 203.0.113.144
正在 Ping 203.0.113.144 具有 32 字节的数据:
来自 203.0.113.144 的回复: 字节=32 时间<1ms TTL=64
来自 203.0.113.144 的回复: 字节=32 时间<1ms TTL=64
来自 203.0.113.144 的回复: 字节=32 时间<1ms TTL=64
3、Launch an instance on the self-service network
3.1 Determine instance options
To launch an instance, you must at least specify the flavor, image name, network, security group, key, and instance name.
root@osclient:~# source demo-openrc
root@osclient ~(myproject/myuser)# openstack flavor list
+----+---------+-----+------+-----------+-------+-----------+
| ID | Name | RAM | Disk | Ephemeral | VCPUs | Is Public |
+----+---------+-----+------+-----------+-------+-----------+
| 0 | m1.nano | 64 | 1 | 0 | 1 | True |
+----+---------+-----+------+-----------+-------+-----------+
root@osclient ~(myproject/myuser)# openstack image list
+--------------------------------------+--------+--------+
| ID | Name | Status |
+--------------------------------------+--------+--------+
| 429decdd-9230-49c0-b735-70364c226eb5 | cirros | active |
+--------------------------------------+--------+--------+
root@osclient ~(myproject/myuser)# openstack network list
+--------------------------------------+-------------+--------------------------------------+
| ID | Name | Subnets |
+--------------------------------------+-------------+--------------------------------------+
| 28d343c8-1cbb-4d3a-b69c-7d9afe5840fa | selfservice | 2825e2f9-b894-49ba-8cdb-399285223219 |
| 48f2b88e-7740-4d94-a631-69e2abadf25b | provider | 8279842e-d7c5-4ba6-a037-831e0a72a938 |
+--------------------------------------+-------------+--------------------------------------+
root@osclient ~(myproject/myuser)# openstack security group list
+--------------------------------------+---------+------------------------+----------------------------------+------+
| ID | Name | Description | Project | Tags |
+--------------------------------------+---------+------------------------+----------------------------------+------+
| 15dfe688-d6fc-4231-a670-7b832e08fb9d | default | Default security group | f5e75a3f7cc347ad89d20dcfe70dae01 | [] |
+--------------------------------------+---------+------------------------+----------------------------------+------+
root@osclient ~(myproject/myuser)#
3.2 Launch the instance
root@osclient ~(myproject/myuser)# openstack server create --flavor m1.nano --image cirros \
> --nic net-id=28d343c8-1cbb-4d3a-b69c-7d9afe5840fa --security-group default \
> --key-name mykey selfservice-instance
+-----------------------------+-----------------------------------------------+
| Field | Value |
+-----------------------------+-----------------------------------------------+
| OS-DCF:diskConfig | MANUAL |
| OS-EXT-AZ:availability_zone | |
| OS-EXT-STS:power_state | NOSTATE |
| OS-EXT-STS:task_state | scheduling |
| OS-EXT-STS:vm_state | building |
| OS-SRV-USG:launched_at | None |
| OS-SRV-USG:terminated_at | None |
| accessIPv4 | |
| accessIPv6 | |
| addresses | |
| adminPass | oi2jwRZqJgic |
| config_drive | |
| created | 2025-04-11T00:55:13Z |
| flavor | m1.nano (0) |
| hostId | |
| id | e6978f67-7b21-4a53-97a4-58bca7e0c7d5 |
| image | cirros (429decdd-9230-49c0-b735-70364c226eb5) |
| key_name | mykey |
| name | selfservice-instance |
| progress | 0 |
| project_id | f5e75a3f7cc347ad89d20dcfe70dae01 |
| properties | |
| security_groups | name='15dfe688-d6fc-4231-a670-7b832e08fb9d' |
| status | BUILD |
| updated | 2025-04-11T00:55:13Z |
| user_id | 9382b59561c04dd1abf0a4cb7a8252ec |
| volumes_attached | |
+-----------------------------+-----------------------------------------------+
root@osclient ~(myproject/myuser)#
3.3 Check the status of your instance
root@osclient ~(myproject/myuser)# openstack server list
+--------------------------------------+----------------------+---------+-------------------------+--------+---------+
| ID | Name | Status | Networks | Image | Flavor |
+--------------------------------------+----------------------+---------+-------------------------+--------+---------+
| e6978f67-7b21-4a53-97a4-58bca7e0c7d5 | selfservice-instance | ACTIVE | selfservice=172.16.1.42 | cirros | m1.nano |
| d2e4bc39-63c8-4c80-b33f-52f4e1891f50 | provider-instance | SHUTOFF | provider=203.0.113.125 | cirros | m1.nano |
+--------------------------------------+----------------------+---------+-------------------------+--------+---------+
root@osclient ~(myproject/myuser)# openstack server show selfservice-instance
+-----------------------------+----------------------------------------------------------+
| Field | Value |
+-----------------------------+----------------------------------------------------------+
| OS-DCF:diskConfig | MANUAL |
| OS-EXT-AZ:availability_zone | nova |
| OS-EXT-STS:power_state | Running |
| OS-EXT-STS:task_state | None |
| OS-EXT-STS:vm_state | active |
| OS-SRV-USG:launched_at | 2025-04-11T00:55:20.000000 |
| OS-SRV-USG:terminated_at | None |
| accessIPv4 | |
| accessIPv6 | |
| addresses | selfservice=172.16.1.42 |
| config_drive | |
| created | 2025-04-11T00:55:13Z |
| flavor | m1.nano (0) |
| hostId | f482eac1735f9b4319d1f2bf7604decf52e3866937ad1fb219a8eeaf |
| id | e6978f67-7b21-4a53-97a4-58bca7e0c7d5 |
| image | cirros (429decdd-9230-49c0-b735-70364c226eb5) |
| key_name | mykey |
| name | selfservice-instance |
| progress | 0 |
| project_id | f5e75a3f7cc347ad89d20dcfe70dae01 |
| properties | |
| security_groups | name='default' |
| status | ACTIVE |
| updated | 2025-04-11T00:55:20Z |
| user_id | 9382b59561c04dd1abf0a4cb7a8252ec |
| volumes_attached | |
+-----------------------------+----------------------------------------------------------+
"admin" role的“admin" user登录到project "myproject",查看instance运行在controller node:
root@osclient ~(myproject/myuser)# source myproject-admin-openrc
root@osclient ~(myproject/admin)# cat myproject-admin-openrc
export OS_PROJECT_DOMAIN_NAME=Default
export OS_USER_DOMAIN_NAME=Default
export OS_PROJECT_NAME=myproject
export OS_USERNAME=admin
export OS_PASSWORD=openstack
export OS_AUTH_URL=http://controller:5000/v3
export OS_IDENTITY_API_VERSION=3
export OS_IMAGE_API_VERSION=2
export PS1='\u@\h \W(myproject/admin)\$ '
root@osclient ~(myproject/admin)# openstack server show selfservice-instance
+-------------------------------------+----------------------------------------------------------+
| Field | Value |
+-------------------------------------+----------------------------------------------------------+
| OS-DCF:diskConfig | MANUAL |
| OS-EXT-AZ:availability_zone | nova |
| OS-EXT-SRV-ATTR:host | controller |
| OS-EXT-SRV-ATTR:hypervisor_hostname | controller |
| OS-EXT-SRV-ATTR:instance_name | instance-00000005 |
| OS-EXT-STS:power_state | Running |
| OS-EXT-STS:task_state | None |
| OS-EXT-STS:vm_state | active |
| OS-SRV-USG:launched_at | 2025-04-11T00:55:20.000000 |
| OS-SRV-USG:terminated_at | None |
| accessIPv4 | |
| accessIPv6 | |
| addresses | selfservice=172.16.1.42 |
| config_drive | |
| created | 2025-04-11T00:55:13Z |
| flavor | m1.nano (0) |
| hostId | f482eac1735f9b4319d1f2bf7604decf52e3866937ad1fb219a8eeaf |
| id | e6978f67-7b21-4a53-97a4-58bca7e0c7d5 |
| image | cirros (429decdd-9230-49c0-b735-70364c226eb5) |
| key_name | mykey |
| name | selfservice-instance |
| progress | 0 |
| project_id | f5e75a3f7cc347ad89d20dcfe70dae01 |
| properties | |
| security_groups | name='default' |
| status | ACTIVE |
| updated | 2025-04-11T00:55:20Z |
| user_id | 9382b59561c04dd1abf0a4cb7a8252ec |
| volumes_attached | |
+-------------------------------------+----------------------------------------------------------+
root@osclient ~(myproject/admin)#
3.4 Access the instance using a virtual console(有问题)
1、Obtain a Virtual Network Computing (VNC) session URL for your instance and access it from a web browser:
root@osclient ~(myproject/myuser)# openstack console url show selfservice-instance
+----------+------------------------------------------------------------------------------------------+
| Field | Value |
+----------+------------------------------------------------------------------------------------------+
| protocol | vnc |
| type | novnc |
| url | http://127.0.0.1:6080/vnc_auto.html?path=%3Ftoken%3D763caade-12cf-4e2d-beae-8028691801db |
+----------+------------------------------------------------------------------------------------------+
问题1:产生的url是127.0.0.1...(已解决)
原因:本次安装,Controller node补充安装compute服务(见《OpenStack Yoga版安装笔记(十三)neutron安装》。但没修改novncproxy_base_url为novncproxy_base_url = http://controller:6080/vnc_auto.html,所以使用的是缺省url。
修改controller的/etc/nova/nova.conf:
root@controller:~# vi /etc/nova/nova.conf
#
# Public address of noVNC VNC console proxy. For more information, refer to the
# documentation. (uri value)
#novncproxy_base_url = http://127.0.0.1:6080/vnc_auto.html
novncproxy_base_url = http://controller:6080/vnc_auto.html
修改后,重启nova服务:
root@controller:~# service nova-api restart
root@controller:~# service nova-scheduler restart
root@controller:~# service nova-conductor restart
root@controller:~# service nova-novncproxy restart
再次获取 selfservice instance的CONSOLE URL:(如果无法正确显示,可以考虑重启controller node)
1、首先确保instance处于开机状态:
root@osclient ~(myproject/myuser)# openstack server list
+--------------------------------------+----------------------+--------+-------------------------+--------+---------+
| ID | Name | Status | Networks | Image | Flavor |
+--------------------------------------+----------------------+--------+-------------------------+--------+---------+
| e6978f67-7b21-4a53-97a4-58bca7e0c7d5 | selfservice-instance | ACTIVE | selfservice=172.16.1.42 | cirros | m1.nano |
| d2e4bc39-63c8-4c80-b33f-52f4e1891f50 | provider-instance | ACTIVE | provider=203.0.113.125 | cirros | m1.nano |
+--------------------------------------+----------------------+--------+-------------------------+--------+---------+
root@osclient ~(myproject/myuser)#
2、获取instance console url:
root@osclient ~(myproject/myuser)# openstack console url show selfservice-instance
+----------+-------------------------------------------------------------------------------------------+
| Field | Value |
+----------+-------------------------------------------------------------------------------------------+
| protocol | vnc |
| type | novnc |
| url | http://controller:6080/vnc_auto.html?path=%3Ftoken%3D501de2a6-c350-427a-8862-4c747e429854 |
+----------+-------------------------------------------------------------------------------------------+
root@osclient ~(myproject/myuser)#
问题2:能显示终端字幕,原因待查明。
查看instance的vnc配置:
root@controller:~# virsh list --all
Id Name State
-----------------------------------
1 instance-00000005 running
root@controller:~# virsh dumpxml instance-00000005 | grep vnc
<graphics type='vnc' port='5900' autoport='yes' listen='10.0.20.11'>
可以看出,虚拟机
instance-00000005
的 VNC 配置如下:
port='5900'
:表示虚拟机的 VNC 服务绑定到5900
端口。这是 VNC 客户端用来连接虚拟机的端口。
autoport='yes'
:表示如果5900
端口已经被占用,VNC 会自动分配一个新的端口。这意味着在某些情况下,虚拟机可能使用其他端口(例如5901
、5902
等)来提供 VNC 服务。
listen='10.0.20.11'
:表示 VNC 服务仅在 IP 地址10.0.20.11
上监听,即只允许从该 IP 地址或子网访问虚拟机的 VNC 服务。
尝试通过添加安全组规则允许通过 5900
端口访问虚拟机,但未能成功。
root@osclient ~(myproject/myuser)# openstack security group rule create --protocol tcp --dst-port 5900 --ingress default
+-------------------------+--------------------------------------+
| Field | Value |
+-------------------------+--------------------------------------+
| created_at | 2025-04-12T00:27:59Z |
| description | |
| direction | ingress |
| ether_type | IPv4 |
| id | 66bf3ce2-90a5-47a3-a739-a89141d17f5a |
| name | None |
| port_range_max | 5900 |
| port_range_min | 5900 |
| project_id | f5e75a3f7cc347ad89d20dcfe70dae01 |
| protocol | tcp |
| remote_address_group_id | None |
| remote_group_id | None |
| remote_ip_prefix | 0.0.0.0/0 |
| revision_number | 0 |
| security_group_id | 15dfe688-d6fc-4231-a670-7b832e08fb9d |
| tags | [] |
| tenant_id | f5e75a3f7cc347ad89d20dcfe70dae01 |
| updated_at | 2025-04-12T00:27:59Z |
+-------------------------+--------------------------------------+
2、在controller查看安全组规则已经生成(即:-A neutron-linuxbri-idef1277e-d -p tcp -m tcp --dport 5900 -j RETURN)
root@controller:~# iptables-save -t filter | grep neutron-linuxbri-idef1277e-d
:neutron-linuxbri-idef1277e-d - [0:0]
-A neutron-linuxbri-idef1277e-d -m state --state RELATED,ESTABLISHED -m comment --comment "Direct packets associated with a known session to the RETURN chain." -j RETURN
-A neutron-linuxbri-idef1277e-d -d 172.16.1.42/32 -p udp -m udp --sport 67 --dport 68 -j RETURN
-A neutron-linuxbri-idef1277e-d -d 255.255.255.255/32 -p udp -m udp --sport 67 --dport 68 -j RETURN
-A neutron-linuxbri-idef1277e-d -m set --match-set NIPv415dfe688-d6fc-4231-a670- src -j RETURN
-A neutron-linuxbri-idef1277e-d -p icmp -j RETURN
-A neutron-linuxbri-idef1277e-d -p tcp -m tcp --dport 22 -j RETURN
-A neutron-linuxbri-idef1277e-d -p tcp -m tcp --dport 5900 -j RETURN
-A neutron-linuxbri-idef1277e-d -m state --state INVALID -m comment --comment "Drop packets that appear related to an existing connection (e.g. TCP ACK/FIN) but do not have an entry in conntrack." -j DROP
-A neutron-linuxbri-idef1277e-d -m comment --comment "Send unmatched traffic to the fallback chain." -j neutron-linuxbri-sg-fallback
-A neutron-linuxbri-sg-chain -m physdev --physdev-out tapdef1277e-db --physdev-is-bridged -m comment --comment "Jump to the VM specific chain." -j neutron-linuxbri-idef1277e-d
root@controller:~#
3、由于未解决vnc终端显示问题,暂时删除新添加的规则:
root@osclient ~(myproject/myuser)# openstack security group rule list default
+--------------------------------------+-------------+-----------+-----------+------------+-----------+--------------------------------------+----------------------+
| ID | IP Protocol | Ethertype | IP Range | Port Range | Direction | Remote Security Group | Remote Address Group |
+--------------------------------------+-------------+-----------+-----------+------------+-----------+--------------------------------------+----------------------+
| 1adec9af-14a9-4288-8364-e79a8fa3b75a | None | IPv4 | 0.0.0.0/0 | | ingress | 15dfe688-d6fc-4231-a670-7b832e08fb9d | None |
| 2cc95680-49b4-4b6b-8cea-52f8cb7302aa | icmp | IPv4 | 0.0.0.0/0 | | ingress | None | None |
| 6452f09e-cbce-4ff9-845e-dcfb7144f62d | tcp | IPv4 | 0.0.0.0/0 | 22:22 | ingress | None | None |
| 66bf3ce2-90a5-47a3-a739-a89141d17f5a | tcp | IPv4 | 0.0.0.0/0 | 5900:5900 | ingress | None | None |
| a5046171-f9e9-451f-acfe-662ef32ea651 | None | IPv6 | ::/0 | | ingress | 15dfe688-d6fc-4231-a670-7b832e08fb9d | None |
| a7dffce7-946e-421e-bfa9-22fa65f4bf7a | None | IPv4 | 0.0.0.0/0 | | egress | None | None |
| d9bae044-c411-4d73-a5f4-ab422e3152a9 | None | IPv6 | ::/0 | | egress | None | None |
+--------------------------------------+-------------+-----------+-----------+------------+-----------+--------------------------------------+----------------------+
root@osclient ~(myproject/myuser)# openstack security group rule delete 66bf3ce2-90a5-47a3-a739-a89141d17f5a
root@osclient ~(myproject/myuser)# openstack security group rule list default
+--------------------------------------+-------------+-----------+-----------+------------+-----------+--------------------------------------+----------------------+
| ID | IP Protocol | Ethertype | IP Range | Port Range | Direction | Remote Security Group | Remote Address Group |
+--------------------------------------+-------------+-----------+-----------+------------+-----------+--------------------------------------+----------------------+
| 1adec9af-14a9-4288-8364-e79a8fa3b75a | None | IPv4 | 0.0.0.0/0 | | ingress | 15dfe688-d6fc-4231-a670-7b832e08fb9d | None |
| 2cc95680-49b4-4b6b-8cea-52f8cb7302aa | icmp | IPv4 | 0.0.0.0/0 | | ingress | None | None |
| 6452f09e-cbce-4ff9-845e-dcfb7144f62d | tcp | IPv4 | 0.0.0.0/0 | 22:22 | ingress | None | None |
| a5046171-f9e9-451f-acfe-662ef32ea651 | None | IPv6 | ::/0 | | ingress | 15dfe688-d6fc-4231-a670-7b832e08fb9d | None |
| a7dffce7-946e-421e-bfa9-22fa65f4bf7a | None | IPv4 | 0.0.0.0/0 | | egress | None | None |
| d9bae044-c411-4d73-a5f4-ab422e3152a9 | None | IPv6 | ::/0 | | egress | None | None |
+--------------------------------------+-------------+-----------+-----------+------------+-----------+--------------------------------------+----------------------+
root@osclient ~(myproject/myuser)#
3.5 qdhcp ping the instance
root@controller:~# ip netns
qdhcp-28d343c8-1cbb-4d3a-b69c-7d9afe5840fa (id: 2)
qdhcp-48f2b88e-7740-4d94-a631-69e2abadf25b (id: 1)
qrouter-782e8b74-a13c-4e8c-83dd-066f49e55ac2 (id: 0)
root@controller:~# ip netns exec qdhcp-28d343c8-1cbb-4d3a-b69c-7d9afe5840fa ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
2: ns-9c9c42d1-7c@if13: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1450 qdisc noqueue state UP group default qlen 1000
link/ether fa:16:3e:be:16:3b brd ff:ff:ff:ff:ff:ff link-netnsid 0
inet 169.254.169.254/32 brd 169.254.169.254 scope global ns-9c9c42d1-7c
valid_lft forever preferred_lft forever
inet 172.16.1.2/24 brd 172.16.1.255 scope global ns-9c9c42d1-7c
valid_lft forever preferred_lft forever
inet6 fe80::a9fe:a9fe/128 scope link
valid_lft forever preferred_lft forever
inet6 fe80::f816:3eff:febe:163b/64 scope link
valid_lft forever preferred_lft forever
root@controller:~# ip netns exec qdhcp-28d343c8-1cbb-4d3a-b69c-7d9afe5840fa ping 172.16.1.42
PING 172.16.1.42 (172.16.1.42) 56(84) bytes of data.
64 bytes from 172.16.1.42: icmp_seq=1 ttl=64 time=1.95 ms
64 bytes from 172.16.1.42: icmp_seq=2 ttl=64 time=0.364 ms
64 bytes from 172.16.1.42: icmp_seq=3 ttl=64 time=0.276 ms
^C
4、Access the instance remotely
4.1 创建浮动IP
(floating IP类似云平台弹性IP的场景)
Create a floating IP address on the provider virtual network:
root@osclient ~(myproject/myuser)# openstack floating ip create provider
+---------------------+--------------------------------------+
| Field | Value |
+---------------------+--------------------------------------+
| created_at | 2025-04-12T01:09:59Z |
| description | |
| dns_domain | None |
| dns_name | None |
| fixed_ip_address | None |
| floating_ip_address | 203.0.113.145 |
| floating_network_id | 48f2b88e-7740-4d94-a631-69e2abadf25b |
| id | 5bb30161-2555-4456-8b06-42e6125ce1d9 |
| name | 203.0.113.145 |
| port_details | None |
| port_id | None |
| project_id | f5e75a3f7cc347ad89d20dcfe70dae01 |
| qos_policy_id | None |
| revision_number | 0 |
| router_id | None |
| status | DOWN |
| subnet_id | None |
| tags | [] |
| updated_at | 2025-04-12T01:09:59Z |
+---------------------+--------------------------------------+
root@osclient ~(myproject/myuser)# openstack project list
+----------------------------------+-----------+
| ID | Name |
+----------------------------------+-----------+
| f5e75a3f7cc347ad89d20dcfe70dae01 | myproject |
+----------------------------------+-----------+
创建了一个浮动 IP 地址
203.0.113.145
,但是当前状态是DOWN
。这意味着这个浮动 IP 尚未与任何虚拟机实例关联,或者没有正确配置路由器和子网。
这个浮动IP实际添加在router的gateway端口上:
(这个gateway和网络上的网关概念略有区别,这里的gateway指router上连接provider network的端口,这个provider network在创建时有--external选项)
root@controller:~# ip netns
qdhcp-28d343c8-1cbb-4d3a-b69c-7d9afe5840fa (id: 2)
qdhcp-48f2b88e-7740-4d94-a631-69e2abadf25b (id: 1)
qrouter-782e8b74-a13c-4e8c-83dd-066f49e55ac2 (id: 0)
root@controller:~# ip netns exec qrouter-782e8b74-a13c-4e8c-83dd-066f49e55ac2 ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
2: qr-fb68b947-33@if8: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1450 qdisc noqueue state UP group default qlen 1000
link/ether fa:16:3e:33:b2:f8 brd ff:ff:ff:ff:ff:ff link-netnsid 0
inet 172.16.1.1/24 brd 172.16.1.255 scope global qr-fb68b947-33
valid_lft forever preferred_lft forever
inet6 fe80::f816:3eff:fe33:b2f8/64 scope link
valid_lft forever preferred_lft forever
3: qg-02f3fada-b8@if9: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default qlen 1000
link/ether fa:16:3e:bd:68:5a brd ff:ff:ff:ff:ff:ff link-netnsid 0
inet 203.0.113.144/24 brd 203.0.113.255 scope global qg-02f3fada-b8
valid_lft forever preferred_lft forever
inet 203.0.113.145/32 brd 203.0.113.145 scope global qg-02f3fada-b8
valid_lft forever preferred_lft forever
inet6 fe80::f816:3eff:febd:685a/64 scope link
valid_lft forever preferred_lft forever
root@controller:~#
4.2 浮动IP关联虚机
Associate the floating IP address with the instance:
root@osclient ~(myproject/myuser)# openstack server add floating ip selfservice-instance 203.0.113.145
root@osclient ~(myproject/myuser)#
已经成功将浮动 IP 203.0.113.145
添加到虚拟机 selfservice-instance
上。
* 查看router的iptables nat表:
root@controller:~# ip netns exec qrouter-782e8b74-a13c-4e8c-83dd-066f49e55ac2 iptables-save -t nat
# Generated by iptables-save v1.8.7 on Sat Apr 12 05:22:45 2025
*nat
:PREROUTING ACCEPT [4257:759117]
:INPUT ACCEPT [0:0]
:OUTPUT ACCEPT [0:0]
:POSTROUTING ACCEPT [3:172]
:neutron-l3-agent-OUTPUT - [0:0]
:neutron-l3-agent-POSTROUTING - [0:0]
:neutron-l3-agent-PREROUTING - [0:0]
:neutron-l3-agent-float-snat - [0:0]
:neutron-l3-agent-snat - [0:0]
:neutron-postrouting-bottom - [0:0]
-A PREROUTING -j neutron-l3-agent-PREROUTING
-A OUTPUT -j neutron-l3-agent-OUTPUT
-A POSTROUTING -j neutron-l3-agent-POSTROUTING
-A POSTROUTING -j neutron-postrouting-bottom
-A neutron-l3-agent-OUTPUT -d 203.0.113.145/32 -j DNAT --to-destination 172.16.1.42
-A neutron-l3-agent-POSTROUTING ! -o qg-02f3fada-b8 -m conntrack ! --ctstate DNAT -j ACCEPT
-A neutron-l3-agent-PREROUTING -d 169.254.169.254/32 -i qr-+ -p tcp -m tcp --dport 80 -j REDIRECT --to-ports 9697
-A neutron-l3-agent-PREROUTING -d 203.0.113.145/32 -j DNAT --to-destination 172.16.1.42
-A neutron-l3-agent-float-snat -s 172.16.1.42/32 -j SNAT --to-source 203.0.113.145 --random-fully
-A neutron-l3-agent-snat -j neutron-l3-agent-float-snat
-A neutron-l3-agent-snat -o qg-02f3fada-b8 -j SNAT --to-source 203.0.113.144 --random-fully
-A neutron-l3-agent-snat -m mark ! --mark 0x2/0xffff -m conntrack --ctstate DNAT -j SNAT --to-source 203.0.113.144 --random-fully
-A neutron-postrouting-bottom -m comment --comment "Perform source NAT on outgoing traffic." -j neutron-l3-agent-snat
COMMIT
# Completed on Sat Apr 12 05:22:45 2025
root@controller:~#
从iptables-save
输出可以看出,当前配置在 Neutron L3 Agent 中涉及了多个 NAT 操作,包括 DNAT、SNAT 和一些连接跟踪规则。这里对关键规则进行解析:
-A neutron-l3-agent-PREROUTING -d 203.0.113.145/32 -j DNAT --to-destination 172.16.1.42
这条规则将外部访问
203.0.113.145
(浮动 IP 地址)的流量转换为内部虚拟机的私有 IP 地址172.16.1.42
。
-A neutron-l3-agent-float-snat -s 172.16.1.42/32 -j SNAT --to-source 203.0.113.145 --random-fully
这条规则表示 SNAT(源地址转换),将源地址为
172.16.1.42
的流量转换为203.0.113.145
(浮动 IP 地址),并随机选择一个源端口。
4.3 检查浮动IP状态
Check the status of your floating IP address:
root@osclient ~(myproject/myuser)# openstack server list
+--------------------------------------+----------------------+--------+----------------------------------------+--------+---------+
| ID | Name | Status | Networks | Image | Flavor |
+--------------------------------------+----------------------+--------+----------------------------------------+--------+---------+
| e6978f67-7b21-4a53-97a4-58bca7e0c7d5 | selfservice-instance | ACTIVE | selfservice=172.16.1.42, 203.0.113.145 | cirros | m1.nano |
| d2e4bc39-63c8-4c80-b33f-52f4e1891f50 | provider-instance | ACTIVE | provider=203.0.113.125 | cirros | m1.nano |
+--------------------------------------+----------------------+--------+----------------------------------------+--------+---------+
root@osclient ~(myproject/myuser)#
root@osclient ~(admin/amdin)# openstack floating ip list
+--------------------------------------+---------------------+------------------+--------------------------------------+--------------------------------------+----------------------------------+
| ID | Floating IP Address | Fixed IP Address | Port | Floating Network | Project |
+--------------------------------------+---------------------+------------------+--------------------------------------+--------------------------------------+----------------------------------+
| 5bb30161-2555-4456-8b06-42e6125ce1d9 | 203.0.113.145 | 172.16.1.42 | def1277e-db96-4200-a351-1c127fc0bcee | 48f2b88e-7740-4d94-a631-69e2abadf25b | f5e75a3f7cc347ad89d20dcfe70dae01 |
+--------------------------------------+---------------------+------------------+--------------------------------------+--------------------------------------+----------------------------------+
root@osclient ~(admin/amdin)#
使用 openstack floating ip show
命令确认浮动 IP 是否已经正确绑定到实例,并且状态是否为 ACTIVE
:
root@osclient ~(myproject/myuser)# openstack floating ip show 203.0.113.145
+---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| Field | Value |
+---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
| created_at | 2025-04-12T01:09:59Z |
| description | |
| dns_domain | None |
| dns_name | None |
| fixed_ip_address | 172.16.1.42 |
| floating_ip_address | 203.0.113.145 |
| floating_network_id | 48f2b88e-7740-4d94-a631-69e2abadf25b |
| id | 5bb30161-2555-4456-8b06-42e6125ce1d9 |
| name | 203.0.113.145 |
| port_details | admin_state_up='True', device_id='e6978f67-7b21-4a53-97a4-58bca7e0c7d5', device_owner='compute:nova', mac_address='fa:16:3e:84:d2:a6', name='', network_id='28d343c8-1cbb-4d3a-b69c-7d9afe5840fa', status='ACTIVE' |
| port_id | def1277e-db96-4200-a351-1c127fc0bcee |
| project_id | f5e75a3f7cc347ad89d20dcfe70dae01 |
| qos_policy_id | None |
| revision_number | 2 |
| router_id | 782e8b74-a13c-4e8c-83dd-066f49e55ac2 |
| status | ACTIVE |
| subnet_id | None |
| tags | [] |
| updated_at | 2025-04-12T01:26:34Z |
+---------------------+--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
root@osclient ~(myproject/myuser)#
4.4 Ping浮动IP
Verify connectivity to the instance via floating IP address from the controller node or any host on the provider physical network:
C:\Users\LXH>ping -n 4 203.0.113.145
正在 Ping 203.0.113.145 具有 32 字节的数据:
来自 203.0.113.1 的回复: 无法访问目标主机。
来自 203.0.113.145 的回复: 字节=32 时间=3ms TTL=63
来自 203.0.113.145 的回复: 字节=32 时间=1ms TTL=63
来自 203.0.113.145 的回复: 字节=32 时间=1ms TTL=63
203.0.113.145 的 Ping 统计信息:
数据包: 已发送 = 4,已接收 = 4,丢失 = 0 (0% 丢失),
往返行程的估计时间(以毫秒为单位):
最短 = 1ms,最长 = 3ms,平均 = 1ms
C:\Users\LXH>
4.5 通过浮动IP访问虚机
Access your instance using SSH from the controller node or any host on the provider physical network:
(虚机用户/密码:cirros/gocubsgo)
C:\>ssh cirros@203.0.113.145
The authenticity of host '203.0.113.145 (203.0.113.145)' can't be established.
ECDSA key fingerprint is SHA256:J9pMLqW++UslBJ60AtcB1IlSVlH4iSZ7VH82dTp0ft8.
This key is not known by any other names
Are you sure you want to continue connecting (yes/no/[fingerprint])? yes
Warning: Permanently added '203.0.113.145' (ECDSA) to the list of known hosts.
cirros@203.0.113.145's password:
$ ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue qlen 1
link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
inet 127.0.0.1/8 scope host lo
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1450 qdisc pfifo_fast qlen 1000
link/ether fa:16:3e:84:d2:a6 brd ff:ff:ff:ff:ff:ff
inet 172.16.1.42/24 brd 172.16.1.255 scope global eth0
valid_lft forever preferred_lft forever
inet6 fe80::f816:3eff:fe84:d2a6/64 scope link
valid_lft forever preferred_lft forever
$
5、Horizon查看OpenStack抽象网络拓扑
使用myuser用户登录,查看myproject下的网络拓扑:
添加说明: