

인스턴스 관리:
네트워크 관리:
스토리지 관리:
사용자 및 프로젝트 관리:
모니터링 및 로그:
| 항목 | Horizon | Horizon Dashboard |
|---|---|---|
| 역할 | 웹 프레임워크 | OpenStack 기본 대시보드 |
| 확장성 | 사용자 정의 대시보드 제작 가능 | 확장성은 제한적 |
| 포커스 | 프레임워크 기능 자체 | OpenStack 관리 및 UI 제공 |
Project와 User는 Keystone을 통해 관리된다.
이는 Horizon의 Identity에서 확인할 수 있다.
이후 위와 같이 GUI를 통해 admin 프로젝트에 assign된 demo User를 생성한다.
이후 first-project라는 프로젝트를 생성한다.
현재 우리가 생성한 클라우드에는 default라는 도메인만이 존재하기 때문애 해당 입력 폼이 비활성화되어 있다.
Default Domain은 OpenStack 설치 시 기본적으로 제공되며, 새로운 Domain을 생성하여 커스터마이징이 가능하다.
이후 위와 같이 Project에 Memeber를 추가한다.
Quota 옵션으로 해당 클라우드의 Resource의 Capacity를 조정하고 할당할 수 있다.
이후 demo user로 다시 로그인 했을 때 해당 user가 여러 프로젝트에 속해있다면, 위와 같이 drop down 메뉴에서 프로젝트를 선택할 수 있다.

Instances
- 클라우드 환경에서 생성된 가상 머신(Virtual Machine)을 의미
- Nova(Compute 서비스)를 통해 생성되며, 사용자는 다양한 설정(IP, 이미지, 플레이버 등)을 기반으로 인스턴스를 배포하고 관리할 수 있음

Images
- 가상 머신(Instance)을 생성하기 위한 디스크 이미지 파일
- 운영 체제(OS), 애플리케이션, 설정 정보 등이 포함된 템플릿 역할을 하며, Glance(Image 서비스)에 의해 관리

Key Pairs
- 가상 머신(Instance)에 안전하게 접근하기 위해 사용되는 SSH 키의 쌍을 의미
- Public Key와 Private Key로 구성되며, Nova(Compute 서비스)에 의해 관리

Server Groups
- 인스턴스(Instance) 배치 전략을 관리하기 위한 논리적 그룹
- 특정 규칙(정책)을 기반으로 인스턴스를 어떻게 물리적 호스트에 배치할지를 결정하여, 고가용성(HA) 또는 워크로드 최적화를 지원
Affinity: 같은 물리적 호스트에 인스턴스가 배치되도록 강제Anti-affinity: 다른 물리적 호스트에 인스턴스가 분산되도록 강제

Hypervisors
- 가상 머신(Instance)을 생성하고 실행하기 위한 가상화 소프트웨어
- 물리적 하드웨어를 가상화하여 다수의 가상 머신을 실행할 수 있도록 함

Host Aggregates
- 물리적 컴퓨트 노드(Compute Nodes)를 논리적으로 그룹화하여 리소스를 분리하고 관리하기 위한 메커니즘
- 컴퓨트 노드를 특성(예: CPU 유형, 지역, 스토리지 유형)별로 그룹화하여 특정 워크로드에 적합한 노드에 인스턴스를 배치
- Host Aggregates는 메타데이터(키-값 쌍)를 정의하여 노드의 속성을 설명하고 관리
- Host Aggregates는 Availability Zones와 결합하여 물리적 리소스의 고가용성 설계를 지원

Flavors
- 가상 머신(Instance)의 컴퓨팅 리소스(CPU, 메모리, 디스크 크기 등)를 정의한 템플릿
- 사용자는 Instance를 생성할 때 원하는 크기와 구성을 선택하기 위해 Flavor를 사용

Volumes
- 가상 머신(Instance)에 연결하여 사용할 수 있는 블록 스토리지(Block Storage)를 의미
- 독립적으로 관리되는 스토리지 장치로, Cinder(Block Storage Service)에 의해 생성 및 관리
- Volume은 Instance와 별도로 존재하며, 필요에 따라 다른 Instance에 재사용하거나 연결할 수 있음

Volume Snapshot
- Volume의 특정 시점 상태를 캡처한 읽기 전용 복제본
- Cinder에 의해 관리되며, 데이터 백업 및 복구, 복제본 생성에 사용

Groups
- Cinder에서 여러 개의 Volume을 논리적으로 그룹화하여 관리하기 위한 기능
- 여러 Volume을 묶어 공동의 작업(스냅샷, 복제 등)을 수행할 수 있도록 지원
Groups Snapshot
- Volume Group의 특정 시점 데이터를 캡처한 복제본
- 여러 Volume이 포함된 Group의 상태를 한 번에 캡처하여 데이터의 일관성을 유지하고, 백업 또는 복구를 지원

Volume Types
- 블록 스토리지(Volume)에 대해 스토리지 계층(성능, 특성 등)을 정의하기 위한 분류 체계
- 다양한 스토리지 백엔드(예: SSD, HDD, 고성능 스토리지)를 구분하여 사용자 요구에 맞는 Volume을 생성할 수 있도록 지원

Network Topology
- 클라우드 환경에서 가상 네트워크의 구조와 구성을 시각적으로 보여주는 기능
- 네트워크, 라우터, 서브넷, 인스턴스 간의 연결 관계를 시각적으로 관리

Networks
- 가상 머신(Instance) 및 기타 리소스 간의 통신을 지원하기 위해 제공되는 가상 네트워크
- Neutron(Networking 서비스)에 의해 관리되며, 사용자 정의 네트워크를 생성, 연결, 관리
- Private Network, Public Network, Floating IP 등을 통해 다양한 네트워크 아키텍처 구성 가능
- DHCP, 라우팅, 보안 그룹, 로드 밸런싱 등의 네트워크 서비스 지원

Routers
- 가상 네트워크 간 트래픽을 전달하고, 가상 네트워크(Private Network)를 외부 네트워크(Public Network)와 연결하는 네트워크 컴포넌트
- 라우팅 및 NAT(Network Address Translation)를 지원
Floating IP로 변환하여 외부와 통신 가능
Security Groups
- 인스턴스(Instance) 네트워크 트래픽을 제어하기 위한 방화벽 규칙의 모음
- Ingress(수신) 및 Egress(송신) 트래픽에 대한 규칙을 정의하여, 인스턴스가 허용된 트래픽만 송수신하도록 보안 계층을 제공
- Security Group은 IP 주소, 포트, 프로토콜을 기반으로 인스턴스의 트래픽을 허용 또는 차단
- Security Group 규칙 변경 시 즉시 적용되어 인스턴스를 재부팅할 필요 없음

Floating IP
- 가상 머신(Instance) 또는 리소스에 동적으로 할당할 수 있는 공용 IP 주소
- 주로 Private Network에 연결된 Instance가 Public Network를 통해 외부 네트워크(예: 인터넷)와 통신할 수 있도록 설정할 때 사용
192.168.1.10 (Instance의 내부 IP)203.0.113.10 (외부에서 접근 가능한 공용 IP)
Trunks
- 네트워크 인터페이스(포트)를 통해 여러 VLAN 서브넷을 하나의 가상 머신(Instance)에 연결할 수 있도록 지원하는 기능
- Trunks를 사용하면 단일 네트워크 포트로 여러 VLAN(802.1Q 태그 기반)을 처리할 수 있음

Network QoS
- 네트워크 트래픽에 대해 대역폭 관리와 트래픽 제어 정책을 설정할 수 있는 기능
- 네트워크 성능을 보장하고, 특정 트래픽 유형에 우선순위를 부여하거나 제한을 적용하는 데 사용

RBAC Policies
- 역할 기반 액세스 제어 정책으로, 특정 리소스(예: 네트워크, 프로젝트 등)에 대한 액세스를 역할(Role)에 따라 관리
- Neutron 및 기타 서비스에서 RBAC 정책을 사용하여 리소스 접근 권한을 세부적으로 제어

Containers
- 애플리케이션과 그 종속성을 단일 패키지로 격리하여 실행하는 가상화된 환경
- OpenStack Zun(Container Service)을 통해 컨테이너를 관리
- Docker, Kubernetes 등과 통합하여 컨테이너 기반 애플리케이션을 운영할 수 있습

System Information 에서 다양 서비스에 대한 정보와 엔드포인트 확인 가능
Metadata Definitions
- 리소스(예: 인스턴스, 볼륨, 네트워크 등)에 사용자 정의 메타데이터를 추가하여 리소스를 설명하거나 관리할 수 있도록 하는 기능
- 사용자 정의 속성, 태그 또는 추가 정보를 저장하는 데 사용되며, OpenStack Horizon 대시보드 또는 CLI를 통해 설정 및 관리할 수 있음

Project
- 리소스(컴퓨팅, 네트워크, 스토리지 등)를 논리적으로 구분하고 할당하기 위한 테넌트(Tenant) 또는 작업 공간
- 주로 사용자의 그룹이나 특정 애플리케이션, 환경을 위한 리소스 격리 단위로 사용
- ex. 회사의 부서별 Project:
- HR_Project: HR 부서 리소스 관리
- IT_Project: IT 부서 리소스 관리
- ex. 개발 환경별 Project:
- Dev_Project: 개발 환경
- Prod_Project: 운영 환경
Tenant
- OpenStack에서 Tenant는 특정 사용자 그룹이나 애플리케이션에 리소스를 격리하여 할당하는 논리적 단위
- Project와 동일한 개념으로, 초기 OpenStack에서는 Tenant라는 용어를 사용
Multitenancy
Multitenancy는 여러 Tenant(Project)가 하나의 OpenStack 클라우드 인프라를 공유하면서도, 서로의 리소스와 데이터가 격리되도록 지원하는 개념
Domain
- 사용자(User)와 Project(Tenant)를 그룹화하고 격리하는 최상위 관리 단위
- Domain 간 리소스 및 데이터가 격리되어 독립적으로 운영 가능
- 각 Domain은 별도의 관리 정책을 가질 수 있음
- OpenStack Identity 서비스(Keystone)에서 제공하며, 주로 멀티테넌트 환경에서 사용자와 리소스의 관리를 효율적으로 수행하기 위해 사용

Groups
- 사용자(User)를 논리적으로 묶어 관리하기 위한 단위
- Keystone을 통해 그룹을 생성하고, 사용자에게 그룹을 할당하여 접근 권한을 효율적으로 관리

Roles
- 사용자(User) 또는 그룹(Group)이 특정 프로젝트(Project) 또는 도메인(Domain) 내에서 수행할 수 있는 작업을 정의하는 권한 집합
- Keystone을 통해 관리되며, 역할 기반 접근 제어(RBAC)를 구현하는 데 사용

Application Credentials
- 애플리케이션이 특정 OpenStack 리소스에 안전하게 접근하도록 하기 위해 생성된 임시 인증 정보
- 사용자의 주요 인증 정보(예: 사용자 이름과 비밀번호)를 노출하지 않고도 애플리케이션이 OpenStack API에 접근할 수 있도록 함
- Application Credentials는 만료 기간을 설정할 수 있어, 필요 이상으로 사용되지 않도록 관리 가능
- 인증에 비밀키와 ID를 사용하여 애플리케이션의 인증 절차를 단순화
API 기반 애플리케이션:
자동화 스크립트:
권한 분리:
CI/CD 파이프라인:
OS Credential은 OpenStack Credential과는 아예 다르기 때문에, 별도로 인증해주어야 한다
RC File이라고 불린다 $ cat keystonerc_admin
unset OS_SERVICE_TOKEN
export OS_USERNAME=admin
export OS_PASSWORD='8cbcacb658684041'
export OS_REGION_NAME=RegionOne
export OS_AUTH_URL=http://10.0.2.15:5000/v3
export PS1='[\u@\h \W(keystone_admin)]\$ '
export OS_PROJECT_NAME=admin
export OS_USER_DOMAIN_NAME=Default
export OS_PROJECT_DOMAIN_NAME=Default
export OS_IDENTITY_API_VERSION=3
# keystonerc_admin 적용
$ source keystonerc_admin
source셸 스크립트나 환경 파일을 현재 셸에 로드하여, 환경 변수 또는 셸 설정을 적용하는 데 사용되는 명령어
$ cp keystonerc_admin demo_rc
$ vi demo_rc
unset OS_SERVICE_TOKEN
export OS_USERNAME=demo
export OS_PASSWORD=demo
export OS_REGION_NAME=RegionOne
export OS_AUTH_URL=http://10.0.2.15:5000/v3
export PS1='[\u@\h \W(demo)]\$ '
export OS_PROJECT_NAME=admin
export OS_USER_DOMAIN_NAME=Default
export OS_PROJECT_DOMAIN_NAME=Default
export OS_IDENTITY_API_VERSION=3
새로운 Credential을 생성하고자 했을 때 위와 같이 기존의 Credential을 복사하고 수정하는 것이 좋은 방법이다.
이떄 이전에 Horizon Dashboard에서 생성했던 것과 마찬가지로 demo User를 생성해준다.
[root@localhost ~(demo)]# openstack flavor create --disk 1 --ram 768 --id 20 newflavor
HttpException: 403: Client Error for url: http://10.0.2.15:8774/v2.1/flavors, Policy doesn't allow os_compute_api:os-flavor-manage:create to be performed.
[root@localhost ~(demo)]# source keystonerc_admin
[root@localhost ~(keystone_admin)]# openstack flavor create --disk 1 --ram 768 --id 20 newflavor
+----------------------------+-----------+
| Field | Value |
+----------------------------+-----------+
| OS-FLV-DISABLED:disabled | False |
| OS-FLV-EXT-DATA:ephemeral | 0 |
| description | None |
| disk | 1 |
| id | 20 |
| name | newflavor |
| os-flavor-access:is_public | True |
| properties | |
| ram | 768 |
| rxtx_factor | 1.0 |
| swap | |
| vcpus | 1 |
+----------------------------+-----------+
위와 같이 각 user의 권한에 따라 동일한 명렁어가 동작하지 않거나, 동작하는 모습을 볼 수 있다.
# nova boot
openstack server create
# neutron net-create
openstack network create
# glance image-list
openstack image list
# cinder create
openstack volume create
User: 사람, 서비스 및 Auth를 획득하는 어떤 것을 지칭
- User는
Token읕 통해 Auth 및 API Call을 할 수 있음
Project: 리소스를 논리적으로 구분하고 할당하기 위한 작업공간
Role: User의 Operational Right
Globally scoped,Project scoped
Token: Openstack API에 접근할 수 있게 하는 Alphanumerical String
- User가 Service를 Call하면 User의 Role을 해석
- Authorization을 여러 scope에서 구분할 수 있는 도구
Scope: API 요청이나 역할(Role)이 적용되는 범위를 정의하는 데 사용
- 리소스의 접근 및 관리 권한을 제어
- 프로젝트(Project)와 도메인(Domain) 수준에서 역할과 권한을 분리
Catalog: 일종의 directory 서비스 (서비스 엔드포인트 목록)
- User가 OpenStack의 다른 서비스에 접근하기 위해 필요한 URL과 정보를 제공

Keystone → User: Token
User → Nova: Token + Request for VM
Nova → Keystone: Verify Token
Keystone → Nova: Verify Token
Nova → Glance: Token + Request for Image
Glance → Nova: Image
Nova → Keystone: Verify Token
Nova → Neutron: Token + Request to Plug VIF into Net
Neutron → Keystone: Token + Verify User
Neutron → Nova: Access to VIF
Nova → User: Successful Response
{
"admin_required": "role:admin",
"compute:start": "role:admin or role:member",
"compute:stop": "role:admin or role:member",
"compute:get_all": "role:admin or role:reader",
"network:create": "role:admin",
"network:list": "role:admin or role:member or role:reader"
}
policy.json 또는 policy.yaml 파일로 관리되며, 서비스마다 별도의 정책 파일 존재policy.json을 수정하더라도 서비스 재시작 없이 바로 반영됨$ source keystone_admin
$ openstack endpoint list
+----------------------------------+-----------+--------------+--------------+---------+-----------+---------------------------------------------+
| ID | Region | Service Name | Service Type | Enabled | Interface | URL |
+----------------------------------+-----------+--------------+--------------+---------+-----------+---------------------------------------------+
| 0ed880ae06824bf7ae6c1de30a98aeee | RegionOne | cinderv3 | volumev3 | True | admin | http://10.0.2.15:8776/v3 |
| 19394e13249040078c6e189adf74f580 | RegionOne | cinderv3 | volumev3 | True | internal | http://10.0.2.15:8776/v3 |
| 26552cbc5c8647068c3602bb2886e169 | RegionOne | neutron | network | True | admin | http://10.0.2.15:9696 |
| 3e5e85abd6f54b5aa179830b5615c7e3 | RegionOne | gnocchi | metric | True | admin | http://10.0.2.15:8041 |
| 406506b6e89e44bdaf74e276b7fea26c | RegionOne | nova | compute | True | internal | http://10.0.2.15:8774/v2.1 |
| 4bcbb56166424817bb34edec212229ef | RegionOne | placement | placement | True | public | http://10.0.2.15:8778 |
| 5f7da72c06db40798203f40d1e289b6e | RegionOne | glance | image | True | public | http://10.0.2.15:9292 |
| 66899c0113894673995b0faa0426329c | RegionOne | swift | object-store | True | admin | http://10.0.2.15:8080/v1/AUTH_%(tenant_id)s |
| 66dc081dc0a24348a2395ad97e3b7086 | RegionOne | aodh | alarming | True | internal | http://10.0.2.15:8042 |
| 78bd86b9efbb4f57aefedd507eb82bc2 | RegionOne | placement | placement | True | admin | http://10.0.2.15:8778 |
| 7dcc552be42341499b46cd8e3bd7044a | RegionOne | gnocchi | metric | True | internal | http://10.0.2.15:8041 |
| 7eaa875799424db482f7efa7756a15c0 | RegionOne | swift | object-store | True | public | http://10.0.2.15:8080/v1/AUTH_%(tenant_id)s |
| 8028fbe9f6b747fdbe7552c796068ed1 | RegionOne | aodh | alarming | True | admin | http://10.0.2.15:8042 |
| 8845f0b6b7a64a9fb46e0021608aba0f | RegionOne | glance | image | True | admin | http://10.0.2.15:9292 |
| a7e9bb6a022f4323bcf9cb388ddaeb49 | RegionOne | swift | object-store | True | internal | http://10.0.2.15:8080/v1/AUTH_%(tenant_id)s |
| b31e4ee5a01a4a11bdaa7bf74ea35493 | RegionOne | neutron | network | True | internal | http://10.0.2.15:9696 |
| b5adf7aa1f45423990b18d7002571096 | RegionOne | keystone | identity | True | admin | http://10.0.2.15:5000 |
| b7a07e07fdc144b782371a4945325b82 | RegionOne | placement | placement | True | internal | http://10.0.2.15:8778 |
| b7dbcfae941b4d88aa6193ec15ad4719 | RegionOne | cinderv3 | volumev3 | True | public | http://10.0.2.15:8776/v3 |
| c5dfda13de9840618d5748d43c36c84a | RegionOne | glance | image | True | internal | http://10.0.2.15:9292 |
| c9d35af259dc4561a5c113e843c362c2 | RegionOne | neutron | network | True | public | http://10.0.2.15:9696 |
| d4604b6649d5466893766af22ff6d062 | RegionOne | aodh | alarming | True | public | http://10.0.2.15:8042 |
| d91eca2e939f438f8f06de2a2d549ca7 | RegionOne | keystone | identity | True | public | http://10.0.2.15:5000 |
| deca57b3145e45c18fd2963e7b857f89 | RegionOne | nova | compute | True | admin | http://10.0.2.15:8774/v2.1 |
| ed4e0109019244799312102a2d51e89c | RegionOne | gnocchi | metric | True | public | http://10.0.2.15:8041 |
| f8eb7281cc0a48d9a41b56fda326bb0f | RegionOne | nova | compute | True | public | http://10.0.2.15:8774/v2.1 |
| fd4a82d2b8a74afa9cb1a29bdc306589 | RegionOne | keystone | identity | True | internal | http://10.0.2.15:5000 |
+----------------------------------+-----------+--------------+--------------+---------+-----------+---------------------------------------------+
openstack endpoint list을 통해 Openstack에 존재하는 모든 endpoint들의 list를 확인할 수 있다.
openstack endpoint show b5adf7aa1f45423990b18d7002571096
+--------------+----------------------------------+
| Field | Value |
+--------------+----------------------------------+
| enabled | True |
| id | b5adf7aa1f45423990b18d7002571096 |
| interface | admin |
| region | RegionOne |
| region_id | RegionOne |
| service_id | 47a94d62cac4428e80796111c41a6609 |
| service_name | keystone |
| service_type | identity |
| url | http://10.0.2.15:5000 |
+--------------+----------------------------------+
이후 Keystone의 endpoint를 ID를 통해 확인하고
openstack catalog list
+-----------+--------------+----------------------------------------------------------------------------+
| Name | Type | Endpoints |
+-----------+--------------+----------------------------------------------------------------------------+
| cinderv3 | volumev3 | RegionOne |
| | | admin: http://10.0.2.15:8776/v3 |
| | | RegionOne |
| | | internal: http://10.0.2.15:8776/v3 |
| | | RegionOne |
| | | public: http://10.0.2.15:8776/v3 |
| | | |
| nova | compute | RegionOne |
| | | internal: http://10.0.2.15:8774/v2.1 |
| | | RegionOne |
| | | admin: http://10.0.2.15:8774/v2.1 |
| | | RegionOne |
| | | public: http://10.0.2.15:8774/v2.1 |
| | | |
| keystone | identity | RegionOne |
| | | admin: http://10.0.2.15:5000 |
| | | RegionOne |
| | | public: http://10.0.2.15:5000 |
| | | RegionOne |
| | | internal: http://10.0.2.15:5000 |
| | | |
| placement | placement | RegionOne |
| | | public: http://10.0.2.15:8778 |
| | | RegionOne |
| | | admin: http://10.0.2.15:8778 |
| | | RegionOne |
| | | internal: http://10.0.2.15:8778 |
| | | |
| neutron | network | RegionOne |
| | | admin: http://10.0.2.15:9696 |
| | | RegionOne |
| | | internal: http://10.0.2.15:9696 |
| | | RegionOne |
| | | public: http://10.0.2.15:9696 |
| | | |
| gnocchi | metric | RegionOne |
| | | admin: http://10.0.2.15:8041 |
| | | RegionOne |
| | | internal: http://10.0.2.15:8041 |
| | | RegionOne |
| | | public: http://10.0.2.15:8041 |
| | | |
| glance | image | RegionOne |
| | | public: http://10.0.2.15:9292 |
| | | RegionOne |
| | | admin: http://10.0.2.15:9292 |
| | | RegionOne |
| | | internal: http://10.0.2.15:9292 |
| | | |
| aodh | alarming | RegionOne |
| | | internal: http://10.0.2.15:8042 |
| | | RegionOne |
| | | admin: http://10.0.2.15:8042 |
| | | RegionOne |
| | | public: http://10.0.2.15:8042 |
| | | |
| swift | object-store | RegionOne |
| | | admin: http://10.0.2.15:8080/v1/AUTH_8dc84595f82b4e6dac4a18f990b05c6d |
| | | RegionOne |
| | | public: http://10.0.2.15:8080/v1/AUTH_8dc84595f82b4e6dac4a18f990b05c6d |
| | | RegionOne |
| | | internal: http://10.0.2.15:8080/v1/AUTH_8dc84595f82b4e6dac4a18f990b05c6d |
| | | |
+-----------+--------------+----------------------------------------------------------------------------+
위와 같이 Catalog를 확닌할 수 있다
Keystone은 다른 endpoint가 Cluster 내에서 서로를 식별할 수 있도록 Catalog를 위와 같이 제공한다.
$ openstack project create newProject
$ openstack project set --description "for testing purpose" newProject
$ openstack project show newProject
+-------------+----------------------------------+
| Field | Value |
+-------------+----------------------------------+
| description | for testing purpose |
| domain_id | default |
| enabled | True |
| id | 8522df3c87154fb194986b039ac84620 |
| is_domain | False |
| name | newProject |
| options | {} |
| parent_id | default |
| tags | [] |
+-------------+----------------------------------+
또한 위와 같이 새로운 프로젝트를 생성하고 열럼할 수 있다.
openstack user create --project newProject --password-prompt developer1
모든 User는 생성시 프로젝트를 지정해줘야 한다
$ openstack role list
+----------------------------------+---------------+
| ID | Name |
+----------------------------------+---------------+
| 3900fedccc434aa9aa3725fb646bd0a8 | ResellerAdmin |
| 5b89ece9caa54eab9412350f9d274307 | SwiftOperator |
| 6e7a20510cc84177921cf699cec334eb | reader |
| 7aa56e6571e0466e984d7d6b6f91334b | member |
| 8026203f634c40ba84a07413f5fe9c2a | admin |
| e5eee3c15ddd4ba3996984b306225d7e | _member_ |
+----------------------------------+---------------+
$ openstack role assignment list --project newProject --user developer1
위와 같이 User가 생성되어도 default하게 role이 부여되지는 않는 것을 볼 수 있기에
$ openstack role add --project newProject --user developer1 admin
$ openstack role add --project newProject --user developer1 _member_
$ openstack role assignment list --project newProject --user developer1
+----------------------------------+----------------------------------+-------+----------------------------------+--------+--------+-----------+
| Role | User | Group | Project | Domain | System | Inherited |
+----------------------------------+----------------------------------+-------+----------------------------------+--------+--------+-----------+
| 8026203f634c40ba84a07413f5fe9c2a | b2eb1472e5554ee788a64a46b9a0c7d0 | | 8522df3c87154fb194986b039ac84620 | | | False |
| e5eee3c15ddd4ba3996984b306225d7e | b2eb1472e5554ee788a64a46b9a0c7d0 | | 8522df3c87154fb194986b039ac84620 | | | False |
+----------------------------------+----------------------------------+-------+----------------------------------+--------+--------+-----------+
User에 직접 이를 할당해주어야 한다.
Horizon Dashboard에서도 이를 확인할 수 있다.
$ openstack command list | grep openstack.identity -A 40
| openstack.identity.v3 | access rule delete |
| | access rule list |
| | access rule show |
| | access token create |
| | application credential create |
| | application credential delete |
| | application credential list |
| | application credential show |
| | catalog list |
| | catalog show |
| | consumer create |
| | consumer delete |
| | consumer list |
| | consumer set |
| | consumer show |
| | credential create |
| | credential delete |
| | credential list |
| | credential set |
| | credential show |
| | domain create |
| | domain delete |
| | domain list |
| | domain set |
| | domain show |
| | ec2 credentials create |
| | ec2 credentials delete |
| | ec2 credentials list |
| | ec2 credentials show |
| | endpoint add project |
| | endpoint create |
| | endpoint delete |
| | endpoint group add project |
| | endpoint group create |
| | endpoint group delete |
| | endpoint group list |
| | endpoint group remove project |
| | endpoint group set |
| | endpoint group show |
| | endpoint list |
| | endpoint remove project |
또한 openstack.identity 명령어를 통해 OpenStack Identity의 명령어를 확인할 수 있다.

$ openstack command list | grep openstack.image -A 10
| openstack.image.v2 | image add project |
| | image create |
| | image delete |
| | image list |
| | image member list |
| | image remove project |
| | image save |
| | image set |
| | image show |
| | image unset |
| openstack.key_manager.v1 | acl delete |
우선 위와 같이 Glance와 관련된 명령어를 확인한다.
Glance는 Openstack 프로젝트 중에서 그리 Major하지 않기 때문에 명령어가 많이 존재하지 않는다.
$ curl -o ./cirros-0.6.2-x86_64-disk.img https://download.cirros-cloud.net/0.6.2/cirros-0.6.2-x86_64-disk.img
$ openstack image create --min-disk 2 --private --disk-format qcow2 --file ./cirros-0.6.2-x86_64-disk.img cirros
$ openstack image list
+--------------------------------------+--------+--------+
| ID | Name | Status |
+--------------------------------------+--------+--------+
| 192715c9-65b6-4682-bbf5-d08c21e99d77 | cirros | active |
+--------------------------------------+--------+--------+
이후 테스트 하기 적합한 CirrOS를 다운로드 받는다.
이후 다운로드 받은 파일을 기반으로 이미지를 생성하고 이를 확인할 수 있다
--private 옵션을 통해 이미지를 생성하게 되면, 다른 프로젝트에 속해있는 user는 해당 image를 열람할 수 없다Nova Networking 대신 Neutron을 사용하는 이유는 아래와 같다
Rich Topologies: Neutron은 복잡하고 다양한 네트워크 토폴로지를 지원하여 사용자 요구에 맞는 유연한 네트워크 설계가 가능
Technology Agnostic: 특정 네트워크 기술에 종속되지 않고 다양한 하드웨어 및 네트워크 프로토콜과 호환 가능
Pluggable Open Architecture: 플러그인 기반의 아키텍처를 통해 네트워크 기술 확장성과 타사 솔루션과의 통합 지원
Enables Advanced Services: Nova Networking에서 제공하지 않는 고급 네트워크 서비스를 지원

Virtual Machine (VM): Nova에 의해 생성된 가상 머신으로, 클라우드 환경에서 실행되는 컴퓨팅 리소스
Virtual Interface (VIF): 가상 머신과 네트워크 간의 연결 인터페이스
Virtual Port: Neutron에서 네트워크의 끝점을 나타내는 논리적 엔터티
L2 Virtual Network: 2계층 가상 네트워크로, 가상 머신이 동일한 네트워크 내에서 IP를 기반으로 통신 가능
Net1, 서브넷 범위: 10.0.0.0/24Virtual Subnet: 가상 네트워크 내의 IP 주소 범위를 정의하는 논리적 구획
Network, Port, Subnet은 모든 Neutron Deployment에 존재하는 Core한 자원
Server (REST API)
Plugin
Message Queue

ML2 Plugin (Modular Layer 2 Plugin)
TypeDriver
MechanismDriver

클라이언트 요청
Neutron Server
Neutron Plugin
Neutron Agent (L2, L3, DHCP)
Compute Node (Nova)
데이터베이스
응답 반환
기본 플러그인에 추가적인 기능을 제공하거나 확장할 수 있는 메커니즘으로, 사용자 정의 리소스와 고급 네트워크 기능을 구현할 수 있음
Add Logical Resources to the REST API
Common Extensions

Cloud Controller Node
Network Node
Compute Node가 존재할 것이기 때문에, 여러 Network Node를 사용할 필요가 있음Compute Node
SDN Service Node
Dashboard Node
External Network
Guest Network

Compute Node
Network Node
Physical Network
Provider Networks는 물리적 네트워크와 직접 연결되며, 가상 라우터 없이 외부 네트워크와 통신 가능
Provider Network는 어떻게 네트워크가 Physically하게 연결되었는지 표현
실제 Data Center의 Physical 네트워크와 일치해야 함
Project에 Public Network에 Direct Access할 수 있도록 함
Flat, VLAN, VxLAN, GRE 등 지원
높은 성능과 간단한 구조로 소규모 또는 HW Base L3 라우터를 활용하는 상황에 적합

1. Controller Node
Compute Node
Physical Network Infrastructure
203.0.113.0/24)을 사용| 특징 | Provider 네트워크 | Project 네트워크 |
|---|---|---|
| 연결 방식 | 물리적 네트워크와 직접 연결 | Neutron 라우터를 통해 연결 |
| 사용 범위 | 모든 테넌트 공유 가능 | 테넌트 간 독립적 격리 |
| 관리 주체 | 네트워크 관리자 | 테넌트 사용자 |
| 네트워크 유형 | Flat, VLAN | VXLAN, GRE |
| 외부 네트워크 통신 | 직접 연결 | Neutron 라우터 필요 |

가상 머신 통신
외부 네트워크 통신
Network(Traffic) Segmentation
ex. 사내 Traffic 유형 분리
- 설정:
- VLAN 10: 일반 직원의 업무 트래픽
- VLAN 20: 보안 감시 카메라의 영상 스트리밍 트래픽
- VLAN 30: 데이터센터 백업 트래픽
Local Network
Flat Network
VLAN (IEEE 802.1Q)
Tunneling (GRE/VxLAN)
L2 트래픽을 L3 네트워크로 캡슐화하여 다른 네트워크 프로토콜 위에서 데이터를 전송하는 기술
캡슐화를 통해 네트워크 간 안전하고 효율적인 통신 가능
주로 데이터센터 간 연결, 멀티테넌시 환경에서 사용
GRE (Generic Routing Encapsulation)

MAC in IP encapsulation
L2 트래픽을 L3 네트워크로 캡슐화하는 단순 터널링 프로토콜
단순성과 멀티프로토콜 캡슐화 지원 (IPv4, IPv6, MPLS 등)
오버헤드 증가 (캡슐화로 인해 데이터 크기 증가)
암호화 미지원 (보안 추가 필요)
데이터센터 간 네트워크 연결
MPLS 기반의 L2 VPN 구현
VxLAN (Virtual Extensible LAN)

MAC in UDP encapsulation
L2 트래픽을 UDP 기반으로 캡슐화하여 L3 네트워크에서 전달하는 터널링 기술
최대 16M 네트워크 세그먼트 지원 (VNI 사용)
UDP 기반 캡슐화로 효율적인 데이터 전송
멀티테넌시 지원 및 데이터센터 확장성 강화
클라우드 데이터센터에서 테넌트 네트워크 격리
대규모 네트워크 확장 및 세분화
| 특징 | GRE | VxLAN |
|---|---|---|
| 캡슐화 프로토콜 | Generic Routing Encapsulation | Virtual Extensible LAN |
| 네트워크 ID 범위 | 제한적 (VLAN ID에 의존) | 최대 16M 개의 네트워크 세그먼트 |
| 캡슐화 방식 | Point-to-Point | UDP 기반 L3 캡슐화 |
| 확장성 | 제한적 | 대규모 네트워크에 적합 |
| 보안 | 기본 보안 미제공 | UDP 기반 캡슐화로 유연성 제공 |
| 사용 사례 | 데이터센터 간 연결 | 클라우드 멀티테넌시 환경 |
Neutron에서 L2 트래픽을 처리하고 관리하는 에이전트
네트워크 플러그인 기반으로 작동 (ex. ML2 Plugin)
Open vSwitch(OVS)를 기반으로 OpenStack Neutron의 L2 네트워크 트래픽을 처리하는 L2 에이전트
Neutron에서 L3 기능을 제공하는 에이전트로, 라우팅 및 NAT(Network Address Translation) 작업을 처리
HA, High Availability
시스템, 네트워크, 애플리케이션이 예상치 못한 장애가 발생해도 지속적으로 운영될 수 있도록 높은 가용성을 보장하는 기술적 설계와 구현 방법
- 클러스터링:
- 여러 시스템을 하나로 묶어 장애 시 다른 시스템이 역할을 대신 수행
- 로드 밸런싱:
- 트래픽을 여러 서버로 분산하여 부하를 균등하게 나누고 고가용성 보장
- 데이터 복제:
- 데이터를 여러 노드에 복제하여 장애 발생 시 데이터 손실 방지
- Heartbeat 및 Failover:
- 상태 확인(Heartbeat)을 통해 장애를 감지하고 다른 노드로 자동 전환(Failover)
Neutron에서 네트워크 트래픽을 제어하기 위한 가상 방화벽 역할을 수행하는 규칙 집합
VM 또는 포트에 적용되어 트래픽의 입출입을 제어
IP Table 규칙 집합:
Ingress/Egress 규칙:
Overlapping IP 지원:
IPv6 지원:
VIF(Virtual InterFace)별로 적용:
Multiple VIF를 가진 VM 지원:
Default 설정:
네트워크 트래픽의 IP 주소를 변환하여 가상 네트워크와 외부 네트워크 간 통신을 가능하게 하는 기술입
VM(Instance)에 외부 네트워크와 통신할 수 있는 Public IP 주소를 할당하는 방식
Neutron L3 Agent의 역할:
Static One-to-One Mapping:
L3 라우팅을 분산 처리하여 성능 병목을 방지하는 OpenStack 네트워크 아키텍처
L3 Agent의 기능을 Compute Node에 분산
특징:
네트워크 스택의 격리된 복사본을 제공하여 서로 독립적인 네트워크 환경을 구현하는 기술
Neutron에서 네트워크 리소스 간의 격리와 독립성을 보장하기 위해 사용
ip netns: 현재 생성된 네트워크 네임스페이스를 나열
Isolated Copy of Network Stack:
Scope Limited to Each Namespace:
Reusing Addresses:
Explicit Configuration Needed:
Supports Routing and Isolation:
$ <pre>openstack network agent list
+--------------------------------------+--------------------+-----------------------+-------------------+-------+-------+---------------------------+
| ID | Agent Type | Host | Availability Zone | Alive | State | Binary |
+--------------------------------------+--------------------+-----------------------+-------------------+-------+-------+---------------------------+
| 0c144c1c-1737-47f1-959c-496f3e17eb90 | Metadata agent | localhost.localdomain | None | XXX | UP | neutron-metadata-agent |
| 14f94549-0d8f-4239-9125-b6a699d1b194 | L3 agent | localhost | nova | :-) | UP | neutron-l3-agent |
| 218c4aca-953e-4545-8833-9a15e91ed10d | Open vSwitch agent | localhost | None | :-) | UP | neutron-openvswitch-agent |
| 4ae60024-c838-4fad-a54f-858639395da9 | DHCP agent | localhost.localdomain | nova | XXX | UP | neutron-dhcp-agent |
| 4d0f06c6-7925-42ab-82bd-2d8eb3d8b29f | L3 agent | localhost.localdomain | nova | XXX | UP | neutron-l3-agent |
| 4ef605ff-82bd-404f-bfce-f7f81afa8ea8 | Metering agent | localhost.localdomain | None | XXX | UP | neutron-metering-agent |
| 507a9478-6777-4caa-8407-a7deccfa0a9d | Metering agent | localhost | None | :-) | UP | neutron-metering-agent |
| 907e81ce-3857-4c69-81e1-62eb623bf093 | DHCP agent | localhost | nova | :-) | UP | neutron-dhcp-agent |
| 912da6e4-20b1-4853-ad7f-b2317fb2c0a0 | Metadata agent | localhost | None | :-) | UP | neutron-metadata-agent |
| ece367e5-3f73-40d8-9790-07e4b9d87ffe | Open vSwitch agent | localhost.localdomain | None | XXX | UP | neutron-openvswitch-agent |
+--------------------------------------+--------------------+-----------------------+-------------------+-------+-------+---------------------------+
우선 위와 같이 network agent들의 리스트를 볼 수 있다.
$ ovs-vsctl show
c7c4cbfc-1f94-4359-9287-b829ff0bddf9
Manager "ptcp:6640:127.0.0.1"
is_connected: true
Bridge br-int
Controller "tcp:127.0.0.1:6633"
is_connected: true
fail_mode: secure
datapath_type: system
Port br-int
Interface br-int
type: internal
Port patch-tun
Interface patch-tun
type: patch
options: {peer=patch-int}
Port int-br-ex
Interface int-br-ex
type: patch
options: {peer=phy-br-ex}
Bridge br-ex
Controller "tcp:127.0.0.1:6633"
is_connected: true
fail_mode: secure
datapath_type: system
Port phy-br-ex
Interface phy-br-ex
type: patch
options: {peer=int-br-ex}
Port enp0s3
Interface enp0s3
Port br-ex
Interface br-ex
type: internal
Bridge br-tun
Controller "tcp:127.0.0.1:6633"
is_connected: true
fail_mode: secure
datapath_type: system
Port patch-int
Interface patch-int
type: patch
options: {peer=patch-tun}
Port br-tun
Interface br-tun
type: internal
ovs_version: "3.1.7-140.el9s"
Open vSwitch(OVS)의 전체 구성 정보를 출력할 수 있으며 의미는 다음과 같다.
Manager
ptcp:6640:127.0.0.1)is_connected: true)Bridge
br-int (Integration Bridge): 가상 머신과 네트워크 트래픽을 연결br-ex (External Bridge): 외부 네트워크와 통신br-tun (Tunnel Bridge): 터널링 트래픽 처리 (GRE/VXLAN)tcp:127.0.0.1:6633)secure로 설정 시, 컨트롤러 장애 시에도 데이터 경로 유지Port
patch-tun, patch-int)enp0s3 for br-ex)br-int, br-tun)Interface
patch, internal, 또는 실제 네트워크 인터페이스peer를 통해 연결된 상대 포트 지정 (예: patch-tun ↔ patch-int)OVS Version
3.1.7-140.el9s)$ openstack network create -h
openstack create network를 통해 새로운 네트워크를 생성할 수 있으며, 주요 파라미터에 대한 정보는 아래와 같다
--provider-network-type: 네트워크 유형 설정 (ex. vxlan, vlan, flat, gre)--provider-physical-network: 물리적 네트워크와 매핑--provider-segment: VLAN ID 또는 네트워크 세그먼트 ID 지정--shared: 네트워크를 여러 프로젝트에서 공유 가능하도록 설정--external: 외부 네트워크로 설정하여 인터넷 연결 가능--mtu-size: 네트워크의 최대 패킷 크기 설정--disable-port-security: 포트 보안을 비활성화하여 보안 그룹 필터링 해제--description: 네트워크의 목적이나 역할에 대한 설명 추가$ openstack network create intnet
+---------------------------+--------------------------------------+
| Field | Value |
+---------------------------+--------------------------------------+
| admin_state_up | UP |
| availability_zone_hints | |
| availability_zones | |
| created_at | 2025-01-14T03:52:24Z |
| description | |
| dns_domain | None |
| id | 7b34e663-7d34-4c5c-b037-a7d5b47187d2 |
| ipv4_address_scope | None |
| ipv6_address_scope | None |
| is_default | False |
| is_vlan_transparent | None |
| mtu | 1450 |
| name | intnet |
| port_security_enabled | True |
| project_id | 8dc84595f82b4e6dac4a18f990b05c6d |
| provider:network_type | vxlan |
| provider:physical_network | None |
| provider:segmentation_id | 82 |
| qos_policy_id | None |
| revision_number | 1 |
| router:external | Internal |
| segments | None |
| shared | False |
| status | ACTIVE |
| subnets | |
| tags | |
| updated_at | 2025-01-14T03:52:24Z |
+---------------------------+--------------------------------------+
우선 intnet이라는 네트워크를 생성한다.
openstack subnet create subnet1 --subnet-range 10.5.5.0/24 --dns-nameserver 8.8.8.8 --network intnet
+----------------------+--------------------------------------+
| Field | Value |
+----------------------+--------------------------------------+
| allocation_pools | 10.5.5.2-10.5.5.254 |
| cidr | 10.5.5.0/24 |
| created_at | 2025-01-14T03:54:48Z |
| description | |
| dns_nameservers | 8.8.8.8 |
| dns_publish_fixed_ip | None |
| enable_dhcp | True |
| gateway_ip | 10.5.5.1 |
| host_routes | |
| id | 204c4ca0-3cba-4668-8b55-2ab7e1a132a2 |
| ip_version | 4 |
| ipv6_address_mode | None |
| ipv6_ra_mode | None |
| name | subnet1 |
| network_id | 7b34e663-7d34-4c5c-b037-a7d5b47187d2 |
| project_id | 8dc84595f82b4e6dac4a18f990b05c6d |
| revision_number | 0 |
| segment_id | None |
| service_types | |
| subnetpool_id | None |
| tags | |
| updated_at | 2025-01-14T03:54:48Z |
+----------------------+--------------------------------------+
이후 새로운 Subnet을 생성한다.
$ ip netns
qdhcp-7b34e663-7d34-4c5c-b037-a7d5b47187d2 (id: 0)
ip netns를 통해 현재 네트워크에 생성된 NS를 볼 수 있다.
$ ip netns exec qdhcp-7b34e663-7d34-4c5c-b037-a7d5b47187d2 ping 10.5.5.2
PING 10.5.5.2 (10.5.5.2) 56(84) bytes of data.
64 bytes from 10.5.5.2: icmp_seq=1 ttl=64 time=1.44 ms
64 bytes from 10.5.5.2: icmp_seq=2 ttl=64 time=0.037 ms
64 bytes from 10.5.5.2: icmp_seq=3 ttl=64 time=0.057 ms
...
DHCP가 같은 namespace 내애서 접근이 가능한 것을 볼 수 있다.
$ ip netns exec qdhcp-7b34e663-7d34-4c5c-b037-a7d5b47187d2 ip addr show
# loopback inferface
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
# DHCP agent's tap interface
7: tap177c8c39-42: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1450 qdisc noqueue state UNKNOWN group default qlen 1000
link/ether fa:16:3e:cd:fc:be brd ff:ff:ff:ff:ff:ff
inet 10.5.5.2/24 brd 10.5.5.255 scope global tap177c8c39-42
valid_lft forever preferred_lft forever
inet6 fe80::f816:3eff:fecd:fcbe/64 scope link
valid_lft forever preferred_lft forever
또한 해당 NS에 존재하는 네트워크 인터페아ㅣ스를 볼 수 있다.
Loopback Interface
네트워크 장치에서 자기 자신과 통신하기 위해 사용하는 가상 네트워크 인터페이스
- 주요 특징:
- 항상 활성화 상태 (
127.0.0.1주소 사용)- 내부 프로세스 간 통신 및 테스트 목적 사용
- 사용 사례:
- 애플리케이션 테스트
- 네트워크 디바이스 간 연결 확인
DHCP Agent's Tap Interface
Neutron의 DHCP Agent가 사용하는 가상 네트워크 인터페이스
- 주요 특징:
- 테넌트 네트워크에 DHCP 서비스를 제공
- 각 테넌트 서브넷마다 고유의 TAP 인터페이스 생성
- 사용 사례:
- VM에 동적으로 IP 주소, DNS 설정 제공
- 테넌트 네트워크에서 IP 주소 관리
$ ovs-vsctl show
c7c4cbfc-1f94-4359-9287-b829ff0bddf9
...
Port tap177c8c39-42
tag: 1
Interface tap177c8c39-42
type: internal
새로운 네트워크를 생성하였기 때문에 OVS의 전체 구성정보를 출력해보면 tap 인터페이스가 생성된 것을 볼 수 있다.
또한 DHCP agent는 별도의 Network 노드에서 구동되는데 이전에 --all-in-one 모드로 설치를 진행했기에, 현재 Openstack의 Inegration Bridge 내에서 해당 노드가 존재한다.
$ openstack router create R2
+-------------------------+--------------------------------------+
| Field | Value |
+-------------------------+--------------------------------------+
| admin_state_up | UP |
| availability_zone_hints | |
| availability_zones | |
| created_at | 2025-01-14T04:19:11Z |
| description | |
| distributed | False |
| enable_ndp_proxy | None |
| external_gateway_info | null |
| flavor_id | None |
| ha | False |
| id | 4358fd19-62ea-42d3-be7d-0ef3140dc249 |
| name | R2 |
| project_id | 8dc84595f82b4e6dac4a18f990b05c6d |
| revision_number | 1 |
| routes | |
| status | ACTIVE |
| tags | |
| tenant_id | 8dc84595f82b4e6dac4a18f990b05c6d |
| updated_at | 2025-01-14T04:19:11Z |
+-------------------------+--------------------------------------+
이후 Subnet을 위한 Router을 생성한다
$ openstack router add subnet R2 subnet1
이 시점에서 R2 라우터는 인터페이스가 붙지 않은 빈 라우터이기에, Private Subnet을 attach한다.
$ ovs-vsctl show
...
Port qr-3fa254c3-77
tag: 1
Interface qr-3fa254c3-77
type: internal
R2 라우터의 인터페이스인 qr-3fa254c3-77가 잘 생성된 것을 확인할 수 다
$ ip netns
qrouter-4358fd19-62ea-42d3-be7d-0ef3140dc249 (id: 1)
qdhcp-7b34e663-7d34-4c5c-b037-a7d5b47187d2 (id: 0)
또한 해당 인터페이스는 Router를 위해 별도로 생성된 Namespace 내에 존재한다.
$ ip netns exec qrouter-4358fd19-62ea-42d3-be7d-0ef3140dc249 ip address show
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
8: qr-3fa254c3-77: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1450 qdisc noqueue state UNKNOWN group default qlen 1000
link/ether fa:16:3e:78:a2:32 brd ff:ff:ff:ff:ff:ff
inet 10.5.5.1/24 brd 10.5.5.255 scope global qr-3fa254c3-77
valid_lft forever preferred_lft forever
inet6 fe80::f816:3eff:fe78:a232/64 scope link
valid_lft forever preferred_lft forever
$ ip netns exec qrouter-4358fd19-62ea-42d3-be7d-0ef3140dc249 ip route
10.5.5.0/24 dev qr-3fa254c3-77 proto kernel scope link src 10.5.5.1
해당 Namespace 내에서 네트워크 정보를 출력해보고
ip netns exec qrouter-4358fd19-62ea-42d3-be7d-0ef3140dc249 ping 10.5.5.1
PING 10.5.5.1 (10.5.5.1) 56(84) bytes of data.
64 bytes from 10.5.5.1: icmp_seq=1 ttl=64 time=0.285 ms
64 bytes from 10.5.5.1: icmp_seq=2 ttl=64 time=0.058 ms
64 bytes from 10.5.5.1: icmp_seq=3 ttl=64 time=0.054 ms
...
ping을 통해 해당 라우터로 접근이 가능한지 확인해야 한다.
$ neutron router-gateway-set R2 external_network
Set gateway for router R2
이후 external public network를 R2 라우터에 attach하여 해당 라우터가 Traffic을 해당 네트워크를 통해 라우팅할 수 있게 한다.
# 현재 네트워크 리스트 확인
openstack network list
+--------------------------------------+------------------+--------------------------------------+
| ID | Name | Subnets |
+--------------------------------------+------------------+--------------------------------------+
| 61af13ca-6eb4-4916-9fe7-2e28d401e2bd | external_network | 5a7d4bd3-011c-4c42-9f77-15c1fa9d8b83 |
| 7b34e663-7d34-4c5c-b037-a7d5b47187d2 | intnet | 204c4ca0-3cba-4668-8b55-2ab7e1a132a2 |
+--------------------------------------+------------------+--------------------------------------+
$ openstack server create --flavor m1.small --image cirros --network 7b34e663-7d34-4c5c-b037-a7d5b47187d2 test-instance
인스턴스를 성공적으로 생성한 이후, 해당 인스턴스에 접근하지 이전에 Security gorup rule을 수정해야 한다.
$ openstack security group list
+--------------------------------------+---------+------------------------+----------------------------------+------+
| ID | Name | Description | Project | Tags |
+--------------------------------------+---------+------------------------+----------------------------------+------+
| 4dfe3e82-ec28-4b47-8090-e2173d047774 | default | Default security group | 8dc84595f82b4e6dac4a18f990b05c6d | [] |
| 672f6b64-8358-4f9d-ae1e-1c16a193af93 | default | Default security group | e13f274a863d4a91a95011b5dd06d8b1 | [] |
+--------------------------------------+---------+------------------------+----------------------------------+------+
$ openstack project list
+----------------------------------+---------------+
| ID | Name |
+----------------------------------+---------------+
| 668c91225e6f4d17a99ed2e4c28afe98 | services |
| 8522df3c87154fb194986b039ac84620 | newProject |
| 8dc84595f82b4e6dac4a18f990b05c6d | admin |
| e13f274a863d4a91a95011b5dd06d8b1 | first-project |
+----------------------------------+---------------+
정확히 어떤 Security Group이 어떤 Project에서 활성화되어 있는지 확인하였을 떄 newProject에 Security Group이 할당되지 않은 것을 확인하여
openstack security group create allow-icmp-ssh --project 8522df3c87154fb194986b039ac84620 --description "Allow ICMP and SSH (TCP:22)"
openstack security group rule create --remote-ip 0.0.0.0/0 --protocol icmp allow-icmp-ssh
openstack security group rule create --remote-ip 0.0.0.0/0 --protocol tcp --dst-port 22 allow-icmp-ssh
위와 같이 Security Group에 newProject에 지정하고 생성한 이후 Rule을 추가한다.
$ openstack security group list
+--------------------------------------+----------------+-----------------------------+----------------------------------+------+
| ID | Name | Description | Project | Tags |
+--------------------------------------+----------------+-----------------------------+----------------------------------+------+
| 1bbabbed-e7dc-478b-98a1-ff37035ef797 | allow-icmp-ssh | Allow ICMP and SSH (TCP:22) | 8522df3c87154fb194986b039ac84620 | [] |
| 4dfe3e82-ec28-4b47-8090-e2173d047774 | default | Default security group | 8dc84595f82b4e6dac4a18f990b05c6d | [] |
| 672f6b64-8358-4f9d-ae1e-1c16a193af93 | default | Default security group | e13f274a863d4a91a95011b5dd06d8b1 | [] |
| e6f1533e-2b32-4c87-84a4-979ad08f3e68 | default | Default security group | 8522df3c87154fb194986b039ac84620 | [] |
+--------------------------------------+----------------+-----------------------------+----------------------------------+------+
위와 같이 security group이 정상적으로 생성된 것을 확인할 수 있다.
최종적인 Network Topology는 위와 같다.
이후 10.5.5.202 인스턴스에 대해 ping 및 ssh 요청을 해보았지만 지속적으로 실패하여 이를 해곃하고자 하였다
$ ip netns exec qrouter-4358fd19-62ea-42d3-be7d-0ef3140dc249 arp -n
Address HWtype HWaddress Flags Mask Iface
10.5.5.202 (incomplete) qr-3fa254c3-77
10.0.2.1 ether 52:54:00:12:35:00 C qg-2e261868-ab
라우터에서 ARP 요청이 전달되는지 확인해본 결과 10.5.5.202에 대한 MAC 주소가 할당되지 않은 것을 볼 수 있었다.
ip netns exec qrouter-4358fd19-62ea-42d3-be7d-0ef3140dc249 ip neigh flush dev qr-3fa254c3-77
이후 Router Namespace에서 ARP 캐시를 초기화하였다
$ openstack network agent list
+--------------------------------------+--------------------+-----------------------+-------------------+-------+-------+---------------------------+
| ID | Agent Type | Host | Availability Zone | Alive | State | Binary |
+--------------------------------------+--------------------+-----------------------+-------------------+-------+-------+---------------------------+
| 0c144c1c-1737-47f1-959c-496f3e17eb90 | Metadata agent | localhost.localdomain | None | XXX | UP | neutron-metadata-agent |
| 14f94549-0d8f-4239-9125-b6a699d1b194 | L3 agent | localhost | nova | :-) | UP | neutron-l3-agent |
| 218c4aca-953e-4545-8833-9a15e91ed10d | Open vSwitch agent | localhost | None | :-) | UP | neutron-openvswitch-agent |
| 4ae60024-c838-4fad-a54f-858639395da9 | DHCP agent | localhost.localdomain | nova | XXX | UP | neutron-dhcp-agent |
| 4d0f06c6-7925-42ab-82bd-2d8eb3d8b29f | L3 agent | localhost.localdomain | nova | XXX | UP | neutron-l3-agent |
| 4ef605ff-82bd-404f-bfce-f7f81afa8ea8 | Metering agent | localhost.localdomain | None | XXX | UP | neutron-metering-agent |
| 507a9478-6777-4caa-8407-a7deccfa0a9d | Metering agent | localhost | None | :-) | UP | neutron-metering-agent |
| 907e81ce-3857-4c69-81e1-62eb623bf093 | DHCP agent | localhost | nova | :-) | UP | neutron-dhcp-agent |
| 912da6e4-20b1-4853-ad7f-b2317fb2c0a0 | Metadata agent | localhost | None | :-) | UP | neutron-metadata-agent |
| ece367e5-3f73-40d8-9790-07e4b9d87ffe | Open vSwitch agent | localhost.localdomain | None | XXX | UP | neutron-openvswitch-agent |
+--------------------------------------+--------------------+-----------------------+-------------------+-------+-------+---------------------------+
이후 network agent들의 리스트를 점검하였다
hostnamectl set-hostname localhost
위 명령으로 hostname 적용을 보장한다
systemctl restart neutron-server
systemctl restart neutron-metadata-agent.service
systemctl restart neutron-l3-agent.service
systemctl restart neutron-dhcp-agent.service
systemctl restart openvswitch.service
systemctl restart neutron-metering-agent.service
이후 관련된 서비스를 모두 재시작하였다
openstack console log show 8013dacc-b5e3-48e3-b9df-08558f074b28
이후 해당 인스턴스의 로그에 아무것도 나오지 않는 것을 이상하게 여겨
위와 같이 Horizon Dashboard 콘솔에서 No bootable device이었다는 상황을 확인할 수 있었다.
yum install -y wget
wget http://download.cirros-cloud.net/0.6.2/cirros-0.6.2-x86_64-disk.img
기존 curl -o로 이미지 파일을 받을 경우 단순 텍스트 파일로 저장되기 때문에 wget을 통해서 이미지를 다시 다운로드 받고
$ openstack image list
+--------------------------------------+--------+--------+
| ID | Name | Status |
+--------------------------------------+--------+--------+
| 192715c9-65b6-4682-bbf5-d08c21e99d77 | cirros | active |
+--------------------------------------+--------+--------+
$ openstack image delete 192715c9-65b6-4682-bbf5-d08c21e99d77
$ openstack image create --disk-format qcow2 --container-format bare --public --file ./cirros-0.6.2-x86_64-disk.img cirros
+------------------+--------------------------------------------------------------------------------------------------------------------------------------------+
| Field | Value |
+------------------+--------------------------------------------------------------------------------------------------------------------------------------------+
| container_format | bare |
| created_at | 2025-01-14T11:07:09Z |
| disk_format | qcow2 |
| file | /v2/images/71905aa9-d10a-4bec-92ec-25ac00b0f81c/file |
| id | 71905aa9-d10a-4bec-92ec-25ac00b0f81c |
| min_disk | 0 |
| min_ram | 0 |
| name | cirros |
| owner | 8dc84595f82b4e6dac4a18f990b05c6d |
| properties | os_hidden='False', owner_specified.openstack.md5='', owner_specified.openstack.object='images/cirros', owner_specified.openstack.sha256='' |
| protected | False |
| schema | /v2/schemas/image |
| status | queued |
| tags | |
| updated_at | 2025-01-14T11:07:09Z |
| visibility | public |
+------------------+--------------------------------------------------------------------------------------------------------------------------------------------+
위와 같이 이미지를 새로 생성한 이후
openstack server delete test-instance
openstack server create --flavor m1.small --image cirros --network intnet test-instance
인스턴스 또한 종료시키고 새롭게 생성해주었다
OpenStack이 인스턴스를 배치할 수 있는 적합한 호스트를 찾지 못했음을 나타낸다
이 문제는
1. Nova 스케줄러가 적절한 컴퓨트 호스트를 찾지 못하거나
2. 호스트가 인스턴스를 실행하기 위한 리소스를 제공하지 못할 때 발생
따라서 Horizon Dashboard 종료하고
free -m
Host 머신에서도 메모리를 추가적으로 메모리를 확보한 이후 인스턴스를 다시 생성해주었다.
해당 오류 또한 메모리가 부족하여 나타나는 현상이었기에
$ openstack console log show test-instance
...
=== network info ===
if-info: lo,up,127.0.0.1,8,,
if-info: eth0,up,10.5.5.104,24,fe80::f816:3eff:fe41:2108/64,
ip-route:default via 10.5.5.1 dev eth0 src 10.5.5.104 metric 1002
ip-route:10.5.5.0/24 dev eth0 scope link src 10.5.5.104 metric 1002
ip-route:169.254.169.254 via 10.5.5.1 dev eth0 src 10.5.5.104 metric 1002
ip-route6:fe80::/64 dev eth0 metric 256
ip-route6:multicast ff00::/8 dev eth0 metric 256
=== datasource: ec2 net ===
instance-id: i-0000000b
name: N/A
availability-zone: nova
local-hostname: test-instance.novalocal
launch-index: 0
=== cirros: current=0.6.2 latest=0.6.2 uptime=25.23 ===
____ ____ ____
/ __/ __ ____ ____ / __ \/ __/
/ /__ / // __// __// /_/ /\ \
\___//_//_/ /_/ \____/___/
http://cirros-cloud.net
메모리를 확보하고 인스턴스를 실행시킨 이후 CirrOS 이미지의 인스턴스가 정상적으로 구동되는 것을 확인할 수 있었으며
ip netns exec qrouter-4358fd19-62ea-42d3-be7d-0ef3140dc249 ping 10.5.5.104
PING 10.5.5.104 (10.5.5.104) 56(84) bytes of data.
64 bytes from 10.5.5.104: icmp_seq=1 ttl=64 time=1.58 ms
64 bytes from 10.5.5.104: icmp_seq=2 ttl=64 time=1.33 ms
...
이전에 생성한 Gateway의 Namespace에서 ICMP 요청이 정상적으로 동작하는 것을 확인할 수 있었다.
ip netns exec qrouter-4358fd19-62ea-42d3-be7d-0ef3140dc249 ssh cirros@10.5.5.104
cirros@10.5.5.104's password: # gocubsgo
$ pwd
/home/cirros
위와 같이 정상적으로 SSH를 통해 접근할 수 있었다.
$ ping 10.5.5.1
PING 10.5.5.1 (10.5.5.1) 56(84) bytes of data.
64 bytes from 10.5.5.1: icmp_seq=1 ttl=64 time=1.70 ms
64 bytes from 10.5.5.1: icmp_seq=2 ttl=64 time=2.07 ms
이후 인스턴스 내에서 게이트웨이로의 연결 또한 확인한다.
$ openstack subnet list
+--------------------------------------+---------------+--------------------------------------+-------------+
| ID | Name | Network | Subnet |
+--------------------------------------+---------------+--------------------------------------+-------------+
| 204c4ca0-3cba-4668-8b55-2ab7e1a132a2 | subnet1 | 7b34e663-7d34-4c5c-b037-a7d5b47187d2 | 10.5.5.0/24 |
| 5a7d4bd3-011c-4c42-9f77-15c1fa9d8b83 | public_subnet | 61af13ca-6eb4-4916-9fe7-2e28d401e2bd | 10.0.2.0/24 |
+--------------------------------------+---------------+--------------------------------------+-------------+
인스턴스는 External Network에서 Reachable 해야만 추가적인 작업을 진행할 수 있다.
이는 Floating IP를 통해 달성될 수 있는데, 우선 위와 같이 public_subnet의 ID를 확인하고
# openstack floating ip create --subnet <subnet_ID> <network_ID>
$ openstack floating ip create --subnet 5a7d4bd3-011c-4c42-9f77-15c1fa9d8b83 61af13ca-6eb4-4916-9fe7-2e28d401e2bd
+---------------------+--------------------------------------+
| Field | Value |
+---------------------+--------------------------------------+
| created_at | 2025-01-15T03:24:10Z |
| description | |
| dns_domain | None |
| dns_name | None |
| fixed_ip_address | None |
| floating_ip_address | 10.0.2.118 |
| floating_network_id | 61af13ca-6eb4-4916-9fe7-2e28d401e2bd |
| id | 549b391c-9074-485a-8694-38552bab5030 |
| name | 10.0.2.118 |
| port_details | None |
| port_id | None |
| project_id | 8dc84595f82b4e6dac4a18f990b05c6d |
| qos_policy_id | None |
| revision_number | 0 |
| router_id | None |
| status | DOWN |
| subnet_id | 5a7d4bd3-011c-4c42-9f77-15c1fa9d8b83 |
| tags | [] |
| updated_at | 2025-01-15T03:24:10Z |
+---------------------+--------------------------------------+
위와 같이 Floating IP를 생성해준 후
openstack server add floating ip test-instance 10.0.2.118
이전에 생성한 인스턴스에 Floating IP를 할당하여준다.
$ ping 10.0.2.118
PING 10.0.2.118 (10.0.2.118) 56(84) bytes of data.
64 bytes from 10.0.2.118: icmp_seq=1 ttl=63 time=3.91 ms
64 bytes from 10.0.2.118: icmp_seq=2 ttl=63 time=2.36 ms
64 bytes from 10.0.2.118: icmp_seq=3 ttl=63 time=1.08 ms
default NS에서 해당 인스턴스로 Floating IP로 접근할 수 있는 것을 볼 수 있다.
$ ssh cirros@10.0.2.118
cirros@10.0.2.118's password:
$ ip a
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue 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: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1450 qdisc pfifo_fast qlen 1000
link/ether fa:16:3e:41:21:08 brd ff:ff:ff:ff:ff:ff
inet 10.5.5.104/24 brd 10.5.5.255 scope global dynamic noprefixroute eth0
valid_lft 82695sec preferred_lft 71895sec
inet6 fe80::f816:3eff:fe41:2108/64 scope link
valid_lft forever preferred_lft forever
$
SSH또한 정상적으로 작동하며 인스턴스 내부에서 네트워크 인터페이스를 확인할 수 있다.
$ openstack ip availability list --project admin
+--------------------------------------+------------------+-----------+----------+
| Network ID | Network Name | Total IPs | Used IPs |
+--------------------------------------+------------------+-----------+----------+
| 61af13ca-6eb4-4916-9fe7-2e28d401e2bd | external_network | 101 | 2 |
| 7b34e663-7d34-4c5c-b037-a7d5b47187d2 | intnet | 253 | 3 |
+--------------------------------------+------------------+-----------+----------+
OpenStack 프로젝트에 할당된 네트워크의 IP 사용 상태를 확인하는 명령어는 위와 같다
openstack command list | grep openstack.network -A 100