Skip to content

Commit 793fa0f

Browse files
authored
[tests] Add integration tests for IDENTITY columns to bulk, live, and reverse Spanner migration templates (#2992)
* [tests] Add integration tests for IDENTITY columns to bulk, live, and reverse Spanner migration templates * Actually add missing test resource...
1 parent 5fd979b commit 793fa0f

File tree

11 files changed

+291
-6
lines changed

11 files changed

+291
-6
lines changed

v2/datastream-to-spanner/src/test/java/com/google/cloud/teleport/v2/templates/DataStreamToSpannerDDLIT.java

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -463,6 +463,36 @@ public void migrationTestWithSequenceColumns() {
463463
assertThatResult(result).meetsConditions();
464464
}
465465

466+
@Test
467+
public void migrationTestWithIdentityColumns() {
468+
// Construct a ChainedConditionCheck with 2 stages.
469+
// 1. Send initial wave of events
470+
// 2. Wait on Spanner to have events
471+
ChainedConditionCheck conditionCheck =
472+
ChainedConditionCheck.builder(
473+
List.of(
474+
uploadDataStreamFile(
475+
jobInfo,
476+
TABLE6,
477+
"identity.avro",
478+
"DataStreamToSpannerDDLIT/Books.avro",
479+
gcsResourceManager),
480+
SpannerRowsCheck.builder(spannerResourceManager, TABLE6)
481+
.setMinRows(3)
482+
.setMaxRows(3)
483+
.build()))
484+
.build();
485+
486+
// Wait for conditions
487+
PipelineOperator.Result result =
488+
pipelineOperator()
489+
.waitForCondition(createConfig(jobInfo, Duration.ofMinutes(8)), conditionCheck);
490+
491+
// Assert Conditions
492+
assertThatResult(result).meetsConditions();
493+
assertBooksBackfillContents();
494+
}
495+
466496
private void assertAllDatatypeColumnsTableBackfillContents() {
467497
List<Map<String, Object>> events = new ArrayList<>();
468498

@@ -951,4 +981,26 @@ private void assertAuthorsBackfillContents() {
951981
spannerResourceManager.runQuery("select id, name from Authors"))
952982
.hasRecordsUnorderedCaseInsensitiveColumns(events);
953983
}
984+
985+
private void assertBooksBackfillContents() {
986+
List<Map<String, Object>> events = new ArrayList<>();
987+
988+
Map<String, Object> row = new HashMap<>();
989+
row.put("id", 1);
990+
row.put("title", "The Lord of the Rings");
991+
events.add(row);
992+
993+
row = new HashMap<>();
994+
row.put("id", 2);
995+
row.put("title", "Pride and Prejudice");
996+
events.add(row);
997+
998+
row = new HashMap<>();
999+
row.put("id", 3);
1000+
row.put("title", "The Hitchhiker's Guide to the Galaxy");
1001+
events.add(row);
1002+
1003+
SpannerAsserts.assertThatStructs(spannerResourceManager.runQuery("select id, title from Books"))
1004+
.hasRecordsUnorderedCaseInsensitiveColumns(events);
1005+
}
9541006
}
Binary file not shown.

v2/datastream-to-spanner/src/test/resources/DataStreamToSpannerDDLIT/mysql-schema.sql

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -129,4 +129,10 @@ CREATE TABLE `Singers` (
129129
`first_name` varchar(1024),
130130
`last_name` varchar(1024),
131131
PRIMARY KEY (`singer_id`)
132-
);
132+
);
133+
134+
CREATE TABLE `Books` (
135+
`id` int NOT NULL AUTO_INCREMENT,
136+
`title` varchar(200),
137+
PRIMARY KEY (`id`)
138+
) DEFAULT CHARSET=latin1;

v2/datastream-to-spanner/src/test/resources/DataStreamToSpannerDDLIT/spanner-schema.sql

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -124,3 +124,8 @@ CREATE TABLE IF NOT EXISTS Singers (
124124
first_name STRING(1024),
125125
last_name STRING(1024),
126126
) PRIMARY KEY (singer_id);
127+
128+
CREATE TABLE IF NOT EXISTS Books (
129+
id INT64 NOT NULL GENERATED BY DEFAULT AS IDENTITY (BIT_REVERSED_POSITIVE),
130+
title STRING(200),
131+
) PRIMARY KEY (id);

v2/sourcedb-to-spanner/src/test/resources/DDLIT/company-mysql-schema.sql

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ INSERT INTO `company` VALUES
1010
(3,'ama','1994-07-05');
1111

1212
CREATE TABLE `employee` (
13-
`employee_id` int(11) PRIMARY KEY NOT NULL,
13+
`employee_id` int(11) AUTO_INCREMENT PRIMARY KEY NOT NULL,
1414
`company_id` int(11) DEFAULT NULL,
1515
`employee_name` varchar(100) DEFAULT NULL,
1616
`employee_address` varchar(100) DEFAULT NULL,

v2/sourcedb-to-spanner/src/test/resources/DDLIT/company-session.json

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -97,8 +97,8 @@
9797
"Comment": "From: employee_id int(10)",
9898
"Id": "c11",
9999
"AutoGen": {
100-
"Name": "",
101-
"GenerationType": ""
100+
"Name": "Identity",
101+
"GenerationType": "Identity"
102102
}
103103
},
104104
"c12": {
@@ -507,7 +507,11 @@
507507
"ForeignKey": false,
508508
"AutoIncrement": false
509509
},
510-
"Id": "c11"
510+
"Id": "c11",
511+
"AutoGen": {
512+
"Name": "Auto Increment",
513+
"GenerationType": "Auto Increment"
514+
}
511515
},
512516
"c12": {
513517
"Name": "company_id",

v2/sourcedb-to-spanner/src/test/resources/DDLIT/company-spanner-schema.sql

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ CREATE TABLE IF NOT EXISTS
99
CREATE TABLE IF NOT EXISTS
1010
employee
1111
(
12-
employee_id INT64 NOT NULL,
12+
employee_id INT64 NOT NULL GENERATED BY DEFAULT AS IDENTITY (BIT_REVERSED_POSITIVE),
1313
company_id INT64,
1414
employee_name STRING(100),
1515
employee_address STRING(100),

v2/spanner-to-sourcedb/src/test/java/com/google/cloud/teleport/v2/templates/SpannerToSourceDbIT.java

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,7 @@ public class SpannerToSourceDbIT extends SpannerToSourceDbITBase {
7575
private static final String TABLE = "Users";
7676
private static final String TABLE_WITH_VIRTUAL_GEN_COL = "TableWithVirtualGeneratedColumn";
7777
private static final String TABLE_WITH_STORED_GEN_COL = "TableWithStoredGeneratedColumn";
78+
private static final String TABLE_WITH_IDENTITY_COL = "TableWithIdentityColumn";
7879
private static final String BOUNDARY_CHECK_TABLE =
7980
"testtable_03TpCoVF16ED0KLxM3v808cH3bTGQ0uK_FEXuZHbttvYZPAeGeqiO";
8081
private static final HashSet<SpannerToSourceDbIT> testInstances = new HashSet<>();
@@ -273,6 +274,23 @@ public void spannerToMySQLSourceDbMaxColAndTableNameTest()
273274
assertBoundaryRowInMySQL();
274275
}
275276

277+
@Test
278+
public void spannerToSourceDbWithIdentityColumns() {
279+
assertThatPipeline(jobInfo).isRunning();
280+
// INSERT
281+
writeRowsWithIdentityColInSpanner();
282+
283+
assertThatPipeline(jobInfo).isRunning();
284+
285+
PipelineOperator.Result result =
286+
pipelineOperator()
287+
.waitForCondition(
288+
createConfig(jobInfo, TEST_TIMEOUT),
289+
() -> jdbcResourceManager.getRowCount(TABLE_WITH_IDENTITY_COL) == 2);
290+
assertThatResult(result).meetsConditions();
291+
assertIdentityColRowsInMySQLAfterInsert();
292+
}
293+
276294
private void writeMaxColRowsInSpanner() {
277295
List<Mutation> mutations = new ArrayList<>();
278296
Mutation.WriteBuilder mutationBuilder =
@@ -413,4 +431,33 @@ private boolean allGenColRowsDeleted() {
413431
long rowCountTable2 = jdbcResourceManager.getRowCount(TABLE_WITH_VIRTUAL_GEN_COL);
414432
return (rowCountTable1 == 0) && (rowCountTable2 == 0);
415433
}
434+
435+
private void writeRowsWithIdentityColInSpanner() {
436+
List<Mutation> mutations = new ArrayList<>();
437+
mutations.add(
438+
Mutation.newInsertBuilder(TABLE_WITH_IDENTITY_COL)
439+
.set("id")
440+
.to(1)
441+
.set("column1")
442+
.to("id1")
443+
.build());
444+
mutations.add(
445+
Mutation.newInsertBuilder(TABLE_WITH_IDENTITY_COL)
446+
.set("id")
447+
.to(2)
448+
.set("column1")
449+
.to("id2")
450+
.build());
451+
452+
spannerResourceManager.write(mutations);
453+
}
454+
455+
private void assertIdentityColRowsInMySQLAfterInsert() {
456+
List<Map<String, Object>> rows = jdbcResourceManager.readTable(TABLE_WITH_IDENTITY_COL);
457+
assertThat(rows).hasSize(2);
458+
assertThat(rows.get(0).get("id")).isEqualTo(1);
459+
assertThat(rows.get(0).get("column1")).isEqualTo("id1");
460+
assertThat(rows.get(1).get("id")).isEqualTo(2);
461+
assertThat(rows.get(1).get("column1")).isEqualTo("id2");
462+
}
416463
}

v2/spanner-to-sourcedb/src/test/resources/SpannerToSourceDbIT/mysql-schema.sql

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,3 +22,9 @@ CREATE TABLE Users (
2222
id INT NOT NULL,
2323
col_qcbF69RmXTRe3B_03TpCoVF16ED0KLxM3v808cH3bTGQ0uK_FEXuZHbttvY VARCHAR(25),
2424
PRIMARY KEY(id));
25+
26+
CREATE TABLE TableWithIdentityColumn (
27+
id BIGINT NOT NULL AUTO_INCREMENT,
28+
column1 VARCHAR(25),
29+
PRIMARY KEY(id)
30+
);

v2/spanner-to-sourcedb/src/test/resources/SpannerToSourceDbIT/session.json

Lines changed: 160 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -363,6 +363,79 @@
363363
"CheckConstraints": null,
364364
"Comment": "Spanner schema for source table TableWithVirtualGeneratedColumn",
365365
"Id": "t47"
366+
},
367+
"t48": {
368+
"Name": "TableWithIdentityColumn",
369+
"ColIds": [
370+
"c54",
371+
"c55"
372+
],
373+
"ShardIdColumn": "",
374+
"ColDefs": {
375+
"c54": {
376+
"Name": "id",
377+
"T": {
378+
"Name": "INT64",
379+
"Len": 0,
380+
"IsArray": false
381+
},
382+
"NotNull": true,
383+
"Comment": "From: id int(10)",
384+
"Id": "c54",
385+
"AutoGen": {
386+
"Name": "Identity",
387+
"GenerationType": "Identity"
388+
},
389+
"DefaultValue": {
390+
"IsPresent": false,
391+
"Value": {
392+
"ExpressionId": "",
393+
"Statement": ""
394+
}
395+
},
396+
"Opts": null
397+
},
398+
"c55": {
399+
"Name": "column1",
400+
"T": {
401+
"Name": "STRING",
402+
"Len": 25,
403+
"IsArray": false
404+
},
405+
"NotNull": false,
406+
"Comment": "From: column1 varchar(25)",
407+
"Id": "c55",
408+
"AutoGen": {
409+
"Name": "",
410+
"GenerationType": ""
411+
},
412+
"DefaultValue": {
413+
"IsPresent": false,
414+
"Value": {
415+
"ExpressionId": "",
416+
"Statement": ""
417+
}
418+
},
419+
"Opts": null
420+
}
421+
},
422+
"PrimaryKeys": [
423+
{
424+
"ColId": "c54",
425+
"Desc": false,
426+
"Order": 1
427+
}
428+
],
429+
"ForeignKeys": null,
430+
"Indexes": null,
431+
"ParentTable": {
432+
"Id": "",
433+
"OnDelete": "",
434+
"InterleaveType": ""
435+
},
436+
"CheckConstraints": null,
437+
"Comment": "Spanner schema for source table TableWithIdentityColumn",
438+
"Id": "t48"
366439
}
367440
},
368441
"SyntheticPKeys": {},
@@ -794,6 +867,89 @@
794867
"CheckConstraints": null,
795868
"Indexes": null,
796869
"Id": "t47"
870+
},
871+
"t48": {
872+
"Name": "TableWithIdentityColumn",
873+
"Schema": "test_limits",
874+
"ColIds": [
875+
"c54",
876+
"c55"
877+
],
878+
"ColDefs": {
879+
"c54": {
880+
"Name": "id",
881+
"Type": {
882+
"Name": "int",
883+
"Mods": [
884+
10
885+
],
886+
"ArrayBounds": null
887+
},
888+
"NotNull": true,
889+
"Ignored": {
890+
"Check": false,
891+
"Identity": false,
892+
"Default": false,
893+
"Exclusion": false,
894+
"ForeignKey": false,
895+
"AutoIncrement": false
896+
},
897+
"Id": "c54",
898+
"AutoGen": {
899+
"Name": "Auto Increment",
900+
"GenerationType": "Auto Increment"
901+
},
902+
"DefaultValue": {
903+
"IsPresent": false,
904+
"Value": {
905+
"ExpressionId": "",
906+
"Statement": ""
907+
}
908+
}
909+
},
910+
"c55": {
911+
"Name": "column1",
912+
"Type": {
913+
"Name": "varchar",
914+
"Mods": [
915+
25
916+
],
917+
"ArrayBounds": null
918+
},
919+
"NotNull": false,
920+
"Ignored": {
921+
"Check": false,
922+
"Identity": false,
923+
"Default": false,
924+
"Exclusion": false,
925+
"ForeignKey": false,
926+
"AutoIncrement": false
927+
},
928+
"Id": "c55",
929+
"AutoGen": {
930+
"Name": "",
931+
"GenerationType": ""
932+
},
933+
"DefaultValue": {
934+
"IsPresent": false,
935+
"Value": {
936+
"ExpressionId": "",
937+
"Statement": ""
938+
}
939+
}
940+
}
941+
},
942+
"PrimaryKeys": [
943+
{
944+
"ColId": "c54",
945+
"Desc": false,
946+
"Order": 1
947+
}
948+
],
949+
"ForeignKeys": null,
950+
"CheckConstraints": null,
951+
"Indexes": null,
952+
"Id": "t48"
797953
}
798954
},
799955
"SchemaIssues": {
@@ -838,6 +994,10 @@
838994
]
839995
},
840996
"TableLevelIssues": null
997+
},
998+
"t48": {
999+
"ColumnLevelIssues": {},
1000+
"TableLevelIssues": null
8411001
}
8421002
},
8431003
"InvalidCheckExp": null,

0 commit comments

Comments
 (0)