2017-04-18 17:09:10 +00:00
|
|
|
from __future__ import unicode_literals
|
|
|
|
|
2020-05-06 12:38:25 +00:00
|
|
|
import string
|
|
|
|
|
2017-04-18 17:09:10 +00:00
|
|
|
import boto3
|
2017-09-18 20:27:56 +00:00
|
|
|
import botocore.exceptions
|
2019-10-31 15:44:26 +00:00
|
|
|
import sure # noqa
|
2017-11-17 08:57:11 +00:00
|
|
|
import datetime
|
2018-04-25 20:27:07 +00:00
|
|
|
import uuid
|
|
|
|
|
2019-09-21 14:55:43 +00:00
|
|
|
from botocore.exceptions import ClientError, ParamValidationError
|
2020-10-06 05:54:49 +00:00
|
|
|
import pytest
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2020-11-08 08:06:35 +00:00
|
|
|
from moto import mock_ec2, mock_ssm
|
2017-04-18 17:09:10 +00:00
|
|
|
|
|
|
|
|
|
|
|
@mock_ssm
|
|
|
|
def test_delete_parameter():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-04-18 17:09:10 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="test", Description="A test parameter", Value="value", Type="String"
|
|
|
|
)
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters(Names=["test"])
|
|
|
|
len(response["Parameters"]).should.equal(1)
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
client.delete_parameter(Name="test")
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters(Names=["test"])
|
|
|
|
len(response["Parameters"]).should.equal(0)
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2017-09-18 20:46:07 +00:00
|
|
|
|
2020-02-26 01:25:44 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_delete_nonexistent_parameter():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
2020-10-06 06:04:09 +00:00
|
|
|
with pytest.raises(ClientError) as ex:
|
2020-02-26 01:25:44 +00:00
|
|
|
client.delete_parameter(Name="test_noexist")
|
2020-10-06 06:04:09 +00:00
|
|
|
ex.value.response["Error"]["Code"].should.equal("ParameterNotFound")
|
|
|
|
ex.value.response["Error"]["Message"].should.equal(
|
2020-02-27 12:29:13 +00:00
|
|
|
"Parameter test_noexist not found."
|
|
|
|
)
|
2020-02-26 01:25:44 +00:00
|
|
|
|
|
|
|
|
2017-08-11 13:19:36 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_delete_parameters():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-08-11 13:19:36 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="test", Description="A test parameter", Value="value", Type="String"
|
|
|
|
)
|
2017-08-11 13:19:36 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters(Names=["test"])
|
|
|
|
len(response["Parameters"]).should.equal(1)
|
2017-08-11 13:19:36 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
result = client.delete_parameters(Names=["test", "invalid"])
|
|
|
|
len(result["DeletedParameters"]).should.equal(1)
|
|
|
|
len(result["InvalidParameters"]).should.equal(1)
|
2017-08-11 13:19:36 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters(Names=["test"])
|
|
|
|
len(response["Parameters"]).should.equal(0)
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2017-09-18 20:46:07 +00:00
|
|
|
|
2017-11-06 09:44:54 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_get_parameters_by_path():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-11-06 09:44:54 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="/foo/name1", Description="A test parameter", Value="value1", Type="String"
|
|
|
|
)
|
2017-11-06 09:44:54 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="/foo/name2", Description="A test parameter", Value="value2", Type="String"
|
|
|
|
)
|
2017-11-06 09:44:54 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="/bar/name3", Description="A test parameter", Value="value3", Type="String"
|
|
|
|
)
|
2017-11-06 09:44:54 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="/bar/name3/name4",
|
|
|
|
Description="A test parameter",
|
|
|
|
Value="value4",
|
|
|
|
Type="String",
|
|
|
|
)
|
2017-11-06 09:44:54 +00:00
|
|
|
|
2018-04-30 18:02:47 +00:00
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="/baz/name1",
|
|
|
|
Description="A test parameter (list)",
|
|
|
|
Value="value1,value2,value3",
|
|
|
|
Type="StringList",
|
|
|
|
)
|
2018-04-30 18:02:47 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="/baz/name2", Description="A test parameter", Value="value1", Type="String"
|
|
|
|
)
|
2018-04-30 18:02:47 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="/baz/pwd",
|
|
|
|
Description="A secure test parameter",
|
|
|
|
Value="my_secret",
|
|
|
|
Type="SecureString",
|
|
|
|
KeyId="alias/aws/ssm",
|
|
|
|
)
|
2018-04-30 18:02:47 +00:00
|
|
|
|
2018-07-13 09:24:11 +00:00
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="foo", Description="A test parameter", Value="bar", Type="String"
|
|
|
|
)
|
2018-07-13 09:24:11 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="baz", Description="A test parameter", Value="qux", Type="String"
|
2018-07-13 09:24:11 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters_by_path(Path="/", Recursive=False)
|
|
|
|
len(response["Parameters"]).should.equal(2)
|
|
|
|
{p["Value"] for p in response["Parameters"]}.should.equal(set(["bar", "qux"]))
|
2019-12-01 01:03:51 +00:00
|
|
|
{p["ARN"] for p in response["Parameters"]}.should.equal(
|
|
|
|
set(
|
|
|
|
[
|
|
|
|
"arn:aws:ssm:us-east-1:1234567890:parameter/foo",
|
|
|
|
"arn:aws:ssm:us-east-1:1234567890:parameter/baz",
|
|
|
|
]
|
|
|
|
)
|
|
|
|
)
|
|
|
|
{
|
|
|
|
p["LastModifiedDate"].should.be.a(datetime.datetime)
|
|
|
|
for p in response["Parameters"]
|
|
|
|
}
|
2018-07-13 09:24:11 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters_by_path(Path="/", Recursive=True)
|
|
|
|
len(response["Parameters"]).should.equal(9)
|
2017-11-06 09:44:54 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters_by_path(Path="/foo")
|
|
|
|
len(response["Parameters"]).should.equal(2)
|
|
|
|
{p["Value"] for p in response["Parameters"]}.should.equal(set(["value1", "value2"]))
|
2017-11-06 09:44:54 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters_by_path(Path="/bar", Recursive=False)
|
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
response["Parameters"][0]["Value"].should.equal("value3")
|
2017-11-06 09:44:54 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters_by_path(Path="/bar", Recursive=True)
|
|
|
|
len(response["Parameters"]).should.equal(2)
|
|
|
|
{p["Value"] for p in response["Parameters"]}.should.equal(set(["value3", "value4"]))
|
2018-04-30 18:02:47 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters_by_path(Path="/baz")
|
|
|
|
len(response["Parameters"]).should.equal(3)
|
|
|
|
|
|
|
|
filters = [{"Key": "Type", "Option": "Equals", "Values": ["StringList"]}]
|
|
|
|
response = client.get_parameters_by_path(Path="/baz", ParameterFilters=filters)
|
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
{p["Name"] for p in response["Parameters"]}.should.equal(set(["/baz/name1"]))
|
2018-04-30 18:02:47 +00:00
|
|
|
|
|
|
|
# note: 'Option' is optional (default: 'Equals')
|
2019-10-31 15:44:26 +00:00
|
|
|
filters = [{"Key": "Type", "Values": ["StringList"]}]
|
|
|
|
response = client.get_parameters_by_path(Path="/baz", ParameterFilters=filters)
|
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
{p["Name"] for p in response["Parameters"]}.should.equal(set(["/baz/name1"]))
|
|
|
|
|
|
|
|
filters = [{"Key": "Type", "Option": "Equals", "Values": ["String"]}]
|
|
|
|
response = client.get_parameters_by_path(Path="/baz", ParameterFilters=filters)
|
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
{p["Name"] for p in response["Parameters"]}.should.equal(set(["/baz/name2"]))
|
|
|
|
|
|
|
|
filters = [
|
|
|
|
{"Key": "Type", "Option": "Equals", "Values": ["String", "SecureString"]}
|
|
|
|
]
|
|
|
|
response = client.get_parameters_by_path(Path="/baz", ParameterFilters=filters)
|
|
|
|
len(response["Parameters"]).should.equal(2)
|
|
|
|
{p["Name"] for p in response["Parameters"]}.should.equal(
|
|
|
|
set(["/baz/name2", "/baz/pwd"])
|
|
|
|
)
|
|
|
|
|
|
|
|
filters = [{"Key": "Type", "Option": "BeginsWith", "Values": ["String"]}]
|
|
|
|
response = client.get_parameters_by_path(Path="/baz", ParameterFilters=filters)
|
|
|
|
len(response["Parameters"]).should.equal(2)
|
|
|
|
{p["Name"] for p in response["Parameters"]}.should.equal(
|
|
|
|
set(["/baz/name1", "/baz/name2"])
|
2018-04-30 18:02:47 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
filters = [{"Key": "KeyId", "Option": "Equals", "Values": ["alias/aws/ssm"]}]
|
|
|
|
response = client.get_parameters_by_path(Path="/baz", ParameterFilters=filters)
|
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
{p["Name"] for p in response["Parameters"]}.should.equal(set(["/baz/pwd"]))
|
|
|
|
|
2019-11-27 22:12:31 +00:00
|
|
|
response = client.get_parameters_by_path(Path="/", Recursive=True, MaxResults=4)
|
|
|
|
len(response["Parameters"]).should.equal(4)
|
|
|
|
response["NextToken"].should.equal("4")
|
|
|
|
response = client.get_parameters_by_path(
|
|
|
|
Path="/", Recursive=True, MaxResults=4, NextToken=response["NextToken"]
|
|
|
|
)
|
|
|
|
len(response["Parameters"]).should.equal(4)
|
|
|
|
response["NextToken"].should.equal("8")
|
|
|
|
response = client.get_parameters_by_path(
|
|
|
|
Path="/", Recursive=True, MaxResults=4, NextToken=response["NextToken"]
|
|
|
|
)
|
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
response.should_not.have.key("NextToken")
|
|
|
|
|
2020-07-28 09:17:35 +00:00
|
|
|
filters = [{"Key": "Name", "Values": ["error"]}]
|
|
|
|
client.get_parameters_by_path.when.called_with(
|
|
|
|
Path="/baz", ParameterFilters=filters
|
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
"The following filter key is not valid: Name. "
|
|
|
|
"Valid filter keys include: [Type, KeyId].",
|
|
|
|
)
|
|
|
|
|
|
|
|
filters = [{"Key": "Path", "Values": ["/error"]}]
|
|
|
|
client.get_parameters_by_path.when.called_with(
|
|
|
|
Path="/baz", ParameterFilters=filters
|
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
"The following filter key is not valid: Path. "
|
|
|
|
"Valid filter keys include: [Type, KeyId].",
|
|
|
|
)
|
|
|
|
|
|
|
|
filters = [{"Key": "Tier", "Values": ["Standard"]}]
|
|
|
|
client.get_parameters_by_path.when.called_with(
|
|
|
|
Path="/baz", ParameterFilters=filters
|
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
"The following filter key is not valid: Tier. "
|
|
|
|
"Valid filter keys include: [Type, KeyId].",
|
|
|
|
)
|
|
|
|
|
2017-11-06 09:44:54 +00:00
|
|
|
|
2017-04-18 17:09:10 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_put_parameter():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2018-03-21 15:56:57 +00:00
|
|
|
response = client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="test", Description="A test parameter", Value="value", Type="String"
|
|
|
|
)
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response["Version"].should.equal(1)
|
2018-03-21 15:56:57 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters(Names=["test"], WithDecryption=False)
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
response["Parameters"][0]["Name"].should.equal("test")
|
|
|
|
response["Parameters"][0]["Value"].should.equal("value")
|
|
|
|
response["Parameters"][0]["Type"].should.equal("String")
|
|
|
|
response["Parameters"][0]["Version"].should.equal(1)
|
2019-12-01 01:03:51 +00:00
|
|
|
response["Parameters"][0]["LastModifiedDate"].should.be.a(datetime.datetime)
|
|
|
|
response["Parameters"][0]["ARN"].should.equal(
|
|
|
|
"arn:aws:ssm:us-east-1:1234567890:parameter/test"
|
|
|
|
)
|
|
|
|
initial_modification_date = response["Parameters"][0]["LastModifiedDate"]
|
2017-11-17 08:57:11 +00:00
|
|
|
|
2018-03-21 15:56:57 +00:00
|
|
|
try:
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="test", Description="desc 2", Value="value 2", Type="String"
|
|
|
|
)
|
|
|
|
raise RuntimeError("Should fail")
|
2018-03-21 15:56:57 +00:00
|
|
|
except botocore.exceptions.ClientError as err:
|
2019-10-31 15:44:26 +00:00
|
|
|
err.operation_name.should.equal("PutParameter")
|
|
|
|
err.response["Error"]["Message"].should.equal("Parameter test already exists.")
|
2017-11-17 08:57:11 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters(Names=["test"], WithDecryption=False)
|
2017-11-17 08:57:11 +00:00
|
|
|
|
|
|
|
# without overwrite nothing change
|
2019-10-31 15:44:26 +00:00
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
response["Parameters"][0]["Name"].should.equal("test")
|
|
|
|
response["Parameters"][0]["Value"].should.equal("value")
|
|
|
|
response["Parameters"][0]["Type"].should.equal("String")
|
|
|
|
response["Parameters"][0]["Version"].should.equal(1)
|
2019-12-01 01:03:51 +00:00
|
|
|
response["Parameters"][0]["LastModifiedDate"].should.equal(
|
|
|
|
initial_modification_date
|
|
|
|
)
|
|
|
|
response["Parameters"][0]["ARN"].should.equal(
|
|
|
|
"arn:aws:ssm:us-east-1:1234567890:parameter/test"
|
|
|
|
)
|
2017-11-17 08:57:11 +00:00
|
|
|
|
2018-03-21 15:56:57 +00:00
|
|
|
response = client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="test",
|
|
|
|
Description="desc 3",
|
|
|
|
Value="value 3",
|
|
|
|
Type="String",
|
|
|
|
Overwrite=True,
|
|
|
|
)
|
2017-11-17 08:57:11 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response["Version"].should.equal(2)
|
2018-03-21 15:56:57 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters(Names=["test"], WithDecryption=False)
|
2017-11-17 08:57:11 +00:00
|
|
|
|
|
|
|
# without overwrite nothing change
|
2019-10-31 15:44:26 +00:00
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
response["Parameters"][0]["Name"].should.equal("test")
|
|
|
|
response["Parameters"][0]["Value"].should.equal("value 3")
|
|
|
|
response["Parameters"][0]["Type"].should.equal("String")
|
|
|
|
response["Parameters"][0]["Version"].should.equal(2)
|
2019-12-01 01:03:51 +00:00
|
|
|
response["Parameters"][0]["LastModifiedDate"].should_not.equal(
|
|
|
|
initial_modification_date
|
|
|
|
)
|
|
|
|
response["Parameters"][0]["ARN"].should.equal(
|
|
|
|
"arn:aws:ssm:us-east-1:1234567890:parameter/test"
|
|
|
|
)
|
2019-10-31 15:44:26 +00:00
|
|
|
|
2017-09-18 13:13:02 +00:00
|
|
|
|
2020-07-28 14:26:59 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_put_parameter_invalid_names():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
invalid_prefix_err = (
|
|
|
|
'Parameter name: can\'t be prefixed with "aws" or "ssm" (case-insensitive).'
|
|
|
|
)
|
|
|
|
|
|
|
|
client.put_parameter.when.called_with(
|
|
|
|
Name="ssm_test", Value="value", Type="String"
|
|
|
|
).should.throw(
|
2020-11-11 15:55:37 +00:00
|
|
|
ClientError, invalid_prefix_err,
|
2020-07-28 14:26:59 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.put_parameter.when.called_with(
|
|
|
|
Name="SSM_TEST", Value="value", Type="String"
|
|
|
|
).should.throw(
|
2020-11-11 15:55:37 +00:00
|
|
|
ClientError, invalid_prefix_err,
|
2020-07-28 14:26:59 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.put_parameter.when.called_with(
|
|
|
|
Name="aws_test", Value="value", Type="String"
|
|
|
|
).should.throw(
|
2020-11-11 15:55:37 +00:00
|
|
|
ClientError, invalid_prefix_err,
|
2020-07-28 14:26:59 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.put_parameter.when.called_with(
|
|
|
|
Name="AWS_TEST", Value="value", Type="String"
|
|
|
|
).should.throw(
|
2020-11-11 15:55:37 +00:00
|
|
|
ClientError, invalid_prefix_err,
|
2020-07-28 14:26:59 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
ssm_path = "/ssm_test/path/to/var"
|
|
|
|
client.put_parameter.when.called_with(
|
|
|
|
Name=ssm_path, Value="value", Type="String"
|
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
'Parameter name: can\'t be prefixed with "ssm" (case-insensitive). If formed as a path, it can consist of '
|
|
|
|
"sub-paths divided by slash symbol; each sub-path can be formed as a mix of letters, numbers and the following "
|
|
|
|
"3 symbols .-_",
|
|
|
|
)
|
|
|
|
|
|
|
|
ssm_path = "/SSM/PATH/TO/VAR"
|
|
|
|
client.put_parameter.when.called_with(
|
|
|
|
Name=ssm_path, Value="value", Type="String"
|
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
'Parameter name: can\'t be prefixed with "ssm" (case-insensitive). If formed as a path, it can consist of '
|
|
|
|
"sub-paths divided by slash symbol; each sub-path can be formed as a mix of letters, numbers and the following "
|
|
|
|
"3 symbols .-_",
|
|
|
|
)
|
|
|
|
|
|
|
|
aws_path = "/aws_test/path/to/var"
|
|
|
|
client.put_parameter.when.called_with(
|
|
|
|
Name=aws_path, Value="value", Type="String"
|
|
|
|
).should.throw(
|
2020-11-11 15:55:37 +00:00
|
|
|
ClientError, "No access to reserved parameter name: {}.".format(aws_path),
|
2020-07-28 14:26:59 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
aws_path = "/AWS/PATH/TO/VAR"
|
|
|
|
client.put_parameter.when.called_with(
|
|
|
|
Name=aws_path, Value="value", Type="String"
|
|
|
|
).should.throw(
|
2020-11-11 15:55:37 +00:00
|
|
|
ClientError, "No access to reserved parameter name: {}.".format(aws_path),
|
2020-07-28 14:26:59 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
|
2018-12-19 23:02:36 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_put_parameter_china():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="cn-north-1")
|
2018-12-19 23:02:36 +00:00
|
|
|
|
|
|
|
response = client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="test", Description="A test parameter", Value="value", Type="String"
|
|
|
|
)
|
2018-12-19 23:02:36 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response["Version"].should.equal(1)
|
2018-12-19 23:02:36 +00:00
|
|
|
|
2017-09-18 13:13:02 +00:00
|
|
|
|
|
|
|
@mock_ssm
|
|
|
|
def test_get_parameter():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-09-18 13:13:02 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="test", Description="A test parameter", Value="value", Type="String"
|
|
|
|
)
|
2017-09-18 13:13:02 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameter(Name="test", WithDecryption=False)
|
2017-09-18 13:13:02 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response["Parameter"]["Name"].should.equal("test")
|
|
|
|
response["Parameter"]["Value"].should.equal("value")
|
|
|
|
response["Parameter"]["Type"].should.equal("String")
|
2019-12-01 01:03:51 +00:00
|
|
|
response["Parameter"]["LastModifiedDate"].should.be.a(datetime.datetime)
|
|
|
|
response["Parameter"]["ARN"].should.equal(
|
|
|
|
"arn:aws:ssm:us-east-1:1234567890:parameter/test"
|
|
|
|
)
|
2017-04-18 17:09:10 +00:00
|
|
|
|
|
|
|
|
2020-07-28 15:59:22 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_get_parameter_with_version_and_labels():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
client.put_parameter(
|
|
|
|
Name="test-1", Description="A test parameter", Value="value", Type="String"
|
|
|
|
)
|
|
|
|
client.put_parameter(
|
|
|
|
Name="test-2", Description="A test parameter", Value="value", Type="String"
|
|
|
|
)
|
|
|
|
|
|
|
|
client.label_parameter_version(
|
|
|
|
Name="test-2", ParameterVersion=1, Labels=["test-label"]
|
|
|
|
)
|
|
|
|
|
|
|
|
response = client.get_parameter(Name="test-1:1", WithDecryption=False)
|
|
|
|
|
|
|
|
response["Parameter"]["Name"].should.equal("test-1")
|
|
|
|
response["Parameter"]["Value"].should.equal("value")
|
|
|
|
response["Parameter"]["Type"].should.equal("String")
|
|
|
|
response["Parameter"]["LastModifiedDate"].should.be.a(datetime.datetime)
|
|
|
|
response["Parameter"]["ARN"].should.equal(
|
|
|
|
"arn:aws:ssm:us-east-1:1234567890:parameter/test-1"
|
|
|
|
)
|
|
|
|
|
|
|
|
response = client.get_parameter(Name="test-2:1", WithDecryption=False)
|
|
|
|
response["Parameter"]["Name"].should.equal("test-2")
|
|
|
|
response["Parameter"]["Value"].should.equal("value")
|
|
|
|
response["Parameter"]["Type"].should.equal("String")
|
|
|
|
response["Parameter"]["LastModifiedDate"].should.be.a(datetime.datetime)
|
|
|
|
response["Parameter"]["ARN"].should.equal(
|
|
|
|
"arn:aws:ssm:us-east-1:1234567890:parameter/test-2"
|
|
|
|
)
|
|
|
|
|
|
|
|
response = client.get_parameter(Name="test-2:test-label", WithDecryption=False)
|
|
|
|
response["Parameter"]["Name"].should.equal("test-2")
|
|
|
|
response["Parameter"]["Value"].should.equal("value")
|
|
|
|
response["Parameter"]["Type"].should.equal("String")
|
|
|
|
response["Parameter"]["LastModifiedDate"].should.be.a(datetime.datetime)
|
|
|
|
response["Parameter"]["ARN"].should.equal(
|
|
|
|
"arn:aws:ssm:us-east-1:1234567890:parameter/test-2"
|
|
|
|
)
|
|
|
|
|
2020-10-06 06:04:09 +00:00
|
|
|
with pytest.raises(ClientError) as ex:
|
2020-07-28 15:59:22 +00:00
|
|
|
client.get_parameter(Name="test-2:2:3", WithDecryption=False)
|
2020-10-06 06:04:09 +00:00
|
|
|
ex.value.response["Error"]["Code"].should.equal("ParameterNotFound")
|
|
|
|
ex.value.response["Error"]["Message"].should.equal(
|
2020-07-28 15:59:22 +00:00
|
|
|
"Parameter test-2:2:3 not found."
|
|
|
|
)
|
|
|
|
|
2020-10-06 06:04:09 +00:00
|
|
|
with pytest.raises(ClientError) as ex:
|
2020-07-28 15:59:22 +00:00
|
|
|
client.get_parameter(Name="test-2:2", WithDecryption=False)
|
2020-10-06 06:04:09 +00:00
|
|
|
ex.value.response["Error"]["Code"].should.equal("ParameterNotFound")
|
2020-10-06 06:46:05 +00:00
|
|
|
ex.value.response["Error"]["Message"].should.equal("Parameter test-2:2 not found.")
|
2020-07-28 15:59:22 +00:00
|
|
|
|
|
|
|
|
2020-05-06 12:38:25 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_get_parameters_errors():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
ssm_parameters = {name: "value" for name in string.ascii_lowercase[:11]}
|
|
|
|
|
|
|
|
for name, value in ssm_parameters.items():
|
|
|
|
client.put_parameter(Name=name, Value=value, Type="String")
|
|
|
|
|
2020-10-06 06:04:09 +00:00
|
|
|
with pytest.raises(ClientError) as e:
|
2020-05-06 12:38:25 +00:00
|
|
|
client.get_parameters(Names=list(ssm_parameters.keys()))
|
2020-10-06 06:04:09 +00:00
|
|
|
ex = e.value
|
2020-05-06 12:38:25 +00:00
|
|
|
ex.operation_name.should.equal("GetParameters")
|
|
|
|
ex.response["ResponseMetadata"]["HTTPStatusCode"].should.equal(400)
|
|
|
|
ex.response["Error"]["Code"].should.contain("ValidationException")
|
|
|
|
ex.response["Error"]["Message"].should.equal(
|
|
|
|
"1 validation error detected: "
|
|
|
|
"Value '[{}]' at 'names' failed to satisfy constraint: "
|
|
|
|
"Member must have length less than or equal to 10.".format(
|
|
|
|
", ".join(ssm_parameters.keys())
|
|
|
|
)
|
|
|
|
)
|
|
|
|
|
|
|
|
|
2017-09-18 20:27:56 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_get_nonexistant_parameter():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-09-18 20:27:56 +00:00
|
|
|
|
|
|
|
try:
|
2019-10-31 15:44:26 +00:00
|
|
|
client.get_parameter(Name="test_noexist", WithDecryption=False)
|
|
|
|
raise RuntimeError("Should of failed")
|
2017-09-18 20:27:56 +00:00
|
|
|
except botocore.exceptions.ClientError as err:
|
2019-10-31 15:44:26 +00:00
|
|
|
err.operation_name.should.equal("GetParameter")
|
|
|
|
err.response["Error"]["Message"].should.equal(
|
|
|
|
"Parameter test_noexist not found."
|
|
|
|
)
|
2017-09-18 20:27:56 +00:00
|
|
|
|
|
|
|
|
2017-06-20 18:47:53 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_describe_parameters():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="test",
|
|
|
|
Description="A test parameter",
|
|
|
|
Value="value",
|
|
|
|
Type="String",
|
|
|
|
AllowedPattern=r".*",
|
|
|
|
)
|
2017-06-20 18:47:53 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters()
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(1)
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Name"].should.equal("test")
|
|
|
|
parameters[0]["Type"].should.equal("String")
|
|
|
|
parameters[0]["AllowedPattern"].should.equal(r".*")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
|
|
|
|
|
|
|
@mock_ssm
|
|
|
|
def test_describe_parameters_paging():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
|
|
|
for i in range(50):
|
2019-10-31 15:44:26 +00:00
|
|
|
client.put_parameter(Name="param-%d" % i, Value="value-%d" % i, Type="String")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters()
|
2019-10-31 15:44:26 +00:00
|
|
|
response["Parameters"].should.have.length_of(10)
|
|
|
|
response["NextToken"].should.equal("10")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.describe_parameters(NextToken=response["NextToken"])
|
|
|
|
response["Parameters"].should.have.length_of(10)
|
|
|
|
response["NextToken"].should.equal("20")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.describe_parameters(NextToken=response["NextToken"])
|
|
|
|
response["Parameters"].should.have.length_of(10)
|
|
|
|
response["NextToken"].should.equal("30")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.describe_parameters(NextToken=response["NextToken"])
|
|
|
|
response["Parameters"].should.have.length_of(10)
|
|
|
|
response["NextToken"].should.equal("40")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.describe_parameters(NextToken=response["NextToken"])
|
|
|
|
response["Parameters"].should.have.length_of(10)
|
|
|
|
response["NextToken"].should.equal("50")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.describe_parameters(NextToken=response["NextToken"])
|
|
|
|
response["Parameters"].should.have.length_of(0)
|
|
|
|
response.should_not.have.key("NextToken")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
2017-06-26 18:20:56 +00:00
|
|
|
|
2017-06-20 18:47:53 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_describe_parameters_filter_names():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
|
|
|
for i in range(50):
|
2019-10-31 15:44:26 +00:00
|
|
|
p = {"Name": "param-%d" % i, "Value": "value-%d" % i, "Type": "String"}
|
2017-06-20 18:47:53 +00:00
|
|
|
if i % 5 == 0:
|
2019-10-31 15:44:26 +00:00
|
|
|
p["Type"] = "SecureString"
|
|
|
|
p["KeyId"] = "a key"
|
2017-06-20 18:47:53 +00:00
|
|
|
client.put_parameter(**p)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.describe_parameters(
|
|
|
|
Filters=[{"Key": "Name", "Values": ["param-22"]}]
|
|
|
|
)
|
2019-09-21 14:55:43 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(1)
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Name"].should.equal("param-22")
|
|
|
|
parameters[0]["Type"].should.equal("String")
|
|
|
|
response.should_not.have.key("NextToken")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
2017-06-26 18:20:56 +00:00
|
|
|
|
2017-06-20 18:47:53 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_describe_parameters_filter_type():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
|
|
|
for i in range(50):
|
2019-10-31 15:44:26 +00:00
|
|
|
p = {"Name": "param-%d" % i, "Value": "value-%d" % i, "Type": "String"}
|
2017-06-20 18:47:53 +00:00
|
|
|
if i % 5 == 0:
|
2019-10-31 15:44:26 +00:00
|
|
|
p["Type"] = "SecureString"
|
|
|
|
p["KeyId"] = "a key"
|
2017-06-20 18:47:53 +00:00
|
|
|
client.put_parameter(**p)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.describe_parameters(
|
|
|
|
Filters=[{"Key": "Type", "Values": ["SecureString"]}]
|
|
|
|
)
|
2019-09-21 14:55:43 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(10)
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Type"].should.equal("SecureString")
|
|
|
|
response.should.have.key("NextToken").which.should.equal("10")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
2017-06-26 18:20:56 +00:00
|
|
|
|
2017-06-20 18:47:53 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_describe_parameters_filter_keyid():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-06-20 18:47:53 +00:00
|
|
|
|
|
|
|
for i in range(50):
|
2019-10-31 15:44:26 +00:00
|
|
|
p = {"Name": "param-%d" % i, "Value": "value-%d" % i, "Type": "String"}
|
2017-06-20 18:47:53 +00:00
|
|
|
if i % 5 == 0:
|
2019-10-31 15:44:26 +00:00
|
|
|
p["Type"] = "SecureString"
|
|
|
|
p["KeyId"] = "key:%d" % i
|
2017-06-20 18:47:53 +00:00
|
|
|
client.put_parameter(**p)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.describe_parameters(
|
|
|
|
Filters=[{"Key": "KeyId", "Values": ["key:10"]}]
|
|
|
|
)
|
2019-09-21 14:55:43 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(1)
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Name"].should.equal("param-10")
|
|
|
|
parameters[0]["Type"].should.equal("SecureString")
|
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
|
|
|
|
@mock_ssm
|
|
|
|
def test_describe_parameters_with_parameter_filters_keyid():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
client.put_parameter(Name="secure-param", Value="secure-value", Type="SecureString")
|
2019-09-21 14:55:43 +00:00
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="custom-secure-param",
|
|
|
|
Value="custom-secure-value",
|
|
|
|
Type="SecureString",
|
|
|
|
KeyId="alias/custom",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
2019-10-31 15:44:26 +00:00
|
|
|
client.put_parameter(Name="param", Value="value", Type="String")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "KeyId", "Values": ["alias/aws/ssm"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(1)
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Name"].should.equal("secure-param")
|
|
|
|
parameters[0]["Type"].should.equal("SecureString")
|
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "KeyId", "Values": ["alias/custom"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(1)
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Name"].should.equal("custom-secure-param")
|
|
|
|
parameters[0]["Type"].should.equal("SecureString")
|
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "KeyId", "Option": "BeginsWith", "Values": ["alias"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(2)
|
2019-10-31 15:44:26 +00:00
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
|
|
|
|
@mock_ssm
|
|
|
|
def test_describe_parameters_with_parameter_filters_name():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
client.put_parameter(Name="param", Value="value", Type="String")
|
|
|
|
client.put_parameter(Name="/param-2", Value="value-2", Type="String")
|
2020-07-28 09:17:35 +00:00
|
|
|
client.put_parameter(Name="/tangent-3", Value="value-3", Type="String")
|
|
|
|
client.put_parameter(Name="tangram-4", Value="value-4", Type="String")
|
|
|
|
client.put_parameter(Name="standby-5", Value="value-5", Type="String")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Name", "Values": ["param"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(1)
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Name"].should.equal("param")
|
|
|
|
parameters[0]["Type"].should.equal("String")
|
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Name", "Values": ["/param"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(1)
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Name"].should.equal("param")
|
|
|
|
parameters[0]["Type"].should.equal("String")
|
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Name", "Values": ["param-2"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(1)
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Name"].should.equal("/param-2")
|
|
|
|
parameters[0]["Type"].should.equal("String")
|
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Name", "Option": "BeginsWith", "Values": ["param"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(2)
|
2019-10-31 15:44:26 +00:00
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
2020-07-28 09:17:35 +00:00
|
|
|
response = client.describe_parameters(
|
|
|
|
ParameterFilters=[{"Key": "Name", "Option": "Contains", "Values": ["ram"]}]
|
|
|
|
)
|
|
|
|
|
|
|
|
parameters = response["Parameters"]
|
|
|
|
parameters.should.have.length_of(3)
|
|
|
|
response.should_not.have.key("NextToken")
|
|
|
|
|
|
|
|
response = client.describe_parameters(
|
|
|
|
ParameterFilters=[{"Key": "Name", "Option": "Contains", "Values": ["/tan"]}]
|
|
|
|
)
|
|
|
|
|
|
|
|
parameters = response["Parameters"]
|
|
|
|
parameters.should.have.length_of(2)
|
|
|
|
response.should_not.have.key("NextToken")
|
|
|
|
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
@mock_ssm
|
|
|
|
def test_describe_parameters_with_parameter_filters_path():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
client.put_parameter(Name="/foo/name1", Value="value1", Type="String")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
client.put_parameter(Name="/foo/name2", Value="value2", Type="String")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
client.put_parameter(Name="/bar/name3", Value="value3", Type="String")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
client.put_parameter(Name="/bar/name3/name4", Value="value4", Type="String")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
client.put_parameter(Name="foo", Value="bar", Type="String")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Path", "Values": ["/fo"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(0)
|
2019-10-31 15:44:26 +00:00
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Path", "Values": ["/"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(1)
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Name"].should.equal("foo")
|
|
|
|
parameters[0]["Type"].should.equal("String")
|
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Path", "Values": ["/", "/foo"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(3)
|
2019-10-31 15:44:26 +00:00
|
|
|
{parameter["Name"] for parameter in response["Parameters"]}.should.equal(
|
|
|
|
{"/foo/name1", "/foo/name2", "foo"}
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
2019-10-31 15:44:26 +00:00
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Path", "Values": ["/foo/"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(2)
|
2019-10-31 15:44:26 +00:00
|
|
|
{parameter["Name"] for parameter in response["Parameters"]}.should.equal(
|
|
|
|
{"/foo/name1", "/foo/name2"}
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
2019-10-31 15:44:26 +00:00
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[
|
|
|
|
{"Key": "Path", "Option": "OneLevel", "Values": ["/bar/name3"]}
|
|
|
|
]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(1)
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Name"].should.equal("/bar/name3/name4")
|
|
|
|
parameters[0]["Type"].should.equal("String")
|
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Path", "Option": "Recursive", "Values": ["/fo"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(0)
|
2019-10-31 15:44:26 +00:00
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Path", "Option": "Recursive", "Values": ["/"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(5)
|
2019-10-31 15:44:26 +00:00
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[
|
|
|
|
{"Key": "Path", "Option": "Recursive", "Values": ["/foo", "/bar"]}
|
|
|
|
]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(4)
|
2019-10-31 15:44:26 +00:00
|
|
|
{parameter["Name"] for parameter in response["Parameters"]}.should.equal(
|
|
|
|
{"/foo/name1", "/foo/name2", "/bar/name3", "/bar/name3/name4"}
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
2019-10-31 15:44:26 +00:00
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Path", "Option": "Recursive", "Values": ["/foo/"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(2)
|
2019-10-31 15:44:26 +00:00
|
|
|
{parameter["Name"] for parameter in response["Parameters"]}.should.equal(
|
|
|
|
{"/foo/name1", "/foo/name2"}
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
2019-10-31 15:44:26 +00:00
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[
|
|
|
|
{"Key": "Path", "Option": "Recursive", "Values": ["/bar/name3"]}
|
|
|
|
]
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(1)
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Name"].should.equal("/bar/name3/name4")
|
|
|
|
parameters[0]["Type"].should.equal("String")
|
|
|
|
response.should_not.have.key("NextToken")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
|
|
|
|
@mock_ssm
|
|
|
|
def test_describe_parameters_invalid_parameter_filters():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2019-09-21 14:55:43 +00:00
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
Filters=[{"Key": "Name", "Values": ["test"]}],
|
|
|
|
ParameterFilters=[{"Key": "Name", "Values": ["test"]}],
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
2019-10-31 15:44:26 +00:00
|
|
|
"You can use either Filters or ParameterFilters in a single request.",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
client.describe_parameters.when.called_with(ParameterFilters=[{}]).should.throw(
|
2019-09-21 14:55:43 +00:00
|
|
|
ParamValidationError,
|
2019-10-31 15:44:26 +00:00
|
|
|
'Parameter validation failed:\nMissing required parameter in ParameterFilters[0]: "Key"',
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "key"}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
'1 validation error detected: Value "key" at "parameterFilters.1.member.key" failed to satisfy constraint: '
|
2019-10-31 15:44:26 +00:00
|
|
|
"Member must satisfy regular expression pattern: tag:.+|Name|Type|KeyId|Path|Label|Tier",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
long_key = "tag:" + "t" * 129
|
2019-09-21 14:55:43 +00:00
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": long_key}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
'1 validation error detected: Value "{value}" at "parameterFilters.1.member.key" failed to satisfy constraint: '
|
2019-10-31 15:44:26 +00:00
|
|
|
"Member must have length less than or equal to 132".format(value=long_key),
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Name", "Option": "over 10 chars"}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
'1 validation error detected: Value "over 10 chars" at "parameterFilters.1.member.option" failed to satisfy constraint: '
|
2019-10-31 15:44:26 +00:00
|
|
|
"Member must have length less than or equal to 10",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
many_values = ["test"] * 51
|
2019-09-21 14:55:43 +00:00
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Name", "Values": many_values}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
'1 validation error detected: Value "{value}" at "parameterFilters.1.member.values" failed to satisfy constraint: '
|
2019-10-31 15:44:26 +00:00
|
|
|
"Member must have length less than or equal to 50".format(value=many_values),
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
long_value = ["t" * 1025]
|
2019-09-21 14:55:43 +00:00
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Name", "Values": long_value}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
'1 validation error detected: Value "{value}" at "parameterFilters.1.member.values" failed to satisfy constraint: '
|
2019-10-31 15:44:26 +00:00
|
|
|
"[Member must have length less than or equal to 1024, Member must have length greater than or equal to 1]".format(
|
|
|
|
value=long_value
|
|
|
|
),
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Name", "Option": "over 10 chars"}, {"Key": "key"}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
2019-10-31 15:44:26 +00:00
|
|
|
"2 validation errors detected: "
|
2019-09-21 14:55:43 +00:00
|
|
|
'Value "over 10 chars" at "parameterFilters.1.member.option" failed to satisfy constraint: '
|
2019-10-31 15:44:26 +00:00
|
|
|
"Member must have length less than or equal to 10; "
|
2019-09-21 14:55:43 +00:00
|
|
|
'Value "key" at "parameterFilters.2.member.key" failed to satisfy constraint: '
|
2019-10-31 15:44:26 +00:00
|
|
|
"Member must satisfy regular expression pattern: tag:.+|Name|Type|KeyId|Path|Label|Tier",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Label"}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
2019-10-31 15:44:26 +00:00
|
|
|
"The following filter key is not valid: Label. Valid filter keys include: [Path, Name, Type, KeyId, Tier].",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Name"}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
2019-10-31 15:44:26 +00:00
|
|
|
"The following filter values are missing : null for filter key Name.",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Name", "Values": []}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ParamValidationError,
|
2019-10-31 15:44:26 +00:00
|
|
|
"Invalid length for parameter ParameterFilters[0].Values, value: 0, valid range: 1-inf",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[
|
|
|
|
{"Key": "Name", "Values": ["test"]},
|
|
|
|
{"Key": "Name", "Values": ["test test"]},
|
|
|
|
]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
2019-10-31 15:44:26 +00:00
|
|
|
"The following filter is duplicated in the request: Name. A request can contain only one occurrence of a specific filter.",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
for value in ["/###", "//", "test"]:
|
2019-09-21 14:55:43 +00:00
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Path", "Values": [value]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
'The parameter doesn\'t meet the parameter name requirements. The parameter name must begin with a forward slash "/". '
|
2019-10-31 15:44:26 +00:00
|
|
|
'It can\'t be prefixed with "aws" or "ssm" (case-insensitive). '
|
|
|
|
"It must use only letters, numbers, or the following symbols: . (period), - (hyphen), _ (underscore). "
|
2019-09-21 14:55:43 +00:00
|
|
|
'Special characters are not allowed. All sub-paths, if specified, must use the forward slash symbol "/". '
|
2019-10-31 15:44:26 +00:00
|
|
|
"Valid example: /get/parameters2-/by1./path0_.",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Path", "Values": ["/aws", "/ssm"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
'Filters for common parameters can\'t be prefixed with "aws" or "ssm" (case-insensitive). '
|
2019-10-31 15:44:26 +00:00
|
|
|
"When using global parameters, please specify within a global namespace.",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Path", "Option": "Equals", "Values": ["test"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
2019-10-31 15:44:26 +00:00
|
|
|
"The following filter option is not valid: Equals. Valid options include: [Recursive, OneLevel].",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Tier", "Values": ["test"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
2019-10-31 15:44:26 +00:00
|
|
|
"The following filter value is not valid: test. Valid values include: [Standard, Advanced, Intelligent-Tiering]",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Type", "Values": ["test"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
2019-10-31 15:44:26 +00:00
|
|
|
"The following filter value is not valid: test. Valid values include: [String, StringList, SecureString]",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
client.describe_parameters.when.called_with(
|
2019-10-31 15:44:26 +00:00
|
|
|
ParameterFilters=[{"Key": "Name", "Option": "option", "Values": ["test"]}]
|
2019-09-21 14:55:43 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
2019-10-31 15:44:26 +00:00
|
|
|
"The following filter option is not valid: option. Valid options include: [BeginsWith, Equals].",
|
2019-09-21 14:55:43 +00:00
|
|
|
)
|
2017-06-20 18:47:53 +00:00
|
|
|
|
2018-07-13 09:24:11 +00:00
|
|
|
|
2017-11-17 08:57:11 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_describe_parameters_attributes():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-11-17 08:57:11 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="aa", Value="11", Type="String", Description="my description"
|
2017-11-17 08:57:11 +00:00
|
|
|
)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
client.put_parameter(Name="bb", Value="22", Type="String")
|
2017-11-17 08:57:11 +00:00
|
|
|
|
|
|
|
response = client.describe_parameters()
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters = response["Parameters"]
|
2019-09-21 14:55:43 +00:00
|
|
|
parameters.should.have.length_of(2)
|
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[0]["Description"].should.equal("my description")
|
|
|
|
parameters[0]["Version"].should.equal(1)
|
|
|
|
parameters[0]["LastModifiedDate"].should.be.a(datetime.date)
|
|
|
|
parameters[0]["LastModifiedUser"].should.equal("N/A")
|
2017-11-17 08:57:11 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
parameters[1].should_not.have.key("Description")
|
|
|
|
parameters[1]["Version"].should.equal(1)
|
2017-06-26 18:20:56 +00:00
|
|
|
|
2018-07-13 09:24:11 +00:00
|
|
|
|
2017-08-16 10:49:03 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_get_parameter_invalid():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
response = client.get_parameters(Names=["invalid"], WithDecryption=False)
|
2017-08-16 10:49:03 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
len(response["Parameters"]).should.equal(0)
|
|
|
|
len(response["InvalidParameters"]).should.equal(1)
|
|
|
|
response["InvalidParameters"][0].should.equal("invalid")
|
2017-08-16 10:49:03 +00:00
|
|
|
|
|
|
|
|
2017-04-18 17:09:10 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_put_parameter_secure_default_kms():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-04-18 17:09:10 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="test", Description="A test parameter", Value="value", Type="SecureString"
|
|
|
|
)
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters(Names=["test"], WithDecryption=False)
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
response["Parameters"][0]["Name"].should.equal("test")
|
|
|
|
response["Parameters"][0]["Value"].should.equal("kms:alias/aws/ssm:value")
|
|
|
|
response["Parameters"][0]["Type"].should.equal("SecureString")
|
|
|
|
|
|
|
|
response = client.get_parameters(Names=["test"], WithDecryption=True)
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
response["Parameters"][0]["Name"].should.equal("test")
|
|
|
|
response["Parameters"][0]["Value"].should.equal("value")
|
|
|
|
response["Parameters"][0]["Type"].should.equal("SecureString")
|
2017-04-18 17:09:10 +00:00
|
|
|
|
|
|
|
|
|
|
|
@mock_ssm
|
|
|
|
def test_put_parameter_secure_custom_kms():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-04-18 17:09:10 +00:00
|
|
|
|
|
|
|
client.put_parameter(
|
2019-10-31 15:44:26 +00:00
|
|
|
Name="test",
|
|
|
|
Description="A test parameter",
|
|
|
|
Value="value",
|
|
|
|
Type="SecureString",
|
|
|
|
KeyId="foo",
|
|
|
|
)
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters(Names=["test"], WithDecryption=False)
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
response["Parameters"][0]["Name"].should.equal("test")
|
|
|
|
response["Parameters"][0]["Value"].should.equal("kms:foo:value")
|
|
|
|
response["Parameters"][0]["Type"].should.equal("SecureString")
|
2017-04-18 17:09:10 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.get_parameters(Names=["test"], WithDecryption=True)
|
|
|
|
|
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
response["Parameters"][0]["Name"].should.equal("test")
|
|
|
|
response["Parameters"][0]["Value"].should.equal("value")
|
|
|
|
response["Parameters"][0]["Type"].should.equal("SecureString")
|
2017-07-26 11:38:12 +00:00
|
|
|
|
2019-11-04 18:04:10 +00:00
|
|
|
|
2019-11-04 17:49:09 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_get_parameter_history():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
|
|
|
|
|
|
|
for i in range(3):
|
|
|
|
client.put_parameter(
|
2019-11-04 18:04:10 +00:00
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter version %d" % i,
|
|
|
|
Value="value-%d" % i,
|
|
|
|
Type="String",
|
|
|
|
Overwrite=True,
|
2019-11-04 17:49:09 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
response = client.get_parameter_history(Name=test_parameter_name)
|
2019-11-04 18:04:10 +00:00
|
|
|
parameters_response = response["Parameters"]
|
2019-11-04 17:49:09 +00:00
|
|
|
|
|
|
|
for index, param in enumerate(parameters_response):
|
2019-11-04 18:04:10 +00:00
|
|
|
param["Name"].should.equal(test_parameter_name)
|
|
|
|
param["Type"].should.equal("String")
|
|
|
|
param["Value"].should.equal("value-%d" % index)
|
|
|
|
param["Version"].should.equal(index + 1)
|
|
|
|
param["Description"].should.equal("A test parameter version %d" % index)
|
2020-03-09 00:32:01 +00:00
|
|
|
param["Labels"].should.equal([])
|
2019-11-04 17:49:09 +00:00
|
|
|
|
|
|
|
len(parameters_response).should.equal(3)
|
|
|
|
|
2019-11-04 18:04:10 +00:00
|
|
|
|
2019-11-04 17:49:09 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_get_parameter_history_with_secure_string():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
|
|
|
|
|
|
|
for i in range(3):
|
|
|
|
client.put_parameter(
|
2019-11-04 18:04:10 +00:00
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter version %d" % i,
|
|
|
|
Value="value-%d" % i,
|
|
|
|
Type="SecureString",
|
|
|
|
Overwrite=True,
|
2019-11-04 17:49:09 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
for with_decryption in [True, False]:
|
2019-11-04 18:04:10 +00:00
|
|
|
response = client.get_parameter_history(
|
|
|
|
Name=test_parameter_name, WithDecryption=with_decryption
|
|
|
|
)
|
|
|
|
parameters_response = response["Parameters"]
|
2019-11-04 17:49:09 +00:00
|
|
|
|
|
|
|
for index, param in enumerate(parameters_response):
|
2019-11-04 18:04:10 +00:00
|
|
|
param["Name"].should.equal(test_parameter_name)
|
|
|
|
param["Type"].should.equal("SecureString")
|
|
|
|
expected_plaintext_value = "value-%d" % index
|
2019-11-04 17:49:09 +00:00
|
|
|
if with_decryption:
|
2019-11-04 18:04:10 +00:00
|
|
|
param["Value"].should.equal(expected_plaintext_value)
|
2019-11-04 17:49:09 +00:00
|
|
|
else:
|
2019-11-04 18:04:10 +00:00
|
|
|
param["Value"].should.equal(
|
|
|
|
"kms:alias/aws/ssm:%s" % expected_plaintext_value
|
|
|
|
)
|
|
|
|
param["Version"].should.equal(index + 1)
|
|
|
|
param["Description"].should.equal("A test parameter version %d" % index)
|
2019-11-04 17:49:09 +00:00
|
|
|
|
|
|
|
len(parameters_response).should.equal(3)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_label_parameter_version():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
2020-03-11 15:57:04 +00:00
|
|
|
client.put_parameter(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter",
|
|
|
|
Value="value",
|
|
|
|
Type="String",
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
response = client.label_parameter_version(
|
|
|
|
Name=test_parameter_name, Labels=["test-label"]
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
response["InvalidLabels"].should.equal([])
|
|
|
|
response["ParameterVersion"].should.equal(1)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_label_parameter_version_with_specific_version():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
2020-03-11 15:57:04 +00:00
|
|
|
client.put_parameter(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter",
|
|
|
|
Value="value",
|
|
|
|
Type="String",
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
response = client.label_parameter_version(
|
|
|
|
Name=test_parameter_name, ParameterVersion=1, Labels=["test-label"]
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
response["InvalidLabels"].should.equal([])
|
|
|
|
response["ParameterVersion"].should.equal(1)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_label_parameter_version_twice():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
|
|
|
test_labels = ["test-label"]
|
2020-03-11 15:57:04 +00:00
|
|
|
client.put_parameter(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter",
|
|
|
|
Value="value",
|
|
|
|
Type="String",
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
response = client.label_parameter_version(
|
|
|
|
Name=test_parameter_name, ParameterVersion=1, Labels=test_labels
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
response["InvalidLabels"].should.equal([])
|
|
|
|
response["ParameterVersion"].should.equal(1)
|
2020-03-11 15:57:04 +00:00
|
|
|
response = client.label_parameter_version(
|
|
|
|
Name=test_parameter_name, ParameterVersion=1, Labels=test_labels
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
response["InvalidLabels"].should.equal([])
|
|
|
|
response["ParameterVersion"].should.equal(1)
|
|
|
|
|
|
|
|
response = client.get_parameter_history(Name=test_parameter_name)
|
|
|
|
len(response["Parameters"]).should.equal(1)
|
|
|
|
response["Parameters"][0]["Labels"].should.equal(test_labels)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_label_parameter_moving_versions():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
|
|
|
test_labels = ["test-label"]
|
|
|
|
|
|
|
|
for i in range(3):
|
|
|
|
client.put_parameter(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter version %d" % i,
|
|
|
|
Value="value-%d" % i,
|
|
|
|
Type="String",
|
2020-03-11 15:57:04 +00:00
|
|
|
Overwrite=True,
|
2020-03-09 00:32:01 +00:00
|
|
|
)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
response = client.label_parameter_version(
|
|
|
|
Name=test_parameter_name, ParameterVersion=1, Labels=test_labels
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
response["InvalidLabels"].should.equal([])
|
|
|
|
response["ParameterVersion"].should.equal(1)
|
2020-03-11 15:57:04 +00:00
|
|
|
response = client.label_parameter_version(
|
|
|
|
Name=test_parameter_name, ParameterVersion=2, Labels=test_labels
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
response["InvalidLabels"].should.equal([])
|
|
|
|
response["ParameterVersion"].should.equal(2)
|
|
|
|
|
|
|
|
response = client.get_parameter_history(Name=test_parameter_name)
|
|
|
|
parameters_response = response["Parameters"]
|
|
|
|
|
|
|
|
for index, param in enumerate(parameters_response):
|
|
|
|
param["Name"].should.equal(test_parameter_name)
|
|
|
|
param["Type"].should.equal("String")
|
|
|
|
param["Value"].should.equal("value-%d" % index)
|
|
|
|
param["Version"].should.equal(index + 1)
|
|
|
|
param["Description"].should.equal("A test parameter version %d" % index)
|
|
|
|
labels = test_labels if param["Version"] == 2 else []
|
|
|
|
param["Labels"].should.equal(labels)
|
|
|
|
|
|
|
|
len(parameters_response).should.equal(3)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_label_parameter_moving_versions_complex():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
|
|
|
|
|
|
|
for i in range(3):
|
|
|
|
client.put_parameter(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter version %d" % i,
|
|
|
|
Value="value-%d" % i,
|
|
|
|
Type="String",
|
2020-03-11 15:57:04 +00:00
|
|
|
Overwrite=True,
|
2020-03-09 00:32:01 +00:00
|
|
|
)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
response = client.label_parameter_version(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
ParameterVersion=1,
|
|
|
|
Labels=["test-label1", "test-label2", "test-label3"],
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
response["InvalidLabels"].should.equal([])
|
|
|
|
response["ParameterVersion"].should.equal(1)
|
2020-03-11 15:57:04 +00:00
|
|
|
response = client.label_parameter_version(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
ParameterVersion=2,
|
|
|
|
Labels=["test-label2", "test-label3"],
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
response["InvalidLabels"].should.equal([])
|
|
|
|
response["ParameterVersion"].should.equal(2)
|
|
|
|
|
|
|
|
response = client.get_parameter_history(Name=test_parameter_name)
|
|
|
|
parameters_response = response["Parameters"]
|
|
|
|
|
|
|
|
for index, param in enumerate(parameters_response):
|
|
|
|
param["Name"].should.equal(test_parameter_name)
|
|
|
|
param["Type"].should.equal("String")
|
|
|
|
param["Value"].should.equal("value-%d" % index)
|
|
|
|
param["Version"].should.equal(index + 1)
|
|
|
|
param["Description"].should.equal("A test parameter version %d" % index)
|
2020-03-11 15:57:04 +00:00
|
|
|
labels = (
|
|
|
|
["test-label2", "test-label3"]
|
|
|
|
if param["Version"] == 2
|
|
|
|
else (["test-label1"] if param["Version"] == 1 else [])
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
param["Labels"].should.equal(labels)
|
|
|
|
|
|
|
|
len(parameters_response).should.equal(3)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_label_parameter_version_exception_ten_labels_at_once():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
2020-03-11 15:57:04 +00:00
|
|
|
test_labels = [
|
|
|
|
"test-label1",
|
|
|
|
"test-label2",
|
|
|
|
"test-label3",
|
|
|
|
"test-label4",
|
|
|
|
"test-label5",
|
|
|
|
"test-label6",
|
|
|
|
"test-label7",
|
|
|
|
"test-label8",
|
|
|
|
"test-label9",
|
|
|
|
"test-label10",
|
|
|
|
"test-label11",
|
|
|
|
]
|
2020-03-09 00:32:01 +00:00
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
client.put_parameter(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter",
|
|
|
|
Value="value",
|
|
|
|
Type="String",
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
client.label_parameter_version.when.called_with(
|
|
|
|
Name="test", ParameterVersion=1, Labels=test_labels
|
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
"An error occurred (ParameterVersionLabelLimitExceeded) when calling the LabelParameterVersion operation: "
|
|
|
|
"A parameter version can have maximum 10 labels."
|
2020-03-11 15:57:04 +00:00
|
|
|
"Move one or more labels to another version and try again.",
|
2020-03-09 00:32:01 +00:00
|
|
|
)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_label_parameter_version_exception_ten_labels_over_multiple_calls():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
client.put_parameter(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter",
|
|
|
|
Value="value",
|
|
|
|
Type="String",
|
|
|
|
)
|
|
|
|
client.label_parameter_version(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
ParameterVersion=1,
|
|
|
|
Labels=[
|
|
|
|
"test-label1",
|
|
|
|
"test-label2",
|
|
|
|
"test-label3",
|
|
|
|
"test-label4",
|
|
|
|
"test-label5",
|
|
|
|
],
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
client.label_parameter_version.when.called_with(
|
2020-03-11 15:57:04 +00:00
|
|
|
Name="test",
|
|
|
|
ParameterVersion=1,
|
|
|
|
Labels=[
|
|
|
|
"test-label6",
|
|
|
|
"test-label7",
|
|
|
|
"test-label8",
|
|
|
|
"test-label9",
|
|
|
|
"test-label10",
|
|
|
|
"test-label11",
|
|
|
|
],
|
2020-03-09 00:32:01 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
"An error occurred (ParameterVersionLabelLimitExceeded) when calling the LabelParameterVersion operation: "
|
|
|
|
"A parameter version can have maximum 10 labels."
|
2020-03-11 15:57:04 +00:00
|
|
|
"Move one or more labels to another version and try again.",
|
2020-03-09 00:32:01 +00:00
|
|
|
)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_label_parameter_version_invalid_name():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
|
|
|
|
|
|
|
response = client.label_parameter_version.when.called_with(
|
|
|
|
Name=test_parameter_name, Labels=["test-label"]
|
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
"An error occurred (ParameterNotFound) when calling the LabelParameterVersion operation: "
|
2020-03-11 15:57:04 +00:00
|
|
|
"Parameter test not found.",
|
2020-03-09 00:32:01 +00:00
|
|
|
)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_label_parameter_version_invalid_parameter_version():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
2020-03-11 15:57:04 +00:00
|
|
|
client.put_parameter(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter",
|
|
|
|
Value="value",
|
|
|
|
Type="String",
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
|
|
|
|
response = client.label_parameter_version.when.called_with(
|
|
|
|
Name=test_parameter_name, Labels=["test-label"], ParameterVersion=5
|
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
"An error occurred (ParameterVersionNotFound) when calling the LabelParameterVersion operation: "
|
|
|
|
"Systems Manager could not find version 5 of test. "
|
2020-03-11 15:57:04 +00:00
|
|
|
"Verify the version and try again.",
|
2020-03-09 00:32:01 +00:00
|
|
|
)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_label_parameter_version_invalid_label():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
2020-03-11 15:57:04 +00:00
|
|
|
client.put_parameter(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter",
|
|
|
|
Value="value",
|
|
|
|
Type="String",
|
|
|
|
)
|
|
|
|
response = client.label_parameter_version(
|
|
|
|
Name=test_parameter_name, ParameterVersion=1, Labels=["awsabc"]
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
response["InvalidLabels"].should.equal(["awsabc"])
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
response = client.label_parameter_version(
|
|
|
|
Name=test_parameter_name, ParameterVersion=1, Labels=["ssmabc"]
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
response["InvalidLabels"].should.equal(["ssmabc"])
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
response = client.label_parameter_version(
|
|
|
|
Name=test_parameter_name, ParameterVersion=1, Labels=["9abc"]
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
response["InvalidLabels"].should.equal(["9abc"])
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
response = client.label_parameter_version(
|
|
|
|
Name=test_parameter_name, ParameterVersion=1, Labels=["abc/123"]
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
response["InvalidLabels"].should.equal(["abc/123"])
|
|
|
|
|
|
|
|
client.label_parameter_version.when.called_with(
|
2020-03-11 15:57:04 +00:00
|
|
|
Name=test_parameter_name, ParameterVersion=1, Labels=["a" * 101]
|
2020-03-09 00:32:01 +00:00
|
|
|
).should.throw(
|
|
|
|
ClientError,
|
|
|
|
"1 validation error detected: "
|
|
|
|
"Value '[%s]' at 'labels' failed to satisfy constraint: "
|
|
|
|
"Member must satisfy constraint: "
|
2020-03-11 15:57:04 +00:00
|
|
|
"[Member must have length less than or equal to 100, Member must have length greater than or equal to 1]"
|
|
|
|
% ("a" * 101),
|
2020-03-09 00:32:01 +00:00
|
|
|
)
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
|
|
|
|
@mock_ssm
|
|
|
|
def test_get_parameter_history_with_label():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
|
|
|
test_labels = ["test-label"]
|
|
|
|
|
|
|
|
for i in range(3):
|
|
|
|
client.put_parameter(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter version %d" % i,
|
|
|
|
Value="value-%d" % i,
|
|
|
|
Type="String",
|
|
|
|
Overwrite=True,
|
|
|
|
)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
client.label_parameter_version(
|
|
|
|
Name=test_parameter_name, ParameterVersion=1, Labels=test_labels
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
|
|
|
|
response = client.get_parameter_history(Name=test_parameter_name)
|
|
|
|
parameters_response = response["Parameters"]
|
|
|
|
|
|
|
|
for index, param in enumerate(parameters_response):
|
|
|
|
param["Name"].should.equal(test_parameter_name)
|
|
|
|
param["Type"].should.equal("String")
|
|
|
|
param["Value"].should.equal("value-%d" % index)
|
|
|
|
param["Version"].should.equal(index + 1)
|
|
|
|
param["Description"].should.equal("A test parameter version %d" % index)
|
|
|
|
labels = test_labels if param["Version"] == 1 else []
|
|
|
|
param["Labels"].should.equal(labels)
|
|
|
|
|
|
|
|
len(parameters_response).should.equal(3)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_get_parameter_history_with_label_non_latest():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
|
|
|
test_labels = ["test-label"]
|
|
|
|
|
|
|
|
for i in range(3):
|
|
|
|
client.put_parameter(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter version %d" % i,
|
|
|
|
Value="value-%d" % i,
|
|
|
|
Type="String",
|
|
|
|
Overwrite=True,
|
|
|
|
)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
client.label_parameter_version(
|
|
|
|
Name=test_parameter_name, ParameterVersion=2, Labels=test_labels
|
|
|
|
)
|
2020-03-09 00:32:01 +00:00
|
|
|
|
|
|
|
response = client.get_parameter_history(Name=test_parameter_name)
|
|
|
|
parameters_response = response["Parameters"]
|
|
|
|
|
|
|
|
for index, param in enumerate(parameters_response):
|
|
|
|
param["Name"].should.equal(test_parameter_name)
|
|
|
|
param["Type"].should.equal("String")
|
|
|
|
param["Value"].should.equal("value-%d" % index)
|
|
|
|
param["Version"].should.equal(index + 1)
|
|
|
|
param["Description"].should.equal("A test parameter version %d" % index)
|
|
|
|
labels = test_labels if param["Version"] == 2 else []
|
|
|
|
param["Labels"].should.equal(labels)
|
|
|
|
|
|
|
|
len(parameters_response).should.equal(3)
|
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2020-03-09 00:32:01 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_get_parameter_history_with_label_latest_assumed():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
test_parameter_name = "test"
|
|
|
|
test_labels = ["test-label"]
|
|
|
|
|
|
|
|
for i in range(3):
|
|
|
|
client.put_parameter(
|
|
|
|
Name=test_parameter_name,
|
|
|
|
Description="A test parameter version %d" % i,
|
|
|
|
Value="value-%d" % i,
|
|
|
|
Type="String",
|
|
|
|
Overwrite=True,
|
|
|
|
)
|
|
|
|
|
|
|
|
client.label_parameter_version(Name=test_parameter_name, Labels=test_labels)
|
|
|
|
|
|
|
|
response = client.get_parameter_history(Name=test_parameter_name)
|
|
|
|
parameters_response = response["Parameters"]
|
|
|
|
|
|
|
|
for index, param in enumerate(parameters_response):
|
|
|
|
param["Name"].should.equal(test_parameter_name)
|
|
|
|
param["Type"].should.equal("String")
|
|
|
|
param["Value"].should.equal("value-%d" % index)
|
|
|
|
param["Version"].should.equal(index + 1)
|
|
|
|
param["Description"].should.equal("A test parameter version %d" % index)
|
|
|
|
labels = test_labels if param["Version"] == 3 else []
|
|
|
|
param["Labels"].should.equal(labels)
|
|
|
|
|
|
|
|
len(parameters_response).should.equal(3)
|
2019-11-04 17:49:09 +00:00
|
|
|
|
2020-03-11 15:57:04 +00:00
|
|
|
|
2019-11-04 20:30:30 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_get_parameter_history_missing_parameter():
|
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
|
|
|
|
try:
|
|
|
|
client.get_parameter_history(Name="test_noexist")
|
|
|
|
raise RuntimeError("Should have failed")
|
|
|
|
except botocore.exceptions.ClientError as err:
|
|
|
|
err.operation_name.should.equal("GetParameterHistory")
|
|
|
|
err.response["Error"]["Message"].should.equal(
|
|
|
|
"Parameter test_noexist not found."
|
|
|
|
)
|
|
|
|
|
|
|
|
|
2017-07-26 11:38:12 +00:00
|
|
|
@mock_ssm
|
|
|
|
def test_add_remove_list_tags_for_resource():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2017-07-26 11:38:12 +00:00
|
|
|
|
|
|
|
client.add_tags_to_resource(
|
2019-10-31 15:44:26 +00:00
|
|
|
ResourceId="test",
|
|
|
|
ResourceType="Parameter",
|
|
|
|
Tags=[{"Key": "test-key", "Value": "test-value"}],
|
2017-07-26 11:38:12 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
response = client.list_tags_for_resource(
|
2019-10-31 15:44:26 +00:00
|
|
|
ResourceId="test", ResourceType="Parameter"
|
2017-07-26 11:38:12 +00:00
|
|
|
)
|
2019-10-31 15:44:26 +00:00
|
|
|
len(response["TagList"]).should.equal(1)
|
|
|
|
response["TagList"][0]["Key"].should.equal("test-key")
|
|
|
|
response["TagList"][0]["Value"].should.equal("test-value")
|
2017-07-26 11:38:12 +00:00
|
|
|
|
|
|
|
client.remove_tags_from_resource(
|
2019-10-31 15:44:26 +00:00
|
|
|
ResourceId="test", ResourceType="Parameter", TagKeys=["test-key"]
|
2017-07-26 11:38:12 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
response = client.list_tags_for_resource(
|
2019-10-31 15:44:26 +00:00
|
|
|
ResourceId="test", ResourceType="Parameter"
|
2017-07-26 11:38:12 +00:00
|
|
|
)
|
2019-10-31 15:44:26 +00:00
|
|
|
len(response["TagList"]).should.equal(0)
|
2018-02-19 15:10:52 +00:00
|
|
|
|
|
|
|
|
|
|
|
@mock_ssm
|
|
|
|
def test_send_command():
|
2019-10-31 15:44:26 +00:00
|
|
|
ssm_document = "AWS-RunShellScript"
|
|
|
|
params = {"commands": ["#!/bin/bash\necho 'hello world'"]}
|
2018-02-19 15:10:52 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2018-02-19 15:59:52 +00:00
|
|
|
# note the timeout is determined server side, so this is a simpler check.
|
2018-02-19 15:58:46 +00:00
|
|
|
before = datetime.datetime.now()
|
2018-02-19 15:59:52 +00:00
|
|
|
|
2018-02-19 15:10:52 +00:00
|
|
|
response = client.send_command(
|
2019-10-31 15:44:26 +00:00
|
|
|
InstanceIds=["i-123456"],
|
2018-02-19 15:10:52 +00:00
|
|
|
DocumentName=ssm_document,
|
2018-02-19 15:58:46 +00:00
|
|
|
Parameters=params,
|
2019-10-31 15:44:26 +00:00
|
|
|
OutputS3Region="us-east-2",
|
|
|
|
OutputS3BucketName="the-bucket",
|
|
|
|
OutputS3KeyPrefix="pref",
|
2018-02-19 15:10:52 +00:00
|
|
|
)
|
2019-10-31 15:44:26 +00:00
|
|
|
cmd = response["Command"]
|
2018-02-19 15:10:52 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
cmd["CommandId"].should_not.be(None)
|
|
|
|
cmd["DocumentName"].should.equal(ssm_document)
|
|
|
|
cmd["Parameters"].should.equal(params)
|
2018-02-19 15:58:46 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
cmd["OutputS3Region"].should.equal("us-east-2")
|
|
|
|
cmd["OutputS3BucketName"].should.equal("the-bucket")
|
|
|
|
cmd["OutputS3KeyPrefix"].should.equal("pref")
|
2018-02-19 15:58:46 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
cmd["ExpiresAfter"].should.be.greater_than(before)
|
2018-04-25 20:27:07 +00:00
|
|
|
|
|
|
|
# test sending a command without any optional parameters
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.send_command(DocumentName=ssm_document)
|
2018-04-25 20:27:07 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
cmd = response["Command"]
|
2018-04-25 20:27:07 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
cmd["CommandId"].should_not.be(None)
|
|
|
|
cmd["DocumentName"].should.equal(ssm_document)
|
2018-04-25 20:27:07 +00:00
|
|
|
|
|
|
|
|
|
|
|
@mock_ssm
|
|
|
|
def test_list_commands():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2018-04-25 20:27:07 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
ssm_document = "AWS-RunShellScript"
|
|
|
|
params = {"commands": ["#!/bin/bash\necho 'hello world'"]}
|
2018-04-25 20:27:07 +00:00
|
|
|
|
|
|
|
response = client.send_command(
|
2019-10-31 15:44:26 +00:00
|
|
|
InstanceIds=["i-123456"],
|
2018-04-25 20:27:07 +00:00
|
|
|
DocumentName=ssm_document,
|
|
|
|
Parameters=params,
|
2019-10-31 15:44:26 +00:00
|
|
|
OutputS3Region="us-east-2",
|
|
|
|
OutputS3BucketName="the-bucket",
|
|
|
|
OutputS3KeyPrefix="pref",
|
|
|
|
)
|
2018-04-25 20:27:07 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
cmd = response["Command"]
|
|
|
|
cmd_id = cmd["CommandId"]
|
2018-04-25 20:27:07 +00:00
|
|
|
|
|
|
|
# get the command by id
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.list_commands(CommandId=cmd_id)
|
2018-04-25 20:27:07 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
cmds = response["Commands"]
|
2018-04-25 20:27:07 +00:00
|
|
|
len(cmds).should.equal(1)
|
2019-10-31 15:44:26 +00:00
|
|
|
cmds[0]["CommandId"].should.equal(cmd_id)
|
2018-04-25 20:27:07 +00:00
|
|
|
|
|
|
|
# add another command with the same instance id to test listing by
|
|
|
|
# instance id
|
2019-10-31 15:44:26 +00:00
|
|
|
client.send_command(InstanceIds=["i-123456"], DocumentName=ssm_document)
|
2018-04-25 20:27:07 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.list_commands(InstanceId="i-123456")
|
2018-04-25 20:27:07 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
cmds = response["Commands"]
|
2018-04-25 20:27:07 +00:00
|
|
|
len(cmds).should.equal(2)
|
|
|
|
|
|
|
|
for cmd in cmds:
|
2019-10-31 15:44:26 +00:00
|
|
|
cmd["InstanceIds"].should.contain("i-123456")
|
2018-04-25 20:27:07 +00:00
|
|
|
|
|
|
|
# test the error case for an invalid command id
|
2020-10-06 05:54:49 +00:00
|
|
|
with pytest.raises(ClientError):
|
2019-10-31 15:44:26 +00:00
|
|
|
response = client.list_commands(CommandId=str(uuid.uuid4()))
|
|
|
|
|
2018-07-24 20:15:53 +00:00
|
|
|
|
|
|
|
@mock_ssm
|
|
|
|
def test_get_command_invocation():
|
2019-10-31 15:44:26 +00:00
|
|
|
client = boto3.client("ssm", region_name="us-east-1")
|
2018-07-24 20:15:53 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
ssm_document = "AWS-RunShellScript"
|
|
|
|
params = {"commands": ["#!/bin/bash\necho 'hello world'"]}
|
2018-07-24 20:15:53 +00:00
|
|
|
|
|
|
|
response = client.send_command(
|
2019-10-31 15:44:26 +00:00
|
|
|
InstanceIds=["i-123456", "i-234567", "i-345678"],
|
2018-07-24 20:15:53 +00:00
|
|
|
DocumentName=ssm_document,
|
|
|
|
Parameters=params,
|
2019-10-31 15:44:26 +00:00
|
|
|
OutputS3Region="us-east-2",
|
|
|
|
OutputS3BucketName="the-bucket",
|
|
|
|
OutputS3KeyPrefix="pref",
|
|
|
|
)
|
2018-07-24 20:15:53 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
cmd = response["Command"]
|
|
|
|
cmd_id = cmd["CommandId"]
|
2018-07-24 20:15:53 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
instance_id = "i-345678"
|
2018-07-24 20:15:53 +00:00
|
|
|
invocation_response = client.get_command_invocation(
|
2019-10-31 15:44:26 +00:00
|
|
|
CommandId=cmd_id, InstanceId=instance_id, PluginName="aws:runShellScript"
|
|
|
|
)
|
2018-07-24 20:15:53 +00:00
|
|
|
|
2019-10-31 15:44:26 +00:00
|
|
|
invocation_response["CommandId"].should.equal(cmd_id)
|
|
|
|
invocation_response["InstanceId"].should.equal(instance_id)
|
2018-07-24 20:15:53 +00:00
|
|
|
|
|
|
|
# test the error case for an invalid instance id
|
2020-10-06 05:54:49 +00:00
|
|
|
with pytest.raises(ClientError):
|
2018-07-24 20:15:53 +00:00
|
|
|
invocation_response = client.get_command_invocation(
|
2019-10-31 15:44:26 +00:00
|
|
|
CommandId=cmd_id, InstanceId="i-FAKE"
|
|
|
|
)
|
2018-07-24 20:15:53 +00:00
|
|
|
|
|
|
|
# test the error case for an invalid plugin name
|
2020-10-06 05:54:49 +00:00
|
|
|
with pytest.raises(ClientError):
|
2018-07-24 20:15:53 +00:00
|
|
|
invocation_response = client.get_command_invocation(
|
2019-10-31 15:44:26 +00:00
|
|
|
CommandId=cmd_id, InstanceId=instance_id, PluginName="FAKE"
|
|
|
|
)
|
2020-11-08 08:06:35 +00:00
|
|
|
|
|
|
|
|
|
|
|
@mock_ec2
|
|
|
|
@mock_ssm
|
|
|
|
def test_get_command_invocations_by_instance_tag():
|
|
|
|
ec2 = boto3.client("ec2", region_name="us-east-1")
|
|
|
|
ssm = boto3.client("ssm", region_name="us-east-1")
|
|
|
|
tag_specifications = [
|
|
|
|
{"ResourceType": "instance", "Tags": [{"Key": "Name", "Value": "test-tag"}]}
|
|
|
|
]
|
|
|
|
num_instances = 3
|
|
|
|
resp = ec2.run_instances(
|
|
|
|
ImageId="ami-1234abcd",
|
|
|
|
MaxCount=num_instances,
|
|
|
|
MinCount=num_instances,
|
|
|
|
TagSpecifications=tag_specifications,
|
|
|
|
)
|
|
|
|
instance_ids = []
|
|
|
|
for instance in resp["Instances"]:
|
|
|
|
instance_ids.append(instance["InstanceId"])
|
|
|
|
instance_ids.should.have.length_of(num_instances)
|
|
|
|
|
|
|
|
command_id = ssm.send_command(
|
|
|
|
DocumentName="AWS-RunShellScript",
|
|
|
|
Targets=[{"Key": "tag:Name", "Values": ["test-tag"]}],
|
|
|
|
)["Command"]["CommandId"]
|
|
|
|
|
|
|
|
resp = ssm.list_commands(CommandId=command_id)
|
|
|
|
resp["Commands"][0]["TargetCount"].should.equal(num_instances)
|
|
|
|
|
|
|
|
for instance_id in instance_ids:
|
|
|
|
resp = ssm.get_command_invocation(CommandId=command_id, InstanceId=instance_id)
|
|
|
|
resp["Status"].should.equal("Success")
|