|
Packit Service |
a04d08 |
# Copyright (C) 2013 Canonical Ltd.
|
|
Packit Service |
a04d08 |
# Copyright 2019 Joyent, Inc.
|
|
Packit Service |
a04d08 |
#
|
|
Packit Service |
a04d08 |
# Author: Ben Howard <ben.howard@canonical.com>
|
|
Packit Service |
a04d08 |
#
|
|
Packit Service |
a04d08 |
# This file is part of cloud-init. See LICENSE file for license information.
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
'''This is a testcase for the SmartOS datasource.
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
It replicates a serial console and acts like the SmartOS console does in
|
|
Packit Service |
a04d08 |
order to validate return responses.
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
'''
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
from binascii import crc32
|
|
Packit Service |
a04d08 |
import json
|
|
Packit Service |
a04d08 |
import multiprocessing
|
|
Packit Service |
a04d08 |
import os
|
|
Packit Service |
a04d08 |
import os.path
|
|
Packit Service |
a04d08 |
import re
|
|
Packit Service |
a04d08 |
import signal
|
|
Packit Service |
a04d08 |
import stat
|
|
Packit Service |
751c4a |
import unittest
|
|
Packit Service |
a04d08 |
import uuid
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
from cloudinit import serial
|
|
Packit Service |
a04d08 |
from cloudinit.sources import DataSourceSmartOS
|
|
Packit Service |
a04d08 |
from cloudinit.sources.DataSourceSmartOS import (
|
|
Packit Service |
a04d08 |
convert_smartos_network_data as convert_net,
|
|
Packit Service |
a04d08 |
SMARTOS_ENV_KVM, SERIAL_DEVICE, get_smartos_environ,
|
|
Packit Service |
a04d08 |
identify_file)
|
|
Packit Service |
a04d08 |
from cloudinit.event import EventType
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
from cloudinit import helpers as c_helpers
|
|
Packit Service |
751c4a |
from cloudinit.util import (b64e, write_file)
|
|
Packit Service |
751c4a |
from cloudinit.subp import (subp, ProcessExecutionError, which)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
from cloudinit.tests.helpers import (
|
|
Packit Service |
a04d08 |
CiTestCase, mock, FilesystemMockingTestCase, skipIf)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
try:
|
|
Packit Service |
a04d08 |
import serial as _pyserial
|
|
Packit Service |
a04d08 |
assert _pyserial # avoid pyflakes error F401: import unused
|
|
Packit Service |
a04d08 |
HAS_PYSERIAL = True
|
|
Packit Service |
a04d08 |
except ImportError:
|
|
Packit Service |
a04d08 |
HAS_PYSERIAL = False
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
DSMOS = 'cloudinit.sources.DataSourceSmartOS'
|
|
Packit Service |
a04d08 |
SDC_NICS = json.loads("""
|
|
Packit Service |
a04d08 |
[
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"nic_tag": "external",
|
|
Packit Service |
a04d08 |
"primary": true,
|
|
Packit Service |
a04d08 |
"mtu": 1500,
|
|
Packit Service |
a04d08 |
"model": "virtio",
|
|
Packit Service |
a04d08 |
"gateway": "8.12.42.1",
|
|
Packit Service |
a04d08 |
"netmask": "255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip": "8.12.42.102",
|
|
Packit Service |
a04d08 |
"network_uuid": "992fc7ce-6aac-4b74-aed6-7b9d2c6c0bfe",
|
|
Packit Service |
a04d08 |
"gateways": [
|
|
Packit Service |
a04d08 |
"8.12.42.1"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"vlan_id": 324,
|
|
Packit Service |
a04d08 |
"mac": "90:b8:d0:f5:e4:f5",
|
|
Packit Service |
a04d08 |
"interface": "net0",
|
|
Packit Service |
a04d08 |
"ips": [
|
|
Packit Service |
a04d08 |
"8.12.42.102/24"
|
|
Packit Service |
a04d08 |
]
|
|
Packit Service |
a04d08 |
},
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"nic_tag": "sdc_overlay/16187209",
|
|
Packit Service |
a04d08 |
"gateway": "192.168.128.1",
|
|
Packit Service |
a04d08 |
"model": "virtio",
|
|
Packit Service |
a04d08 |
"mac": "90:b8:d0:a5:ff:cd",
|
|
Packit Service |
a04d08 |
"netmask": "255.255.252.0",
|
|
Packit Service |
a04d08 |
"ip": "192.168.128.93",
|
|
Packit Service |
a04d08 |
"network_uuid": "4cad71da-09bc-452b-986d-03562a03a0a9",
|
|
Packit Service |
a04d08 |
"gateways": [
|
|
Packit Service |
a04d08 |
"192.168.128.1"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"vlan_id": 2,
|
|
Packit Service |
a04d08 |
"mtu": 8500,
|
|
Packit Service |
a04d08 |
"interface": "net1",
|
|
Packit Service |
a04d08 |
"ips": [
|
|
Packit Service |
a04d08 |
"192.168.128.93/22"
|
|
Packit Service |
a04d08 |
]
|
|
Packit Service |
a04d08 |
}
|
|
Packit Service |
a04d08 |
]
|
|
Packit Service |
a04d08 |
""")
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
SDC_NICS_ALT = json.loads("""
|
|
Packit Service |
a04d08 |
[
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"interface": "net0",
|
|
Packit Service |
a04d08 |
"mac": "90:b8:d0:ae:64:51",
|
|
Packit Service |
a04d08 |
"vlan_id": 324,
|
|
Packit Service |
a04d08 |
"nic_tag": "external",
|
|
Packit Service |
a04d08 |
"gateway": "8.12.42.1",
|
|
Packit Service |
a04d08 |
"gateways": [
|
|
Packit Service |
a04d08 |
"8.12.42.1"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"netmask": "255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip": "8.12.42.51",
|
|
Packit Service |
a04d08 |
"ips": [
|
|
Packit Service |
a04d08 |
"8.12.42.51/24"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"network_uuid": "992fc7ce-6aac-4b74-aed6-7b9d2c6c0bfe",
|
|
Packit Service |
a04d08 |
"model": "virtio",
|
|
Packit Service |
a04d08 |
"mtu": 1500,
|
|
Packit Service |
a04d08 |
"primary": true
|
|
Packit Service |
a04d08 |
},
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"interface": "net1",
|
|
Packit Service |
a04d08 |
"mac": "90:b8:d0:bd:4f:9c",
|
|
Packit Service |
a04d08 |
"vlan_id": 600,
|
|
Packit Service |
a04d08 |
"nic_tag": "internal",
|
|
Packit Service |
a04d08 |
"netmask": "255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip": "10.210.1.217",
|
|
Packit Service |
a04d08 |
"ips": [
|
|
Packit Service |
a04d08 |
"10.210.1.217/24"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"network_uuid": "98657fdf-11f4-4ee2-88a4-ce7fe73e33a6",
|
|
Packit Service |
a04d08 |
"model": "virtio",
|
|
Packit Service |
a04d08 |
"mtu": 1500
|
|
Packit Service |
a04d08 |
}
|
|
Packit Service |
a04d08 |
]
|
|
Packit Service |
a04d08 |
""")
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
SDC_NICS_DHCP = json.loads("""
|
|
Packit Service |
a04d08 |
[
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"interface": "net0",
|
|
Packit Service |
a04d08 |
"mac": "90:b8:d0:ae:64:51",
|
|
Packit Service |
a04d08 |
"vlan_id": 324,
|
|
Packit Service |
a04d08 |
"nic_tag": "external",
|
|
Packit Service |
a04d08 |
"gateway": "8.12.42.1",
|
|
Packit Service |
a04d08 |
"gateways": [
|
|
Packit Service |
a04d08 |
"8.12.42.1"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"netmask": "255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip": "8.12.42.51",
|
|
Packit Service |
a04d08 |
"ips": [
|
|
Packit Service |
a04d08 |
"8.12.42.51/24"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"network_uuid": "992fc7ce-6aac-4b74-aed6-7b9d2c6c0bfe",
|
|
Packit Service |
a04d08 |
"model": "virtio",
|
|
Packit Service |
a04d08 |
"mtu": 1500,
|
|
Packit Service |
a04d08 |
"primary": true
|
|
Packit Service |
a04d08 |
},
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"interface": "net1",
|
|
Packit Service |
a04d08 |
"mac": "90:b8:d0:bd:4f:9c",
|
|
Packit Service |
a04d08 |
"vlan_id": 600,
|
|
Packit Service |
a04d08 |
"nic_tag": "internal",
|
|
Packit Service |
a04d08 |
"netmask": "255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip": "10.210.1.217",
|
|
Packit Service |
a04d08 |
"ips": [
|
|
Packit Service |
a04d08 |
"dhcp"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"network_uuid": "98657fdf-11f4-4ee2-88a4-ce7fe73e33a6",
|
|
Packit Service |
a04d08 |
"model": "virtio",
|
|
Packit Service |
a04d08 |
"mtu": 1500
|
|
Packit Service |
a04d08 |
}
|
|
Packit Service |
a04d08 |
]
|
|
Packit Service |
a04d08 |
""")
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
SDC_NICS_MIP = json.loads("""
|
|
Packit Service |
a04d08 |
[
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"interface": "net0",
|
|
Packit Service |
a04d08 |
"mac": "90:b8:d0:ae:64:51",
|
|
Packit Service |
a04d08 |
"vlan_id": 324,
|
|
Packit Service |
a04d08 |
"nic_tag": "external",
|
|
Packit Service |
a04d08 |
"gateway": "8.12.42.1",
|
|
Packit Service |
a04d08 |
"gateways": [
|
|
Packit Service |
a04d08 |
"8.12.42.1"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"netmask": "255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip": "8.12.42.51",
|
|
Packit Service |
a04d08 |
"ips": [
|
|
Packit Service |
a04d08 |
"8.12.42.51/24",
|
|
Packit Service |
a04d08 |
"8.12.42.52/24"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"network_uuid": "992fc7ce-6aac-4b74-aed6-7b9d2c6c0bfe",
|
|
Packit Service |
a04d08 |
"model": "virtio",
|
|
Packit Service |
a04d08 |
"mtu": 1500,
|
|
Packit Service |
a04d08 |
"primary": true
|
|
Packit Service |
a04d08 |
},
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"interface": "net1",
|
|
Packit Service |
a04d08 |
"mac": "90:b8:d0:bd:4f:9c",
|
|
Packit Service |
a04d08 |
"vlan_id": 600,
|
|
Packit Service |
a04d08 |
"nic_tag": "internal",
|
|
Packit Service |
a04d08 |
"netmask": "255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip": "10.210.1.217",
|
|
Packit Service |
a04d08 |
"ips": [
|
|
Packit Service |
a04d08 |
"10.210.1.217/24",
|
|
Packit Service |
a04d08 |
"10.210.1.151/24"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"network_uuid": "98657fdf-11f4-4ee2-88a4-ce7fe73e33a6",
|
|
Packit Service |
a04d08 |
"model": "virtio",
|
|
Packit Service |
a04d08 |
"mtu": 1500
|
|
Packit Service |
a04d08 |
}
|
|
Packit Service |
a04d08 |
]
|
|
Packit Service |
a04d08 |
""")
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
SDC_NICS_MIP_IPV6 = json.loads("""
|
|
Packit Service |
a04d08 |
[
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"interface": "net0",
|
|
Packit Service |
a04d08 |
"mac": "90:b8:d0:ae:64:51",
|
|
Packit Service |
a04d08 |
"vlan_id": 324,
|
|
Packit Service |
a04d08 |
"nic_tag": "external",
|
|
Packit Service |
a04d08 |
"gateway": "8.12.42.1",
|
|
Packit Service |
a04d08 |
"gateways": [
|
|
Packit Service |
a04d08 |
"8.12.42.1"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"netmask": "255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip": "8.12.42.51",
|
|
Packit Service |
a04d08 |
"ips": [
|
|
Packit Service |
a04d08 |
"2001:4800:78ff:1b:be76:4eff:fe06:96b3/64",
|
|
Packit Service |
a04d08 |
"8.12.42.51/24"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"network_uuid": "992fc7ce-6aac-4b74-aed6-7b9d2c6c0bfe",
|
|
Packit Service |
a04d08 |
"model": "virtio",
|
|
Packit Service |
a04d08 |
"mtu": 1500,
|
|
Packit Service |
a04d08 |
"primary": true
|
|
Packit Service |
a04d08 |
},
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"interface": "net1",
|
|
Packit Service |
a04d08 |
"mac": "90:b8:d0:bd:4f:9c",
|
|
Packit Service |
a04d08 |
"vlan_id": 600,
|
|
Packit Service |
a04d08 |
"nic_tag": "internal",
|
|
Packit Service |
a04d08 |
"netmask": "255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip": "10.210.1.217",
|
|
Packit Service |
a04d08 |
"ips": [
|
|
Packit Service |
a04d08 |
"10.210.1.217/24"
|
|
Packit Service |
a04d08 |
],
|
|
Packit Service |
a04d08 |
"network_uuid": "98657fdf-11f4-4ee2-88a4-ce7fe73e33a6",
|
|
Packit Service |
a04d08 |
"model": "virtio",
|
|
Packit Service |
a04d08 |
"mtu": 1500
|
|
Packit Service |
a04d08 |
}
|
|
Packit Service |
a04d08 |
]
|
|
Packit Service |
a04d08 |
""")
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
SDC_NICS_IPV4_IPV6 = json.loads("""
|
|
Packit Service |
a04d08 |
[
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"interface": "net0",
|
|
Packit Service |
a04d08 |
"mac": "90:b8:d0:ae:64:51",
|
|
Packit Service |
a04d08 |
"vlan_id": 324,
|
|
Packit Service |
a04d08 |
"nic_tag": "external",
|
|
Packit Service |
a04d08 |
"gateway": "8.12.42.1",
|
|
Packit Service |
a04d08 |
"gateways": ["8.12.42.1", "2001::1", "2001::2"],
|
|
Packit Service |
a04d08 |
"netmask": "255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip": "8.12.42.51",
|
|
Packit Service |
a04d08 |
"ips": ["2001::10/64", "8.12.42.51/24", "2001::11/64",
|
|
Packit Service |
a04d08 |
"8.12.42.52/32"],
|
|
Packit Service |
a04d08 |
"network_uuid": "992fc7ce-6aac-4b74-aed6-7b9d2c6c0bfe",
|
|
Packit Service |
a04d08 |
"model": "virtio",
|
|
Packit Service |
a04d08 |
"mtu": 1500,
|
|
Packit Service |
a04d08 |
"primary": true
|
|
Packit Service |
a04d08 |
},
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"interface": "net1",
|
|
Packit Service |
a04d08 |
"mac": "90:b8:d0:bd:4f:9c",
|
|
Packit Service |
a04d08 |
"vlan_id": 600,
|
|
Packit Service |
a04d08 |
"nic_tag": "internal",
|
|
Packit Service |
a04d08 |
"netmask": "255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip": "10.210.1.217",
|
|
Packit Service |
a04d08 |
"ips": ["10.210.1.217/24"],
|
|
Packit Service |
a04d08 |
"gateways": ["10.210.1.210"],
|
|
Packit Service |
a04d08 |
"network_uuid": "98657fdf-11f4-4ee2-88a4-ce7fe73e33a6",
|
|
Packit Service |
a04d08 |
"model": "virtio",
|
|
Packit Service |
a04d08 |
"mtu": 1500
|
|
Packit Service |
a04d08 |
}
|
|
Packit Service |
a04d08 |
]
|
|
Packit Service |
a04d08 |
""")
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
SDC_NICS_SINGLE_GATEWAY = json.loads("""
|
|
Packit Service |
a04d08 |
[
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"interface":"net0",
|
|
Packit Service |
a04d08 |
"mac":"90:b8:d0:d8:82:b4",
|
|
Packit Service |
a04d08 |
"vlan_id":324,
|
|
Packit Service |
a04d08 |
"nic_tag":"external",
|
|
Packit Service |
a04d08 |
"gateway":"8.12.42.1",
|
|
Packit Service |
a04d08 |
"gateways":["8.12.42.1"],
|
|
Packit Service |
a04d08 |
"netmask":"255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip":"8.12.42.26",
|
|
Packit Service |
a04d08 |
"ips":["8.12.42.26/24"],
|
|
Packit Service |
a04d08 |
"network_uuid":"992fc7ce-6aac-4b74-aed6-7b9d2c6c0bfe",
|
|
Packit Service |
a04d08 |
"model":"virtio",
|
|
Packit Service |
a04d08 |
"mtu":1500,
|
|
Packit Service |
a04d08 |
"primary":true
|
|
Packit Service |
a04d08 |
},
|
|
Packit Service |
a04d08 |
{
|
|
Packit Service |
a04d08 |
"interface":"net1",
|
|
Packit Service |
a04d08 |
"mac":"90:b8:d0:0a:51:31",
|
|
Packit Service |
a04d08 |
"vlan_id":600,
|
|
Packit Service |
a04d08 |
"nic_tag":"internal",
|
|
Packit Service |
a04d08 |
"netmask":"255.255.255.0",
|
|
Packit Service |
a04d08 |
"ip":"10.210.1.27",
|
|
Packit Service |
a04d08 |
"ips":["10.210.1.27/24"],
|
|
Packit Service |
a04d08 |
"network_uuid":"98657fdf-11f4-4ee2-88a4-ce7fe73e33a6",
|
|
Packit Service |
a04d08 |
"model":"virtio",
|
|
Packit Service |
a04d08 |
"mtu":1500
|
|
Packit Service |
a04d08 |
}
|
|
Packit Service |
a04d08 |
]
|
|
Packit Service |
a04d08 |
""")
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
MOCK_RETURNS = {
|
|
Packit Service |
a04d08 |
'hostname': 'test-host',
|
|
Packit Service |
a04d08 |
'root_authorized_keys': 'ssh-rsa AAAAB3Nz...aC1yc2E= keyname',
|
|
Packit Service |
a04d08 |
'disable_iptables_flag': None,
|
|
Packit Service |
a04d08 |
'enable_motd_sys_info': None,
|
|
Packit Service |
a04d08 |
'test-var1': 'some data',
|
|
Packit Service |
a04d08 |
'cloud-init:user-data': '\n'.join(['#!/bin/sh', '/bin/true', '']),
|
|
Packit Service |
a04d08 |
'sdc:datacenter_name': 'somewhere2',
|
|
Packit Service |
a04d08 |
'sdc:operator-script': '\n'.join(['bin/true', '']),
|
|
Packit Service |
a04d08 |
'sdc:uuid': str(uuid.uuid4()),
|
|
Packit Service |
a04d08 |
'sdc:vendor-data': '\n'.join(['VENDOR_DATA', '']),
|
|
Packit Service |
a04d08 |
'user-data': '\n'.join(['something', '']),
|
|
Packit Service |
a04d08 |
'user-script': '\n'.join(['/bin/true', '']),
|
|
Packit Service |
a04d08 |
'sdc:nics': json.dumps(SDC_NICS),
|
|
Packit Service |
a04d08 |
}
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
DMI_DATA_RETURN = 'smartdc'
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
# Useful for calculating the length of a frame body. A SUCCESS body will be
|
|
Packit Service |
a04d08 |
# followed by more characters or be one character less if SUCCESS with no
|
|
Packit Service |
a04d08 |
# payload. See Section 4.3 of https://eng.joyent.com/mdata/protocol.html.
|
|
Packit Service |
a04d08 |
SUCCESS_LEN = len('0123abcd SUCCESS ')
|
|
Packit Service |
a04d08 |
NOTFOUND_LEN = len('0123abcd NOTFOUND')
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
class PsuedoJoyentClient(object):
|
|
Packit Service |
a04d08 |
def __init__(self, data=None):
|
|
Packit Service |
a04d08 |
if data is None:
|
|
Packit Service |
a04d08 |
data = MOCK_RETURNS.copy()
|
|
Packit Service |
a04d08 |
self.data = data
|
|
Packit Service |
a04d08 |
self._is_open = False
|
|
Packit Service |
a04d08 |
return
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def get(self, key, default=None, strip=False):
|
|
Packit Service |
a04d08 |
if key in self.data:
|
|
Packit Service |
a04d08 |
r = self.data[key]
|
|
Packit Service |
a04d08 |
if strip:
|
|
Packit Service |
a04d08 |
r = r.strip()
|
|
Packit Service |
a04d08 |
else:
|
|
Packit Service |
a04d08 |
r = default
|
|
Packit Service |
a04d08 |
return r
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def get_json(self, key, default=None):
|
|
Packit Service |
a04d08 |
result = self.get(key, default=default)
|
|
Packit Service |
a04d08 |
if result is None:
|
|
Packit Service |
a04d08 |
return default
|
|
Packit Service |
a04d08 |
return json.loads(result)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def exists(self):
|
|
Packit Service |
a04d08 |
return True
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def open_transport(self):
|
|
Packit Service |
a04d08 |
assert(not self._is_open)
|
|
Packit Service |
a04d08 |
self._is_open = True
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def close_transport(self):
|
|
Packit Service |
a04d08 |
assert(self._is_open)
|
|
Packit Service |
a04d08 |
self._is_open = False
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
class TestSmartOSDataSource(FilesystemMockingTestCase):
|
|
Packit Service |
a04d08 |
jmc_cfact = None
|
|
Packit Service |
a04d08 |
get_smartos_environ = None
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def setUp(self):
|
|
Packit Service |
a04d08 |
super(TestSmartOSDataSource, self).setUp()
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
self.add_patch(DSMOS + ".get_smartos_environ", "get_smartos_environ")
|
|
Packit Service |
a04d08 |
self.add_patch(DSMOS + ".jmc_client_factory", "jmc_cfact")
|
|
Packit Service |
a04d08 |
self.legacy_user_d = self.tmp_path('legacy_user_tmp')
|
|
Packit Service |
a04d08 |
os.mkdir(self.legacy_user_d)
|
|
Packit Service |
a04d08 |
self.add_patch(DSMOS + ".LEGACY_USER_D", "m_legacy_user_d",
|
|
Packit Service |
a04d08 |
autospec=False, new=self.legacy_user_d)
|
|
Packit Service |
a04d08 |
self.add_patch(DSMOS + ".identify_file", "m_identify_file",
|
|
Packit Service |
a04d08 |
return_value="text/plain")
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def _get_ds(self, mockdata=None, mode=DataSourceSmartOS.SMARTOS_ENV_KVM,
|
|
Packit Service |
a04d08 |
sys_cfg=None, ds_cfg=None):
|
|
Packit Service |
a04d08 |
self.jmc_cfact.return_value = PsuedoJoyentClient(mockdata)
|
|
Packit Service |
a04d08 |
self.get_smartos_environ.return_value = mode
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
tmpd = self.tmp_dir()
|
|
Packit Service |
a04d08 |
dirs = {'cloud_dir': self.tmp_path('cloud_dir', tmpd),
|
|
Packit Service |
a04d08 |
'run_dir': self.tmp_path('run_dir')}
|
|
Packit Service |
a04d08 |
for d in dirs.values():
|
|
Packit Service |
a04d08 |
os.mkdir(d)
|
|
Packit Service |
a04d08 |
paths = c_helpers.Paths(dirs)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
if sys_cfg is None:
|
|
Packit Service |
a04d08 |
sys_cfg = {}
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
if ds_cfg is not None:
|
|
Packit Service |
a04d08 |
sys_cfg['datasource'] = sys_cfg.get('datasource', {})
|
|
Packit Service |
a04d08 |
sys_cfg['datasource']['SmartOS'] = ds_cfg
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
return DataSourceSmartOS.DataSourceSmartOS(
|
|
Packit Service |
a04d08 |
sys_cfg, distro=None, paths=paths)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_no_base64(self):
|
|
Packit Service |
a04d08 |
ds_cfg = {'no_base64_decode': ['test_var1'], 'all_base': True}
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(ds_cfg=ds_cfg)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_uuid(self):
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(MOCK_RETURNS['sdc:uuid'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['instance-id'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_platform_info(self):
|
|
Packit Service |
a04d08 |
"""All platform-related attributes are properly set."""
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
self.assertEqual('joyent', dsrc.cloud_name)
|
|
Packit Service |
a04d08 |
self.assertEqual('joyent', dsrc.platform_type)
|
|
Packit Service |
a04d08 |
self.assertEqual('serial (/dev/ttyS1)', dsrc.subplatform)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_root_keys(self):
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(MOCK_RETURNS['root_authorized_keys'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['public-keys'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_hostname_b64(self):
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(MOCK_RETURNS['hostname'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['local-hostname'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_hostname(self):
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(MOCK_RETURNS['hostname'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['local-hostname'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_hostname_if_no_sdc_hostname(self):
|
|
Packit Service |
a04d08 |
my_returns = MOCK_RETURNS.copy()
|
|
Packit Service |
a04d08 |
my_returns['sdc:hostname'] = 'sdc-' + my_returns['hostname']
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=my_returns)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(my_returns['hostname'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['local-hostname'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_sdc_hostname_if_no_hostname(self):
|
|
Packit Service |
a04d08 |
my_returns = MOCK_RETURNS.copy()
|
|
Packit Service |
a04d08 |
my_returns['sdc:hostname'] = 'sdc-' + my_returns['hostname']
|
|
Packit Service |
a04d08 |
del my_returns['hostname']
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=my_returns)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(my_returns['sdc:hostname'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['local-hostname'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_sdc_uuid_if_no_hostname_or_sdc_hostname(self):
|
|
Packit Service |
a04d08 |
my_returns = MOCK_RETURNS.copy()
|
|
Packit Service |
a04d08 |
del my_returns['hostname']
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=my_returns)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(my_returns['sdc:uuid'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['local-hostname'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_userdata(self):
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(MOCK_RETURNS['user-data'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['legacy-user-data'])
|
|
Packit Service |
a04d08 |
self.assertEqual(MOCK_RETURNS['cloud-init:user-data'],
|
|
Packit Service |
a04d08 |
dsrc.userdata_raw)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_sdc_nics(self):
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(json.loads(MOCK_RETURNS['sdc:nics']),
|
|
Packit Service |
a04d08 |
dsrc.metadata['network-data'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_sdc_scripts(self):
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(MOCK_RETURNS['user-script'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['user-script'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
legacy_script_f = "%s/user-script" % self.legacy_user_d
|
|
Packit Service |
a04d08 |
print("legacy_script_f=%s" % legacy_script_f)
|
|
Packit Service |
a04d08 |
self.assertTrue(os.path.exists(legacy_script_f))
|
|
Packit Service |
a04d08 |
self.assertTrue(os.path.islink(legacy_script_f))
|
|
Packit Service |
a04d08 |
user_script_perm = oct(os.stat(legacy_script_f)[stat.ST_MODE])[-3:]
|
|
Packit Service |
a04d08 |
self.assertEqual(user_script_perm, '700')
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_scripts_shebanged(self):
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(MOCK_RETURNS['user-script'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['user-script'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
legacy_script_f = "%s/user-script" % self.legacy_user_d
|
|
Packit Service |
a04d08 |
self.assertTrue(os.path.exists(legacy_script_f))
|
|
Packit Service |
a04d08 |
self.assertTrue(os.path.islink(legacy_script_f))
|
|
Packit Service |
a04d08 |
shebang = None
|
|
Packit Service |
a04d08 |
with open(legacy_script_f, 'r') as f:
|
|
Packit Service |
a04d08 |
shebang = f.readlines()[0].strip()
|
|
Packit Service |
a04d08 |
self.assertEqual(shebang, "#!/bin/bash")
|
|
Packit Service |
a04d08 |
user_script_perm = oct(os.stat(legacy_script_f)[stat.ST_MODE])[-3:]
|
|
Packit Service |
a04d08 |
self.assertEqual(user_script_perm, '700')
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_scripts_shebang_not_added(self):
|
|
Packit Service |
a04d08 |
"""
|
|
Packit Service |
a04d08 |
Test that the SmartOS requirement that plain text scripts
|
|
Packit Service |
a04d08 |
are executable. This test makes sure that plain texts scripts
|
|
Packit Service |
a04d08 |
with out file magic have it added appropriately by cloud-init.
|
|
Packit Service |
a04d08 |
"""
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
my_returns = MOCK_RETURNS.copy()
|
|
Packit Service |
a04d08 |
my_returns['user-script'] = '\n'.join(['#!/usr/bin/perl',
|
|
Packit Service |
a04d08 |
'print("hi")', ''])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=my_returns)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(my_returns['user-script'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['user-script'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
legacy_script_f = "%s/user-script" % self.legacy_user_d
|
|
Packit Service |
a04d08 |
self.assertTrue(os.path.exists(legacy_script_f))
|
|
Packit Service |
a04d08 |
self.assertTrue(os.path.islink(legacy_script_f))
|
|
Packit Service |
a04d08 |
shebang = None
|
|
Packit Service |
a04d08 |
with open(legacy_script_f, 'r') as f:
|
|
Packit Service |
a04d08 |
shebang = f.readlines()[0].strip()
|
|
Packit Service |
a04d08 |
self.assertEqual(shebang, "#!/usr/bin/perl")
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_userdata_removed(self):
|
|
Packit Service |
a04d08 |
"""
|
|
Packit Service |
a04d08 |
User-data in the SmartOS world is supposed to be written to a file
|
|
Packit Service |
a04d08 |
each and every boot. This tests to make sure that in the event the
|
|
Packit Service |
a04d08 |
legacy user-data is removed, the existing user-data is backed-up
|
|
Packit Service |
a04d08 |
and there is no /var/db/user-data left.
|
|
Packit Service |
a04d08 |
"""
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
user_data_f = "%s/mdata-user-data" % self.legacy_user_d
|
|
Packit Service |
a04d08 |
with open(user_data_f, 'w') as f:
|
|
Packit Service |
a04d08 |
f.write("PREVIOUS")
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
my_returns = MOCK_RETURNS.copy()
|
|
Packit Service |
a04d08 |
del my_returns['user-data']
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=my_returns)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertFalse(dsrc.metadata.get('legacy-user-data'))
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
found_new = False
|
|
Packit Service |
a04d08 |
for root, _dirs, files in os.walk(self.legacy_user_d):
|
|
Packit Service |
a04d08 |
for name in files:
|
|
Packit Service |
a04d08 |
name_f = os.path.join(root, name)
|
|
Packit Service |
a04d08 |
permissions = oct(os.stat(name_f)[stat.ST_MODE])[-3:]
|
|
Packit Service |
a04d08 |
if re.match(r'.*\/mdata-user-data$', name_f):
|
|
Packit Service |
a04d08 |
found_new = True
|
|
Packit Service |
a04d08 |
print(name_f)
|
|
Packit Service |
a04d08 |
self.assertEqual(permissions, '400')
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
self.assertFalse(found_new)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_vendor_data_not_default(self):
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(MOCK_RETURNS['sdc:vendor-data'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['vendor-data'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_default_vendor_data(self):
|
|
Packit Service |
a04d08 |
my_returns = MOCK_RETURNS.copy()
|
|
Packit Service |
a04d08 |
def_op_script = my_returns['sdc:vendor-data']
|
|
Packit Service |
a04d08 |
del my_returns['sdc:vendor-data']
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=my_returns)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertNotEqual(def_op_script, dsrc.metadata['vendor-data'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
# we expect default vendor-data is a boothook
|
|
Packit Service |
a04d08 |
self.assertTrue(dsrc.vendordata_raw.startswith("#cloud-boothook"))
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_disable_iptables_flag(self):
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(MOCK_RETURNS['disable_iptables_flag'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['iptables_disable'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_motd_sys_info(self):
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
self.assertEqual(MOCK_RETURNS['enable_motd_sys_info'],
|
|
Packit Service |
a04d08 |
dsrc.metadata['motd_sys_info'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_default_ephemeral(self):
|
|
Packit Service |
a04d08 |
# Test to make sure that the builtin config has the ephemeral
|
|
Packit Service |
a04d08 |
# configuration.
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds()
|
|
Packit Service |
a04d08 |
cfg = dsrc.get_config_obj()
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
assert 'disk_setup' in cfg
|
|
Packit Service |
a04d08 |
assert 'fs_setup' in cfg
|
|
Packit Service |
a04d08 |
self.assertIsInstance(cfg['disk_setup'], dict)
|
|
Packit Service |
a04d08 |
self.assertIsInstance(cfg['fs_setup'], list)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_override_disk_aliases(self):
|
|
Packit Service |
a04d08 |
# Test to make sure that the built-in DS is overriden
|
|
Packit Service |
a04d08 |
builtin = DataSourceSmartOS.BUILTIN_DS_CONFIG
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
mydscfg = {'disk_aliases': {'FOO': '/dev/bar'}}
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
# expect that these values are in builtin, or this is pointless
|
|
Packit Service |
a04d08 |
for k in mydscfg:
|
|
Packit Service |
a04d08 |
self.assertIn(k, builtin)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(ds_cfg=mydscfg)
|
|
Packit Service |
a04d08 |
ret = dsrc.get_data()
|
|
Packit Service |
a04d08 |
self.assertTrue(ret)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
self.assertEqual(mydscfg['disk_aliases']['FOO'],
|
|
Packit Service |
a04d08 |
dsrc.ds_cfg['disk_aliases']['FOO'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
self.assertEqual(dsrc.device_name_to_device('FOO'),
|
|
Packit Service |
a04d08 |
mydscfg['disk_aliases']['FOO'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_reconfig_network_on_boot(self):
|
|
Packit Service |
a04d08 |
# Test to ensure that network is configured from metadata on each boot
|
|
Packit Service |
a04d08 |
dsrc = self._get_ds(mockdata=MOCK_RETURNS)
|
|
Packit Service |
a04d08 |
self.assertSetEqual(set([EventType.BOOT_NEW_INSTANCE, EventType.BOOT]),
|
|
Packit Service |
a04d08 |
dsrc.update_events['network'])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
class TestIdentifyFile(CiTestCase):
|
|
Packit Service |
a04d08 |
"""Test the 'identify_file' utility."""
|
|
Packit Service |
a04d08 |
@skipIf(not which("file"), "command 'file' not available.")
|
|
Packit Service |
a04d08 |
def test_file_happy_path(self):
|
|
Packit Service |
a04d08 |
"""Test file is available and functional on plain text."""
|
|
Packit Service |
a04d08 |
fname = self.tmp_path("myfile")
|
|
Packit Service |
a04d08 |
write_file(fname, "plain text content here\n")
|
|
Packit Service |
a04d08 |
with self.allow_subp(["file"]):
|
|
Packit Service |
a04d08 |
self.assertEqual("text/plain", identify_file(fname))
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
751c4a |
@mock.patch(DSMOS + ".subp.subp")
|
|
Packit Service |
a04d08 |
def test_returns_none_on_error(self, m_subp):
|
|
Packit Service |
a04d08 |
"""On 'file' execution error, None should be returned."""
|
|
Packit Service |
a04d08 |
m_subp.side_effect = ProcessExecutionError("FILE_FAILED", exit_code=99)
|
|
Packit Service |
a04d08 |
fname = self.tmp_path("myfile")
|
|
Packit Service |
a04d08 |
write_file(fname, "plain text content here\n")
|
|
Packit Service |
a04d08 |
self.assertEqual(None, identify_file(fname))
|
|
Packit Service |
a04d08 |
self.assertEqual(
|
|
Packit Service |
a04d08 |
[mock.call(["file", "--brief", "--mime-type", fname])],
|
|
Packit Service |
a04d08 |
m_subp.call_args_list)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
class ShortReader(object):
|
|
Packit Service |
a04d08 |
"""Implements a 'read' interface for bytes provided.
|
|
Packit Service |
a04d08 |
much like io.BytesIO but the 'endbyte' acts as if EOF.
|
|
Packit Service |
a04d08 |
When it is reached a short will be returned."""
|
|
Packit Service |
a04d08 |
def __init__(self, initial_bytes, endbyte=b'\0'):
|
|
Packit Service |
a04d08 |
self.data = initial_bytes
|
|
Packit Service |
a04d08 |
self.index = 0
|
|
Packit Service |
a04d08 |
self.len = len(self.data)
|
|
Packit Service |
a04d08 |
self.endbyte = endbyte
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
@property
|
|
Packit Service |
a04d08 |
def emptied(self):
|
|
Packit Service |
a04d08 |
return self.index >= self.len
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def read(self, size=-1):
|
|
Packit Service |
a04d08 |
"""Read size bytes but not past a null."""
|
|
Packit Service |
a04d08 |
if size == 0 or self.index >= self.len:
|
|
Packit Service |
a04d08 |
return b''
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
rsize = size
|
|
Packit Service |
a04d08 |
if size < 0 or size + self.index > self.len:
|
|
Packit Service |
a04d08 |
rsize = self.len - self.index
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
next_null = self.data.find(self.endbyte, self.index, rsize)
|
|
Packit Service |
a04d08 |
if next_null >= 0:
|
|
Packit Service |
a04d08 |
rsize = next_null - self.index + 1
|
|
Packit Service |
a04d08 |
i = self.index
|
|
Packit Service |
a04d08 |
self.index += rsize
|
|
Packit Service |
a04d08 |
ret = self.data[i:i + rsize]
|
|
Packit Service |
a04d08 |
if len(ret) and ret[-1:] == self.endbyte:
|
|
Packit Service |
a04d08 |
ret = ret[:-1]
|
|
Packit Service |
a04d08 |
return ret
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
class TestJoyentMetadataClient(FilesystemMockingTestCase):
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
invalid = b'invalid command\n'
|
|
Packit Service |
a04d08 |
failure = b'FAILURE\n'
|
|
Packit Service |
a04d08 |
v2_ok = b'V2_OK\n'
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def setUp(self):
|
|
Packit Service |
a04d08 |
super(TestJoyentMetadataClient, self).setUp()
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
self.serial = mock.MagicMock(spec=serial.Serial)
|
|
Packit Service |
a04d08 |
self.request_id = 0xabcdef12
|
|
Packit Service |
a04d08 |
self.metadata_value = 'value'
|
|
Packit Service |
a04d08 |
self.response_parts = {
|
|
Packit Service |
a04d08 |
'command': 'SUCCESS',
|
|
Packit Service |
a04d08 |
'crc': 'b5a9ff00',
|
|
Packit Service |
a04d08 |
'length': SUCCESS_LEN + len(b64e(self.metadata_value)),
|
|
Packit Service |
a04d08 |
'payload': b64e(self.metadata_value),
|
|
Packit Service |
a04d08 |
'request_id': '{0:08x}'.format(self.request_id),
|
|
Packit Service |
a04d08 |
}
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def make_response():
|
|
Packit Service |
a04d08 |
payloadstr = ''
|
|
Packit Service |
a04d08 |
if 'payload' in self.response_parts:
|
|
Packit Service |
a04d08 |
payloadstr = ' {0}'.format(self.response_parts['payload'])
|
|
Packit Service |
a04d08 |
return ('V2 {length} {crc} {request_id} '
|
|
Packit Service |
a04d08 |
'{command}{payloadstr}\n'.format(
|
|
Packit Service |
a04d08 |
payloadstr=payloadstr,
|
|
Packit Service |
a04d08 |
**self.response_parts).encode('ascii'))
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
self.metasource_data = None
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def read_response(length):
|
|
Packit Service |
a04d08 |
if not self.metasource_data:
|
|
Packit Service |
a04d08 |
self.metasource_data = make_response()
|
|
Packit Service |
a04d08 |
self.metasource_data_len = len(self.metasource_data)
|
|
Packit Service |
a04d08 |
resp = self.metasource_data[:length]
|
|
Packit Service |
a04d08 |
self.metasource_data = self.metasource_data[length:]
|
|
Packit Service |
a04d08 |
return resp
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
self.serial.read.side_effect = read_response
|
|
Packit Service |
a04d08 |
self.patched_funcs.enter_context(
|
|
Packit Service |
a04d08 |
mock.patch('cloudinit.sources.DataSourceSmartOS.random.randint',
|
|
Packit Service |
a04d08 |
mock.Mock(return_value=self.request_id)))
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def _get_client(self):
|
|
Packit Service |
a04d08 |
return DataSourceSmartOS.JoyentMetadataClient(
|
|
Packit Service |
a04d08 |
fp=self.serial, smartos_type=DataSourceSmartOS.SMARTOS_ENV_KVM)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def _get_serial_client(self):
|
|
Packit Service |
a04d08 |
self.serial.timeout = 1
|
|
Packit Service |
a04d08 |
return DataSourceSmartOS.JoyentMetadataSerialClient(None,
|
|
Packit Service |
a04d08 |
fp=self.serial)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def assertEndsWith(self, haystack, prefix):
|
|
Packit Service |
a04d08 |
self.assertTrue(haystack.endswith(prefix),
|
|
Packit Service |
a04d08 |
"{0} does not end with '{1}'".format(
|
|
Packit Service |
a04d08 |
repr(haystack), prefix))
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def assertStartsWith(self, haystack, prefix):
|
|
Packit Service |
a04d08 |
self.assertTrue(haystack.startswith(prefix),
|
|
Packit Service |
a04d08 |
"{0} does not start with '{1}'".format(
|
|
Packit Service |
a04d08 |
repr(haystack), prefix))
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def assertNoMoreSideEffects(self, obj):
|
|
Packit Service |
a04d08 |
self.assertRaises(StopIteration, obj)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_writes_a_single_line(self):
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
client.get('some_key')
|
|
Packit Service |
a04d08 |
self.assertEqual(1, self.serial.write.call_count)
|
|
Packit Service |
a04d08 |
written_line = self.serial.write.call_args[0][0]
|
|
Packit Service |
a04d08 |
self.assertEndsWith(written_line.decode('ascii'),
|
|
Packit Service |
a04d08 |
b'\n'.decode('ascii'))
|
|
Packit Service |
a04d08 |
self.assertEqual(1, written_line.count(b'\n'))
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def _get_written_line(self, key='some_key'):
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
client.get(key)
|
|
Packit Service |
a04d08 |
return self.serial.write.call_args[0][0]
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_writes_bytes(self):
|
|
Packit Service |
751c4a |
self.assertIsInstance(self._get_written_line(), bytes)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_line_starts_with_v2(self):
|
|
Packit Service |
a04d08 |
foo = self._get_written_line()
|
|
Packit Service |
a04d08 |
self.assertStartsWith(foo.decode('ascii'), b'V2'.decode('ascii'))
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_uses_get_command(self):
|
|
Packit Service |
a04d08 |
parts = self._get_written_line().decode('ascii').strip().split(' ')
|
|
Packit Service |
a04d08 |
self.assertEqual('GET', parts[4])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_base64_encodes_argument(self):
|
|
Packit Service |
a04d08 |
key = 'my_key'
|
|
Packit Service |
a04d08 |
parts = self._get_written_line(key).decode('ascii').strip().split(' ')
|
|
Packit Service |
a04d08 |
self.assertEqual(b64e(key), parts[5])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_calculates_length_correctly(self):
|
|
Packit Service |
a04d08 |
parts = self._get_written_line().decode('ascii').strip().split(' ')
|
|
Packit Service |
a04d08 |
expected_length = len(' '.join(parts[3:]))
|
|
Packit Service |
a04d08 |
self.assertEqual(expected_length, int(parts[1]))
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_uses_appropriate_request_id(self):
|
|
Packit Service |
a04d08 |
parts = self._get_written_line().decode('ascii').strip().split(' ')
|
|
Packit Service |
a04d08 |
request_id = parts[3]
|
|
Packit Service |
a04d08 |
self.assertEqual(8, len(request_id))
|
|
Packit Service |
a04d08 |
self.assertEqual(request_id, request_id.lower())
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_uses_random_number_for_request_id(self):
|
|
Packit Service |
a04d08 |
line = self._get_written_line()
|
|
Packit Service |
a04d08 |
request_id = line.decode('ascii').strip().split(' ')[3]
|
|
Packit Service |
a04d08 |
self.assertEqual('{0:08x}'.format(self.request_id), request_id)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_checksums_correctly(self):
|
|
Packit Service |
a04d08 |
parts = self._get_written_line().decode('ascii').strip().split(' ')
|
|
Packit Service |
a04d08 |
expected_checksum = '{0:08x}'.format(
|
|
Packit Service |
a04d08 |
crc32(' '.join(parts[3:]).encode('utf-8')) & 0xffffffff)
|
|
Packit Service |
a04d08 |
checksum = parts[2]
|
|
Packit Service |
a04d08 |
self.assertEqual(expected_checksum, checksum)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_reads_a_line(self):
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
client.get('some_key')
|
|
Packit Service |
a04d08 |
self.assertEqual(self.metasource_data_len, self.serial.read.call_count)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_returns_valid_value(self):
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
value = client.get('some_key')
|
|
Packit Service |
a04d08 |
self.assertEqual(self.metadata_value, value)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_throws_exception_for_incorrect_length(self):
|
|
Packit Service |
a04d08 |
self.response_parts['length'] = 0
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
self.assertRaises(DataSourceSmartOS.JoyentMetadataFetchException,
|
|
Packit Service |
a04d08 |
client.get, 'some_key')
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_throws_exception_for_incorrect_crc(self):
|
|
Packit Service |
a04d08 |
self.response_parts['crc'] = 'deadbeef'
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
self.assertRaises(DataSourceSmartOS.JoyentMetadataFetchException,
|
|
Packit Service |
a04d08 |
client.get, 'some_key')
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_throws_exception_for_request_id_mismatch(self):
|
|
Packit Service |
a04d08 |
self.response_parts['request_id'] = 'deadbeef'
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
client._checksum = lambda _: self.response_parts['crc']
|
|
Packit Service |
a04d08 |
self.assertRaises(DataSourceSmartOS.JoyentMetadataFetchException,
|
|
Packit Service |
a04d08 |
client.get, 'some_key')
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_get_metadata_returns_None_if_value_not_found(self):
|
|
Packit Service |
a04d08 |
self.response_parts['payload'] = ''
|
|
Packit Service |
a04d08 |
self.response_parts['command'] = 'NOTFOUND'
|
|
Packit Service |
a04d08 |
self.response_parts['length'] = NOTFOUND_LEN
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
client._checksum = lambda _: self.response_parts['crc']
|
|
Packit Service |
a04d08 |
self.assertIsNone(client.get('some_key'))
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_negotiate(self):
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
reader = ShortReader(self.v2_ok)
|
|
Packit Service |
a04d08 |
client.fp.read.side_effect = reader.read
|
|
Packit Service |
a04d08 |
client._negotiate()
|
|
Packit Service |
a04d08 |
self.assertTrue(reader.emptied)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_negotiate_short_response(self):
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
# chopped '\n' from v2_ok.
|
|
Packit Service |
a04d08 |
reader = ShortReader(self.v2_ok[:-1] + b'\0')
|
|
Packit Service |
a04d08 |
client.fp.read.side_effect = reader.read
|
|
Packit Service |
a04d08 |
self.assertRaises(DataSourceSmartOS.JoyentMetadataTimeoutException,
|
|
Packit Service |
a04d08 |
client._negotiate)
|
|
Packit Service |
a04d08 |
self.assertTrue(reader.emptied)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_negotiate_bad_response(self):
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
reader = ShortReader(b'garbage\n' + self.v2_ok)
|
|
Packit Service |
a04d08 |
client.fp.read.side_effect = reader.read
|
|
Packit Service |
a04d08 |
self.assertRaises(DataSourceSmartOS.JoyentMetadataFetchException,
|
|
Packit Service |
a04d08 |
client._negotiate)
|
|
Packit Service |
a04d08 |
self.assertEqual(self.v2_ok, client.fp.read())
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_serial_open_transport(self):
|
|
Packit Service |
a04d08 |
client = self._get_serial_client()
|
|
Packit Service |
a04d08 |
reader = ShortReader(b'garbage\0' + self.invalid + self.v2_ok)
|
|
Packit Service |
a04d08 |
client.fp.read.side_effect = reader.read
|
|
Packit Service |
a04d08 |
client.open_transport()
|
|
Packit Service |
a04d08 |
self.assertTrue(reader.emptied)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_flush_failure(self):
|
|
Packit Service |
a04d08 |
client = self._get_serial_client()
|
|
Packit Service |
a04d08 |
reader = ShortReader(b'garbage' + b'\0' + self.failure +
|
|
Packit Service |
a04d08 |
self.invalid + self.v2_ok)
|
|
Packit Service |
a04d08 |
client.fp.read.side_effect = reader.read
|
|
Packit Service |
a04d08 |
client.open_transport()
|
|
Packit Service |
a04d08 |
self.assertTrue(reader.emptied)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_flush_many_timeouts(self):
|
|
Packit Service |
a04d08 |
client = self._get_serial_client()
|
|
Packit Service |
a04d08 |
reader = ShortReader(b'\0' * 100 + self.invalid + self.v2_ok)
|
|
Packit Service |
a04d08 |
client.fp.read.side_effect = reader.read
|
|
Packit Service |
a04d08 |
client.open_transport()
|
|
Packit Service |
a04d08 |
self.assertTrue(reader.emptied)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_list_metadata_returns_list(self):
|
|
Packit Service |
a04d08 |
parts = ['foo', 'bar']
|
|
Packit Service |
a04d08 |
value = b64e('\n'.join(parts))
|
|
Packit Service |
a04d08 |
self.response_parts['payload'] = value
|
|
Packit Service |
a04d08 |
self.response_parts['crc'] = '40873553'
|
|
Packit Service |
a04d08 |
self.response_parts['length'] = SUCCESS_LEN + len(value)
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
self.assertEqual(client.list(), parts)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_list_metadata_returns_empty_list_if_no_customer_metadata(self):
|
|
Packit Service |
a04d08 |
del self.response_parts['payload']
|
|
Packit Service |
a04d08 |
self.response_parts['length'] = SUCCESS_LEN - 1
|
|
Packit Service |
a04d08 |
self.response_parts['crc'] = '14e563ba'
|
|
Packit Service |
a04d08 |
client = self._get_client()
|
|
Packit Service |
a04d08 |
self.assertEqual(client.list(), [])
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
class TestNetworkConversion(CiTestCase):
|
|
Packit Service |
a04d08 |
def test_convert_simple(self):
|
|
Packit Service |
a04d08 |
expected = {
|
|
Packit Service |
a04d08 |
'version': 1,
|
|
Packit Service |
a04d08 |
'config': [
|
|
Packit Service |
a04d08 |
{'name': 'net0', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'type': 'static', 'gateway': '8.12.42.1',
|
|
Packit Service |
a04d08 |
'address': '8.12.42.102/24'}],
|
|
Packit Service |
a04d08 |
'mtu': 1500, 'mac_address': '90:b8:d0:f5:e4:f5'},
|
|
Packit Service |
a04d08 |
{'name': 'net1', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'type': 'static',
|
|
Packit Service |
a04d08 |
'address': '192.168.128.93/22'}],
|
|
Packit Service |
a04d08 |
'mtu': 8500, 'mac_address': '90:b8:d0:a5:ff:cd'}]}
|
|
Packit Service |
a04d08 |
found = convert_net(SDC_NICS)
|
|
Packit Service |
a04d08 |
self.assertEqual(expected, found)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_convert_simple_alt(self):
|
|
Packit Service |
a04d08 |
expected = {
|
|
Packit Service |
a04d08 |
'version': 1,
|
|
Packit Service |
a04d08 |
'config': [
|
|
Packit Service |
a04d08 |
{'name': 'net0', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'type': 'static', 'gateway': '8.12.42.1',
|
|
Packit Service |
a04d08 |
'address': '8.12.42.51/24'}],
|
|
Packit Service |
a04d08 |
'mtu': 1500, 'mac_address': '90:b8:d0:ae:64:51'},
|
|
Packit Service |
a04d08 |
{'name': 'net1', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'type': 'static',
|
|
Packit Service |
a04d08 |
'address': '10.210.1.217/24'}],
|
|
Packit Service |
a04d08 |
'mtu': 1500, 'mac_address': '90:b8:d0:bd:4f:9c'}]}
|
|
Packit Service |
a04d08 |
found = convert_net(SDC_NICS_ALT)
|
|
Packit Service |
a04d08 |
self.assertEqual(expected, found)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_convert_simple_dhcp(self):
|
|
Packit Service |
a04d08 |
expected = {
|
|
Packit Service |
a04d08 |
'version': 1,
|
|
Packit Service |
a04d08 |
'config': [
|
|
Packit Service |
a04d08 |
{'name': 'net0', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'type': 'static', 'gateway': '8.12.42.1',
|
|
Packit Service |
a04d08 |
'address': '8.12.42.51/24'}],
|
|
Packit Service |
a04d08 |
'mtu': 1500, 'mac_address': '90:b8:d0:ae:64:51'},
|
|
Packit Service |
a04d08 |
{'name': 'net1', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'type': 'dhcp4'}],
|
|
Packit Service |
a04d08 |
'mtu': 1500, 'mac_address': '90:b8:d0:bd:4f:9c'}]}
|
|
Packit Service |
a04d08 |
found = convert_net(SDC_NICS_DHCP)
|
|
Packit Service |
a04d08 |
self.assertEqual(expected, found)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_convert_simple_multi_ip(self):
|
|
Packit Service |
a04d08 |
expected = {
|
|
Packit Service |
a04d08 |
'version': 1,
|
|
Packit Service |
a04d08 |
'config': [
|
|
Packit Service |
a04d08 |
{'name': 'net0', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'type': 'static', 'gateway': '8.12.42.1',
|
|
Packit Service |
a04d08 |
'address': '8.12.42.51/24'},
|
|
Packit Service |
a04d08 |
{'type': 'static',
|
|
Packit Service |
a04d08 |
'address': '8.12.42.52/24'}],
|
|
Packit Service |
a04d08 |
'mtu': 1500, 'mac_address': '90:b8:d0:ae:64:51'},
|
|
Packit Service |
a04d08 |
{'name': 'net1', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'type': 'static',
|
|
Packit Service |
a04d08 |
'address': '10.210.1.217/24'},
|
|
Packit Service |
a04d08 |
{'type': 'static',
|
|
Packit Service |
a04d08 |
'address': '10.210.1.151/24'}],
|
|
Packit Service |
a04d08 |
'mtu': 1500, 'mac_address': '90:b8:d0:bd:4f:9c'}]}
|
|
Packit Service |
a04d08 |
found = convert_net(SDC_NICS_MIP)
|
|
Packit Service |
a04d08 |
self.assertEqual(expected, found)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_convert_with_dns(self):
|
|
Packit Service |
a04d08 |
expected = {
|
|
Packit Service |
a04d08 |
'version': 1,
|
|
Packit Service |
a04d08 |
'config': [
|
|
Packit Service |
a04d08 |
{'name': 'net0', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'type': 'static', 'gateway': '8.12.42.1',
|
|
Packit Service |
a04d08 |
'address': '8.12.42.51/24'}],
|
|
Packit Service |
a04d08 |
'mtu': 1500, 'mac_address': '90:b8:d0:ae:64:51'},
|
|
Packit Service |
a04d08 |
{'name': 'net1', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'type': 'dhcp4'}],
|
|
Packit Service |
a04d08 |
'mtu': 1500, 'mac_address': '90:b8:d0:bd:4f:9c'},
|
|
Packit Service |
a04d08 |
{'type': 'nameserver',
|
|
Packit Service |
a04d08 |
'address': ['8.8.8.8', '8.8.8.1'], 'search': ["local"]}]}
|
|
Packit Service |
a04d08 |
found = convert_net(
|
|
Packit Service |
a04d08 |
network_data=SDC_NICS_DHCP, dns_servers=['8.8.8.8', '8.8.8.1'],
|
|
Packit Service |
a04d08 |
dns_domain="local")
|
|
Packit Service |
a04d08 |
self.assertEqual(expected, found)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_convert_simple_multi_ipv6(self):
|
|
Packit Service |
a04d08 |
expected = {
|
|
Packit Service |
a04d08 |
'version': 1,
|
|
Packit Service |
a04d08 |
'config': [
|
|
Packit Service |
a04d08 |
{'name': 'net0', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'type': 'static', 'address':
|
|
Packit Service |
a04d08 |
'2001:4800:78ff:1b:be76:4eff:fe06:96b3/64'},
|
|
Packit Service |
a04d08 |
{'type': 'static', 'gateway': '8.12.42.1',
|
|
Packit Service |
a04d08 |
'address': '8.12.42.51/24'}],
|
|
Packit Service |
a04d08 |
'mtu': 1500, 'mac_address': '90:b8:d0:ae:64:51'},
|
|
Packit Service |
a04d08 |
{'name': 'net1', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'type': 'static',
|
|
Packit Service |
a04d08 |
'address': '10.210.1.217/24'}],
|
|
Packit Service |
a04d08 |
'mtu': 1500, 'mac_address': '90:b8:d0:bd:4f:9c'}]}
|
|
Packit Service |
a04d08 |
found = convert_net(SDC_NICS_MIP_IPV6)
|
|
Packit Service |
a04d08 |
self.assertEqual(expected, found)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_convert_simple_both_ipv4_ipv6(self):
|
|
Packit Service |
a04d08 |
expected = {
|
|
Packit Service |
a04d08 |
'version': 1,
|
|
Packit Service |
a04d08 |
'config': [
|
|
Packit Service |
a04d08 |
{'mac_address': '90:b8:d0:ae:64:51', 'mtu': 1500,
|
|
Packit Service |
a04d08 |
'name': 'net0', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'address': '2001::10/64', 'gateway': '2001::1',
|
|
Packit Service |
a04d08 |
'type': 'static'},
|
|
Packit Service |
a04d08 |
{'address': '8.12.42.51/24',
|
|
Packit Service |
a04d08 |
'gateway': '8.12.42.1',
|
|
Packit Service |
a04d08 |
'type': 'static'},
|
|
Packit Service |
a04d08 |
{'address': '2001::11/64', 'type': 'static'},
|
|
Packit Service |
a04d08 |
{'address': '8.12.42.52/32', 'type': 'static'}]},
|
|
Packit Service |
a04d08 |
{'mac_address': '90:b8:d0:bd:4f:9c', 'mtu': 1500,
|
|
Packit Service |
a04d08 |
'name': 'net1', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'address': '10.210.1.217/24',
|
|
Packit Service |
a04d08 |
'type': 'static'}]}]}
|
|
Packit Service |
a04d08 |
found = convert_net(SDC_NICS_IPV4_IPV6)
|
|
Packit Service |
a04d08 |
self.assertEqual(expected, found)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_gateways_not_on_all_nics(self):
|
|
Packit Service |
a04d08 |
expected = {
|
|
Packit Service |
a04d08 |
'version': 1,
|
|
Packit Service |
a04d08 |
'config': [
|
|
Packit Service |
a04d08 |
{'mac_address': '90:b8:d0:d8:82:b4', 'mtu': 1500,
|
|
Packit Service |
a04d08 |
'name': 'net0', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'address': '8.12.42.26/24',
|
|
Packit Service |
a04d08 |
'gateway': '8.12.42.1', 'type': 'static'}]},
|
|
Packit Service |
a04d08 |
{'mac_address': '90:b8:d0:0a:51:31', 'mtu': 1500,
|
|
Packit Service |
a04d08 |
'name': 'net1', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'address': '10.210.1.27/24',
|
|
Packit Service |
a04d08 |
'type': 'static'}]}]}
|
|
Packit Service |
a04d08 |
found = convert_net(SDC_NICS_SINGLE_GATEWAY)
|
|
Packit Service |
a04d08 |
self.assertEqual(expected, found)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_routes_on_all_nics(self):
|
|
Packit Service |
a04d08 |
routes = [
|
|
Packit Service |
a04d08 |
{'linklocal': False, 'dst': '3.0.0.0/8', 'gateway': '8.12.42.3'},
|
|
Packit Service |
a04d08 |
{'linklocal': False, 'dst': '4.0.0.0/8', 'gateway': '10.210.1.4'}]
|
|
Packit Service |
a04d08 |
expected = {
|
|
Packit Service |
a04d08 |
'version': 1,
|
|
Packit Service |
a04d08 |
'config': [
|
|
Packit Service |
a04d08 |
{'mac_address': '90:b8:d0:d8:82:b4', 'mtu': 1500,
|
|
Packit Service |
a04d08 |
'name': 'net0', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'address': '8.12.42.26/24',
|
|
Packit Service |
a04d08 |
'gateway': '8.12.42.1', 'type': 'static',
|
|
Packit Service |
a04d08 |
'routes': [{'network': '3.0.0.0/8',
|
|
Packit Service |
a04d08 |
'gateway': '8.12.42.3'},
|
|
Packit Service |
a04d08 |
{'network': '4.0.0.0/8',
|
|
Packit Service |
a04d08 |
'gateway': '10.210.1.4'}]}]},
|
|
Packit Service |
a04d08 |
{'mac_address': '90:b8:d0:0a:51:31', 'mtu': 1500,
|
|
Packit Service |
a04d08 |
'name': 'net1', 'type': 'physical',
|
|
Packit Service |
a04d08 |
'subnets': [{'address': '10.210.1.27/24', 'type': 'static',
|
|
Packit Service |
a04d08 |
'routes': [{'network': '3.0.0.0/8',
|
|
Packit Service |
a04d08 |
'gateway': '8.12.42.3'},
|
|
Packit Service |
a04d08 |
{'network': '4.0.0.0/8',
|
|
Packit Service |
a04d08 |
'gateway': '10.210.1.4'}]}]}]}
|
|
Packit Service |
a04d08 |
found = convert_net(SDC_NICS_SINGLE_GATEWAY, routes=routes)
|
|
Packit Service |
a04d08 |
self.maxDiff = None
|
|
Packit Service |
a04d08 |
self.assertEqual(expected, found)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
751c4a |
@unittest.skipUnless(get_smartos_environ() == SMARTOS_ENV_KVM,
|
|
Packit Service |
751c4a |
"Only supported on KVM and bhyve guests under SmartOS")
|
|
Packit Service |
751c4a |
@unittest.skipUnless(os.access(SERIAL_DEVICE, os.W_OK),
|
|
Packit Service |
751c4a |
"Requires write access to " + SERIAL_DEVICE)
|
|
Packit Service |
751c4a |
@unittest.skipUnless(HAS_PYSERIAL is True, "pyserial not available")
|
|
Packit Service |
a04d08 |
class TestSerialConcurrency(CiTestCase):
|
|
Packit Service |
a04d08 |
"""
|
|
Packit Service |
a04d08 |
This class tests locking on an actual serial port, and as such can only
|
|
Packit Service |
a04d08 |
be run in a kvm or bhyve guest running on a SmartOS host. A test run on
|
|
Packit Service |
a04d08 |
a metadata socket will not be valid because a metadata socket ensures
|
|
Packit Service |
a04d08 |
there is only one session over a connection. In contrast, in the
|
|
Packit Service |
a04d08 |
absence of proper locking multiple processes opening the same serial
|
|
Packit Service |
a04d08 |
port can corrupt each others' exchanges with the metadata server.
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
This takes on the order of 2 to 3 minutes to run.
|
|
Packit Service |
a04d08 |
"""
|
|
Packit Service |
a04d08 |
allowed_subp = ['mdata-get']
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def setUp(self):
|
|
Packit Service |
a04d08 |
self.mdata_proc = multiprocessing.Process(target=self.start_mdata_loop)
|
|
Packit Service |
a04d08 |
self.mdata_proc.start()
|
|
Packit Service |
a04d08 |
super(TestSerialConcurrency, self).setUp()
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def tearDown(self):
|
|
Packit Service |
a04d08 |
# os.kill() rather than mdata_proc.terminate() to avoid console spam.
|
|
Packit Service |
a04d08 |
os.kill(self.mdata_proc.pid, signal.SIGKILL)
|
|
Packit Service |
a04d08 |
self.mdata_proc.join()
|
|
Packit Service |
a04d08 |
super(TestSerialConcurrency, self).tearDown()
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def start_mdata_loop(self):
|
|
Packit Service |
a04d08 |
"""
|
|
Packit Service |
a04d08 |
The mdata-get command is repeatedly run in a separate process so
|
|
Packit Service |
a04d08 |
that it may try to race with metadata operations performed in the
|
|
Packit Service |
a04d08 |
main test process. Use of mdata-get is better than two processes
|
|
Packit Service |
a04d08 |
using the protocol implementation in DataSourceSmartOS because we
|
|
Packit Service |
a04d08 |
are testing to be sure that cloud-init and mdata-get respect each
|
|
Packit Service |
a04d08 |
others locks.
|
|
Packit Service |
a04d08 |
"""
|
|
Packit Service |
a04d08 |
rcs = list(range(0, 256))
|
|
Packit Service |
a04d08 |
while True:
|
|
Packit Service |
a04d08 |
subp(['mdata-get', 'sdc:routes'], rcs=rcs)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
def test_all_keys(self):
|
|
Packit Service |
a04d08 |
self.assertIsNotNone(self.mdata_proc.pid)
|
|
Packit Service |
a04d08 |
ds = DataSourceSmartOS
|
|
Packit Service |
a04d08 |
keys = [tup[0] for tup in ds.SMARTOS_ATTRIB_MAP.values()]
|
|
Packit Service |
a04d08 |
keys.extend(ds.SMARTOS_ATTRIB_JSON.values())
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
client = ds.jmc_client_factory(smartos_type=SMARTOS_ENV_KVM)
|
|
Packit Service |
a04d08 |
self.assertIsNotNone(client)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
# The behavior that we are testing for was observed mdata-get running
|
|
Packit Service |
a04d08 |
# 10 times at roughly the same time as cloud-init fetched each key
|
|
Packit Service |
a04d08 |
# once. cloud-init would regularly see failures before making it
|
|
Packit Service |
a04d08 |
# through all keys once.
|
|
Packit Service |
a04d08 |
for _ in range(0, 3):
|
|
Packit Service |
a04d08 |
for key in keys:
|
|
Packit Service |
a04d08 |
# We don't care about the return value, just that it doesn't
|
|
Packit Service |
a04d08 |
# thrown any exceptions.
|
|
Packit Service |
a04d08 |
client.get(key)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
self.assertIsNone(self.mdata_proc.exitcode)
|
|
Packit Service |
a04d08 |
|
|
Packit Service |
a04d08 |
# vi: ts=4 expandtab
|