Skip to content

Commit 4706714

Browse files
Merge pull request #351 from dongwook-chan/zerofill
Support 'ZEROFILL' attribute for numeric datatypes
2 parents e56bbce + 37f91b0 commit 4706714

File tree

4 files changed

+28
-0
lines changed

4 files changed

+28
-0
lines changed

pymysqlreplication/column.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ def __parse_column_definition(self, column_type, column_schema, packet):
2222
self.character_set_name = column_schema["CHARACTER_SET_NAME"]
2323
self.comment = column_schema["COLUMN_COMMENT"]
2424
self.unsigned = column_schema["COLUMN_TYPE"].find("unsigned") != -1
25+
self.zerofill = column_schema["COLUMN_TYPE"].find("zerofill") != -1
2526
self.type_is_bool = False
2627
self.is_primary = column_schema["COLUMN_KEY"] == "PRI"
2728

pymysqlreplication/row_event.py

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,7 @@ def _read_column_data(self, cols_bitmap):
9292
column = self.columns[i]
9393
name = self.table_map[self.table_id].columns[i].name
9494
unsigned = self.table_map[self.table_id].columns[i].unsigned
95+
zerofill = self.table_map[self.table_id].columns[i].zerofill
9596

9697
if BitGet(cols_bitmap, i) == 0:
9798
values[name] = None
@@ -102,21 +103,29 @@ def _read_column_data(self, cols_bitmap):
102103
elif column.type == FIELD_TYPE.TINY:
103104
if unsigned:
104105
values[name] = struct.unpack("<B", self.packet.read(1))[0]
106+
if zerofill:
107+
values[name] = format(values[name], '03d')
105108
else:
106109
values[name] = struct.unpack("<b", self.packet.read(1))[0]
107110
elif column.type == FIELD_TYPE.SHORT:
108111
if unsigned:
109112
values[name] = struct.unpack("<H", self.packet.read(2))[0]
113+
if zerofill:
114+
values[name] = format(values[name], '05d')
110115
else:
111116
values[name] = struct.unpack("<h", self.packet.read(2))[0]
112117
elif column.type == FIELD_TYPE.LONG:
113118
if unsigned:
114119
values[name] = struct.unpack("<I", self.packet.read(4))[0]
120+
if zerofill:
121+
values[name] = format(values[name], '010d')
115122
else:
116123
values[name] = struct.unpack("<i", self.packet.read(4))[0]
117124
elif column.type == FIELD_TYPE.INT24:
118125
if unsigned:
119126
values[name] = self.packet.read_uint24()
127+
if zerofill:
128+
values[name] = format(values[name], '08d')
120129
else:
121130
values[name] = self.packet.read_int24()
122131
elif column.type == FIELD_TYPE.FLOAT:
@@ -155,6 +164,8 @@ def _read_column_data(self, cols_bitmap):
155164
elif column.type == FIELD_TYPE.LONGLONG:
156165
if unsigned:
157166
values[name] = self.packet.read_uint64()
167+
if zerofill:
168+
values[name] = format(values[name], '020d')
158169
else:
159170
values[name] = self.packet.read_int64()
160171
elif column.type == FIELD_TYPE.YEAR:

pymysqlreplication/tests/test_data_objects.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,7 @@ def test_column_serializable(self):
5656
self.assertIn("character_set_name", serialized)
5757
self.assertIn("comment", serialized)
5858
self.assertIn("unsigned", serialized)
59+
self.assertIn("zerofill", serialized)
5960
self.assertIn("type_is_bool", serialized)
6061
self.assertIn("is_primary", serialized)
6162

pymysqlreplication/tests/test_data_type.py

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -609,6 +609,21 @@ def test_encoding_utf8(self):
609609
event = self.create_and_insert_value(create_query, insert_query)
610610
self.assertMultiLineEqual(event.rows[0]["values"]["test"], string)
611611

612+
def test_zerofill(self):
613+
create_query = "CREATE TABLE test ( \
614+
test TINYINT UNSIGNED ZEROFILL DEFAULT NULL, \
615+
test2 SMALLINT UNSIGNED ZEROFILL DEFAULT NULL, \
616+
test3 MEDIUMINT UNSIGNED ZEROFILL DEFAULT NULL, \
617+
test4 INT UNSIGNED ZEROFILL DEFAULT NULL, \
618+
test5 BIGINT UNSIGNED ZEROFILL DEFAULT NULL \
619+
)"
620+
insert_query = "INSERT INTO test (test, test2, test3, test4, test5) VALUES(1, 1, 1, 1, 1)"
621+
event = self.create_and_insert_value(create_query, insert_query)
622+
self.assertEqual(event.rows[0]["values"]["test"], '001')
623+
self.assertEqual(event.rows[0]["values"]["test2"], '00001')
624+
self.assertEqual(event.rows[0]["values"]["test3"], '00000001')
625+
self.assertEqual(event.rows[0]["values"]["test4"], '0000000001')
626+
self.assertEqual(event.rows[0]["values"]["test5"], '00000000000000000001')
612627

613628
if __name__ == "__main__":
614629
unittest.main()

0 commit comments

Comments
 (0)