class TestIntegerKey(TankTestBase): def setUp(self): super(TestIntegerKey, self).setUp() self.int_field = IntegerKey("field_name") def test_bad_default(self): """Case that specified default does not match type.""" default_value = "default_value" self.assertRaises(TankError, IntegerKey, "field_name", default=default_value) def test_illegal_choice(self): """Choice conflict with type.""" choices_value = ["a", "b"] self.assertRaises(TankError, IntegerKey, "field_name", choices=choices_value) def test_format_set(self): format_spec = "03" template_field = IntegerKey("field_name", format_spec=format_spec) self.assertEquals(format_spec, template_field.format_spec) def test_validate_string_good(self): value = "23" self.assertTrue(self.int_field.validate(value)) def test_validate_int_good(self): value = 23 self.assertTrue(self.int_field.validate(value)) def test_validate_bad(self): value = "a" self.assertFalse(self.int_field.validate(value)) def test_str_from_value_good(self): value = 3 expected = "%s" % value result = self.int_field.str_from_value(value) self.assertEquals(expected, result) def test_str_from_value_zero(self): value = 0 expected = "%d" % value result = self.int_field.str_from_value(value) self.assertEquals(expected, result) def test_str_from_value_bad(self): value = "a" expected = "%s Illegal value %s, expected an Integer" % (str( self.int_field), value) self.check_error_message(TankError, expected, self.int_field.str_from_value, value) def test_str_from_value_formatted(self): formatted_field = IntegerKey("field_name", format_spec="03") value = 3 expected = "%03d" % value result = formatted_field.str_from_value(value) self.assertEquals(expected, result) def test_str_from_value_ignore_type(self): value = "a" expected = value result = self.int_field.str_from_value(value, ignore_type=True) self.assertEquals(expected, result) def test_value_from_str(self): str_value = "32" self.assertEquals(32, self.int_field.value_from_str(str_value)) def test_repr(self): expected = "<Sgtk IntegerKey field_name>" self.assertEquals(expected, str(self.int_field))
class TestIntegerKey(TankTestBase): def setUp(self): super(TestIntegerKey, self).setUp() self.int_field = IntegerKey("field_name") def test_bad_default(self): """Case that specified default does not match type.""" default_value = "default_value" self.assertRaises(TankError, IntegerKey, "field_name", default=default_value) def test_illegal_choice(self): """Choice conflict with type.""" choices_value = ["a", "b"] self.assertRaises(TankError, IntegerKey, "field_name", choices=choices_value) def test_format_set(self): format_spec = "03" template_field = IntegerKey("field_name", format_spec=format_spec) self.assertEquals(format_spec, template_field.format_spec) def test_validate_string_good(self): value = "23" self.assertTrue(self.int_field.validate(value)) def test_validate_int_good(self): value = 23 self.assertTrue(self.int_field.validate(value)) def test_validate_bad(self): value = "a" self.assertFalse(self.int_field.validate(value)) def test_str_from_value_good(self): value = 3 expected = "%s" % value result = self.int_field.str_from_value(value) self.assertEquals(expected, result) def test_str_from_value_zero(self): value = 0 expected = "%d" % value result = self.int_field.str_from_value(value) self.assertEquals(expected, result) def test_str_from_value_bad(self): value = "a" expected = "%s Illegal value %s, expected an Integer" % (str(self.int_field), value) self.check_error_message(TankError, expected, self.int_field.str_from_value, value) def test_str_from_value_formatted(self): formatted_field = IntegerKey("field_name", format_spec="03") value = 3 expected = "%03d" % value result = formatted_field.str_from_value(value) self.assertEquals(expected, result) def test_str_from_value_ignore_type(self): value = "a" expected = value result = self.int_field.str_from_value(value, ignore_type=True) self.assertEquals(expected, result) def test_value_from_str(self): str_value = "32" self.assertEquals(32, self.int_field.value_from_str(str_value)) def test_repr(self): expected = "<Sgtk IntegerKey field_name>" self.assertEquals(expected, str(self.int_field))
class TestIntegerKey(ShotgunTestBase): def setUp(self): super(TestIntegerKey, self).setUp() self.int_field = IntegerKey("field_name") def test_bad_default(self): """Case that specified default does not match type.""" default_value = "default_value" self.assertRaises(TankError, IntegerKey, "field_name", default=default_value) def test_illegal_choice(self): """Choice conflict with type.""" choices_value = ["a", "b"] self.assertRaises(TankError, IntegerKey, "field_name", choices=choices_value) def test_format_set(self): format_spec = "03" template_field = IntegerKey("field_name", format_spec=format_spec) self.assertEqual(format_spec, template_field.format_spec) def test_validate_string_good(self): value = "23" self.assertTrue(self.int_field.validate(value)) def test_validate_int_good(self): value = 23 self.assertTrue(self.int_field.validate(value)) def test_validate_bad(self): value = "a" self.assertFalse(self.int_field.validate(value)) def test_str_from_value_good(self): value = 3 expected = "%s" % value result = self.int_field.str_from_value(value) self.assertEqual(expected, result) def test_str_from_value_zero(self): value = 0 expected = "%d" % value result = self.int_field.str_from_value(value) self.assertEqual(expected, result) def test_str_from_value_bad(self): value = "a" expected = "%s Illegal value '%s', expected an Integer" % ( str(self.int_field), value, ) self.check_error_message(TankError, expected, self.int_field.str_from_value, value) def test_str_from_value_formatted(self): formatted_field = IntegerKey("field_name", format_spec="03") value = 3 expected = "%03d" % value result = formatted_field.str_from_value(value) self.assertEqual(expected, result) def test_str_from_value_ignore_type(self): value = "a" expected = value result = self.int_field.str_from_value(value, ignore_type=True) self.assertEqual(expected, result) def test_value_from_str(self): str_value = "32" self.assertEqual(32, self.int_field.value_from_str(str_value)) def test_repr(self): expected = "<Sgtk IntegerKey field_name>" self.assertEqual(expected, str(self.int_field)) def test_init_validation(self): """ Makes sure that parameter validation is correct in the constructor. """ # This should obviously work self._validate_key(IntegerKey("version_number"), strict_matching=None, format_spec=None) # When specifying parameters, they should be set accordingly. self._validate_key( IntegerKey("version_number", format_spec="03", strict_matching=True), strict_matching=True, format_spec="03", ) self._validate_key( IntegerKey("version_number", format_spec="03", strict_matching=False), strict_matching=False, format_spec="03", ) self._validate_key( IntegerKey("version_number", format_spec="3", strict_matching=False), strict_matching=False, format_spec="3", ) # When specifying a format but not specifying the strict_matching, it should # still have strict_matching. self._validate_key( IntegerKey("version_number", format_spec="03"), strict_matching=True, format_spec="03", ) # Make sure than an error is raised when wrong types are passed in. with self.assertRaisesRegex(TankError, "is not of type boolean"): IntegerKey("version_number", strict_matching=1) with self.assertRaisesRegex(TankError, "is not of type string"): IntegerKey("version_number", format_spec=1) # Make sure that if the user specifies strict_matching with no format # there is an error error_regexp = "strict_matching can't be set" with self.assertRaisesRegex(TankError, error_regexp): IntegerKey("version_number", strict_matching=False) with self.assertRaisesRegex(TankError, error_regexp): IntegerKey("version_number", strict_matching=True) # We support 4 format_spec values: # - None # - non zero positive number # - zero followed by a non zero positive number IntegerKey("version_number", format_spec=None) IntegerKey("version_number", format_spec="1") IntegerKey("version_number", format_spec="01") # Make sure invalid formats are caught with self.assertRaisesRegex(TankError, "format_spec can't be empty"): IntegerKey("version_number", format_spec="") error_regexp = "has to either be" # We don't support the sign option. with self.assertRaisesRegex(TankError, error_regexp): IntegerKey("version_number", format_spec=" 3", strict_matching=False) with self.assertRaisesRegex(TankError, error_regexp): # Should throw because the padding number is not non zero. IntegerKey("version_number", format_spec="00") with self.assertRaisesRegex(TankError, error_regexp): # Should throw because it is not a non zero positive integer IntegerKey("version_number", format_spec="0") with self.assertRaisesRegex(TankError, error_regexp): # Should throw because the padding caracter is invalid IntegerKey("version_number", format_spec="a0") with self.assertRaisesRegex(TankError, error_regexp): # Should throw because the padding size is not a number. IntegerKey("version_number", format_spec="0a") def test_no_format_spec(self): key = IntegerKey("version_number") key.value_from_str def _validate_key(self, key, strict_matching, format_spec): """ Makes sure that an integer key's formatting options are correctly set. """ self.assertEqual(key.strict_matching, strict_matching) self.assertEqual(key.format_spec, format_spec) def test_non_strict_matching(self): """ In non strict mode, tokens can actually have less numbers than the padding requests. Also, if there are more, can also match. """ self._test_non_strict_matching("0") self._test_non_strict_matching("") def _test_non_strict_matching(self, padding_char): """ Allows to test strict matching with a specific padding character. :param padding_char: Character to test padding with. Should be space or 0. """ key = IntegerKey("version_number", format_spec="%s3" % padding_char, strict_matching=False) # The padding char is missing in the format specifier, but we still need when validating # results. if padding_char == "": padding_char = " " # It should match because they are valid numbers. self.assertEqual(key.value_from_str("000"), 0) self.assertEqual(key.value_from_str("0"), 0) self.assertEqual(key.value_from_str("0"), 0) # While the number doesn't make any sense as far as formatting is concerned, this used # to work in old versions of Toolkit and needs to keep working in non strict mode. self.assertEqual(key.value_from_str("%s000" % padding_char), 0) # It should match a template with too many digits... self.assertEqual(key.value_from_str("20000"), 20000) # ... even if they are all zeros because lossy matching. self.assertEqual(key.value_from_str("00000"), 0) # From path to tokens back to path should be lossy. value = key.value_from_str("1") self.assertEqual("%s%s1" % (padding_char, padding_char), key.str_from_value(value)) self._test_nan(key, "expected an Integer") def _test_nan(self, key, error_msg): """ Tests a key with against values that are not numbers. :param key: Key to test. :param error_msg: Text that partially matches the error message. """ # Should fail because not a number with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("aaaa") with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("0a") with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("a0") with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("aa") def _test_strict_matching(self, padding_char): """ Allows to test strict matching with any padding type. """ # have a template that formats with two digits of padding. key = IntegerKey("version_number", format_spec="%s3" % padding_char, strict_matching=True) self.assertTrue(key.strict_matching) # The padding char is missing in the format specifier, but we still need when validating # results. if padding_char == "": padding_char = " " # From path to tokens back to path should get back the same string when the expected number of # digits are found. value = key.value_from_str("%s%s1" % (padding_char, padding_char)) self.assertEqual("%s%s1" % (padding_char, padding_char), key.str_from_value(value)) # It should match a template with more digits. value = key.value_from_str("20000") self.assertEqual("20000", key.str_from_value(value)) key.value_from_str("123") error_msg = "does not match format spec" # It should not match a string with too few digits with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("1") # It should not match a template with too many digits that are all zero because that would # lossy. (there are more zeros than the format spec can rebuild) with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("0000") # It should not match negative numbers either with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("-1000") # It should not match baddly padded numbers with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("0100") # It should not match negative values with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("-01") self._test_nan(key, error_msg) def test_strict_matching(self): """ In strict mode, tokens have to have as much padding as the format specifier suggests. Less will not match. """ self._test_strict_matching("") self._test_strict_matching("0")
class TestIntegerKey(ShotgunTestBase): def setUp(self): super(TestIntegerKey, self).setUp() self.int_field = IntegerKey("field_name") def test_bad_default(self): """Case that specified default does not match type.""" default_value = "default_value" self.assertRaises(TankError, IntegerKey, "field_name", default=default_value) def test_illegal_choice(self): """Choice conflict with type.""" choices_value = ["a", "b"] self.assertRaises(TankError, IntegerKey, "field_name", choices=choices_value) def test_format_set(self): format_spec = "03" template_field = IntegerKey("field_name", format_spec=format_spec) self.assertEqual(format_spec, template_field.format_spec) def test_validate_string_good(self): value = "23" self.assertTrue(self.int_field.validate(value)) def test_validate_int_good(self): value = 23 self.assertTrue(self.int_field.validate(value)) def test_validate_bad(self): value = "a" self.assertFalse(self.int_field.validate(value)) def test_str_from_value_good(self): value = 3 expected = "%s" % value result = self.int_field.str_from_value(value) self.assertEqual(expected, result) def test_str_from_value_zero(self): value = 0 expected = "%d" % value result = self.int_field.str_from_value(value) self.assertEqual(expected, result) def test_str_from_value_bad(self): value = "a" expected = "%s Illegal value '%s', expected an Integer" % (str(self.int_field), value) self.check_error_message(TankError, expected, self.int_field.str_from_value, value) def test_str_from_value_formatted(self): formatted_field = IntegerKey("field_name", format_spec="03") value = 3 expected = "%03d" % value result = formatted_field.str_from_value(value) self.assertEqual(expected, result) def test_str_from_value_ignore_type(self): value = "a" expected = value result = self.int_field.str_from_value(value, ignore_type=True) self.assertEqual(expected, result) def test_value_from_str(self): str_value = "32" self.assertEqual(32, self.int_field.value_from_str(str_value)) def test_repr(self): expected = "<Sgtk IntegerKey field_name>" self.assertEqual(expected, str(self.int_field)) def test_init_validation(self): """ Makes sure that parameter validation is correct in the constructor. """ # This should obviously work self._validate_key( IntegerKey("version_number"), strict_matching=None, format_spec=None ) # When specifying parameters, they should be set accordingly. self._validate_key( IntegerKey("version_number", format_spec="03", strict_matching=True), strict_matching=True, format_spec="03" ) self._validate_key( IntegerKey("version_number", format_spec="03", strict_matching=False), strict_matching=False, format_spec="03" ) self._validate_key( IntegerKey("version_number", format_spec="3", strict_matching=False), strict_matching=False, format_spec="3" ) # When specifying a format but not specifying the strict_matching, it should # still have strict_matching. self._validate_key( IntegerKey("version_number", format_spec="03"), strict_matching=True, format_spec="03" ) # Make sure than an error is raised when wrong types are passed in. with self.assertRaisesRegex(TankError, "is not of type boolean"): IntegerKey("version_number", strict_matching=1) with self.assertRaisesRegex(TankError, "is not of type string"): IntegerKey("version_number", format_spec=1) # Make sure that if the user specifies strict_matching with no format # there is an error error_regexp = "strict_matching can't be set" with self.assertRaisesRegex(TankError, error_regexp): IntegerKey("version_number", strict_matching=False) with self.assertRaisesRegex(TankError, error_regexp): IntegerKey("version_number", strict_matching=True) # We support 4 format_spec values: # - None # - non zero positive number # - zero followed by a non zero positive number IntegerKey("version_number", format_spec=None) IntegerKey("version_number", format_spec="1") IntegerKey("version_number", format_spec="01") # Make sure invalid formats are caught with self.assertRaisesRegex(TankError, "format_spec can't be empty"): IntegerKey("version_number", format_spec="") error_regexp = "has to either be" # We don't support the sign option. with self.assertRaisesRegex(TankError, error_regexp): IntegerKey("version_number", format_spec=" 3", strict_matching=False) with self.assertRaisesRegex(TankError, error_regexp): # Should throw because the padding number is not non zero. IntegerKey("version_number", format_spec="00") with self.assertRaisesRegex(TankError, error_regexp): # Should throw because it is not a non zero positive integer IntegerKey("version_number", format_spec="0") with self.assertRaisesRegex(TankError, error_regexp): # Should throw because the padding caracter is invalid IntegerKey("version_number", format_spec="a0") with self.assertRaisesRegex(TankError, error_regexp): # Should throw because the padding size is not a number. IntegerKey("version_number", format_spec="0a") def test_no_format_spec(self): key = IntegerKey("version_number") key.value_from_str def _validate_key(self, key, strict_matching, format_spec): """ Makes sure that an integer key's formatting options are correctly set. """ self.assertEqual(key.strict_matching, strict_matching) self.assertEqual(key.format_spec, format_spec) def test_non_strict_matching(self): """ In non strict mode, tokens can actually have less numbers than the padding requests. Also, if there are more, can also match. """ self._test_non_strict_matching('0') self._test_non_strict_matching('') def _test_non_strict_matching(self, padding_char): """ Allows to test strict matching with a specific padding character. :param padding_char: Character to test padding with. Should be space or 0. """ key = IntegerKey("version_number", format_spec="%s3" % padding_char, strict_matching=False) # The padding char is missing in the format specifier, but we still need when validating # results. if padding_char == '': padding_char = ' ' # It should match because they are valid numbers. self.assertEqual(key.value_from_str("000"), 0) self.assertEqual(key.value_from_str("0"), 0) self.assertEqual(key.value_from_str("0"), 0) # While the number doesn't make any sense as far as formatting is concerned, this used # to work in old versions of Toolkit and needs to keep working in non strict mode. self.assertEqual(key.value_from_str("%s000" % padding_char), 0) # It should match a template with too many digits... self.assertEqual(key.value_from_str("20000"), 20000) # ... even if they are all zeros because lossy matching. self.assertEqual(key.value_from_str("00000"), 0) # From path to tokens back to path should be lossy. value = key.value_from_str("1") self.assertEqual("%s%s1" % (padding_char, padding_char), key.str_from_value(value)) self._test_nan(key, "expected an Integer") def _test_nan(self, key, error_msg): """ Tests a key with against values that are not numbers. :param key: Key to test. :param error_msg: Text that partially matches the error message. """ # Should fail because not a number with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("aaaa") with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("0a") with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("a0") with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("aa") def _test_strict_matching(self, padding_char): """ Allows to test strict matching with any padding type. """ # have a template that formats with two digits of padding. key = IntegerKey("version_number", format_spec="%s3" % padding_char, strict_matching=True) self.assertTrue(key.strict_matching) # The padding char is missing in the format specifier, but we still need when validating # results. if padding_char == '': padding_char = ' ' # From path to tokens back to path should get back the same string when the expected number of # digits are found. value = key.value_from_str("%s%s1" % (padding_char, padding_char)) self.assertEqual("%s%s1" % (padding_char, padding_char), key.str_from_value(value)) # It should match a template with more digits. value = key.value_from_str("20000") self.assertEqual("20000", key.str_from_value(value)) key.value_from_str("123") error_msg = "does not match format spec" # It should not match a string with too few digits with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("1") # It should not match a template with too many digits that are all zero because that would # lossy. (there are more zeros than the format spec can rebuild) with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("0000") # It should not match negative numbers either with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("-1000") # It should not match baddly padded numbers with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("0100") # It should not match negative values with self.assertRaisesRegex(TankError, error_msg): key.value_from_str("-01") self._test_nan(key, error_msg) def test_strict_matching(self): """ In strict mode, tokens have to have as much padding as the format specifier suggests. Less will not match. """ self._test_strict_matching('') self._test_strict_matching('0')