I thought that it would be redundant to create a mock with each test code while creating the test code, so I tried and errored to see if it could be shared. Below is a sample app and sample test code at the start. Make the EC2 creation part of the test code common.
--App: Acquires and outputs EC2 information
app.py
import boto3
def main():
client = boto3.client('ec2')
#Get all instance information.
instances = client.describe_instances()
#Extract the instance name.
instace_name = [instance['KeyName'] for r in instances.get('Reservations') for instance in r.get('Instances')]
#Output instance name
print(instace_name)
--Test code: Create EC2 with mock and run the app
test.py
import unittest
import boto3
from moto import mock_ec2
from app import app
class MyTestCase(unittest.TestCase):
@mock_ec2
def test_case_1(self):
client = boto3.client('ec2')
#Set the conditions for EC2 to be created
ec2objects = [
{'KeyName': 'test_ec2_name_1'}
]
#Create EC2
for o in ec2objects:
client.run_instances(
ImageId='ami-03cf127a',
MinCount=1,
MaxCount=1,
KeyName=o.get('KeyName'))
#Run the app
app.main()
@mock_ec2
def test_case_2(self):
client = boto3.client('ec2')
#Set the conditions for EC2 to be created
ec2objects = [
{'KeyName': 'test_ec2_name_2'}
]
#Create EC2
for o in ec2objects:
client.run_instances(
ImageId='ami-03cf127a',
MinCount=1,
MaxCount=1,
KeyName=o.get('KeyName'))
#Run the app
app.main()
if __name__ == '__main__':
unittest.main()
Write the code to create EC2 in the setUp method and try to create EC2 before executing the test case.
test.py
import unittest
import boto3
from moto import mock_ec2
from app import app
class MyTestCase(unittest.TestCase):
@mock_ec2
def setUp(self):
client = boto3.client('ec2')
#Set the conditions for EC2 to be created
ec2objects = [
{'KeyName': 'test_ec2_name_1'}
]
#Create EC2
for o in ec2objects:
client.run_instances(
ImageId='ami-03cf127a',
MinCount=1,
MaxCount=1,
KeyName=o.get('KeyName'))
@mock_ec2
def test_case_1(self):
#Run the app
app.main()
@mock_ec2
def test_case_2(self):
#Run the app
app.main()
if __name__ == '__main__':
unittest.main()
result.
test_case_1 (tests.test_setUp.MyTestCase) ... []
ok
test_case_2 (tests.test_setUp.MyTestCase) ... []
ok
----------------------------------------------------------------------
Ran 2 tests in 0.458s
OK
EC2 name is not output. The expiration date of the mock by moto seems to be until the end of the method, and if it is described in the setUp method, the mock will disappear at the end of the setUp method. As a result, the mock does not exist when the test case is executed.
From the result of the previous section, I found that mock must be created without test cases, so I will create a common class and try to execute the methods in the common class from each case.
test.py
import unittest
import boto3
from moto import mock_ec2
from app import app
class common:
@staticmethod
def enviroment_1(name):
client = boto3.client('ec2')
#Set the conditions for EC2 to be created
ec2objects = [
{'KeyName': name}
]
#Create EC2
for o in ec2objects:
client.run_instances(
ImageId='ami-03cf127a',
MinCount=1,
MaxCount=1,
KeyName=o.get('KeyName'))
class MyTestCase(unittest.TestCase):
@mock_ec2
def setUp(self):
self.common = common
@mock_ec2
def test_case_1(self):
#Create EC2
self.common.enviroment_1('test_ec2_name_1')
#Run the app
app.main()
@mock_ec2
def test_case_2(self):
#Create EC2
self.common.enviroment_1('test_ec2_name_2')
#Run the app
app.main()
if __name__ == '__main__':
unittest.main()
result.
test_case_1 (tests.test_common.MyTestCase) ... ['test_ec2_name_1']
ok
test_case_2 (tests.test_common.MyTestCase) ... ['test_ec2_name_2']
ok
----------------------------------------------------------------------
Ran 2 tests in 0.489s
OK
I was able to share it in a nice way, and the results I expected were returned. However, creating a common class increases the number of codes, so I want to make it a little easier.
In the first place, I finally realize that it is the quickest if I can create common methods other than test cases in the test class.
test.py
import unittest
import boto3
from moto import mock_ec2
from app import app
class MyTestCase(unittest.TestCase):
@mock_ec2
def test_cace_1(self):
#Create EC2
self.__common('test_ec2_name_1')
#Run the app
app.main()
@mock_ec2
def test_cace_2(self):
#Create EC2
self.__common('test_ec2_name_2')
#Run the app
app.main()
def __common(self, name):
client = boto3.client('ec2')
#Set the conditions for EC2 to be created
ec2objects = [
{'KeyName': name}
]
#Create EC2
for o in ec2objects:
client.run_instances(
ImageId='ami-03cf127a',
MinCount=1,
MaxCount=1,
KeyName=o.get('KeyName'))
if __name__ == '__main__':
unittest.main()
result.
test_case_1 (tests.test.MyTestCase) ... ['test_ec2_name_1']
ok
test_case_2 (tests.test.MyTestCase) ... ['test_ec2_name_2']
ok
----------------------------------------------------------------------
Ran 2 tests in 0.361s
OK
did it. This is the smartest commonality that can be done now.
Recommended Posts