Skip to content

Commit 5d756eb

Browse files
authored
Merge pull request #268 from metafacture/267-addListAsBind
Add `list_as()` Fix bind.
2 parents d223a4e + 8c3b656 commit 5d756eb

File tree

7 files changed

+269
-0
lines changed

7 files changed

+269
-0
lines changed

README.md

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -688,6 +688,29 @@ do list(path: "<sourceField>", "var": "<variableName>")
688688
end
689689
```
690690

691+
#### `do list_as`
692+
693+
Iterates over each _named_ element of an array (like [`do list`](#do-list) with a variable name). If multiple arrays are given, iterates over the _corresponding_ elements from each array (i.e., all elements with the same array index, skipping elements whose arrays have already been exhausted).
694+
695+
```perl
696+
do list_as(element_1: "<sourceField_1>"[, ...])
697+
...
698+
end
699+
```
700+
701+
E.g.:
702+
703+
```perl
704+
# "ccm:university":["https://ror.org/0304hq317"]
705+
# "ccm:university_DISPLAYNAME":["Gottfried Wilhelm Leibniz Universität Hannover"]
706+
set_array("sourceOrga[]")
707+
do list_as(orgId: "ccm:university[]", orgName: "ccm:university_DISPLAYNAME[]")
708+
copy_field(orgId, "sourceOrga[].$append.id")
709+
copy_field(orgName, "sourceOrga[].$last.name")
710+
end
711+
# {"sourceOrga":[{"id":"https://ror.org/0304hq317","name":"Gottfried Wilhelm Leibniz Universität Hannover"}]}
712+
```
713+
691714
#### `do once`
692715

693716
Executes the statements only once (when the bind is first encountered), not repeatedly for each record.

metafix/src/main/java/org/metafacture/metafix/FixBind.java

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,34 @@ public void execute(final Metafix metafix, final Record record, final List<Strin
6060
}
6161
},
6262

63+
list_as {
64+
@Override
65+
public void execute(final Metafix metafix, final Record record, final List<String> params, final Map<String, String> options, final RecordTransformer recordTransformer) {
66+
final Map<String, Value.Array> lists = new HashMap<>();
67+
options.forEach((k, v) -> Value.asList(record.get(v), a -> lists.put(k, a)));
68+
69+
final int size = lists.values().stream().mapToInt(a -> a.size()).max().orElse(0);
70+
for (int i = 0; i < size; ++i) {
71+
final int index = i;
72+
73+
lists.forEach((k, v) -> {
74+
final Value value = index < v.size() ? v.get(index) : null;
75+
76+
if (value != null) {
77+
record.put(k, v.get(index));
78+
}
79+
else {
80+
record.remove(k);
81+
}
82+
});
83+
84+
recordTransformer.transform(record);
85+
}
86+
87+
lists.keySet().forEach(record::remove);
88+
}
89+
},
90+
6391
once {
6492
private final Map<Metafix, Set<String>> executed = new HashMap<>();
6593

metafix/src/test/java/org/metafacture/metafix/MetafixBindTest.java

Lines changed: 160 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -744,6 +744,166 @@ public void shouldPerformComplexOperationWithPathWildcard() {
744744
);
745745
}
746746

747+
@Test
748+
public void shouldDoListAsWithSingleList() {
749+
MetafixTestHelpers.assertFix(streamReceiver, Arrays.asList(
750+
"set_array('sourceOrga[]')",
751+
"do list_as(orgId: 'ccm:university[]')",
752+
" copy_field(orgId, 'sourceOrga[].$append.id')",
753+
"end"
754+
),
755+
i -> {
756+
i.startRecord("1");
757+
i.startEntity("ccm:university[]");
758+
i.literal("1", "https://ror.org/0304hq317");
759+
i.literal("2", "https://ror.org/014nnvj65");
760+
i.endEntity();
761+
i.endRecord();
762+
},
763+
(o, f) -> {
764+
o.get().startRecord("1");
765+
o.get().startEntity("ccm:university[]");
766+
o.get().literal("1", "https://ror.org/0304hq317");
767+
o.get().literal("2", "https://ror.org/014nnvj65");
768+
o.get().endEntity();
769+
o.get().startEntity("sourceOrga[]");
770+
o.get().startEntity("1");
771+
o.get().literal("id", "https://ror.org/0304hq317");
772+
o.get().endEntity();
773+
o.get().startEntity("2");
774+
o.get().literal("id", "https://ror.org/014nnvj65");
775+
f.apply(2).endEntity();
776+
o.get().endRecord();
777+
}
778+
);
779+
}
780+
781+
@Test
782+
public void shouldDoListAsWithMultipleLists() {
783+
MetafixTestHelpers.assertFix(streamReceiver, Arrays.asList(
784+
"set_array('sourceOrga[]')",
785+
"do list_as(orgId: 'ccm:university[]', orgName: 'ccm:university_DISPLAYNAME[]', orgLoc: 'ccm:university_LOCATION[]')",
786+
" copy_field(orgId, 'sourceOrga[].$append.id')",
787+
" copy_field(orgName, 'sourceOrga[].$last.name')",
788+
" copy_field(orgLoc, 'sourceOrga[].$last.location')",
789+
"end"
790+
),
791+
i -> {
792+
i.startRecord("1");
793+
i.startEntity("ccm:university[]");
794+
i.literal("1", "https://ror.org/0304hq317");
795+
i.literal("2", "https://ror.org/014nnvj65");
796+
i.endEntity();
797+
i.startEntity("ccm:university_DISPLAYNAME[]");
798+
i.literal("1", "Gottfried Wilhelm Leibniz Universität Hannover");
799+
i.literal("2", "Technische Hochschule Köln");
800+
i.endEntity();
801+
i.startEntity("ccm:university_LOCATION[]");
802+
i.literal("1", "Hannover");
803+
i.literal("2", "Köln");
804+
i.endEntity();
805+
i.endRecord();
806+
},
807+
(o, f) -> {
808+
o.get().startRecord("1");
809+
o.get().startEntity("ccm:university[]");
810+
o.get().literal("1", "https://ror.org/0304hq317");
811+
o.get().literal("2", "https://ror.org/014nnvj65");
812+
o.get().endEntity();
813+
o.get().startEntity("ccm:university_DISPLAYNAME[]");
814+
o.get().literal("1", "Gottfried Wilhelm Leibniz Universität Hannover");
815+
o.get().literal("2", "Technische Hochschule Köln");
816+
o.get().endEntity();
817+
o.get().startEntity("ccm:university_LOCATION[]");
818+
o.get().literal("1", "Hannover");
819+
o.get().literal("2", "Köln");
820+
o.get().endEntity();
821+
o.get().startEntity("sourceOrga[]");
822+
o.get().startEntity("1");
823+
o.get().literal("id", "https://ror.org/0304hq317");
824+
o.get().literal("name", "Gottfried Wilhelm Leibniz Universität Hannover");
825+
o.get().literal("location", "Hannover");
826+
o.get().endEntity();
827+
o.get().startEntity("2");
828+
o.get().literal("id", "https://ror.org/014nnvj65");
829+
o.get().literal("name", "Technische Hochschule Köln");
830+
o.get().literal("location", "Köln");
831+
f.apply(2).endEntity();
832+
o.get().endRecord();
833+
}
834+
);
835+
}
836+
837+
@Test // checkstyle-disable-line JavaNCSS
838+
public void shouldDoListAsWithMultipleListsOfDifferentSizes() {
839+
MetafixTestHelpers.assertFix(streamReceiver, Arrays.asList(
840+
"set_array('sourceOrga[]')",
841+
"do list_as(orgId: 'ccm:university[]', orgName: 'ccm:university_DISPLAYNAME[]', orgLoc: 'ccm:university_LOCATION[]')",
842+
" set_hash('sourceOrga[].$append')",
843+
" copy_field(orgId, 'sourceOrga[].$last.id')",
844+
" copy_field(orgName, 'sourceOrga[].$last.name')",
845+
" copy_field(orgLoc, 'sourceOrga[].$last.location')",
846+
"end"
847+
),
848+
i -> {
849+
i.startRecord("1");
850+
i.startEntity("ccm:university[]");
851+
i.literal("1", "https://ror.org/0304hq317");
852+
i.literal("2", "https://ror.org/014nnvj65");
853+
i.endEntity();
854+
i.startEntity("ccm:university_DISPLAYNAME[]");
855+
i.literal("1", "Gottfried Wilhelm Leibniz Universität Hannover");
856+
i.literal("2", "Technische Hochschule Köln");
857+
i.literal("3", "Universität zu Köln");
858+
i.literal("4", "Stadtbibliothek Köln");
859+
i.endEntity();
860+
i.startEntity("ccm:university_LOCATION[]");
861+
i.literal("1", "Hannover");
862+
i.literal("2", "Köln");
863+
i.literal("3", "Köln");
864+
i.endEntity();
865+
i.endRecord();
866+
},
867+
(o, f) -> {
868+
o.get().startRecord("1");
869+
o.get().startEntity("ccm:university[]");
870+
o.get().literal("1", "https://ror.org/0304hq317");
871+
o.get().literal("2", "https://ror.org/014nnvj65");
872+
o.get().endEntity();
873+
o.get().startEntity("ccm:university_DISPLAYNAME[]");
874+
o.get().literal("1", "Gottfried Wilhelm Leibniz Universität Hannover");
875+
o.get().literal("2", "Technische Hochschule Köln");
876+
o.get().literal("3", "Universität zu Köln");
877+
o.get().literal("4", "Stadtbibliothek Köln");
878+
o.get().endEntity();
879+
o.get().startEntity("ccm:university_LOCATION[]");
880+
o.get().literal("1", "Hannover");
881+
o.get().literal("2", "Köln");
882+
o.get().literal("3", "Köln");
883+
o.get().endEntity();
884+
o.get().startEntity("sourceOrga[]");
885+
o.get().startEntity("1");
886+
o.get().literal("id", "https://ror.org/0304hq317");
887+
o.get().literal("name", "Gottfried Wilhelm Leibniz Universität Hannover");
888+
o.get().literal("location", "Hannover");
889+
o.get().endEntity();
890+
o.get().startEntity("2");
891+
o.get().literal("id", "https://ror.org/014nnvj65");
892+
o.get().literal("name", "Technische Hochschule Köln");
893+
o.get().literal("location", "Köln");
894+
o.get().endEntity();
895+
o.get().startEntity("3");
896+
o.get().literal("name", "Universität zu Köln");
897+
o.get().literal("location", "Köln");
898+
o.get().endEntity();
899+
o.get().startEntity("4");
900+
o.get().literal("name", "Stadtbibliothek Köln");
901+
f.apply(2).endEntity();
902+
o.get().endRecord();
903+
}
904+
);
905+
}
906+
747907
@Test
748908
public void shouldExecuteOnlyOnce() {
749909
MetafixTestHelpers.assertFix(streamReceiver, Arrays.asList(
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
{
2+
"ccm:university" : [ "https://ror.org/0304hq317", "https://ror.org/014nnvj65" ],
3+
"ccm:university_DISPLAYNAME" : [ "Gottfried Wilhelm Leibniz Universität Hannover", "Technische Hochschule Köln" ],
4+
"sourceOrganization" : [ {
5+
"id" : "https://ror.org/0304hq317",
6+
"name" : "Gottfried Wilhelm Leibniz Universität Hannover"
7+
}, {
8+
"id" : "https://ror.org/014nnvj65",
9+
"name" : "Technische Hochschule Köln"
10+
} ]
11+
}
12+
{
13+
"ccm:university" : [ "https://ror.org/02k7v4d05", "https://ror.org/04cvxnb49", "https://ror.org/024d6js02" ],
14+
"ccm:university_DISPLAYNAME" : [ "Universität Bern", "Johann Wolfgang Goethe-Universität Frankfurt am Main", "Karls-Universität Prag" ],
15+
"sourceOrganization" : [ {
16+
"id" : "https://ror.org/02k7v4d05",
17+
"name" : "Universität Bern"
18+
}, {
19+
"id" : "https://ror.org/04cvxnb49",
20+
"name" : "Johann Wolfgang Goethe-Universität Frankfurt am Main"
21+
}, {
22+
"id" : "https://ror.org/024d6js02",
23+
"name" : "Karls-Universität Prag"
24+
} ]
25+
}
26+
{
27+
"ccm:university" : [ "https://ror.org/04tsk2644" ],
28+
"ccm:university_DISPLAYNAME" : [ "Ruhr-Universität Bochum" ],
29+
"sourceOrganization" : [ {
30+
"id" : "https://ror.org/04tsk2644",
31+
"name" : "Ruhr-Universität Bochum"
32+
} ]
33+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
{
2+
"ccm:university" : [ "https://ror.org/0304hq317", "https://ror.org/014nnvj65" ],
3+
"ccm:university_DISPLAYNAME" : [ "Gottfried Wilhelm Leibniz Universität Hannover", "Technische Hochschule Köln" ]
4+
}
5+
{
6+
"ccm:university" : [ "https://ror.org/02k7v4d05", "https://ror.org/04cvxnb49", "https://ror.org/024d6js02" ],
7+
"ccm:university_DISPLAYNAME" : [ "Universität Bern", "Johann Wolfgang Goethe-Universität Frankfurt am Main", "Karls-Universität Prag" ]
8+
}
9+
{
10+
"ccm:university" : [ "https://ror.org/04tsk2644" ],
11+
"ccm:university_DISPLAYNAME" : [ "Ruhr-Universität Bochum" ]
12+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
set_array("sourceOrganization[]")
2+
do list_as(orgId: "ccm:university[]", orgName: "ccm:university_DISPLAYNAME[]")
3+
copy_field(orgId, "sourceOrganization[].$append.id")
4+
copy_field(orgName, "sourceOrganization[].$last.name")
5+
end
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
FLUX_DIR + "input.json"
2+
|open-file
3+
|as-records
4+
|decode-json
5+
|fix(FLUX_DIR + "test.fix")
6+
|encode-json(prettyPrinting="true")
7+
|write(FLUX_DIR + "output-metafix.json")
8+
;

0 commit comments

Comments
 (0)